2012-05-14 36 views
3

我搜索了很多,仍然無法找到一個可靠的解決方案。假設你的應用程序中有方法。此方法使用「System.Web.Configuration.WebConfigurationManager.OpenWebConfiguration」訪問web.config中的某些設置。如果您嘗試測試這些方法,您的測試將失敗,因爲您的測試項目沒有web.config。在.NET中引用Web.Config的測試方法C#

解決此問題的最佳方法是什麼?對於具有簡單配置文件的項目,我通常使用類似這樣的方法作爲外觀方法。

public class Config 
{ 
    public static String getKeyValue(String keyName) 
    { 
     if (keyName == String.Empty) return String.Empty; 
     String result = ""; 

     System.Configuration.Configuration rootWebConfig1 = 
      System.Web.Configuration.WebConfigurationManager.OpenWebConfiguration(null); 
     if (rootWebConfig1.AppSettings.Settings.Count > 0) 
     { 
      System.Configuration.KeyValueConfigurationElement reportEngineKey = 
       rootWebConfig1.AppSettings.Settings[keyName]; 

      if (reportEngineKey != null) 
      { 
       result = reportEngineKey.Value; 

      } 

     } 

     return result; 
    } 
} 

每次我試圖爲OpenWebConfiguration()的路徑,我得到了錯誤「相對虛擬路徑是不允許的」

回答

2

爲了使這種情況更具可測性,我通常採取製作自己的「設置管理器」的方法,並給它一個接口。因此,例如:

public interface IConfig 
{ 
    string GetSettingValue(string settingName); 
} 

然後我可以有我的「真實」的實施:

public sealed class Config : IConfig 
{ 
    public string GetSettingValue(string settingName) 
    { 
     // your code from your getKeyValue() method would go here 
    } 
} 

然後我的代碼,使用它會採取這樣的一個實例(這是Dependency Inversion Principal的一個例子) :

public void DoStuff(IConfig configuration) 
{ 
    string someSetting = configuration.GetSettingValue("ThatThingINeed"); 
    // use setting... 
} 

所以現在我的生產代碼,我可以打電話DoStuff和傳遞的Config一個實例。 當我需要測試時,我可以使用一個模擬工具(Moq,JustMock,RhinoMocks等)來創建一個假的IConfig,它返回一個已知的值而不會觸及實際的.config文件,或者您可以在沒有模擬框架的情況下執行製作你自己的模擬(並將它們存儲在你的測試項目中)。

public class ConfigMock : IConfig 
{ 
    private Dictionary<string, string> settings; 

    public void SetSettingValue(string settingName, string value) 
    { 
     settings[settingName] = value; 
    } 

    public string GetSettingValue(string settingName) 
    { 
     return settings[settingName]; 
    } 
} 

[Test] 
public void SomeExampleTest() 
{ 
    var config = new ConfigMock(); 
    config.SetSettingValue("MySetting", "SomeValue"); 

    var underTest = new MyClass(); 
    underTest.DoStuff(config); 
} 
+0

另外請注意,這只是1使這個可測試的方式。這絕不是唯一的方法。還有一些模擬框架可以模擬「靜態」方法,你可以使用其中的一個來模擬你現有的'Config.getKeyValue()'方法,幾乎​​沒有其他代碼改變。 – CodingWithSpike

+0

我想補充一下,kprobst下面的答案與這個答案是一致的。創建接口,然後使用Moq庫(或另一個模擬框架)來構建'ConfigMock'在此答案中提供的模擬對象。 –

+0

謝謝!它似乎是一個乾淨而可重用的方法。 – Reza

0

要做到這一點,最簡單的方法是使用一個嘲諷圖書館等作爲moq。需要一點時間才能搞清楚,但是一旦你這樣做了,你就可以抽離大部分管道工作,以返回你需要的值,以便進行可重複的,一致的測試。