簡體   English   中英

使用NUnit對app.config文件進行單元測試

[英]Unit testing the app.config file with NUnit

當你們在單元測試一個依賴app.config文件值的應用程序時? 如何測試這些值是否正確讀入以及程序如何對輸入到配置文件中的錯誤值做出反應?

必須修改NUnit應用程序的配置文件是荒謬的,但我無法讀取我要測試的app.config的值。

編輯:我想我應該澄清一下。 我並不擔心ConfigurationManager無法讀取值,但我擔心測試我的程序如何對讀入的值做出反應。

我通常會隔離外部依賴項,例如在自己的Facade類中讀取配置文件,但功能很少。 在測試中,我可以創建這個類的模擬版本,實現並使用它而不是真正的配置文件。 您可以創建自己的模型或使用像moq或rhino模擬這樣的框架。

這樣,您可以輕松地嘗試使用不同配置值的代碼,而無需編寫首先編寫xml配置文件的復雜測試。 讀取配置的代碼通常非常簡單,只需要很少的測試。

您可以在測試設置中在運行時修改配置部分。 例如:

// setup
System.Configuration.Configuration config = 
     ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
config.Sections.Add("sectionname", new ConfigSectionType());
ConfigSectionType section = (ConfigSectionType)config.GetSection("sectionname");
section.SomeProperty = "value_you_want_to_test_with";
config.Save(ConfigurationSaveMode.Modified);
ConfigurationManager.RefreshSection("sectionname");

// carry out test ...

您當然可以設置自己的幫助方法來更優雅地執行此操作。

您可以調用ConfigurationManager.AppSettings的set方法來設置該特定單元測試所需的值。

[SetUp]
public void SetUp()
{
  ConfigurationManager.AppSettings.Set("SettingKey" , "SettingValue");
  // rest of unit test code follows
}

當單元測試運行時,它將使用這些值來運行代碼

您可以使用ConfigurationManager類讀取和寫入app.config文件

我在使用web.config時遇到了類似的問題....我找到了一個有趣的解決方案。 您可以封裝配置讀取功能,例如:

public class MyClass {

public static Func<string, string> 
     GetConfigValue = s => ConfigurationManager.AppSettings[s];

//...

}

然后通常使用

string connectionString = MyClass.GetConfigValue("myConfigValue");

但在單元測試中初始化“覆蓋”這樣的函數:

MyClass.GetConfigValue = s =>  s == "myConfigValue" ? "Hi", "string.Empty";

更多關於它:

http://rogeralsing.com/2009/05/07/the-simplest-form-of-configurable-dependency-injection/

更優雅的解決方案是在配置設置本身上使用普通舊依賴注入。 恕我直言這比模擬配置閱讀類/包裝等更清潔。

例如,假設“天氣”類需要“ServiceUrl”才能運行(例如說它調用Web服務來獲取天氣)。 而不是讓某些代碼行主動進入配置文件以獲取該設置(無論該代碼是在Weather類中還是可以根據其他一些響應進行模擬的單獨配置閱讀器),Weather類可以允許要注入的設置,可以通過參數傳遞給構造函數,也可以通過屬性設置器注入。 這樣,單元測試非常簡單直接,甚至不需要嘲笑。

然后可以使用Inversion of Control(或Dependency Injection)容器注入設置的值,因此Weather類的使用者不需要從某處顯式提供值,因為它由容器處理。

這對我有用:

 public static void BasicSetup()
  {
     ConnectionStringSettings connectionStringSettings = 
          new ConnectionStringSettings();
     connectionStringSettings.Name = "testmasterconnection";
     connectionStringSettings.ConnectionString = 
          "server=localhost;user=some;database=some;port=3306;";
     ConfigurationManager.ConnectionStrings.Clear();
     ConfigurationManager.ConnectionStrings.Add(connectionStringSettings);
  }

您始終可以將讀入位包裝在接口中,並從配置文件中讀取特定的實現。 然后,您將使用Mock Objects編寫測試,以查看程序如何處理錯誤值。 就個人而言,我不會測試這個特定的實現,因為這是.NET Framework代碼(我假設 - 希望 - MS已經測試過它)。

System.Configuration.Abstractions在測試這種東西時是一件很美的事。

這是GitHub項目站點,其中包含一些很好的示例: 在此處輸入鏈接描述

這是NuGet網站: https//www.nuget.org/packages/System.Configuration.Abstractions/

我在幾乎所有的.NET項目中都使用它。

實際上,進一步思考它,我想我應該做的是創建一個ConfigFileReader類,用於我的項目,然后在單元測試工具中偽造它?

這是平常的事嗎?

最簡單的選擇是包裝讀取配置的方法,以便在測試期間替換值。 創建一個用於讀取配置的接口,並將該接口的實現作為構造函數參數傳入或作為屬性設置在對象上(就像使用依賴注入/控制反轉一樣)。 在生產環境中,傳入一個真正從配置中讀取的實現; 在測試環境中,傳入一個返回已知值的測試實現。

如果你沒有選擇重構可測試性的代碼但仍然需要測試它,那么Typemock Isolator提供了實際模擬.NET框架配置類的能力,所以你可以說“下次我要求這樣 - 和 - 這樣的appSettings值,返回這個已知值。“

我遇到過同樣的問題,

你可以使用Nunit-console.exe c:\\ path1 \\ testdll1.dll c:\\ path2 \\ testdll2.dll

這工作正常,即使兩個dll指向不同的app.configs ex testdll1.dll.config和testdll2.dll.config

如果你想使用Nunit項目配置並包裝這兩個dll,那么你就無法擁有兩個配置

如果您的Nunit項目與Project1.nunit位於同一位置的project1.nunit,則必須擁有project1.config。

希望這可以幫助

好吧,我剛遇到同樣的問題......我想測試一個從網站引用的BL項目。 但我只想測試BL。 因此,在測試項目的預構建事件中,我將app.Config文件復制到bin \\ debug文件夾中,並從app.config引用它們...

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM