Плохая ли практика запускать тесты в базе данных, а не в поддельных репозиториях?

StackOverflow https://stackoverflow.com/questions/607620

Вопрос

Я знаю, в чем преимущества, и использую поддельные данные, когда работаю с более сложными системами.

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

Важно ли по-прежнему создавать фальшивые данные или я могу забыть о дополнительном кодировании и сразу перейти к реальным данным?

Когда я говорю о реальной базе данных, я имею в виду не производственную базу данных, а тестовую базу данных, а использующую реальную действующую СУБД и ту же схему, что и реальная база данных.

Это было полезно?

Решение

Причинами использования поддельных данных вместо реальной БД являются:

  1. Скорость.Если ваши тесты медленные, вы не будете их запускать.Издевательство над БД может заставить ваши тесты работать намного быстрее, чем в противном случае.
  2. Контроль.Ваши тесты должны быть единственным источником тестовых данных.Когда вы используете поддельные данные, ваши тесты выбирают, какие подделки вы будете использовать.Таким образом, нет никаких шансов, что ваши тесты будут испорчены из-за того, что кто-то оставил БД в незнакомом состоянии.
  3. Заказать Независимость.Мы хотим, чтобы наши тесты можно было запускать в любом порядке.Входные данные одного теста не должны зависеть от результатов другого.Когда ваши тесты управляют тестовыми данными, тесты могут быть независимыми друг от друга.
  4. Независимость от окружающей среды.Ваши тесты должны работать в любой среде.Вы сможете запускать их в поезде, самолете, дома или на работе.Они не должны зависеть от внешних сервисов.Когда вы используете поддельные данные, вам не нужна внешняя БД.

Теперь, если вы создаете небольшое приложение и, используя настоящую БД (например, MySQL), вы можете достичь вышеуказанных целей, то обязательно используйте БД.Я делаю.Но не заблуждайтесь: по мере роста вашего приложения вы в конечном итоге столкнетесь с необходимостью макетирования БД.Это нормально, делайте это, когда вам нужно.ЯГНИ.Просто убедитесь, что вы ДЕЛАЕТЕ это, КОГДА вам нужно.Если вы отпустите это, вы заплатите.

Другие советы

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

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

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

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

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

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

Я думаю, это зависит от того, зафиксированы ли ваши запросы внутри репозитория (лучший вариант, IMO) или от того, предоставляет ли репозиторий составные запросы;например - если у вас есть метод репозитория:

IQueryable<Customer> GetCustomers() {...}

Тогда ваш пользовательский интерфейс может запросить:

var foo = GetCustomers().Where(x=>SomeUnmappedFunction(x));

bool SomeUnmappedFunction(Customer customer) {
   return customer.RegionId == 12345 && customer.Name.StartsWith("foo");
}

Это пройдет для объектно-ориентированного фальшивого репозитория, но не для действительный реализации БД.Конечно, вы можете свести это на нет, заставив репозиторий обрабатывать все запросы внутри себя (без внешней композиции);например:

Customer[] GetCustomers(int? regionId, string nameStartsWith, ...) {...}

Поскольку это невозможно составить, вы можете проверить БД и пользовательский интерфейс независимо.При использовании составных запросов вы вынуждены постоянно использовать интеграционные тесты, если хотите, чтобы они были полезными.

Это скорее зависит от того, настроена ли БД автоматически тестом, а также изолирована ли база данных от других разработчиков.

На данный момент это может не быть проблемой (например.только один разработчик).Однако (при ручной настройке базы данных) настройка базы является дополнительным препятствием для запуска тестов, и это очень плохо.

Если вы просто пишете простое одноразовое приложение, которое, как вы абсолютно уверены, не будет расти, я думаю, что многие «лучшие практики» просто улетят в окно.

Вы не нуждаться использовать DI/IOC, проводить модульные тесты или имитировать доступ к вашей базе данных, если все, что вы пишете, — это простая форма «Свяжитесь с нами».Однако где провести грань между «простым» приложением и «сложным» сложно.

Другими словами, руководствуйтесь здравым смыслом, поскольку на этот вопрос не существует однозначного ответа.

Это нормально для сценария, если вы не рассматриваете их как «модульные» тесты.Это будут интеграционные тесты.Вам также стоит подумать, будете ли вы снова и снова вручную тестировать через пользовательский интерфейс, поскольку вместо этого вы можете просто автоматизировать дымовые тесты.Учитывая это, вы можете даже подумать о том, чтобы вообще не проводить интеграционные тесты, а просто работать на уровне функциональных/UI-тестов (поскольку они уже будут охватывать интеграцию).

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

Поскольку Real DB не мешает вам и вы можете работать быстрее, я был бы прагматичен и пошел бы на это.

В модульном тестировании «тест» важнее, чем «модуль».

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

Однако есть несколько недостатков:

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

И, как вы заметили, у вас есть простое приложение;когда это станет менее простым, вам понадобятся тесты, которые можно будет классифицировать как модульные и системные тесты.Модульные тесты должны быть нацелены на простую часть функциональности, которую будет гораздо проще реализовать с поддельными данными.

Одним из преимуществ поддельных репозиториев является то, что ваше регрессионное/модульное тестирование является последовательным, поскольку вы можете ожидать одинаковых результатов для одних и тех же запросов.Это упрощает создание определенных модульных тестов.

Есть несколько недостатков, если ваш код (если не только запрос на чтение) изменяет данные:- Если в вашем коде есть ошибка (вероятно, именно поэтому вы и тестируете), вы можете в конечном итоге нарушить работу рабочей базы данных.Даже если ты его не сломал.- если производственная база данных меняется со временем, особенно во время выполнения вашего кода, вы можете потерять контроль над добавленными вами тестовыми материалами и впоследствии столкнуться с трудностями при их удалении из базы данных.- Производственные запросы из других систем, обращающихся к базе данных, могут воспринимать ваши тестовые данные как реальные данные, и это может где-то в будущем испортить результаты важных бизнес-процессов.Например, даже если вы пометили свои данные определенным флагом или префиксом, можете ли вы гарантировать, что любой, кто обращается к базе данных, будет придерживаться этой схемы?

Кроме того, некоторые базы данных регулируются законами о конфиденциальности, поэтому в зависимости от вашего контракта и того, кто владеет основной БД, вам может быть разрешен или не разрешен по закону доступ к реальным данным.

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

Это действительно простое приложение, и вы не видите, как оно растет. Я не вижу проблем с запуском ваших тестов на реальной БД.Однако если вы считаете, что приложение будет расти, важно учитывать это в своих тестах.

Делайте все как можно проще, и если в дальнейшем вам потребуется более гибкое тестирование, сделайте это.Однако планируйте заранее, потому что вы не хотите через 3 года иметь огромное приложение, основанное на старых и хакерских (для больших приложений) тестах.

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

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

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top