Skip to content

fix(ipr): replace LEDGER_REMOTE_PATTERN regex with URL parser + regression test#3642

Merged
bokelley merged 1 commit into
mainfrom
bokelley/ipr-url-parser-test
Apr 30, 2026
Merged

fix(ipr): replace LEDGER_REMOTE_PATTERN regex with URL parser + regression test#3642
bokelley merged 1 commit into
mainfrom
bokelley/ipr-url-parser-test

Conversation

@bokelley

Copy link
Copy Markdown
Contributor

Summary

Closes #3635.

#3532 fixed a one-character bug in scripts/ipr/check-and-record.mjs LEDGER_REMOTE_PATTERN that was silently rejecting bare-URL git remotes (the shape actions/checkout@v6 produces). The fix was correct, but the underlying mechanism — a regex that depends on backtracking semantics around the literal @ — is the kind of code that breaks again the next time anyone touches it. This PR replaces it with a URL parser and pins the accept/reject matrix as a unit test.

Changes

  • New module scripts/ipr/ledger-remote.mjs exporting isLedgerRemoteAllowed(url). Parses with new URL() and explicitly checks scheme, host, and normalized path. Credentials in userinfo are ignored; default-port https is accepted; SSH and other schemes are rejected at the new URL() step or at the protocol check.
  • scripts/ipr/check-and-record.mjsassertLedgerRemote() now calls the helper. Removed the regex constant.
  • New test tests/ipr-ledger-remote.test.mjs — 17 cases covering the matrix from the issue plus default-port and unparseable inputs.

Why this is the right shape

The regex tried to express a structural property ("this URL is github.com over https for adcontextprotocol/adcp, regardless of credentials") via character-class arithmetic. The URL parser checks the structural property directly. Reading the function tells you exactly which URLs pass — no need to mentally simulate backtracking. The accept/reject set is now also documented machine-checkably in the test.

Test plan

  • npx vitest run tests/ipr-ledger-remote.test.mjs — 17/17 pass
  • npm run typecheck — clean
  • Verified the new helper agrees with the post-fix(ipr): make ledger-remote credential prefix optional in URL guard #3532 regex on every URL the regex matched, plus correctly rejects two cases the regex did not (non-default port :8443, host-confusion via userinfo to a non-github host)
  • No production behavior change expected for the IPR workflow — the helper accepts every URL actions/checkout is known to emit (bare or credentialed)

🤖 Generated with Claude Code

…ssion test (closes #3635)

scripts/ipr/check-and-record.mjs previously used a regex (LEDGER_REMOTE_PATTERN) to
guard the push target of signature-ledger writes. The regex was both narrow
(rejected bare-URL origins, fixed in #3532 by making credentials optional) and
fragile (relied on backtracking semantics around the literal `@`).

Replace it with isLedgerRemoteAllowed() in scripts/ipr/ledger-remote.mjs, which
parses the remote URL via `new URL()` and explicitly checks scheme=https,
host=github.com, and pathname=/adcontextprotocol/adcp (after stripping a single
trailing `/` and `.git`). Credentials in userinfo are ignored; default-port https
is accepted; SSH and non-https URLs throw at parse time and are rejected.

tests/ipr-ledger-remote.test.mjs pins the accept/reject matrix so future
workflow tweaks (token rotation, checkout version bumps, mirror introduction)
can't silently re-narrow the guard the way the original regex did.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@bokelley bokelley merged commit 8f5ca7a into main Apr 30, 2026
13 checks passed
@bokelley bokelley deleted the bokelley/ipr-url-parser-test branch April 30, 2026 09:54
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.

fix(ipr): replace LEDGER_REMOTE_PATTERN regex with URL parser + add regression test

1 participant