Продвинутый тест-дизайн
Техники тест-дизайна за пределами классов эквивалентности и границ — тестирование переходов состояний и по сценариям использования, попарные комбинации, предугадывание ошибок, тестовый оракул, покрытие кода против покрытия требований и проектирование системы под тестируемость.
9 вопросов
JuniorТеорияОчень частоЧто такое тестовый оракул и что может им служить на практике?
Что такое тестовый оракул и что может им служить на практике?
Тестовый оракул — это то, что говорит вам, что наблюдаемый результат верен. Им может быть спецификация, эталонная реализация, предыдущая версия, инвариант, которому результат обязан удовлетворять, или суждение человека. Без оракула тест показывает лишь, что система не упала, а не что она сделала правильное.
Типичные ошибки
- ✗Путать оракул с инструментом, который запускает тест
- ✗Считать, что оракулом может быть только письменная спецификация
- ✗Называть прогон без падения успешным вообще без оракула
Уточняющие вопросы
- →Что такое проблема оракула и когда она бьёт сильнее всего?
- →Как инвариант может служить оракулом без точного ожидаемого значения?
MiddleТеорияОчень частоЧто такое тестирование переходов состояний и что оно ловит помимо классов?
Что такое тестирование переходов состояний и что оно ловит помимо классов?
Тестирование переходов состояний моделирует систему как состояния, события и переходы, затем выводит кейсы из диаграммы. Проверяются валидные переходы, ожидаемое итоговое состояние и — главное — недопустимые события в состоянии, которое должно их отвергать. Оно ловит зависящие от порядка и истории дефекты, которых классы эквивалентности, беря каждый вход отдельно, не видят.
Типичные ошибки
- ✗Проверять только валидные переходы, но не недопустимые события в состоянии
- ✗Игнорировать итоговое состояние, проверяя лишь отсутствие ошибки
- ✗Применять её к независимым входам, где порядок не несёт смысла
Уточняющие вопросы
- →Как решить, стоит ли строить модель состояний для фичи?
- →Какие кейсы добавляет обход недопустимых переходов помимо основного пути?
JuniorТеорияЧастоЧто такое предугадывание ошибок и на чём тестировщик строит догадки?
Что такое предугадывание ошибок и на чём тестировщик строит догадки?
Предугадывание ошибок — техника, основанная на опыте: тестировщик предполагает, где вероятны дефекты, и сразу пишет кейсы под них. Догадки берутся из прошлых дефектов, известных слабых мест, привычек разработчиков и типовых ловушек — пустой ввод, ноль, null, дубликаты. Она дополняет формальные техники и никогда их не заменяет.
Типичные ошибки
- ✗Считать предугадывание ошибок случайным вводом без опоры на опыт
- ✗Использовать её вместо классов эквивалентности и граничного анализа
- ✗Никогда не возвращать реальные прошлые дефекты обратно в догадки
Уточняющие вопросы
- →Какие прошлые артефакты вы бы изучили, чтобы уточнить догадки?
- →Почему предугадывание ошибок не может быть единственной техникой в релизе?
MiddleТеорияЧастоЧто такое попарное тестирование и почему оно сокращает число комбинаций?
Что такое попарное тестирование и почему оно сокращает число комбинаций?
Попарное (2-way комбинаторное) тестирование покрывает каждую пару значений параметров хотя бы в одном кейсе вместо каждой полной комбинации. Оно опирается на эмпирику: большинство дефектов вызывают один-два взаимодействующих фактора, поэтому проверка всех пар находит их малой долей полного набора. Настоящие тройные взаимодействия оно упускает.
Типичные ошибки
- ✗Ожидать, что попарное поймает тройные и выше взаимодействия
- ✗Путать его со случайной выборкой двух значений на поле
- ✗Думать, что оно воспроизводит исчерпывающее покрытие дешевле
Уточняющие вопросы
- →Когда вы перейдёте от попарного к 3-way покрытию?
- →Как ограничения между параметрами меняют сгенерированный набор?
MiddleТеорияЧастоЧто такое тестирование по сценариям использования и как оно выводит кейсы?
Что такое тестирование по сценариям использования и как оно выводит кейсы?
Тестирование по сценариям использования выводит кейсы из взаимодействий актёра с системой, записанных как use case. Проверяется основной успешный сценарий целиком, затем каждый альтернативный и исключительный поток из use case. Следуя целям пользователя через компоненты, оно находит интеграционные и потоковые дефекты, которые изолированные компонентные тесты упускают.
Типичные ошибки
- ✗Проверять только основной сценарий, пропуская альтернативные и исключительные потоки
- ✗Путать use case с одним экраном UI или компонентом
- ✗Терять цель актёра и проверять шаги изолированно
Уточняющие вопросы
- →Как превратить альтернативный поток в независимый тест-кейс?
- →Почему эта техника вскрывает интеграционные дефекты, упущенные юнит-тестами?
JuniorТеорияИногдаЧем покрытие кода отличается от покрытия требований и что означают его уровни?
Чем покрытие кода отличается от покрытия требований и что означают его уровни?
Покрытие требований спрашивает, какую долю требований или риска прогоняют ваши кейсы; покрытие кода — какую долю исходника они выполняют. У покрытия кода есть уровни: операторов (каждая строка), ветвей (каждое ребро true/false) и путей (каждый маршрут по коду). Высокое покрытие кода не означает, что поведение действительно проверено.
Типичные ошибки
- ✗Смешивать покрытие кода с покрытием требований
- ✗Читать 100% покрытия операторов как доказательство верного поведения
- ✗Путать покрытие ветвей с покрытием операторов
Уточняющие вопросы
- →Почему набор может дать 100% покрытия операторов, но упустить ветвь?
- →Почему покрытие путей растёт комбинаторно на реальном коде?
MiddleДизайнИногдаКоманда начинает новый сервис управления заказами и подключает вас на этапе проектирования, до появления кода. Лид спрашивает, как QA может сделать систему тестируемой с самого начала, а не прикручивать тестирование потом. Работая с разработчиками, какие свойства проектирования под тестируемость вы бы продвигали — вокруг наблюдаемости, управляемости, изоляции и детерминизма — и как каждое удешевляет поиск дефектов? Объясните, как вы договоритесь об этом с разработчиками, нацеленными на выпуск фич, и как поймёте, что система реально стала тестируемее.
Команда начинает новый сервис управления заказами и подключает вас на этапе проектирования, до появления кода. Лид спрашивает, как QA может сделать систему тестируемой с самого начала, а не прикручивать тестирование потом. Работая с разработчиками, какие свойства проектирования под тестируемость вы бы продвигали — вокруг наблюдаемости, управляемости, изоляции и детерминизма — и как каждое удешевляет поиск дефектов? Объясните, как вы договоритесь об этом с разработчиками, нацеленными на выпуск фич, и как поймёте, что система реально стала тестируемее.
Продвигайте наблюдаемость (логи, метрики, состояние), управляемость (хуки, feature flags, засеваемые часы), изоляцию (стаб внешних зависимостей на шве) и детерминизм (без скрытого времени и случайности). Каждое сокращает разрыв между дефектом и симптомом, делая сбои воспроизводимыми. Продавайте хуки как быструю обратную связь и мерьте успех временем обнаружения дефектов.
Типичные ошибки
- ✗Считать тестируемость делом только QA без вклада на этапе проектирования
- ✗Приравнивать тестируемость к одному числу покрытия кода
- ✗Добавлять тестовые чёрные ходы, обходящие реальную валидацию и инварианты
Уточняющие вопросы
- →Какой один хук тестируемости даёт лучшую отдачу на самой ранней фиче?
- →Как не дать управляющему хуку ослабить безопасность на проде?
SeniorДизайнИногдаВ продукт добавляют подсказчик ответов поддержки на ML: по сообщению клиента он возвращает предлагаемый ответ и оценку уверенности. Один и тот же вход может давать разные формулировки между версиями модели, и даже идентичные входы могут слегка меняться в рантайме, так что единственной ожидаемой строки для проверки нет. Команде всё равно нужен регрессионный сигнал, ловящий падение качества до релиза. Как вы спроектируете подход к тестированию, когда классического оракула точного совпадения не существует — какие виды оракула вы подставите, как удержите набор стабильным против допустимой вариации, как выберете сэмпл из огромного пространства входов и на чём зашлюзуете релиз?
В продукт добавляют подсказчик ответов поддержки на ML: по сообщению клиента он возвращает предлагаемый ответ и оценку уверенности. Один и тот же вход может давать разные формулировки между версиями модели, и даже идентичные входы могут слегка меняться в рантайме, так что единственной ожидаемой строки для проверки нет. Команде всё равно нужен регрессионный сигнал, ловящий падение качества до релиза. Как вы спроектируете подход к тестированию, когда классического оракула точного совпадения не существует — какие виды оракула вы подставите, как удержите набор стабильным против допустимой вариации, как выберете сэмпл из огромного пространства входов и на чём зашлюзуете релиз?
Замените оракул точного совпадения слабыми: инварианты (нет утечки PII, уверенность в диапазоне), метаморфные отношения (перефразированный вход хранит смысл) и золотой набор по схожести, а не равенству строк. Стабилизируйте, проверяя свойства и пороги, а не формулировки. Сэмплируйте пространство взвешенными попарными комбинациями. Шлюзуйте на агрегатных метриках, но не на одном ответе.
Типичные ошибки
- ✗Навязывать оракул точного совпадения недетерминированному выводу
- ✗Заключать, что фичу нельзя тестировать, раз вывод меняется
- ✗Шлюзовать на одном ответе вместо агрегатных метрик качества
Уточняющие вопросы
- →Приведите метаморфное отношение, которое вы бы проверяли на этом подсказчике.
- →Как задать порог релиза, не переобучаясь на золотой набор?
MiddleДизайнРедкоОформление заказа идёт четырьмя шагами — корзина, адрес, оплата, подтверждение — и сервер завершает простаивающую сессию через 15 минут. Покупатель может идти вперёд, прыгать назад к правке раннего шага или перезагружать страницу, а таймаут может сработать в любой момент, включая середину оплаты. Зарезервированный товар освобождается при смерти сессии. Спроектируйте подход к тестированию того, как поток ведёт себя при взаимодействии состояния и времени: какие состояния и переходы вы смоделируете, что обязано произойти при срабатывании таймаута на каждом шаге и как вы проверите, что заказ не списан и не подтверждён на истёкшей сессии, а товар не зарезервирован дважды и не потерян.
Оформление заказа идёт четырьмя шагами — корзина, адрес, оплата, подтверждение — и сервер завершает простаивающую сессию через 15 минут. Покупатель может идти вперёд, прыгать назад к правке раннего шага или перезагружать страницу, а таймаут может сработать в любой момент, включая середину оплаты. Зарезервированный товар освобождается при смерти сессии. Спроектируйте подход к тестированию того, как поток ведёт себя при взаимодействии состояния и времени: какие состояния и переходы вы смоделируете, что обязано произойти при срабатывании таймаута на каждом шаге и как вы проверите, что заказ не списан и не подтверждён на истёкшей сессии, а товар не зарезервирован дважды и не потерян.
Смоделируйте каждый шаг как состояние с событиями next, back, reload и timeout и выведите кейсы из диаграммы. Для каждого шага проверьте, что таймаут приводит в безопасное истёкшее состояние, освобождает резерв ровно раз и блокирует списание. Читайте корректность из серверного состояния сессии и заказа, а не UI; товар не зарезервирован дважды и не потерян.
Типичные ошибки
- ✗Проверять только прямой основной путь, но не таймаут посреди потока
- ✗Читать pass/fail из UI, а не из серверного состояния сессии и заказа
- ✗Игнорировать резерв товара — двойной резерв или потерю при истечении
Уточняющие вопросы
- →Как проверить таймаут, срабатывающий ровно во время вызова оплаты?
- →Какое серверное доказательство подтверждает, что истёкшую сессию нельзя списать?