Skip to content

Stop the fork API addressing a repo name that doesn't exist - #9

Merged
ederign merged 2 commits into
mainfrom
fix/slug-extractor-truncated-repo-names
Aug 28, 2026
Merged

Stop the fork API addressing a repo name that doesn't exist#9
ederign merged 2 commits into
mainfrom
fix/slug-extractor-truncated-repo-names

Conversation

@ederign

@ederign ederign commented Aug 28, 2026

Copy link
Copy Markdown
Owner

What

clone_target.py carried its own copy of extract_slug that stripped .git with url.rstrip(".git"). rstrip takes a character set, not a suffix, so it kept eating trailing characters from {'.','g','i','t'} once .git was gone:

rh-forge-ui.git → rh-forge-ui → rh-forge-u

Every fork API call then addressed a repository that isn't there:

404 GET  /repos/ederign/rh-forge-u        (get-a-repository)
404 POST /repos/rh-forge/rh-forge-u/forks (create-a-fork)

GitHub answers 404 rather than 403 for a repo a token cannot see, so this was indistinguishable from a credentials fault — the PAT was audited first (classic vs fine-grained, SSO, org opt-in) and was fine all along.

Latent since the copy was made. It only bites repo names ending in a character from that set; odh-dashboard, kale, mlflow and codeflare-sdk all end outside it. rh-forge-ui is the first target that doesn't.

How

Deleted clone_target._extract_slug and pointed both call sites (_url_matches, _setup_fork_remote) at github_utils.extract_slug, which already used .removesuffix(".git"). Deleting rather than patching is the point — two copies of one function are what let the correct version sit next to the broken one without either fixing the other.

Verification

Reproduction now passes end to end against the live private repo:

$ python3 scripts/clone_target.py rh-forge/rh-forge-ui RHAI-760 --clean \
    --dest /tmp/tr --fork-owner ederign --gh-token-var RH_FORGE_GITHUB_TOKEN
Cloned to: /tmp/tr
Branch: epic/RHAI-760
Fork remote: https://github.com/ederign/rh-forge-ui.git
  • TestExtractSlug::test_repo_name_ending_in_git_suffix_chars — the character-set case
  • TestSetupForkRemote::test_repo_name_ending_in_i_is_not_truncated — asserts the exact args reaching ensure_fork, pinning the call site that broke
  • make test-unit: 762 passed
  • check_ledger.py --all: 157 files consistent

Ledger companion

  • docs/bugs/fixed/bug-slug-extractor-truncated-repo-names.md
  • docs/bugs/open/bug-clone-fault-marks-epic-failed.md — the follow-on: a clone fault marks the epic terminally Failed, so this 404 needed a hand-edit of the data repo to retry, where ADR-0025 would have left it Ready. Filed, not fixed here.

🤖 Generated with Claude Code

ederign and others added 2 commits August 28, 2026 10:47
clone_target.py carried its own copy of extract_slug that stripped the
.git suffix with url.rstrip(".git"). rstrip takes a character set, not a
suffix, so it kept eating trailing characters from {'.','g','i','t'} once
.git was gone: rh-forge-ui became rh-forge-u.

Every fork API call then addressed a repository that isn't there. GitHub
answers 404 rather than 403 for a repo a token cannot see, so the symptom
was indistinguishable from a credentials problem and RHAI-760 was
diagnosed as a bad PAT for some time before the name was suspected.

Latent since the copy was made. It only bites names ending in a character
from that set, and no previous target had one -- odh-dashboard, kale,
mlflow and codeflare-sdk all end outside it.

Delete the copy rather than patch it, and point both call sites at
github_utils.extract_slug, which already used .removesuffix(".git"). Two
copies of one function are precisely what let the correct version sit
next to the broken one without either fixing the other.

Also file the follow-on: a clone fault marks the epic terminally Failed,
so this 404 needed a hand-edit of the data repo to retry, where ADR-0025
would have left it Ready.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
@ederign
ederign merged commit 0d77bb4 into main Aug 28, 2026
2 checks passed
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