Challenges of Unit Testing Private Methods in C#
Unit testing private methods in C# can be tricky due to their encapsulated nature. Although Visual Studio provides automatically generated accessor classes, runtime errors may still occur during testing.
Code examples and test cases
Consider the following code snippet and its corresponding test:
<code class="language-csharp">// 被测试单元 class TypeA { private List<TypeB> myList = new List<TypeB>(); private void MyFunc() { /* 忽略处理过程 */ } } // 单元测试 public void MyFuncTest() { TypeA_Accessor target = new TypeA_Accessor(); target.myList.Add(new TypeA_Accessor.TypeB()); target.MyFunc(); }</code>
Runtime error
Compilation successful, but runtime error due to type conversion issue:
<code>无法将类型为 'System.Collections.Generic.List`1[MyProj.TypeA.TypeA_Accessor+TypeB]' 的对象转换为类型为 'System.Collections.Generic.List`1[MyProj.TypeA.TypeA+TypeB]' 的对象。</code>
The root cause is that target
is of type TypeA_Accessor
, not the expected TypeA
. This mismatch causes the conversion to fail.
Solution
Before .NET Core 2.0
Use the PrivateObject
class to access private methods and fields:
<code class="language-csharp">PrivateObject target = new PrivateObject(new TypeA()); var retVal = target.Invoke("MyFunc");</code>
.NET Core 2.0 and above
ThePrivateObject
class is no longer supported. The alternative is to set the private method to internal
for testing purposes, or consider refactoring the code to avoid the need to test the private method.
The above is the detailed content of How Can I Effectively Unit Test Private Methods in C# While Avoiding Runtime Errors?. For more information, please follow other related articles on the PHP Chinese website!