2010-05-13 31 views
0

如何创建一个单元测试,在asp.net如何创建一个单元测试,更新记录到数据库在asp.net

+4

如果您正在更新数据库中的记录,它是一个集成测试,而不是单元测试。 – Oded 2010-05-13 09:02:02

+1

“的测试是不是一个单元测试,如果: 它谈论到数据库 它通过网络进行通信 倒是文件系统 [...]。” - 迈克尔“修改代码的工作” Feathers,2005 [http://www.artima.com/weblogs/viewpost.jsp?thread=126923] – Johnsyweb 2010-05-13 13:22:48

回答

1

虽然在技术上我们不叫这个更新记录到数据库'单元测试',但是'集成测试'(如Oded解释),你可以通过使用单元测试框架(如MSTest(Visual Studio 2008/2010 professional的一部分)或免费的单元测试框架之一)如NUnit。

但是,测试ASP.NET Web项目通常很困难,尤其是当您将所有逻辑放入网页时。最好的办法是将所有业务逻辑提取到单独的层(通常是解决方案中的单独项目),并从网页中调用该逻辑。但是也许你已经有了这种分离,这将会很棒。

这样你也可以在你的测试中调用这个逻辑。对于集成测试,最好有一个单独的测试数据库。测试数据库必须包含已知(和稳定的)数据集(或者完全为空)。不要使用生产数据库的副本,因为数据更改时,测试可能突然失败。你也应该确保数据库中由集成测试所做的所有更改都应该回滚。否则,测试数据库中的数据会不断变化,这可能会导致您的测试突然失败。

我在集成测试中始终使用TransactionScope(并且从未在我的生产代码中)。这确保所有数据都会回滚。以下是对这样的集成测试可能看起来像一个例子,在使用的MSTest:

[TestClass] 
public class CustomerMovedCommandTests 
{ 
    // This test test whether the Execute method of the 
    // CustomerMovedCommand class in the business layer 
    // does the expected changes in the database. 
    [TestMethod] 
    public void Execute_WithValidAddress_Succeeds() 
    { 
     using (new TransactionScope()) 
     { 
      // Arrange 
      int custId = 100; 

      using (var db = new ContextFactory.CreateContext()) 
      { 
       // Insert customer 100 into test database. 
       db.Customers.InsertOnSubmit(new Customer() 
       { 
        Id = custId, City = "London", Country = "UK" 
       }); 

       db.SubmitChanges(); 
      }     

      string expectedCity = "New York"; 
      string expectedCountry = "USA"; 

      var command = new CustomerMovedCommand(); 
      command.CustomerId = custId; 
      command.NewAddress = new Address() 
      { 
       City = expectedCity, Country = expectedCountry 
      }; 

      // Act 
      command.Execute(); 

      // Assert 
      using (var db = new ContextFactory.CreateContext()) 
      { 
       var c = db.Customers.Single(c => c.Id == custId); 

       Assert.AreEqual(expectedCity, c.City); 
       Assert.AreEqual(expectedCountry, c.Country); 
      } 
     } // Dispose rolls back everything. 
    } 
} 

我希望这可以帮助,但下一次,请更具体一点在你的问题。

+1

很好的解释。关于'单元测试'我会补充你可以'模拟'你的图层。原则是尽可能地模拟真实情况下会发生什么情况,以验证您的代码而不做实际的事情:影响您的数据,文件或进程......数据模拟将模拟您的数据库中将执行的操作但不会连接或访问数据库。我想这不是你想要检查的内容,而是一种从数据库映射测试(集成测试)中隔离数据访问测试(单元测试)的方式。模拟通常是'单元测试',因为环境并不重要。 – JoeBilly 2010-05-13 10:21:29

+0

@JoeBilly:我同意。集成测试应该是最后的手段,您应该尝试使架构单元测试更友好。但是,这需要付出很多努力(和经验)。作为一名顾问,我经常建议经验较少的团队开始进行集成测试,因为我不需要对其架构进行任何更改。 LINQ确实让事情变得更糟:您永远不会知道您的O/RM是否支持您编写的LINQ查询。正因为如此,我喜欢看到内存提供者被添加到实体框架中,其行为与真正的EF数据库提供者完全一样。 – Steven 2010-05-13 19:16:56