73

我想编写一个类库,它为我创建一个复杂的对象,但应该尽可能少地暴露。我希望它被包含到其他项目中,并且我只有一次调用这个库,例如返回一个内部创建的类的对象。我不想让其他人显式地创建这些对象,但我仍然想为这个类库创建一个测试项目。

例如:

var result = Manager.Instance.Create(definition)

这应该是对类库的唯一访问。

根据定义参数,它使用不同的子类来创建请求的实例并相应地设置其属性。因此,我想通过测试以某种方式确保整个创建过程运行良好。但是由于我也不想暴露结果对象的极少内部属性,因此我无法仅使用此公共访问方法进行测试,因为我没有任何要断言的属性。

我知道你不应该测试内部机制,这通常是糟糕的设计,我也正在阅读这篇文章,但是否有任何方法可以创建库和单元测试项目,然后可能会限制对此类的访问? 用包装纸什么的?

4

3 回答 3

159

在 .NET 中,您可以使用类库中的InternalsVisibleToAttribute 使您的内部类型对单元测试项目可见。

这样,您可以将您的类保留在内部,并且仍然可以从您授予访问权限的其他程序集中使用它。

你像这样使用它:

[assembly:InternalsVisibleTo("NameOfYourUnitTestProject")]
于 2013-03-15T19:50:55.030 回答
16

对于最新的csproj 2017格式化项目,如果你的项目没有该AssemblyInfo.cs文件,可以添加如下设置:

  <ItemGroup>
    <AssemblyAttribute Include="System.Runtime.CompilerServices.InternalsVisibleTo">
      <_Parameter1>$(MSBuildProjectName).Tests</_Parameter1>
    </AssemblyAttribute>
  </ItemGroup>

您也可以使用其他变量来替换MSBuildProjectName,例如AssemblyName或直接使用 unittest 项目名称。

您可以通过添加来检查ProjectName.AssemblyInfo.csobj 文件夹 ( obj\Debug\netstandard2.0) 是否已更新InternalsVisibleTo

于 2018-05-18T08:50:42.240 回答
0

在我的情况下(.NET5 应用程序)我需要两个 csproj 条目:

<ItemGroup>
    <AssemblyAttribute Include="System.Runtime.CompilerServices.InternalsVisibleTo">
        <_Parameter1>MyAppName.UnitTests</_Parameter1>
    </AssemblyAttribute>
</ItemGroup>

以及我的班级的 internalvisibleto 属性以使其正常工作:

[assembly: InternalsVisibleTo("DynamicProxyGenAssembly2, PublicKey=0024000004800000940000000602000000240000525341310004000001000100c547cac37abd99c8db225ef2f6c8a3602f3b3606cc9891605d02baa56104f4cfc0734aa39b93bf7852f7d9266654753cc297e7d2edfe0bac1cdcf9f717241550e0a7b191195b7667bb4f64bcb8e2121380fd1d9d46ad2d92d2d15605093924cceaf74c4861eff62abf69b9291ed0a340e113be11e6a7d3113e92484cf7045cc7")] 
namespace MyAppName.Api.Something...
于 2021-09-30T11:39:09.317 回答