当测试具有主机类型“Moles”时,无法访问配置文件中的信息

当unit testing的主机类型为“Moles”时,我们在通过unit testing访问.net配置文件(例如app.config和web.config)中的信息时遇到问题。 这引起了不少令人头疼的问题,所以我希望有人知道可以做些什么。

我们正在使用Visual Studio 2010,我相信我们已经在安装了VS 2010 SP1的机器上安装了这个,并且没有安装SP1的机器,以及在32位和64位机器上尝试它。

我冒昧地将测试缩减到最简单的条件。 可以通过组合由以下两个文件组成的unit testing项目来重新创建该问题,并在取消注释唯一的注释行之后运行测试。 测试在没有主机类型的情况下工作,但是当您将Moles作为主机类型引入时,测试中的空断言将失败。 我们不确定为什么。

一,配置文件App.config:

      

接下来,包含单个测试的测试类:

 namespace TestProject { using System.Configuration; using Microsoft.VisualStudio.TestTools.UnitTesting; [TestClass] public class UnitTest { [TestMethod] //[HostType("Moles")] public void TestMethod() { var data = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None); Assert.IsNotNull(data.ConnectionStrings.ConnectionStrings["Connection"]); } } } 

如果有人能提供任何见解,我将不胜感激。

非常感谢,

缺口

我不确定它是否能完成这项工作,但您可以尝试这种解决方法:使用文件映射打开配置。 代码如下所示:

 ExeConfigurationFileMap fileMap = new ExeConfigurationFileMap(); fileMap.ExeConfigFilename = configurationFilePath; System.Configuration.Configuration configuration = ConfigurationManager.OpenMappedExeConfiguration( fileMap, ConfigurationUserLevel.None); 

每次执行unit testing时,应通过dependency injection传递应用程序和用户设置。 这是通过为设置创建一个Stub来实现的,这很容易做到。

  1. 在正在测试的项目中创建一个接口,该接口包含每个配置设置的属性。 让我们称之为“ISettings”,以供参考。

  2. 在实现接口的目标程序集中创建存根(类)。 存根中的每个属性应仅包含一个从配置文件返回相应设置的get。 我们将此存根称为“SettingsStub”。 此存根由目标程序集在生产环境中使用。

  3. 将ISettings类型参数添加到目标类型(正在测试的类)构造函数中。 必须将目标类中的字段设置为传递给构造函数的ISettings对象。 您可以创建一个重载构造函数,并根据某些设计模式(MVVM等)的要求保留默认构造函数。 默认构造函数(没有参数的构造函数)可以简单地实例化一个新的SettingsStub,以便在生产中使用。 测试必须始终使用重载的构造函数!

  4. 为测试项目创建一个设置存根,它还实现了ISettings。 我们将其称为TestSettingsStub。 此存根包含大多数测试可接受的硬编码值。

  5. 重建目标和测试项目。 Moles生成名为SISettings的Stub类型。

当您不需要调整任何设置值时,请使用具体的TestSrtyingsStub。 或者,当需要针对一个或两个测试调整值时,使用Miles Stub类型。 Moles Stub类型的目的是避免需要创建包含一个或两个唯一更改的许多存根。

调用重载的构造函数时,SettingsStub,TestSettigsStub和SISettings类型可以互换使用。 现在,您可以在测试期间完全控制每个上下文中使用的设置,而无需切换逻辑或手动更改设置值。 目标代码只是从本地字段检索设置值,而不是直接从配置文件中检索。 请参阅dependency injection和控制反转(IOC)主题。

像往常一样,为了安全起见,您的开发工作站开发无法访问生产网络上的外部依赖系统(数据库等)!

快乐的编码!

我同意Mike的回答在逻辑上是正确的(即你没有将你的配置加载与类别分开 – 可能),实际问题是对于Moles主机类型,根据你的原始问题,你需要调用调用例如,配置系统

  MConfigurationManager.AllInstances.OpenExeConfiguration (... finish your moleing here...) 

语法是近似的 – 我不记得在这种情况下你是否最终得到了SConfigurationManager或MConfigurationManager。

我完全不同意迈克的说法是“……开发工作站无法访问外部依赖系统……”这句话很可怕。 我们将这些东西称为集成测试。

是的,您作为开发人员应该创建它们。 在某些时候,您将编写触及具体实现的代码(例如数据库,支持服务等等),如果您没有测试该交互,那么您几乎做错了。