Słuchajcie, wiecie jak to jest z tymi obietnicami. Wypije się za dużo kakałka, nie wyśpi, a potem obiecujesz ludziom, że napiszesz konkretny artykuł na specyficzny temat. No i tak właśnie to ten, napisałem go. Obietnic się dotrzymuje, koniec i kropka ;). Tak jak obiecałem, będzie to sposób przesłania raportu o pokryciu kodu testami do serwera SonarQube. Miałem trochę na głowię - zagraniczna delegacja, rozwój firmy - więc chwile to zajęło, ale mieszczę się jeszcze w terminie ;).
Chcąc podążać jeden do jednego z tym artykułem musisz mieć przygotowane dwie rzeczy: serwer SonarQube i projekt ze skonfigurowanymi raportami pokrycia testów przez narzędzie Coverlet. Jeżeli jeszcze tego nie masz polecam zapoznać się z moimi poprzednimi artykułami:
Generowanie raportu za pomocą Coverlet
Dla tych, co już posiedli odpowiednią wiedzę, ale jak ja lubią mieć pewność, małe przypomnienie. Raport generujemy za pomocą komendy:
$ dotnet test /p:CollectCoverage=true /p:CoverletOutputFormat=opencover /p:CoverletOutput=./opencover /p:Exclude="[xunit.runner.*]*"
Coverlet stworzy w projekcie testowym plik z raportem: opnecover.opencover.xml, który musimy już sami przeprocesować za pomocą SonarQube.
Integracja z SonarQube
Do integrowanie raportów potrzebujemy, do polecenia dotnet sonarscanner begin
, dodać kilka kolejnych argumentów. Tym razem będą to:
- sonar.cs.opencover.reportsPath -> Ścieżka, po której sonar może znaleźć plik z raportem
- sonar.exlusions -> Wyrażenia regularne za pomocą, których możemy wykluczyć wybrane pliki z raportów (Ja w ten sposób wykluczam wszystkie pliki generowane przez oprogramowanie zewnętrzne, np. plik opencover.xml wygenerowany przez Coverlet)
- sonar.coverage.exclusions -> Wyrażenia regularne pozwalające wykluczyć pliki, dla których nie chcemy aby pokrycie kodu było mierzone. Przykładem takich plików są same testy. Jeżeli tego nie zrobimy testy będą podświetlać się na czerwono jako linie kodu bez pokrycia testami.
Pełne zapytanie wygląda następująco.
dotnet sonarscanner begin /k:"{ProjectName}" /d:sonar.host.url=http://{IP}:9000 /d:sonar.cs.opencover.reportsPaths="./test/opencover.opencover.xml"
/d:sonar.exclusions="**\*.xml" /d:sonar.coverage.exclusions="**Specs*.cs, *.xml"
Może się zdarzyć, że otrzymacie błąd o braku ProjectGuid
w swoich projektach. Nie przejmujcie się. Wystarczy otworzyć plik solucji (*.sln) i skopiować wygenerowany, dla danego projektu, Guid do jego pliku *.csproj
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<ProjectGuid>E3845B50-7C5F-4B76-BC37-395F37FAC61A</ProjectGuid>
<OutputType>Exe</OutputType>
<TargetFramework>netcoreapp2.2</TargetFramework>
</PropertyGroup>
</Project>
Nie pozostaje nic innego jak zbudować projekt i wysłać raporty do analizy.
Na zakończenie, dla ułatwienia, pokazuje pełny skrypt:
$ dotnet test /p:CollectCoverage=true /p:CoverletOutputFormat=opencover /p:CoverletOutput=./opencover /p:Exclude="\[xunit.runner.\*\]\*"
$ dotnet sonarscanner begin /k:"Covrlet" /d:sonar.host.url=http://{IP}:9000 /d:sonar.cs.opencover.reportsPaths="./test/opencover.opencover.xml"
/d:sonar.exclusions="**\*.xml" /d:sonar.coverage.exclusions="**Specs*.cs, *.xml"
$ dotnet build
$ dotnet sonarscanner end
Czas sprawdzić SonarQube. Otrzymujemy piękny raport, zarówno dotyczący ogólnego stopnia pokrycia całego kodu,
jak i pojedynczych plików:
Podsumowanie
Dzięki za przeczytanie artykułu. Za tydzień odejdziemy trochę od tematu Coverlet i SonarQube. Szczerze powiedziawszy nie wiem co znajdzie się w następnym artykule, chciałbym jednak by było to coś specjalnego. Za tydzień będzie okrągły, 64, artykuł na moim blogu! Nawet nie zauważyłem jak to tak zleciało ;) Jeżeli macie jakieś pomysły, o czym mógłbym napisać, dajcie znać w komentarzach lub poprzez sekcję Kontakt.
Do Następnego!
Cześć