День 1115. #UnitTesting
Вы Неправильно Называете Тесты! Окончание
Начало
Продолжение
Шаблон Given-When-Then
Альтернативой шаблону
[MethodUnderTest]_[Scenario]_[ExpectedResult]
является шаблон Given-When-Then (Дано-Когда-Тогда):
public class BankAccountShould
{
public void Have_balance_of_zero_when_created()
public void Have_balance_increased_after_a_deposit()
…
}
В этом шаблоне класс модульного теста описывает тестируемый объект (банковский счёт), тогда как сами тесты — варианты использования, связанные с этим объектом.
Этот шаблон имеет два явных преимущества:
1. Позволяет сокращать имена тестов
Тестируемый объект всегда один и тот же, поэтому вам не нужно повторять его имя в тестах; оно извлекается в имя класса.
2. Помогает организовать тесты с простой иерархической структурой
Если вы хотите протестировать банковский счёт при нескольких условиях, вы можете создать отдельный класс для каждого из этих условий (например, BankAccountForPreferredClientsShould). Затем вы можете поместить все полученные классы в одну папку, чтобы они были хорошо сгруппированы.
Но попадает ли этот шаблон в категорию жёстких политик именования, которых следует избегать? Вспомним причину, по которой мы вообще избегаем жёстких имён: они мешают нам описать поведение кода в понятном для человека виде.
Если политика именования не вредит читаемости тестовых имён, то с ней всё в порядке. Просто не забывайте всегда отдавать предпочтение читаемости, а не политики. Будьте готовы делать исключения, когда политика препятствует читаемости.
Приведенные выше тесты также читаются как простое описание поведения системы. Но есть примеры, когда и Given-When-Then не работает:
public class PricingCalculatorShould
{
public void Return_zero_given_zero_quantity()
public void Throw_argument_OutOfRangeException_given_quantity_less_than_zero()
…
}
Здесь слово given присутствует в обоих тестах как часть политики именования. Это сигнал о том, что предпочтение отдали политике именования, а не читаемости. Ещё одна проблема — слово Return. Остерегайтесь терминов программирования в именах тестов. С точки зрения бизнеса неясно, к чему они относятся, где и что именно возвращает калькулятор?
Наконец, есть проблема со вторым тестом. Исключение OutOfRangeException — это деталь реализации, и оно никогда не должно быть частью имён тестов. Лучше всего перефразировать название с точки зрения клиента и показать, в чём именно проявляется это исключение:
Cannot_calculate_quantities_less_than_zero()
Итого
Политики именования сами по себе не плохи. Они становятся проблемой, только когда они препятствуют читаемости. Если вы следуете политике именования, такой как Given-When-Then, всегда будьте готовы пойти на компромисс в пользу читаемости имени теста, если по какой-то причине имя теста не соответствует политике.
Источник: enterprisecraftsmanship.com/posts/y…ts-wrong