jacoco-coverage-policy
JaCoCo configuration and policy enforcement — 90% line+branch floor, 95% target, 95% on new code. Use when wiring JaCoCo into the Maven build or interpreting `jacoco.xml`.
SKILL.md.claude/skills/jacoco-coverage-policy/SKILL.md
GitHubJaCoCo coverage policy
Numbers (this toolkit's defaults)
| Metric | Hard floor | Target | New-code rule |
|---|---|---|---|
| Line coverage | 90% | 95–100% | 95% (new + changed lines only) |
| Branch coverage | 90% | 95–100% | 95% |
"Hard floor" = build fails. "Target" = aspirational; not enforced but tracked.
"New code" = lines added or modified vs origin/main (PR base).
Maven config
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.8.12</version>
<executions>
<execution>
<id>prepare</id>
<goals><goal>prepare-agent</goal></goals>
</execution>
<execution>
<id>report</id>
<phase>verify</phase>
<goals><goal>report</goal></goals>
</execution>
<execution>
<id>check</id>
<phase>verify</phase>
<goals><goal>check</goal></goals>
<configuration>
<rules>
<rule>
<element>BUNDLE</element>
<limits>
<limit><counter>LINE</counter><value>COVEREDRATIO</value><minimum>0.90</minimum></limit>
<limit><counter>BRANCH</counter><value>COVEREDRATIO</value><minimum>0.90</minimum></limit>
</limits>
</rule>
<rule>
<element>PACKAGE</element>
<limits>
<limit><counter>LINE</counter><value>COVEREDRATIO</value><minimum>0.85</minimum></limit>
</limits>
</rule>
</rules>
</configuration>
</execution>
</executions>
</plugin>
Excludes (the only allowed)
**/*Application.class(themainclass)- Generated code:
**/generated/**,**/openapi/** - DTOs that are pure records with no logic (when measuring branch coverage; line coverage stays)
**/config/**is not excluded. Configuration is real code.
Brownfield onboarding
If current coverage is below 90%:
Measure current values per package.
Write them into
.specs/_baseline.json:{ "jacoco": { "overall_line": 0.74, "overall_branch": 0.62, "per_package": { "com.example.shop.checkout": { "line": 0.81, "branch": 0.70 } } } }Set Maven thresholds to current values minus 1% (ratchet).
Each feature must improve the metric (or hold) for touched packages.
New code is held to 95% regardless of baseline.
"New code at 95%"
The harness computes new-code coverage by intersecting the lines added or changed since git merge-base origin/main HEAD (including uncommitted and untracked files) with JaCoCo's <line nr="N" mi="0" ci="3" mb="0" cb="2"/> entries. A diff line with ci > 0 is covered; one with ci == 0 is uncovered; a diff line with no <line> entry is not executable and is ignored. Threshold: 95% (NEW_CODE_THRESHOLD).
This is implemented in .github/scripts/check-new-code-coverage.sh.
Anti-patterns
- Excluding a class because it's "hard to test".
<excludes>**/*Service*</excludes>— services are exactly what you must test.- Treating coverage as the goal. It's a floor, not a target. Mutation testing is the real signal.