From 42235dcb6a227efa44453903db01ff0dab969d0c Mon Sep 17 00:00:00 2001 From: Mathias Date: Mon, 31 Aug 2026 07:24:07 +0200 Subject: [PATCH] fix(scan): an allowlist was hiding a real Gitea PAT on a false justification MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit infra#344. The removed block suppressed docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md, and its description stated why: "Literal placeholder word REDACTED matched as if it were a token (verified 2026-08-04: extracted Secret == 'REDACTED' exactly, gitleaks' curl-auth-header rule matched the placeholder text itself, not a real credential)" That is not what the file contained. Line 1054 carried a real 40-character hex Gitea PAT in an `Authorization: token ...` header — not the eight-character word REDACTED. Whether the file changed after the check or the check was wrong, the justification has been guarding the wrong thing since. Confirmed dead by side-effect before touching it, never by printing it: `GET /api/v1/user` with that token returns 401. So there is nothing to rotate. It is redacted here anyway, because a dead credential in a doc is still a working example of how to write a live one, and git history keeps the original either way. Two independent failures had to line up, which is the same pair as infra#256: 1. The `paths` clause made the block far broader than its description. gitleaks ORs global allowlist clauses and ignores `condition = "AND"`, so the ENTIRE file was immune — a live token pasted into that doc tomorrow would have been suppressed on the strength of a note about a different value. 2. The justification was never re-checked against the file it justifies. With the token redacted the allowlist has nothing left to do, so it is deleted rather than narrowed. Repo scans clean, and a planted live-shaped credential in that same file is now caught. Refs: mathias/infra#344, mathias/infra#256, mathias/infra#317 --- .gitleaks.toml | 18 +++++++++++++----- .../plans/2026-04-22-phase4-attempt-wiring.md | 2 +- 2 files changed, 14 insertions(+), 6 deletions(-) diff --git a/.gitleaks.toml b/.gitleaks.toml index dd9196e..7e82577 100644 --- a/.gitleaks.toml +++ b/.gitleaks.toml @@ -56,8 +56,16 @@ paths = [ '''ingestion/internal/claudewatcher/watcher_test\.go$''', ] -[[allowlists]] -description = "Literal placeholder word REDACTED matched as if it were a token (verified 2026-08-04: extracted Secret == 'REDACTED' exactly, gitleaks' curl-auth-header rule matched the placeholder text itself, not a real credential)" -condition = "AND" -paths = ['''docs/superpowers/plans/2026-04-22-phase4-attempt-wiring\.md$'''] -regexes = ['''REDACTED'''] +# infra#344: the allowlist that used to sit here is gone, and so is the reason +# for it. It suppressed docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md +# on the stated grounds that "extracted Secret == 'REDACTED' exactly ... the +# placeholder text itself, not a real credential" (verified 2026-08-04). That was +# not what the file contained: line 1054 carried a real 40-char hex Gitea PAT in +# an `Authorization: token ...` header. Confirmed dead by side-effect — GET +# /api/v1/user with it returns 401 — and redacted in that file, so there is now +# nothing to allowlist. +# +# The `paths` entry also made the block far broader than its description: gitleaks +# ORs global allowlist clauses and ignores `condition = "AND"`, so the whole file +# was immune, not just lines matching /REDACTED/. A live token added to that doc +# would have been suppressed on the strength of a note about a different value. diff --git a/docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md b/docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md index 898fc84..cfb7a8a 100644 --- a/docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md +++ b/docs/superpowers/plans/2026-04-22-phase4-attempt-wiring.md @@ -1051,7 +1051,7 @@ git push ```bash # Poll until complete (replace RUN_ID with the new run): curl -s "https://gitea.d-ma.be/api/v1/repos/mathias/hyperguild/actions/runs?limit=2" \ - -H "Authorization: token 736a8c36adcc6ecb41fff56e5ae4d0eb3105a670" \ + -H "Authorization: token " \ | python3 -c "import sys,json; [print(r['id'],r['status'],r.get('conclusion','—')) for r in json.load(sys.stdin)['workflow_runs']]" ```