2011-03-19 65 views
0

我正在處理與存儲庫模式的ASP MVC 3 PROJECT,我想知道我們是如何編寫存儲庫(聚合)CRUD操作的單元測試。我堅持保存部分,我想要回滾我的保存,從數據庫中刪除它,像 Transaction.rollback,它我不爲我工作,任何人都可以請幫我一些示例代碼如何做到這一點。存儲庫模式,NHibernate和單元測試

這裏是我的代碼的概述

Begintransaction 
session.save(Parent parent) in repository 
transaction.commit. 

單元測試:

opensession; 
_rep.Save(parent); 

其實,如果有一種方法或一段代碼,我可以投入的刪除部分我的測試類在每次測試之後運行在Save方法後的mycase中說出並刪除特定記錄,還有一件事情被認爲是,因爲這是每次測試後的運行我DNT知道如何處理它,當它試圖做在其他測試方法(刪除,獲取所有)後等同的東西。,我都困惑。

回答

0

如果你想測試你的數據庫訪問,你可以使用SQLite等內存數據庫進行測試。當您的測試完成時,該數據庫將消失,您不必清理測試數據。另一個優勢是速度。在內存數據庫比SQL Server等要快得多。

0

我想你需要回滾來保持數據庫清潔並避免測試之間的干擾。您可以通過爲每個單元測試提供自己的數據庫來實現此目的有一篇不錯的文章,介紹如何在Sql Server精簡版中有效實現這一點:http://www.differentpla.net/content/2009/03/using-sql-server-compact-edition-unit-testing

編輯:一些例子:http://nhdatabasescopes.codeplex.com/

+0

我們嘗試了SQL服務器CE並遇到了許多兼容性問題(某些功能不受CE支持)。現在我們正在使用SQLite沒有問題。 – Zebi 2011-03-19 17:46:48

+0

SQLLite可以完成同樣的事情。這裏描述:http://jasondentler.com/blog/2009/08/nhibernate-unit-testing-with-sqlite-in-memory-db/。所描述的方法的缺點是每次SQLiteDatabaseScope被實例化時都必須構建數據庫......並且需要很長時間。 – 2011-03-19 17:57:06

+0

我們正在使用一個專門的測試會話工廠,它是爲我們的測試而創建的,並保留到所有測試運行(使用自定義提供程序覆蓋關閉連接方法而不執行任何操作)。 – Zebi 2011-03-19 18:01:37

1

首先,你應該如果它要執行一個典型的單元測試或涉及到數據庫的集成測試決定。如果你想測試你的實體,你應該用你注入你的測試類假的,或者是模擬庫(IOC容器將是很好)。因此不需要回滾(因爲不涉及數據庫)。如果您執行集成測試,那麼我建議您在內存數據庫中使用Sqlite。它非常輕巧。儘管Sqlite的一個問題是它不提供事務支持。

0

在您的NUnit安裝和TearDown方法中,您需要刪除並在數據庫中創建指定的表(使用腳本)。所以,之前和之後你的每個測試運行,所有的數據都會的,當然被刪除留下您測試只空表。

下面的示例使用MySql數據庫,但即使是其他數據庫,代碼應該是很相似的:

public class DatabaseCleanup 
    { 
     private string _connectionString; 
     private MySqlConnection _mySqlConnection; 
     private string _filePath; 
     public DatabaseCleanup() 
     { 
      _filePath = @"C:\createdatabase.sql"; 
      _connectionString = @"Server=localhost;Port=3306;Database=dbname;Uid=username;Password=password;"; 
      _mySqlConnection = new MySqlConnection(_connectionString); 
     } 

     public void Create() 
     { 
      string script = File.ReadAllText(_filePath); 
      ExecuteScript(script); 
     } 

     private void ExecuteScript(string script) 
     { 
      try 
      { 
       MySqlCommand command = new MySqlCommand(script, _mySqlConnection); 
       _mySqlConnection.Open(); 
       command.ExecuteNonQuery(); 
       _mySqlConnection.Close(); 
      } 
      catch (Exception exception) 
      { 
       throw; 
      } 
      finally 
      { 
       _mySqlConnection.Close(); 
      } 
     } 
    } 

在上面的代碼中提到的腳本createdatabase.sql就是一個包含刪除表的SQL文件,並創建表語句,你可以根據你的數據庫提供。下面就是一個例子:

DROP TABLE IF EXISTS `my_table`; 

CREATE TABLE `my_table` (
    `Id` varchar(50) NOT NULL, 
    `Name` varchar(50) NOT NULL, 
    PRIMARY KEY (`Id`) 
) ENGINE=InnoDB DEFAULT CHARSET=utf8; 

然後,您可以使用DatabaseCleanup類在NUnit測試類的安裝和拆卸方法:

DatabaseCleanup databaseCleanup = new DatabaseCleanup(); 
databaseCleanup.Create(); 

要小心,不要運行在生產環境中,此數據庫清理代碼。僅在開發和測試環境中運行此類測試。

P.S.,我不喜歡人們在這裏說使用像SqlLite這樣的內存數據庫。這完全破壞了整合測試的全部目的。這意味着在開發環境中使用不同的數據庫測試代碼,然後在生產服務器上的不同數據庫平臺上部署和部署;然後面對噩夢!