When following a Test Driven Development (TDD) approach and adhering to Object-Oriented Programming (OOP) principles, especially encapsulation, tests need to be written to cover internal classes and methods.
To allow internal members in a project to be accessible to a test assembly, simply add the following code block to the csproj
file:
When following best practices, unit test project names should be the same name as the assembly that is been tested and ended with .Tests
. This is the reason why the above code uses $(AssemblyName).Tests
as the name of the test project.
Instead of using $(AssemblyName).Tests
, the name of the test assembly can be used directly, example:
Example usage
As an example, create a solution named InternalsDemo
with two projects:
InternalsDemo
– Class Library (.NET Standard)InternalsDemo.Tests
– xUnit Test Project (.NET Core)
Install the following nuget packages in the InternalsDemo.Tests
project:
- AutoFixture
- Moq
- FluentAssertions
Reference InternalsDemo
in the InternalsDemo.Tests
project:

In the InternalsDemo
project, create the following classes.
Note that the implementation of the HeroService
is internal
.
In the InternalsDemo.Tests
project, add the following test case:
Now that all the classes are set up, build the solution. The build should fail with the following error:
'HeroService' is inaccessible due to its protection level
To resolve this, open the InternalsDemo
csproj and add the following code:

You will now be able to build the solution and run the unit test.
Summary
Microsoft have provided an easy way for developers to expose internal members in a project to other assemblies. This is done by adding a simple snippet of code in the csproj
file.
The source code used in this article can be found here.
Software versions used in this article
- Visual studio 2019 v4.8.03752
- .net standard v2.0.3
- AutoFixture v4.11.0
- Moq v4.14.1
- xunit v2.4.1
- FluentAssertions v5.10.3
- ReSharper Ultimate v2020.1.1