Как удалить все данные базы данных с помощью NHibernate? - PullRequest
3 голосов
/ 08 июля 2010

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

=============================================== ===========

Хорошо, вот результаты. Я проверяю это в базе данных (Postgre). Я протестирую CreateSchema (1), решение DanP (2) и решение apollodude217 (3). Я запускаю тесты 5 раз для каждого метода и беру среднее время.

Раунд 1 - 10 тестов
(1) - ~ 26 с
(2) - 9,0 с
(3) - 9,3 с

Раунд 2 - 100 тестов
(1) - Давай, я не буду делать это на моей машине
(2) - 12,6 с
(3) - 18,6 с

Я думаю, что нет необходимости проводить дополнительные тесты.

Ответы [ 6 ]

3 голосов
/ 08 июля 2010

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

Наши модульные тесты обычно выполняются на Sqlite в памяти, это очень быстро. Эта база данных существует только до тех пор, пока соединение открыто, поэтому вся база данных создается заново для каждого теста. Мы переключаемся на Sqlserver, изменяя конфигурацию сборки.

2 голосов
/ 09 июля 2010

Лично я использую хранимую процедуру, чтобы сделать это, но это может быть возможно с исполняемым HQL (см. Этот пост для получения более подробной информации: http://fabiomaulo.blogspot.com/2009/05/nh21-executable-hql.html)

Что-то в русле сеанса.Удалить ("из объекта");

2 голосов
/ 08 июля 2010

Я не утверждаю, что это быстрее, но вы можете сделать что-то подобное для каждого сопоставленного класса:

// untested
var entities = MySession.CreateCriteria(typeof(MappedClass)).List<MappedClass>();
foreach(var entity in entities)
    MySession.Delete(entity);  // please optimize

Это (одно) не работает как минимум в 2 случаях:

  1. При наличии данных, которые должны быть в вашей базе данных при запуске приложения.
  2. Если у вас есть тип, в котором несохраненное значение свойства identity равно "any".
1 голос
/ 08 июля 2010

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

0 голосов
/ 09 июля 2010

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

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

НТН

0 голосов
/ 08 июля 2010

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

Альтернативой может быть написание сценария, который отбрасывает все внешние ключив базе данных затем удалите / обрежьте все таблицы.Однако это не приведет к сбросу каких-либо автоматически сгенерированных идентификаторов или последовательностей.Это не похоже на элегантное решение и определенно требует больше времени.В любом случае, это не то, что должно быть сделано через ORM, не только через NHibernate.

Почему вы отказываетесь от возможности воссоздания?Каковы ваши требования?Схема слишком сложная?Кто-то еще проектирует базу данных?Хотите избежать фрагментации файла?

...