Comments 12
в чем преимущество вашей библиотеки или недостаток\перегруженность TestStack.BDDfy
C Reflection API, я думаю, все понятно.
С Fluent API — BDDFy в качестве контекста передает тестовый объект целиком, что заставляет использовать поля вместо локальных (для каждого действия!) переменных, волшебный вызов BDDFy() в конце (мелочь, но надо же к чему-то еще придраться).
Спасибо за наводку — до вас я эту библиотеку просмотрел бегло, сейчас прочитал документацию целиком. Остался один небольшой нюанс — как написать сценарий для варианта с ожидаемым исключением?
BDD — поведенческий подход, а потому в общем случае — произошло исключение, но реально то обычно проверяем тип\текст\содержимое исключения, так что проще не заделывать под исключения отдельный синтаксис.
Если что — ответ авторский:
https://github.com/TestStack/TestStack.BDDfy/issues/14
BDDFy в качестве контекста передает тестовый объект целиком, что заставляет использовать поля вместо локальных (для каждого действия!) переменных
Тут дело вкуса, имхо, потому что в вашем случае при 3-5 переменных читать код становится нереально.
Исключение — как угодно.
BDD — поведенческий подход, а потому в общем случае — произошло исключение, но реально то обычно проверяем тип\текст\содержимое исключения, так что проще не заделывать под исключения отдельный синтаксис.
Если что — ответ авторский:
Авторский ответ как раз показывает, что случай с ожидаемым исключением обрабатывается совсем не как угодно, а через свирепый ad-hoc:
public void WhenICallAMethodWithExpectedException()
{
_action = () => MethodUnderTestWhichThrowsException();
}
[Test]
public void ThenMyTestShouldBeASuccess()
{
Assert.Throws<InvalidOperationException>(() => _action());
}
Это сильно искажает исходный смысл теста (по сравнению с аналогичным "гладким"), так как When перестает что-то делать, а реальное тестовое действие исполняется вручную лишь при вызове Then.
У меня никакого переноса действий нет, а случай ожидаемого исключения обрабатывается единообразно со всеми остальными.
Тут дело вкуса, имхо, потому что в вашем случае при 3-5 переменных читать код становится нереально.
Для юнит-тестов переменных, сквозных для всего теста, нужно от одной до трех: тестируемый объект, мок, ожидаемое исключение. Все эти переменные у меня поддерживаются из коробки.
Переменные, локальные для конкретного этапа, будут локальными и в соответствующих лямбдах.
На случаи, когда требуется больше одного тестового объекта на сценарий, я (пока) не замахивался.
ПС: и переменных прилично в приложениях, как минимум пользователь, сущность с которой он работает и пара служебных. Так что тест — окружение пользователя, вполне работающий подход.
Только я в тестах и кейсов таких особо не встречаю, обычно таки на пользователя вываливается текст читабельный в диалоге, а не ошибка.
Это значит, что до уровня юнит-тестов вы обычно, скорее всего, не опускаетесь: там пользователь не человек и исключение — полноценный результат.
Так что тест — окружение пользователя, вполне работающий подход.
Это если по классу на тест, что на мой взгляд тяжеловато.
Что там от «поведения», я чуток не понимаю?
Сверхлегкая BDD: малая механизация автономных тестов