logo
Тестирование      02/09/2021

Что надо знать о TDD и BDD: как тесты помогают разработчикам работать в команде и понять заказчика

Мария Головко BLOG

Java Developer в NIX

Вам знакома басня про лебедя, рака и щуку? Три совершенно разных существа тянули воз: лебедь пытался взлетать с ним, рак пятился с повозкой назад, а щука упорно тащила телегу на дно. Единства между ними не произошло, поэтому затея была обречена на провал — воз так и не сдвинулся с места. 

Так аллегорично можно описать стандартный рабочий процесс, в котором заказчик хочет одно, руководитель проекта понимает задачу по-другому, а специалисты (дизайнеры, программисты, тестировщики) все делают по-своему… Иногда такие проекты доводят до конца. Однако зачастую они, как повозка из упомянутой басни, остаются на месте.

Чтобы в своей профессии вы не повторяли судьбу героев басни, были созданы методологии тестирования Test Driven Development (TDD) и Behavior Driven Development (BDD). Давайте разберемся, как они работают.

TDD и BDD: основные отличия модульного и интеграционного тестирования

Test Driven Development (TDD) — это разработка, основанная на тестировании. Предположим, вы получаете от заказчика запрос на добавление в разрабатываемый продукт нового функционала. Под этот запрос составляется техническая документация в виде тестов: в них согласованы и записаны новые требования, которые заказчик предъявляет к продукту.

Тестирование в TDD происходит через итерации (циклы) и соответствует такому порядку:

  • сперва написанные тесты прогоняются через существующий код, на этом этапе новые тесты упадут (failing tests);
  • под упавшие тесты разработчик пишет новый код, который покроет необходимый функционал для теста, заставив его проходить;
  • когда тесты с новым кодом будут пройдены с положительным результатом, можно приступать к рефакторингу — правке кода, в котором из него убирается все лишнее.

Все эти шаги TDD-разработки будут повторяться энное количество раз, пока специалисты не приведут код в соответствие с документацией и не удостоверятся в работоспособности новой функции.

Шаги TDD-разработки

Шаги TDD-разработки

Методология TDD относится к юнит-тестированию (модульному тестированию) и позволяет проверять отдельно взятые части продукта. Чаще всего TDD пишут сами разработчики, тесты реализуются в виде программного кода.

Но как протестировать не отдельный модуль продукта, а сложный сценарий с большим количеством условий и переменных? 

Онлайн-курс Frontend-разробник від Powercode academy.
Курс на якому ти напишеш свій чистий код на JavaScript, попрацюєш із різними видами верстки, а також адаптаціями проектів під будь-які екрани. .
Зарееструватися

В этом случае прибегают к использованию методологии Behavior Driven Development — разработке на основе поведения. В отличие от TDD, этот подход строится на написании нескольких пользовательских сценариев, под которые составляются тесты. BDD позволяет «‎предугадать», как поведет себя пользователь, используя продукт в соответствии с требованиями, которые записаны в технической документации. Порядок прохождения тестов схож с TDD. Единственное отличие — перед прохождением отдельных тестов формулируется ряд предварительных условий (сценариев), при которых они должны быть пройдены.

BDD позволяет «‎предугадать», как поведет себя пользователь используя продукт в соответствии с требованиями, которые записаны в техдокументации

Сравненение BDD и TDD / TestLodge

Требования для BDD обычно составляет группа экспертов и не в виде программного кода, а словесно — на языке, понятном всем участникам проекта.

Behavior Driven Development относится к методам интеграционного тестирования. Оно позволяет понять, правильно ли взаимодействуют друг с другом отдельно взятые части программы.

Подход также эффективен в end-to-end-тестировании (Е2Е) и дает программистам представление о том, как функционирует вся разрабатываемая ими система. Получается, несмотря на то, что BDD и является расширением TDD-методологии, они имеют разное предназначение и реализуются разным набором инструментов.

В общем, мы друг друга поняли 

Методологии BDD- и TDD- тестирования помогают достичь взаимопонимания между заказчиком продукта и всеми участниками, задействованными в его реализации.

Четкое следование прописанным заранее спецификациям позволяет избежать подводных камней в виде неоговоренных сценариев или разрозненной трактовки функционала продукта разными специалистами.

Весомое преимущество таких подходов в тестировании — отсутствие невалидных (недостоверных) сценариев. Каждый участник проекта еще на стадии проектирования может увидеть нереализуемые функции и рассказать об этом коллегам. Так можно исключить даже саму возможность создания неэффективного и бесполезного кода.

Еще один плюс — наличие технической документации. TDD и BDD предполагают четко структурированную документацию, которая помогает быстрее адаптироваться новичкам, зашедшим в проект, уже на этапе производства.

Разработка больше не зависит от человеческого фактора: чтобы понять, что происходило в проекте с момента его создания, достаточно открыть нужный файл. 

Курс Full-stack developer від Mate academy.
Опануйте нову професію завдяки курсу Full-stack developer! Ви отримаєте необхідні навички та допомогу у працевлаштуванні! .
Отримати знижку на курс

Как составлять тесты? 

Давайте подытожим кратким списком рекомендаций по составлению тестов:

  • в процессе создания и разработки новых сценариев для BDD-тестирования должны участвовать все члены команды и заказчик;
  • описывайте желаемое поведение в сценариях, руководствуясь уже существующими спецификациями поведения (behavioral specifications); 
  • не пытайтесь проверить в одном тесте сразу несколько сценариев или функций — это перегружает его;
  • следите за тем, чтобы модульное тестирование всегда выполнялось быстро (здесь стандарт — миллисекунды);
  • юнит-тесты должны быть самостоятельными и не иметь внешних зависимостей от баз данных, файловых систем;
  • тесты предназначены не только для проверки кода, но и для ведения технической документации;
  • void-методы, которые не возвращают никаких данных, тоже надо тестировать.

Инструменты для реализации юнит-тестирования  

Юнит-тестирование на Java осуществляется при помощи фреймворка JUnit. Он относится к семейству фреймворков xUnit и используется преимущественно для Test-Driven- и Behavior-Driven-разработки. На сегодня JUnit 5 — самая свежая версия фреймворка, которая совместима с версиями Java 8 и выше.

Курс QA Manual (Тестування ПЗ мануальне) від Powercode academy.
Навчіться знаходити помилки та контролювати якість сайтів та додатків.
Записатися на курс

Это значит, что фреймворк поддерживает Stream API, лямбды, функциональные интерфейсы и массу других «плюшек», которые таит в себе Java 8+.

Характерным отличием JUnit 5 от своей предыдущей версии является возможность запускать сразу несколько раннеров для одного и того же класса (JUnit4 был способен выполнять только один класс-раннер). JUnit 5 состоит из трех отдельных пакетов, которые можно подключать независимо друг от друга:

  • JUnit Platform — предоставляет инструменты для обработки тестов на JUnit для JVM (Java Virtual Machine);
  • JUnit Vintage — обеспечивает обратную совместимость с тестами, разработанными на предыдущих версиях JUnit; 
  • Junit Jupiter — объединяет в себе программную и экстеншн-модели для написания тестов с использованием всего функционала пятой версии JUnit.
JUnit 5 состоит из трех отдельных пакетов, которые можно подключать независимо друг от друга

JUnit 5 состоит из трех отдельных пакетов, которые можно подключать независимо друг от друга

Экстеншн-модели и аннотации в JUnit 5

Экстеншн-модель в JUnit Jupiter — это разновидность совершенно нового API, позволяющая расширять функционал отдельного теста и добавлять новые условия для работы с ним. Для работы с экстеншн-моделью существуют экстеншн-поинты.

Существует пять основных видов экстеншн-поинтов: 

  • постобработка тестового экземпляра — расширение функционирует с помощью интерфейса реализации TestInstancePostProcessor и может быть выполнено после того, как был создан хотя бы один экземпляр теста;
  • условное выполнение теста — расширение на базе интерфейса ExecutionCondition, которое контролирует запуск теста по условию;
  • Бізнес англійська від Englishdom.
    Тут навчають за методикою Кембриджу, завдяки якій англійську вивчили понад 1 мільярд людей. Саме вона використовується в найкращих навчальних закладах світу, і саме за нею створені курси.
    Інформація про курс
  • обратные вызовы жизненного цикла — набор расширений, связанных с событиями в жизненном цикле теста;
  • разрешение параметра — расширение, которое определяет получение параметра в конструкторе или методе теста во время выполнения ParameterResolver;
  • обработка исключений — определяет поведение теста при обнаружении определенного типа исключений. Реализован интерфейсом TestExecutionExceptionHandler.

Помимо интерфейсов в JUnit5 представлен довольно обширный список аннотаций. Рассмотрим некоторые из них:

  • @RepeatedTest — повторяющиеся тесты. Разновидность тестов, которые выполняются энное количество раз, а описываются всего один. Повторяющиеся тесты довольно легко настроить при помощи таких параметров как: имя (name), и желаемое количество повторений теста (value).
  • @ParametrizedTest — параметризированный тест. Позволяет запускать тест несколько раз, передавая ему разные аргументы. При выполнении этого теста каждый вызов будет обрабатываться отдельно.
  • @TestTemplate — метод, предназначенный для многократного вызова тестов в зависимости от количества контекстов, возвращаемых зарегистрированными провайдерами. @TestTemplate правильно рассматривать не как отдельный тест, а как шаблон для целого ряда тестовых случаев.
  • @TestFactory — сам по себе метод не является тестом в классическом понимании, а скорее — фабрикой, а отдельные вызовы (динамические тесты) — продуктами фабрики. Динамический тест генерируется в рантайме фабричными методами. Методы @TestFactory не должны быть private или static и могут дополнительно объявлять параметры, которые должны быть обработаны, при помощи @ParameterResolvers.
  • @TempDir — встроенный экстеншн, который используется для создания и очистки временного каталога для одного или всех тестов в классе. Чтобы им воспользоваться, нужно аннотировать неприватное поле типа java.nio.file.Path или java.io.File при помощи @TempDir.
  • Психологічний профорієнтаційний тест для IT-фахівців від Hillel IT School.
    Пройдіть психологічний профорієнтаційний тест для IT-фахівців щоб дізнатися ваші сильні сторони, вподобання і інтереси і з'ясувати, яка IT-спеціальність вам підходить.
    Пройти тест

В JUnit пятой версии также расширен функционал Assertions API. Например, теперь вы сможете работать с методом assertAll, который построен на использовании лямбд. Он позволяет производить групповые проверки: каждая следующая проверка выполняется только в том случае, если предыдущая верна:

@Test
    void groupedAssertions() {
        // In a grouped assertion all assertions are executed, and all
        // failures will be reported together.
        assertAll("person",
            () -> assertEquals("Jane", person.getFirstName()),
            () -> assertEquals("Doe", person.getLastName())
        );
    }

@Test
    void dependentAssertions() {
        // Within a code block, if an assertion fails the
        // subsequent code in the same block will be skipped.
        assertAll("properties",
            () -> {
                String firstName = person.getFirstName();
                assertNotNull(firstName);

                // Executed only if the previous assertion is valid.
                assertAll("first name",
                    () -> assertTrue(firstName.startsWith("J")),
                    () -> assertTrue(firstName.endsWith("e"))
                );
            },
            () -> {
                // Grouped assertion, so processed independently
                // of results of first name assertions.
                String lastName = person.getLastName();
                assertNotNull(lastName);

                // Executed only if the previous assertion is valid.
                assertAll("last name",
                    () -> assertTrue(lastName.startsWith("D")),
                    () -> assertTrue(lastName.endsWith("e"))
                );
            }
        );
    }

JUnit 5 также позволяет контролировать выполнение теста в зависимости от внешних условий. Вы можете выбирать ОС, на которой будете проводить тестирование, а также версию Java, на которой будет работать тест. Контролировать можно и то, при каких системных настройках будет запущен тест.

Также JUnit 5 помогает создавать свои собственные аннотации. Для этого необходимо указать @Target (ElementType.METHOD) для нового интерфейса и затем перечислить все аннотации, которые должны сработать при подключении вашей аннотации. Вот несколько примеров таких аннотаций:

@EnabledOnOs({ LINUX, MAC })

@DisabledOnOs(WINDOWS)

@EnabledOnJre(JAVA_8)

@EnabledOnJre({ JAVA_9, JAVA_10 })

@EnabledForJreRange(min = JAVA_9, max = JAVA_11)

@DisabledOnJre(JAVA_9)

@DisabledForJreRange(min = JAVA_9, max = JAVA_11)

@EnabledIfSystemProperty(named = "os.arch", matches = ".*64.*")

@DisabledIfSystemProperty(named = "ci-server", matches = "true")


@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Test
@EnabledOnOs(MAC)
@interface TestOnMac {
}

@TestOnMac

Тестируй себя сам

Для любого разработчика очень важно уметь самостоятельно применять методы юнит-тестирования. Такой подход позволяет на ранних этапах уловить непонятные аспекты ТЗ до того, как будет реализован код. Помимо этого, TDD- и BDD- тестирование обеспечивает постоянную коммуникацию внутри команды: и исполнитель, и заказчик, и руководитель всегда будут находиться в одной плоскости понимания проекта. Именно в таком единстве всех участников процесса и заключается главное преимущество использования интеграционного и модульного тестирования.

If you have found a spelling error, please, notify us by selecting that text and pressing Ctrl+Enter.

Онлайн-курс Бізнес-аналіз. Basic Level від Hillel IT School.
В ході курсу студенти навчаться техніці збору і аналізу вимог, документуванню та управлінню документацією, управлінню ризиками та змінами, а також навчаться моделювати процеси і прототипуванню.
Приєднатися

Этот материал – не редакционный, это – личное мнение его автора. Редакция может не разделять это мнение.

Топ-5 самых популярных блогеров октября

CEO & Founder в Trustee
Всего просмотровВсего просмотров
15
#1
Всего просмотровВсего просмотров
15
Recruiter| Talent Acquisition Specialist
Всего просмотровВсего просмотров
10
#2
Всего просмотровВсего просмотров
10
Рейтинг блогеров

Самые обсуждаемые статьи

Топ текстов

Ваша жалоба отправлена модератору

Сообщить об опечатке

Текст, который будет отправлен нашим редакторам: