Eenheid testen C# in .NET met behulp van dotnet-test en xUnit
Deze zelfstudie laat zien hoe u een oplossing bouwt die een eenheidstestproject en broncodeproject bevat. Als u de zelfstudie wilt volgen met behulp van een vooraf gebouwde oplossing, bekijkt of downloadt u de voorbeeldcode. Zie Voorbeelden en zelfstudies voor downloadinstructies.
De oplossing maken
In deze sectie wordt een oplossing gemaakt die de bron- en testprojecten bevat. De voltooide oplossing heeft de volgende mapstructuur:
/unit-testing-using-dotnet-test
unit-testing-using-dotnet-test.sln
/PrimeService
PrimeService.cs
PrimeService.csproj
/PrimeService.Tests
PrimeService_IsPrimeShould.cs
PrimeServiceTests.csproj
De volgende instructies bevatten de stappen voor het maken van de testoplossing. Zie Opdrachten voor het maken van een testoplossing voor instructies voor het maken van de testoplossing in één stap.
Open een shellvenster.
Voer de volgende opdracht uit:
dotnet new sln -o unit-testing-using-dotnet-test
Met de
dotnet new sln
opdracht maakt u een nieuwe oplossing in de map unit-testing-using-dotnet-test .Wijzig de map in de map unit-testing-using-dotnet-test .
Voer de volgende opdracht uit:
dotnet new classlib -o PrimeService
Met de
dotnet new classlib
opdracht maakt u een nieuw klassebibliotheekproject in de map PrimeService . De nieuwe klassebibliotheek bevat de code die moet worden getest.Wijzig de naam van Class1.cs in PrimeService.cs.
Vervang de code in PrimeService.cs door de volgende code:
using System; namespace Prime.Services { public class PrimeService { public bool IsPrime(int candidate) { throw new NotImplementedException("Not implemented."); } } }
Met de voorgaande code wordt:
- Hiermee wordt een NotImplementedException bericht met een bericht weergegeven dat het niet is geïmplementeerd.
- Wordt verderop in de zelfstudie bijgewerkt.
Voer in de map unit-testing-using-dotnet-test de volgende opdracht uit om het klassebibliotheekproject toe te voegen aan de oplossing:
dotnet sln add ./PrimeService/PrimeService.csproj
Maak het project PrimeService.Tests door de volgende opdracht uit te voeren:
dotnet new xunit -o PrimeService.Tests
De bovenstaande opdracht:
- Hiermee maakt u het project PrimeService.Tests in de map PrimeService.Tests . Het testproject gebruikt xUnit als testbibliotheek.
- Hiermee configureert u de testrunner door de volgende
<PackageReference />
elementen toe te voegen aan het projectbestand:Microsoft.NET.Test.Sdk
xunit
xunit.runner.visualstudio
coverlet.collector
Voeg het testproject toe aan het oplossingsbestand door de volgende opdracht uit te voeren:
dotnet sln add ./PrimeService.Tests/PrimeService.Tests.csproj
Voeg de
PrimeService
klassebibliotheek toe als een afhankelijkheid aan het project PrimeService.Tests :dotnet add ./PrimeService.Tests/PrimeService.Tests.csproj reference ./PrimeService/PrimeService.csproj
Opdrachten voor het maken van de oplossing
In deze sectie vindt u een overzicht van alle opdrachten in de vorige sectie. Sla deze sectie over als u de stappen in de vorige sectie hebt voltooid.
Met de volgende opdrachten maakt u de testoplossing op een Windows-computer. Werk voor macOS en Unix de ren
opdracht bij naar de versie van het besturingssysteem om de naam van ren
een bestand te wijzigen:
dotnet new sln -o unit-testing-using-dotnet-test
cd unit-testing-using-dotnet-test
dotnet new classlib -o PrimeService
ren .\PrimeService\Class1.cs PrimeService.cs
dotnet sln add ./PrimeService/PrimeService.csproj
dotnet new xunit -o PrimeService.Tests
dotnet add ./PrimeService.Tests/PrimeService.Tests.csproj reference ./PrimeService/PrimeService.csproj
dotnet sln add ./PrimeService.Tests/PrimeService.Tests.csproj
Volg de instructies voor 'Vervang de code in PrimeService.cs door de volgende code' in de vorige sectie.
Een test maken
Een populaire benadering in testgestuurde ontwikkeling (TDD) is het schrijven van een (mislukte) test voordat de doelcode wordt geïmplementeerd. In deze zelfstudie wordt gebruikgemaakt van de TDD-benadering. De IsPrime
methode kan worden aangeroepen, maar is niet geïmplementeerd. Een testoproep mislukt IsPrime
. Met TDD wordt een test geschreven die bekend is dat het mislukt. De doelcode wordt bijgewerkt om de testpas te maken. U blijft deze aanpak herhalen, een mislukte test schrijven en vervolgens de doelcode bijwerken om door te geven.
Werk het project PrimeService.Tests bij:
- Verwijder PrimeService.Tests/UnitTest1.cs.
- Maak een PrimeService.Tests/PrimeService_IsPrimeShould.cs-bestand .
- Vervang de code in PrimeService_IsPrimeShould.cs door de volgende code:
using Xunit;
using Prime.Services;
namespace Prime.UnitTests.Services
{
public class PrimeService_IsPrimeShould
{
[Fact]
public void IsPrime_InputIs1_ReturnFalse()
{
var primeService = new PrimeService();
bool result = primeService.IsPrime(1);
Assert.False(result, "1 should not be prime");
}
}
}
Het [Fact]
kenmerk declareert een testmethode die wordt uitgevoerd door de testloper. Voer in de map PrimeService.Tests de opdracht uit dotnet test
. De dotnet-testopdracht bouwt beide projecten en voert de tests uit. De xUnit-testloper bevat het programmainvoerpunt om de tests uit te voeren. dotnet test
start de testloper met behulp van het eenheidstestproject.
De test mislukt omdat IsPrime
deze niet is geïmplementeerd. Schrijf met behulp van de TDD-benadering alleen voldoende code, zodat deze test is geslaagd. Werk IsPrime
bij met de volgende code:
public bool IsPrime(int candidate)
{
if (candidate == 1)
{
return false;
}
throw new NotImplementedException("Not fully implemented.");
}
Voer dotnet test
uit. De test is geslaagd.
Meer tests toevoegen
Voeg priemnummertests toe voor 0 en -1. U kunt de test die u in de vorige stap hebt gemaakt, kopiëren en kopieën maken van de volgende code om 0 en -1 te testen. Maar doe het niet, want er is een betere manier.
var primeService = new PrimeService();
bool result = primeService.IsPrime(1);
Assert.False(result, "1 should not be prime");
Het kopiëren van testcode wanneer alleen een parameter verandert, resulteert in codeduplicatie en test-bloat. Met de volgende xUnit-kenmerken kunt u een suite met vergelijkbare tests schrijven:
[Theory]
vertegenwoordigt een reeks tests die dezelfde code uitvoeren, maar verschillende invoerargumenten hebben.[InlineData]
kenmerk geeft waarden op voor deze invoer.
In plaats van nieuwe tests te maken, past u de voorgaande xUnit-kenmerken toe om één theorie te maken. Vervang de volgende code:
[Fact]
public void IsPrime_InputIs1_ReturnFalse()
{
var primeService = new PrimeService();
bool result = primeService.IsPrime(1);
Assert.False(result, "1 should not be prime");
}
met de volgende code:
[Theory]
[InlineData(-1)]
[InlineData(0)]
[InlineData(1)]
public void IsPrime_ValuesLessThan2_ReturnFalse(int value)
{
var result = _primeService.IsPrime(value);
Assert.False(result, $"{value} should not be prime");
}
In de voorgaande code [Theory]
kunt [InlineData]
u verschillende waarden testen die kleiner zijn dan twee. Twee is het kleinste priemnummer.
Voeg de volgende code toe na de klassedeclaratie en vóór het [Theory]
kenmerk:
private readonly PrimeService _primeService;
public PrimeService_IsPrimeShould()
{
_primeService = new PrimeService();
}
Uitvoeren dotnet test
en twee van de tests mislukken. Als u alle tests wilt laten slagen, werkt u de IsPrime
methode bij met de volgende code:
public bool IsPrime(int candidate)
{
if (candidate < 2)
{
return false;
}
throw new NotImplementedException("Not fully implemented.");
}
Voeg na de TDD-benadering meer mislukte tests toe en werk vervolgens de doelcode bij. Bekijk de voltooide versie van de tests en de volledige implementatie van de bibliotheek.
De voltooide IsPrime
methode is geen efficiënt algoritme voor het testen van de primaliteit.