jacocoTestReport任务仅生成报告,不校验阈值;真正执行阈值检查的是独立任务jacocoTestCoverageVerification(Gradle 7.4+)或旧版jacocoTestCoverageCheck。

jacocoTestReport 任务里不能设阈值,得用 jacocoTestCoverageVerification
很多人在 jacocoTestReport 块里硬塞 check 或 minimum 配置,结果构建不报错、阈值形同虚设。这是因为 jacocoTestReport 只负责生成报告,不参与校验逻辑。真正做阈值检查的是独立任务 jacocoTestCoverageVerification(Gradle 7.4+)或旧版的 jacocoTestCoverageCheck(Gradle
实操建议:
- Gradle 7.4 及以上:直接添加
jacocoTestCoverageVerification任务,并在其中配置violationRules - Gradle 6.x / 7.0–7.3:用
jacocoTestCoverageCheck,注意它默认不自动绑定到test或check生命周期,需手动dependsOn - 别把
executionData写错路径——默认是$buildDir/jacoco/test.exec,但多模块下容易变成$buildDir/jacoco/test-,得统一指定.exec
LINE COVEREDRATIO 最小值设 0.8 还是 80?看版本
JaCoCo 的 minimum 参数接受浮点数(如 0.8)或百分比整数(如 80),但行为取决于 Gradle 插件版本和 JaCoCo 版本组合。Gradle 7.6+ + JaCoCo 0.8.11+ 接受 0.8;而早期组合(如 Gradle 6.9 + JaCoCo 0.8.7)只认 80,填 0.8 会静默忽略阈值。
常见错误现象:
- 配置了
minimum = 0.8,但覆盖率 50% 时构建仍成功 - 控制台没报任何 Jacoco check 相关日志,说明规则根本没加载
稳妥做法:统一用整数百分比写法,比如 minimum = 80,兼容性最强。
多模块项目里,聚合报告和门禁必须分开配置
单模块项目直接在根 build.gradle 加插件和 check 任务就行;但多模块下,如果只在根项目 apply jacoco 插件,子模块的 test.exec 文件不会被自动收集,jacocoTestCoverageVerification 会找不到数据,报 No execution data files found。
正确路径:
- 每个子模块都 apply
jacoco插件(否则其测试不插桩) - 根项目额外 apply
jacoco-aggregation插件(Gradle 7.4+ 自带),并定义聚合任务 - 门禁检查必须基于聚合后的
executionData,而不是任一子模块的单独文件 - 示例关键片段:
jacocoAggregation { dependsOn subprojects.test executionData.from subprojects.map { it.layout.buildDirectory.dir('jacoco').file('test.exec') } }
exclude 模式写错会导致门禁误判,尤其 Kotlin 和 Lombok
exclude 不是正则,是 Ant-style 路径模式。写成 exclude 'com.example.*' 是错的——* 只能匹配单层目录,跨包得用 **。更麻烦的是,Kotlin 编译后类名带 $(如 ServiceKt$doWork$1.class),Lombok 生成的 $accessor 类也常被误计入。这些类若未排除,可能拉低整体覆盖率,导致门禁失败。
推荐排除项(加在 jacoco 块内):
-
exclude '**/*Mapper*'(MyBatis Mapper 接口无实现) -
exclude '**/dto/**'(纯数据类,通常不测) -
exclude '**/*Kt*'和exclude '**/*$*(覆盖 Kotlin 合成类和 Lombok 辅助类) - Android 项目还要加
exclude '**/R.class'、exclude '**/BuildConfig.class'
排除不是为了凑数字,而是让阈值反映真实业务逻辑的覆盖质量。一个没 exclude 的 Lombok $accessor 类,哪怕只有两行字节码,也可能卡住 80% 的门禁线。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











