C# 当单元测试位于不同的程序集中时,如何存根Properties.Settings对象?

C# 当单元测试位于不同的程序集中时,如何存根Properties.Settings对象?,c#,.net,settings,rhino-mocks,stubbing,C#,.net,Settings,Rhino Mocks,Stubbing,我有一个对象引用了一堆属性.设置.默认值…值,我需要在这个对象的单元测试中存根这些值 不幸的是,设置对象的类型被声明为internal,因此我无法从单元测试项目访问它 如何对这些属性的返回值进行存根?我用Rhino Mock进行模拟。一般来说,我不会。与其让“内部”对象实际读取Properties.Settings.Default,不如让它们声明一个可配置的属性(在构造时或通过属性),并让另一段代码填充它们 这样,您可以在单元测试中测试除默认读取内容以外的所有内容,并且您与读取默认值的方式的耦合

我有一个对象引用了一堆
属性.设置.默认值…
值,我需要在这个对象的单元测试中存根这些值

不幸的是,设置对象的类型被声明为
internal
,因此我无法从单元测试项目访问它


如何对这些属性的返回值进行存根?我用Rhino Mock进行模拟。

一般来说,我不会。与其让“内部”对象实际读取Properties.Settings.Default,不如让它们声明一个可配置的属性(在构造时或通过属性),并让另一段代码填充它们


这样,您可以在单元测试中测试除默认读取内容以外的所有内容,并且您与读取默认值的方式的耦合性会降低,从而使将来更容易切换机制。

另外一个您可能会发现有助于解决内部问题的技巧,实际上,您可以有选择地使内部代码对单元测试可见。在您正在测试的代码中,打开AssemblyInfo.cs并添加如下内容:

#if UNITTEST
[assembly: System.Runtime.CompilerServices.InternalsVisibleTo("YourUnitTestAssembly")]
#endif

然后您只需要在构建中定义UNITTEST符号,您的测试程序集就可以查看所有内部成员。

我知道这是一个老问题,但我想我会添加我的解决方案,因为它很简单,可以帮助别人

创建的设置类是一个分部类,我们可以利用它创建自己的默认实现

在“属性”文件夹中创建新文件

internal partial class Settings : ISettings
{
    private static ISettings _setInstance;

    internal static ISettings Get
    {
        get
        {
            return _setInstance = _setInstance  ?? Default;
        }
        set { _setInstance = value; }
    }
}
然后,当我们在应用程序的其他地方使用它时,我们可以调用Settings.Get。。 如果要从测试中设置值,请创建一个从ISettings继承的类,并设置新的实现

如果在单独的项目中找到测试,则必须添加另一个类以将setter公开。
我们无法将设置文件更改为public,因为这将在下次更改或添加值时被覆盖。

是的,通过这种方式,对象通过不依赖属性而更易于重用。设置也“不太可能损坏”。通过查找默认值,对象有两个职责-其实际工作,并且知道在哪里可以找到设置。如果有1000个类都依赖于properties.settings,然后决定数据来自其他地方,这将是一个严重的问题!