Test coverage — unit gates and capability coverage
AI-generated content
This document was generated by an AI assistant. Verify accuracy before relying on the details.
Two different things are called "coverage" here and they answer different questions. The unit gate is a percentage of executed lines, enforced per workspace member by vitest. The capability coverage is a count of the application's 248 user-facing capabilities that a test has actually driven against the live staging deployment — it says what the software is known to do, not how much of the code ran. The second is the one that found 21 confirmed defects; the first is the one that blocks a merge.
At a glance
| unit gate | capability coverage | |
|---|---|---|
| Question | how much code did the tests execute? | which capabilities are proven to work? |
| Unit | % of lines/statements/functions/branches | one row per capability |
| Threshold | 85%, global and uniform | no threshold — a verdict per row |
| Enforced by | vitest, per member (vitest.shared.mjs:20) | apps/ui/test/e2e-feature-index.test.mjs |
| Status | expected RED until the test fan-out lands | 63% covered, measured 16/09/2026 |
Details
The unit gate
vitest.shared.mjs sets COVERAGE_THRESHOLD = 85 and applies it to lines, statements, functions and branches alike. Each member scopes coverage.include to its own sources and vitest exits non-zero below the threshold, which fails the Coverage workflow.
Measured 16/09/2026 across apps/*, packages/* and services/*: 99.18 % of lines, and no member below the gate. The numbers and the per-member table are in the coverage report, regenerated by pnpm report:coverage.
That contradicts the workflow's own header, which still describes the gate as "expected RED until the test fan-out lands" with a baseline of "~65% global lines" and names @adb/data, @adb/mongo-broker, @adb/doc-renderer-service and @adb/shared-types as "well below 85%". Re-measured today, those four are at 98.77 %, 100 %, 98.87 % and 98.63 %. The comment is stale — the fan-out landed. .github/workflows/coverage.yml should be updated; this page records the measurement rather than the comment.
Two things the headline figure does not say, and both matter:
- it is not "99 % of the codebase". Each member measures only what its own
coverage.includedeclares.apps/uiscopes its gate to logic (app/{server,api,lib,hooks,auth,i18n},workers/**), holdsapp/lib/rights/**at 100 %, and deliberately excludes its components and route modules. The figure compares each member against its own declaration; - it says nothing about whether the tests passed. Two members —
@adb/action-logsand@adb/aggregates— reported coverage above the gate and still failed their run, on a failing test rather than on the threshold. The report names them for that reason. Two others (@adb/ui-storybook,@adb/reports-service) produced no figure at all, which is an unknown and not a zero.
Capability coverage
Every capability the Angular application exposes is one row in apps/ui/e2e/feature-index.md, with the route, the Angular source, the upstream call, and a verdict naming the spec that proves it. The verdict vocabulary is closed to five values and a test rejects a sixth invented in passing.
| verdict | meaning | count | share |
|---|---|---|---|
staging: yes | driven end to end against the live app | 156 | 63% |
staging: partial | partly driven, and the row says which part | 36 | 15% |
characterised as unreachable | no user path reaches it | 23 | 9% |
characterised as broken | reached, and the application failed | 19 | 8% |
staging: none | not covered, and the row says why | 14 | 6% |
| total | 248 |
The 42 rows marked unreachable or broken are a result, not a backlog: they are what the exercise was for.
Trajectory. The column did not exist before this programme; the first pass verified 84 of 255 rows (33%) on 13/09/2026, and the count reached 156 of 248 (63%) on 16/09.
What it found
apps/ui/e2e/staging/TO-FIX.md carries 21 confirmed defects, ordered by what the user loses:
| severity | meaning | n |
|---|---|---|
| data loss | an action destroys or overwrites what the user is not looking at | 3 |
| silent wrong write | the save is acknowledged and something else is stored | 3 |
| blocked capability | the function exists and cannot complete | 6 |
| wrong figure displayed | a money total on screen that does not match its lines | 1 |
| server configuration | a route denied to everyone, administrators included | 1 |
| misleading message | the screen asserts the opposite of the data | 1 |
| mock screen | a static mock served as a real screen | 1 |
| to qualify | established, severity not yet decided | 5 |
Each defect has two specs — see the staging suite.
Five findings were withdrawn
Writing the spec that specifies a fix forces a re-measurement, and five findings did not survive it. They are listed with their real cause in TO-FIX.md. This matters as much as the 21 that stood: a false finding is paid for by whoever is sent to fix working code. The most instructive was a row locator that matched the table's header — a collapsed column filter puts every one of its options in the header's text content, so hasText matched it for any value.
Open questions
- The unit gate's path to green is the test fan-out, which is its own programme; no date.
- Capability coverage is measured on account 1's organisation. A second organisation exercises a different data shape, and a handful of rows are known to differ between them.
- The 5 defects marked "to qualify" need a product decision before they can be estimated.