Издевательские объекты в тестах JUnit - лучшая практика?

Считаете ли вы, что насмешливые объекты в тесте JUnit - это лучшая практика? Я не вижу большого преимущества. Конечно, если у вас есть база данных, которая не должна учитываться в вашем тесте, это имеет смысл, но почему не просто введена другая реализация этого компонента (если используется spring). Объект factory для тестов сделает это намного проще. У меня нет большого опыта (мы используем Mockito), но я уже видел, что код приложения изменяется, поэтому некоторые свойства становятся макетными! Тестовые примеры никогда не должны влиять на такие изменения в продуктивном коде в моем выступлении.

Итак, что вы думаете об этой теме? В каких случаях вы издеваетесь над своим объектом или почему вы этого не делаете?

Ответ 1

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

Объект factory для тестов предположительно создавал бы объекты с stubbed, а mocking framework - это, по сути, универсальные объекты-объекты для использования в тестах. Но макеты обеспечивают намного больше, чем делают заглушки - различие, которое здесь подробно описывает Мартин Фаулер: http://martinfowler.com/articles/mocksArentStubs.html.

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

Ответ 2

Я уже видел, что приложение код изменяется, поэтому некоторые свойства становятся насмешливыми! Испытательные случаи никогда не должны влиять на такие изменения в продуктивный код в моем oppinion.

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

Даже если вы не согласны с этой философией (я не покупаю ее на 100% самостоятельно), если вы считаете, что автоматические тесты дают ценность, то изменение производственного кода для поддержки этой ценности имеет смысл (если только серьезно компрометирует дизайн каким-то другим способом).

Ответ 3

  • Определяет калибровку интерфейсов классов (обнаружение интерфейса)
  • Позволяет создавать сверху вниз
  • Изоляция (модульное тестирование)
  • Разъясняет взаимодействие между классами
  • Иногда единственный способ увидеть, делает ли объект то, что вы хотите (Mocks and Tell Dont Ask)
  • Поощрение лучших структурированных тестов. Например, jukito автоматически вводит макеты, чтобы вы могли сосредоточиться на вещах, которые вы хотите проверить.
  • Позволяет сохранять инкапсуляцию
  • Уменьшает зависимости

  • Объект значения не следует издеваться

Отказывание фреймворков из-за необходимости. Как сказал Мэтью Гиллиард, если происходит какая-то насмешка, то это признак того, что дизайн может быть улучшен или отсутствует фокус теста. Тесты выявляют множество проблем в коде.

но почему не просто введена другая реализация этого компонента (если используется spring).

Вам нужно написать реализацию. Используя насмешливую структуру, это делается для вас.

Я уже видел, что код приложения изменяется, поэтому некоторые свойства становятся макетными! По моему мнению, тестовые примеры никогда не должны усиливать такие изменения в продуктивном коде.

Если макетируемые средства проверяются, то это наоборот. Например, в TDD-тесте определяется производственный код.

Ответ 4

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

Однако существует некоторая путаница в том, как это относится к понятию тестируемости. Сложный, свернутый код не проверяется, потому что его трудно понять. Хорошо продуманный код, который имеет чистый и простой дизайн, обычно легче понять и поддерживать; почему это должно быть трудно unit test, то?

Путаница возникает из-за некоторых произвольных ограничений, обнаруженных в некоторых насмешливых инструментах, таких как невозможность издеваться над методами final или static или необходимость иметь тестируемую единицу непосредственно с использованием макетных объектов, созданных в тестовом коде. Другие издевательские инструменты не имеют этих ограничений и, следовательно, не требуют, чтобы "код приложения был изменен, чтобы некоторые свойства были макетными". С современными языками программирования/платформами (Java, С#, Python, Ruby и т.д.) Все вымывается; это просто вопрос разоблачения этой власти в насмешливом API, и это уже сделано для каждого из этих языков (в интересах полного раскрытия я разрабатываю один такой инструмент).