Стыковка для интеграционных тестов
Как вы издеваетесь над многими зависимостями, необходимыми для тестов интеграции?
Я использую Mockito для своих "чистых" модульных тестов. "Pure" в этом случае означает тестирование одного класса, издевательства над всеми его зависимостями. Красивая.
Теперь приступим к интеграционным испытаниям. Скажем, в этом случае тест интеграции проверит что-то вроде этого:
- Сообщение помещается в очередь
- Сообщение обработано
- Ответное сообщение помещается в очередь ответов
Пусть также говорят, что обработка, которая происходит на шаге 2, является серьезной проблемой. Он опирается на множество взаимодействий с базами данных, на несколько внешних сервисов, файловую систему и всевозможные вещи. Есть также много побочных эффектов, которые поток инициирует, поэтому я не могу просто обеспечить правильность ответа - мне нужно проверить побочные эффекты.
Каждая из этих зависимостей обернута одним классом службы без состояния, что делает их приятными и макетируемыми.
Как люди справляются с этим?
Я хотел бы использовать Mockito, чтобы я мог проверить побочные эффекты, которые будет иметь этот поток. Тем не менее, документация Mocktio (и в значительной степени ее реализация), похоже, сильно сопротивляется использованию ее в контексте, отличном от "чистых" модульных тестов. Я попытался пройти этот маршрут, но
- Трудно заполнить данные заглушки (как там их много)
- Сложно иметь Spring вставить те закодированные экземпляры в мой beans
- Трудно "reset" издеваться, чтобы я мог проверить другой набор взаимодействий, не очистив заглушки.
ИЗМЕНИТЬ
Я знаю, что я мог бы обрабатывать проблему с базой данных чем-то вроде экземпляра HSQLDB, но все же проблема внешних служб. Для повторяемости я не могу полагаться на то, что эти службы находятся в состоянии, в котором я нуждаюсь, и т.д. Единственный вариант, который я вижу там, заключается в том, чтобы издеваться над ними.
Whatdaya do?
Ответы
Ответ 1
Отличный вопрос.
Кажется, вы попали в пределы Мокито. Mockito отлично, если вы хотите проверить взаимодействие объектов.
То, что вы хотите, похоже, является наблюдаемостью (и управляемостью) на более высоком уровне абстракции. Я боюсь, что вы должны быть тщательно разработаны и изготовлены вручную.
На уровне единицы эти макеты могут быть сгенерированы с помощью Mockito. На уровне интеграции это становится намного сложнее, и вам понадобятся целевые интерфейсы для тестирования.
Ответ 2
Чтобы издеваться над такими вещами, как базы данных, веб-сервисы, файловая система и т.д., вы, вероятно, захотите немного реорганизовать. Для каждой внешней службы вы должны написать класс-оболочку, который имеет метод для каждой операции, которую вы хотите выполнить. Каждый такой метод не должен иметь фактической логики, а просто проходит через его параметры таким образом, что внешняя служба будет понимать, и возвращает объект, который содержит любые данные, возвращаемые внешней службой. Например, если вы взаимодействуете с базой данных, класс-оболочка может форматировать свои параметры в оператор SQL, отправить их в существующий объект Connection
и вернуть List
для результата.
Поскольку методы класса-оболочки не содержат никакой логики (то есть нет if/else, нет циклов и обработки исключений); нет необходимости в unit test классе-оболочке. Вы должны интегрировать тест класса оболочки, чтобы убедиться, что его обязанности выполнены правильно (то есть, что оператор SQL имеет желаемый эффект для базы данных, например).
Теперь перезапишите классы, которые взаимодействуют с внешними службами, чтобы они взаимодействовали с классами-оболочками. Затем легко выполнить unit test их - вам просто нужно высмеять классы-оболочки.
Ответ 3
Если есть какая-то инфраструктура для http или rest mock, использование этого должно быть хорошим.
Все сложные зависимости могут быть записаны, изменены и воспроизведены.