【问题标题】:Mocking up ConfigurationManager.Appsettings without using Facade Approach在不使用外观方法的情况下模拟 ConfigurationManager.Appsettings
【发布时间】:2017-02-21 06:05:20
【问题描述】:

我要测试一个方法,我得到了一切工作,除了我无法 moq ConfigurationManager.AppSettings。

我的方法定义为

  public async Task<IDictionary<string, object>> Action(IDictionary<string, object> context)
    {
        if (ConfigurationManager.AppSettings[ApplicationUserFromDomainUserKey] == null)
            throw new ConfigurationErrorsException(ApplicationUserFromDomainUserKey);
        string storedProcedure = ConfigurationManager.AppSettings.Get(ApplicationUserFromDomainUserKey);

        if (ConfigurationManager.ConnectionStrings[DbConnectionKey] == null)
            throw new ConfigurationErrorsException(DbConnectionKey);
        ...

}

我在this question 中看到,使用外观方法的方法会很好,但它会弄脏我不使用 IoC / DI 的类实现

我也读过这个intresting article,但这仅适用于 Vs 企业版,我希望它可以在 CI/VS 专业版上运行

我正在使用 NUnit 进行测试,我的测试是

        [Test]
    public void MissingAppSettingsKey()
    {
            var pipeline = new RetrieveApplicationUsernamePipelineStep();

            var context = new Dictionary<string, object>()
            {
                [Resources.DomainUser] = "andrea",
                [Resources.Domain] = "ifinformatica.net",
                [Resources.ApplicationId] = 0
            };

            Assert.ThrowsAsync<ConfigurationErrorsException>(async () => await pipeline.Action(context));

        }

    }

附:我还使用 resharper 的工具进行测试,这让我也无法运行 microsoft 单元测试框架

【问题讨论】:

  • 那么你的问题是什么?
  • 如果您不想注入配置,至少可以让您的应用程序不使用ConfigurationManager.AppSettings,而是使用您选择的单例,这样更易​​于更改。如果您甚至不想这样做 ,可以retarget the .config file being read at runtime,因为这是 hacky(并且对于您需要生成文件的测试来说绝对不是最佳选择)。

标签: c# unit-testing


【解决方案1】:

更简单的方法是开始使用有限的 DI 实现来移除 ConfigurationManager 依赖项。

重载您的构造函数(无论它是什么)以将 AppSettings 条目作为参数。

所以如果你像这样创建你的对象:

  MyObject myObj = new MyObject(SomeParam);

..with 构造函数声明...

  public MyObject(ParamObj someParam)
  {
    //...implementation....
  }

...像这样重载它...

  public MyObject(ParamObj someParam)
   : this(someParam, Convert.ToInt32(ConfigurationManager.AppSettings["mySetting"]))
  {
    //...implementation....
  }


  public MyObject(ParamObj someParam, int mySettingValue)
  {
    //...implementation....
  }

这意味着当您测试时,您使用不调用/不需要ConfigurationManager 的构造函数来构造对象。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-24
    • 2020-11-13
    • 1970-01-01
    • 2022-07-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多