Skip to content

ci: feature-debt lock — fail-closed block on features that ignore the coverage deficit (TD-023)#1406

Merged
neuron7xLab merged 4 commits into
mainfrom
feat/feature-debt-lock-gate
Jun 28, 2026
Merged

ci: feature-debt lock — fail-closed block on features that ignore the coverage deficit (TD-023)#1406
neuron7xLab merged 4 commits into
mainfrom
feat/feature-debt-lock-gate

Conversation

@neuron7xLab

Copy link
Copy Markdown
Owner

What

Process-level realisation of the system's Fail-Closed philosophy, per the TD-023 directive "no new features until the PR pays down coverage debt".

scripts/ci/check_feature_debt_lock.py BLOCKS any PR that:

  • adds > 25 net production lines to a tracked surface (core/backtest/execution/analytics/risk/ingestion), AND
  • pays down 0 test lines for a deficit surface (backtest/, analytics/), AND
  • declares no audited Debt-Exempt: <reason> trailer.

Pure function of the git diff — no coverage run, deterministic, fast.

Why this and not more coverage tests

Coverage paydown is already in flight (#1403/#1404/#1405). The non-duplicative, higher-leverage move is the enforcement mechanism: wire the discipline into CI so the deficit cannot grow.

Verification

  • 6 falsifiable tests: block / paydown / exemption / sub-threshold / tests-only / wrong-surface.
  • Gate self-run on this PR → PASS (CI/tests only). ruff + mypy --strict + black clean; INVENTORY + commit-acceptor bound; debt at baselines.

Rollout (safety)

Ships advisory (runs on every PR, fails closed on violations) so it does not flag-day-break the ~30 in-flight PRs. Promote to an absolute block by adding feature-debt-lock to branch-protection required-checks — a one-line admin change documented in reports/TECH_DEBT_REGISTRY.md (TD-023-LOCK).

🤖 Generated with Claude Code

neuron7xLab and others added 2 commits June 27, 2026 23:23
…overage deficit (TD-023)

Applies the system's Fail-Closed philosophy to the GENERATION PROCESS itself.
scripts/ci/check_feature_debt_lock.py blocks any PR that adds > 25 net production
lines to a tracked surface while paying down ZERO test lines for the deficit
surfaces (backtest/, analytics/) and declaring no audited 'Debt-Exempt: <reason>'
trailer. The decision is a pure function of the git diff (no coverage run) — fast
and deterministic. 6 falsifiable tests cover block / paydown / exemption /
sub-threshold / tests-only / wrong-surface. Wired as an advisory pull_request
workflow (feature-debt-lock.yml), promotable to an ABSOLUTE block by adding it to
branch-protection required-checks once the in-flight backlog clears. Realises the
directive: no new features until the PR pays down coverage debt.

Inventory + acceptor bound; debt at baselines.

Debt-Exempt: this PR is the debt-lock mechanism itself (CI/tests only, no product surface)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…rkflow

repo-policy pin-guard requires actions pinned to a commit SHA; actions/upload-artifact@v4
is a tag. The artifact upload was non-essential (the verdict is the exit code +
stdout), so remove the step. The workflow now uses only the SHA-pinned checkout
and setup-python actions.

Debt-Exempt: CI workflow pin fix, no product surface

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 3f76809de5

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread .github/workflows/feature-debt-lock.yml Outdated
--json reports/feature_debt_lock.json
- name: Upload verdict
if: always()
uses: actions/upload-artifact@v4

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Pin the artifact upload action to a SHA

I checked the required repo-policy job in .github/workflows/pr-gate.yml, which scans every .github/workflows/*.yml uses: reference and rejects anything not ending in a 40-character SHA, and .github/workflows/README.md documents the same policy. This new actions/upload-artifact@v4 reference is therefore a newly introduced policy violation that makes the PR Gate fail before this workflow can be merged; pin it to an audited commit SHA like the other actions in this file.

Useful? React with 👍 / 👎.

Comment thread scripts/ci/check_feature_debt_lock.py Outdated
paydown_files.append(path)

exempt_reasons = [
ln.split(EXEMPT_TRAILER, 1)[1].strip() for ln in log.splitlines() if EXEMPT_TRAILER in ln

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Require an actual Debt-Exempt trailer

Because this accepts any commit-log line containing the substring, a feature PR with no paydown can bypass the block by merely mentioning the token, e.g. This PR does not use Debt-Exempt: <reason>, which sets exempt=True despite there being no audited trailer or reason. Restrict this to a real non-empty trailer line so the fail-closed override cannot be triggered by incidental prose.

Useful? React with 👍 / 👎.

@neuron7xLab neuron7xLab enabled auto-merge (squash) June 28, 2026 04:01
@neuron7xLab neuron7xLab merged commit 69acdeb into main Jun 28, 2026
35 checks passed
@neuron7xLab neuron7xLab deleted the feat/feature-debt-lock-gate branch June 28, 2026 04:04
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant