- you can use the plain 'jacoco' plugin for this to work
- move the sonarqube plugin and its properties to your build.gradle in a module (e.g. app/build.gradle)
- add a jacocoTestReport task that depends on testDebugUnitTest (you can see the template below)
- add testOptions to the android configuration in the build.gradle and finalize the jacocoTestReport task (see template below)
- make sure that the xml.destination from the reports attribute of the jacocoTestReport task is the same as the sonar.coverage.jacoco.xmlReportPaths property of the sonaqube task
- with that configuration, it is sufficient to run the following command as the last part in your CI pipeline file: run: ./gradlew build sonarqube --info
plugins {
id 'com.android.application'
////////// 1. simple jacoco plugin //////////
id 'jacoco'
////////// 2. move sonarqube plugin into app/build.gradle //////////
id 'org.sonarqube' version '3.3'
}
android {
compileSdk 32
defaultConfig {
applicationId "com.example.demo_repo"
minSdk 30
targetSdk 32
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
////////// 4. add testOptions //////////
testOptions {
unitTests.all {
useJUnitPlatform()
finalizedBy jacocoTestReport
}
}
}
////////// 3. add jacocoTestReport task like so //////////
task jacocoTestReport(type: JacocoReport, dependsOn: 'testDebugUnitTest') {
reports {
xml.enabled true
////////// 5. xml.destination must be same as sonaqube property //////////
xml.destination file("${project.projectDir}/build/reports/jacoco/jacocoTestReport/jacocoTestReport.xml")
}
def fileFilter = ['**/R.class', '**/R$*.class', '**/BuildConfig.*', '**/Manifest*.*', '**/*Test*.*', 'android/**/*.*']
def debugTree = fileTree(dir: "${buildDir}/intermediates/javac/debug", excludes: fileFilter)
def mainSrc = "${project.projectDir}/src/main/java"
sourceDirectories.from = files([mainSrc])
classDirectories.from = files([debugTree])
executionData.from = files("${buildDir}/jacoco/testDebugUnitTest.exec")
}
////////// 2. move also sonarqube properties //////////
sonarqube {
properties {
property "sonar.projectKey", "SE2-sample-tut-project_demo-repo"
property "sonar.organization", "se2-sample-tut-project"
property "sonar.host.url", "https://sonarcloud.io"
property "sonar.java.coveragePlugin", "jacoco"
////////// 5. property same as xml.destination of jacocoTestReport //////////
property "sonar.coverage.jacoco.xmlReportPaths", "${project.projectDir}/build/reports/jacoco/jacocoTestReport/jacocoTestReport.xml"
}
}
dependencies {
implementation 'androidx.appcompat:appcompat:1.3.0'
implementation 'com.google.android.material:material:1.4.0'
implementation 'androidx.constraintlayout:constraintlayout:2.0.4'
testImplementation 'org.junit.jupiter:junit-jupiter-api:5.7.0'
testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine:5.7.0'
androidTestImplementation 'androidx.test.ext:junit:1.1.3'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0'
}