Sonarqube is a code quality inspection tool able to detect bugs, security vulnerabilities and various patterns of code smells. It is highly integrated with Maven and out of the box Java tools but if your are the DevOps guy of a team working on a python project, lost in the middle of Java projects, you might ask yourself: how can I keep my pipeline on tracks. If you are using pytest to run your tests, good news: sending coverage and reports in a Sonarqube friendly format will be fairly easy.
Project setting
I won’t go into the details on how to set things server side. Concerning your project, I’ll assume the following structure (adapt to your needs)
your_project/
some_package/
...
__main__.py
tests/
some_test.py
sonar-project.properties
You should thus add the following sonar-project.properties
file at the root of the repository.
sonar.host.url=https://sonar.somewhere.com:8200
sonar.projectKey=some_key
sonar.projectName=some_project
sonar.projectVersion=1.0.0
sonar.sources=your_project
sonar.sources=tests
sonar.language=py
sonar.sourceEncoding=UTF-8
# Test Results
sonar.python.xunit.reportPath=pytest.xml
# Coverage
sonar.python.coverage.reportPaths=coverage.xml
Edit the Run Test step of your pipeline
Sonarqube expects coverage information and unit tests reports to be send in XML. Both coverage and pytest can export their results in the adequate format using
coverage run --source='./your_project' -m pytest tests --junitxml=pytest.xml
coverage xml
This will produce a pytest.xml
and a coverage.xml
file during the pipeline execution. Add the following lines to your .gitignore
in case some messy developer runs these commands on his workstation.
#.gitignore
pytest.xml
coverage.xml
Analyse code and send metrics
If the agent running the CI jobs or the docker image you use does not have SonarScanner installed, pre-compiled binaries can be found here. To scan your project and send the coverage and UT report to the server, just add the following command to your pipeline
./path/to/sonar-scanner -Dproject.settings=./sonar-project.properties -Dsonar.password=$password -Dsonar.login=$login
That’s all folks