Skip to content

Commit 8c9017e

Browse files
authored
Merge pull request #533 from bsv-blockchain/codex/backlog-ci-scope-20260915
fix(ci): keep elapsed review deadlines out of ordinary merge gates
2 parents a386bc2 + 562a86c commit 8c9017e

14 files changed

Lines changed: 182 additions & 44 deletions

‎.github/SECURITY.md‎

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -107,8 +107,9 @@ last-pusher-independent approval is not an unconditional requirement.
107107
Do not dismiss a finding or add an override merely to make CI green. A genuine
108108
false positive or unavoidable temporary compatibility substitution must be
109109
registered in `governance/repository-health/exceptions.json` with an owner,
110-
rationale, evidence, review deadline, and objective removal condition. Expired
111-
exceptions fail CI.
110+
rationale, evidence, review deadline, and objective removal condition. Elapsed review deadlines are maintenance reminders in ordinary source CI.
111+
The separate weekly Maintenance review deadlines workflow enforces them;
112+
malformed, unowned, or unregistered exceptions still fail ordinary CI.
112113

113114
Public services such as Overlay, Wallet Storage, WAB, Message Box, and Wallet
114115
Relay may need to accept clients from previously unknown domains. Their public
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
name: Maintenance review deadlines
2+
3+
on:
4+
schedule:
5+
- cron: '23 15 * * 1'
6+
workflow_dispatch:
7+
8+
permissions: {}
9+
10+
concurrency:
11+
group: maintenance-review
12+
cancel-in-progress: false
13+
14+
jobs:
15+
review:
16+
runs-on: ubuntu-latest
17+
timeout-minutes: 10
18+
permissions:
19+
contents: read
20+
steps:
21+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
22+
with:
23+
persist-credentials: false
24+
- uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7.0.0
25+
with:
26+
node-version: 24.x
27+
- name: Review exception deadlines
28+
run: node scripts/repository-health.mjs --maintenance --summary-file "$GITHUB_STEP_SUMMARY"
29+
- name: Review documentation deadlines
30+
if: ${{ !cancelled() }}
31+
run: node scripts/documentation-policy.mjs --all

‎CONTRIBUTING.md‎

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -181,7 +181,10 @@ container migrations are coordinated programs, not routine bumps.
181181
Do not introduce a broad override or suppression. If no compatible upstream
182182
fix exists, register the narrowest temporary exception with an owner, evidence,
183183
review date, objective removal condition, and tests. Rehearse removal after
184-
relevant upstream releases.
184+
relevant upstream releases. Elapsed documentation and exception review dates
185+
are maintenance warnings in source CI, enforced by the separate weekly
186+
Maintenance review deadlines workflow. Passing time alone must not block a PR;
187+
structural errors, generated drift, security audits, and code checks still do.
185188

186189
## Versions, changelogs, and migrations
187190

‎docs/about/doc-agent.md‎

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ id: about-doc-agent
33
title: 'Documentation Maintenance'
44
kind: meta
55
version: '2.1.0'
6-
last_updated: '2026-09-14'
7-
last_verified: '2026-09-14'
6+
last_updated: '2026-09-15'
7+
last_verified: '2026-09-15'
88
review_cadence_days: 30
99
status: stable
1010
tags: [about, documentation, maintenance, automation]
@@ -51,8 +51,8 @@ id: unique-slug
5151
title: 'Page title'
5252
kind: spec
5353
version: '1.0.0'
54-
last_updated: '2026-07-27'
55-
last_verified: '2026-07-27'
54+
last_updated: '2026-09-15'
55+
last_verified: '2026-09-15'
5656
review_cadence_days: 30
5757
status: stable
5858
tags: [protocol, reference]
@@ -78,7 +78,7 @@ tags: [protocol, reference]
7878
pnpm docs:facts
7979

8080
# Verify generated facts, parity metadata, package README contracts,
81-
# package-doc versions, and review cadence for affected pages
81+
# package-doc versions, and advisory review reminders for affected pages
8282
pnpm docs:facts:check
8383

8484
# Validate frontmatter and source links
@@ -119,9 +119,10 @@ revision expressions outside that syntax.
119119
Release, scheduled, and manual GitHub runs have no change scope unless one is
120120
provided explicitly. All invocations still enforce package documentation,
121121
generated-content consistency through `docs:facts:check`, and date consistency
122-
(verification cannot predate an update or be in the future). Only review expiry
123-
is scoped. The full audit is an opt-in maintenance command, not an unrelated
124-
PR's merge requirement. Re-verify an affected expired page against its source
122+
(verification cannot predate an update or be in the future). Only review-expiry reminders
123+
are scoped; they are warnings in ordinary source checks. The full audit is an opt-in maintenance command, not an unrelated
124+
PR's merge requirement. The weekly Maintenance review deadlines workflow
125+
runs this audit independently and fails on overdue reviews. Re-verify an affected expired page against its source
125126
before updating its date; do not bulk-advance unrelated verification dates.
126127

127128
The package README contract covers every public package and requires registry

‎docs/reference/dependency-policy.md‎

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ id: dependency-release-policy
33
title: 'Dependency and Release Policy'
44
kind: reference
55
version: '1.3.1'
6-
last_updated: '2026-08-30'
7-
last_verified: '2026-08-30'
6+
last_updated: '2026-09-15'
7+
last_verified: '2026-09-15'
88
review_cadence_days: 30
99
status: stable
1010
tags: [reference, dependencies, security, releases]
@@ -145,7 +145,9 @@ temporary `gaxios` substitutions, and Message Box plus UHRP cloud storage need
145145
`uuid`; the Wave 37 review removed every substitution from a service where the
146146
frozen graph stayed clean without it. The machine-readable registry now maps
147147
every remaining selector and exact value to its exception. CI rejects a new,
148-
changed, stale, expired, unowned, or upstream-unlinked override.
148+
changed, stale, unowned, or upstream-unlinked override. Elapsed review dates
149+
produce maintenance reminders in source CI and fail the separate weekly
150+
maintenance audit (`node scripts/repository-health.mjs --maintenance`).
149151

150152
Wave 40 rechecked the prior 20 selectors against the frozen graphs, current
151153
upstream manifests, and the advisory audit. The 2026-09-04 security review

‎docs/reference/repository-health.md‎

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@ id: repository-health
33
title: 'Repository Health Controls'
44
kind: reference
55
version: '1.4.1'
6-
last_updated: '2026-09-14'
7-
last_verified: '2026-09-14'
6+
last_updated: '2026-09-15'
7+
last_verified: '2026-09-15'
88
review_cadence_days: 30
99
status: stable
1010
tags: [reference, governance, quality, security, releases]
@@ -56,8 +56,10 @@ package READMEs that do not identify, install, demonstrate, and license the
5656
registry artifact, and missing, duplicated, version-drifted, or
5757
pre-consolidation public package pages.
5858

59-
Documentation review expiry applies only to edited pages and pages associated
60-
with directly changed sources. Package and service inventories supply their
59+
Documentation review reminders apply only to edited pages and pages associated
60+
with directly changed sources. Elapsed dates are warnings, including on affected
61+
pages, so an ordinary code change is never blocked just because time passed.
62+
The separate weekly Maintenance review deadlines workflow enforces all dates. Package and service inventories supply their
6163
page relationships; `freshness.sourcePaths` in the documentation policy maps
6264
other pages to source files or directories. The check uses the PR merge-base
6365
diff, the push before/after diff, or local changes against `origin/main`.
@@ -224,7 +226,8 @@ checks:
224226
3. generated artifact boundaries have valid owners, sources, generators, narrow
225227
review/analysis policies, and exact CodeQL exclusion coverage;
226228
4. published package versions match the recorded baseline;
227-
5. exception records are owned, structurally valid, and unexpired;
229+
5. exception records are owned and structurally valid; elapsed review dates
230+
are maintenance warnings in source CI and errors with `--maintenance`;
228231
6. current package-contract findings exactly match the ratcheted snapshot; and
229232
7. generated stack/conformance facts, all 33 public package README contracts,
230233
and one current consolidated package page per public package are current;

‎governance/documentation-policy.json‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@
2828
},
2929
"freshness": {
3030
"scope": "changed-pages-and-direct-sources",
31-
"rationale": "Review expiry blocks only pages edited in the change or documenting its directly changed sources. Package pages use the project inventory (including shared sourceRoots), service pages use the service inventory, and other source relationships are declared below. Unrelated review deadlines never block a PR. Structural and generated-content checks remain repository-wide.",
31+
"rationale": "Ordinary source checks report elapsed review deadlines as maintenance warnings for changed pages and directly changed sources. The separate maintenance workflow enforces every review deadline. Structural, date-consistency, and generated-content checks remain blocking; passing time alone never blocks an ordinary PR.",
3232
"sourcePaths": {
3333
"docs/about/contributing.md": ["CONTRIBUTING.md"],
3434
"docs/about/doc-agent.md": [

‎governance/repository-health/exceptions.json‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -163,13 +163,13 @@
163163
"category": "override",
164164
"target": "pnpm-workspace.yaml override nanoid releases below 3.3.18",
165165
"owner": "ts-stack-maintainers",
166-
"reason": "Vite's current PostCSS dependency range can select nanoid releases affected by GHSA-2v37-7h3g-55p8, whose patched 3.x boundary was raised to 3.3.18 on 2026-08-13. Selecting 3.3.18 is the narrowest compatible remediation and leaves runtime application packages unchanged.",
166+
"reason": "Vite's current PostCSS dependency range can select nanoid releases affected by GHSA-2v37-7h3g-55p8, whose patched 3.x boundary was raised to 3.3.18 on 2026-08-13. Selecting 3.3.18 is the narrowest compatible remediation and leaves runtime application packages unchanged. Reviewed 2026-09-15: installed PostCSS 8.5.23 still declares nanoid ^3.3.16, which permits versions below the fixed 3.3.18 boundary; retain the narrow constraint. Calendar renewal is now maintenance-owned and cannot block unrelated source CI.",
167167
"evidence": [
168168
"pnpm-workspace.yaml#overrides",
169169
"https://github.com/advisories/GHSA-2v37-7h3g-55p8"
170170
],
171171
"created": "2026-08-09",
172-
"reviewBy": "2026-09-13",
172+
"reviewBy": "2026-10-15",
173173
"removeWhen": "Remove when the supported Vite and PostCSS dependency graph naturally resolves nanoid 3.3.18 or newer and the frozen audit remains green."
174174
},
175175
{

‎scripts/dependency-release-governance.mjs‎

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -194,9 +194,8 @@ function validateOverrideRegistry(policy, exceptions, errors) {
194194
}
195195

196196
const byId = new Map(exceptions.exceptions.map(exception => [exception.id, exception]))
197-
const today = new Date().toISOString().slice(0, 10)
198197
for (const registration of policy.overrideRegistry) {
199-
validateOverrideException(registration, byId, policy.owner, today, errors)
198+
validateOverrideException(registration, byId, policy.owner, errors)
200199
}
201200
const review = policy.overrideRemovalReview
202201
if (
@@ -255,7 +254,7 @@ function validateDirectInventoryPolicy(policy, errors) {
255254
}
256255
}
257256

258-
function validateOverrideException(registration, exceptionsById, owner, today, errors) {
257+
function validateOverrideException(registration, exceptionsById, owner, errors) {
259258
const exception = exceptionsById.get(registration.exceptionId)
260259
if (exception?.category !== 'override') {
261260
errors.push(
@@ -264,7 +263,6 @@ function validateOverrideException(registration, exceptionsById, owner, today, e
264263
return
265264
}
266265
if (exception.owner !== owner) errors.push(`${exception.id} must be owned by ${owner}`)
267-
if (exception.reviewBy < today) errors.push(`${exception.id} expired on ${exception.reviewBy}`)
268266
const hasExternalEvidence = (exception.evidence ?? []).some(
269267
item =>
270268
item.startsWith('https://github.com/') &&

‎scripts/documentation-freshness.mjs‎

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,3 +110,13 @@ export function documentationDateFindings(updated, verified, cadence, today, aff
110110
if (verifiedDate > today) findings.push('last_verified cannot be in the future')
111111
return findings
112112
}
113+
114+
// Calendar reminders do not determine whether a source change is correct.
115+
// The full maintenance audit enforces deadlines independently of merge CI.
116+
export function documentationDateReport(updated, verified, cadence, today, affected, fullAudit) {
117+
const findings = documentationDateFindings(updated, verified, cadence, today, affected)
118+
const warnings = fullAudit
119+
? []
120+
: findings.filter(item => item.startsWith('verification expired '))
121+
return { errors: findings.filter(item => !warnings.includes(item)), warnings }
122+
}

0 commit comments

Comments
 (0)