[BUG] Routine push to main returns HTTP 403 from git proxy despite "Allow unrestricted branch pushes" being enabled
Preflight Checklist
- [x] I have searched existing issues and this hasn't been reported yet
- [x] This is a single bug report (please file separate reports for different bugs)
- [x] I am using the latest version of Claude Code
What's Wrong?
A routine configured with "Allow unrestricted branch pushes" enabled cannot push to main. The Anthropic git proxy returns HTTP 403 on git push origin main, even though the setting that should permit this is on.
This appears related to #24535 (proxy restricts pushes to claude/* only) and #44949 (inconsistent enforcement of the "Allow unrestricted branch pushes" setting), but is a clean minimal repro of the inverse case: setting is ON, push to main is still blocked.
What Should Happen?
With "Allow unrestricted branch pushes" enabled for the repository, git push origin main should succeed and the commit should land on origin/main.
Error Messages/Logs
The push fails with HTTP 403 from the proxy. Full trace below.
Trace log (/tmp/push-trace.log)
++ git fetch origin main
From http://127.0.0.1:44229/git/<branch>
* branch main -> FETCH_HEAD
++ git checkout main
Switched to branch 'main'
Your branch is up to date with 'origin/main'.
++ git pull --ff-only origin main
From http://127.0.0.1:44229/git/<branch>
* branch main -> FETCH_HEAD
Already up to date.
++ git add drafts/
++ git commit -m 'Push test 2026-05-11T20:13:41Z'
[main 3d56787] Push test 2026-05-11T20:13:41Z
1 file changed, 3 insertions(+)
create mode 100644 drafts/push-test-20260511-201332.md
++ git push origin main
error: RPC failed; HTTP 403 curl 22 The requested URL returned error: 403
send-pack: unexpected disconnect while reading sideband packet
fatal: the remote end hung up unexpectedly
Everything up-to-date
++ echo PUSH_EXIT_CODE:1
PUSH_EXIT_CODE:1
Steps to Reproduce
Steps to reproduce
Create a routine with "Allow unrestricted git push — Let the agent push to any branch on this repo, including the default branch." set to True.
Give these instructions to the routine:
You are running a push test. Do exactly the steps below.
Step 1 — Write a test file
Create drafts/push-test-<timestamp>.md with a short test message.
Step 2 — Commit and attempt to push to main
Run these commands exactly:
set -x
exec > >(tee -a /tmp/push-trace.log) 2>&1
git fetch origin main
git checkout main
git pull --ff-only origin main
git add drafts/
git commit -m "Push test"
git push origin main
Step 3 — Report exit code and trace log
Hard rules
- The push command is exactly
git push origin main. - Do not add flags, do not use a refspec mapping, do not retry on failure,
do not fall back to a claude/* branch.
Claude Model
Sonnet (default)
Is this a regression?
I don't know
Last Working Version
_No response_
Claude Code Version
2.1.138
Platform
Anthropic API
Operating System
macOS
Terminal/Shell
Terminal.app (macOS)
Additional Information
_No response_
7 Comments
Found 3 possible duplicate issues:
This issue will be automatically closed as a duplicate in 3 days.
🤖 Generated with Claude Code
Another autonomous-routine cascade observation, independent from the original repro and from the Falcon trading-bot cascade on 2026-05-11/12. Adding it in case it helps prioritize.
Setup: Cloud-scheduled Claude Code Routine fires on cron, runs an end-of-day trading bookkeeping workflow that publishes JSON artifacts to a shared cross-repo knowledge base and then commits + pushes EOD state to its own bot repo
main.Symptom on 2026-05-12 ~20:00 UTC (daily-summary fire):
mainand failed silently. No corresponding commit onmain, no fallback branch on remote — commit was lost on container reap before the in-script PR-fallback path completed its merge poll._safe-pushv2.1.1 wrapper that retries on HTTP 403 /git-receive-packsideband-disconnect and falls back to a feature branch +gh pr create+gh pr merge --squashpoll-retry. On this fire the fallback branch was either never created or the container terminated before the wrapper exited cleanly.Why this is a stronger signal than a manual
git pushrepro:_safe-pushwrappers with 403 handling — failure is upstream of the wrapper's intercept.Operator-side mitigation adopted (not a substitute for the fix):
git fetch --all && git branch -r --no-merged origin/main | grep <bot-fallback-pattern>— surfaces unmerged fallback branches before any new work.memory/data files only.Ask: is there a planned fix horizon for #58141? Even an exposed
ended_reasondistinguishable from #54260's silent-successrun_once_firedwould let operator-loop wrappers detect this failure mode programmatically rather than via remote-branch grep.This should be fixed now.
Additional evidence from an autonomous trading-bot deployment hitting this issue continuously since 2026-05-11. Refined bug model based on empirical scope-narrowing across multiple repos and branches.
Refined scope: source-repo + default-branch only
In our deployment, the proxy block applies specifically to the default branch of the trigger's
sourcesgit_repository — NOT all main pushes. Same routine, three push targets, three different outcomes:| Push target | Outcome |
|---|---|
|
<trigger.source.repo>/main(default branch of source) | 403 / sideband disconnect (blocked) ||
<trigger.source.repo>/<feature-branch>(same repo, non-default branch) | succeeds ||
<other-repo>/main(different repo, e.g. a shared KB the routine also pushes to) | succeeds |All 8 of our cloud triggers have
allow_unrestricted_git_push: trueconfigured insources[].git_repository, verified via RemoteTrigger API. The setting is correctly enabled; the proxy ignores it for the source-repo default-branch path specifically.Error signature (matches OP exactly)
Workaround that works
Push to a feature branch from the routine, then open a draft PR. The operator (or a follow-up routine) ff-merges/cherry-picks to main. Our
_safe-pushwrapper does this automatically on 403/500.Ruled out (operator-side empirical checks)
HTTP 403 "Upgrade to GitHub Pro or make this repository public to enable this feature"— feature is paywalled, literally unavailable on our private Free-tier repo. Cannot be the cause.git push origin mainfrom local works continuously throughout the same incident window.allow_unrestricted_git_pushconfig: verifiedtrueon every trigger.Operational impact
Real one — for autonomous routines that need to commit work to their source repo's main (daily summaries, EOD logs, state persistence), every fire requires operator-loop merge of fallback branches. Two consecutive trading days (2026-05-11 → 2026-05-12) lost to CAUTIOUS_MODE skips when the cascade prevented EOD heartbeat commits from landing on main, even though the work itself was preserved on fallback branches.
The bug surface is narrower than "all main pushes broken" — only source-repo + default branch — but for source-repo-state-persistence use cases it's a complete block.
Hope this helps narrow the proxy logic. Happy to provide more specific trigger configs or git-proxy log lines if useful.
Thanks @ashwin-ant — will verify on next two natural cron fires (a daily-summary at 20:03Z tonight + a higher-stakes trading-routine fire tomorrow 13:45Z) and report back. For reference, our most recent fire at 2026-05-14 15:01Z still hit the 403 / sideband-disconnect pattern (commit landed on a fallback branch), so the fix either landed after that fire or doesn't propagate to existing triggers / requires routine recreation.
Will report observability:
Holding our operator-loop merge discipline until both fires confirm clean. Will comment with the verification outcome.
Verifying — both natural cron fires landed clean on Hawkeye after your fix:
2cc3783, direct-to-main push succeeded, heartbeat row writtencec50fc, direct-to-main push succeeded, heartbeat row writtenBoth pushed directly to
origin/mainwithout falling back to thehawkeye-bot/<routine>-<date>fallback-branch path that we'd been seeing on every push 2026-05-11 through 2026-05-12. Hawkeye is now 8 of 8 routine fires clean on 5/13 + 5/14 vs 4 of 8 on 5/11–5/12 (mixed #58141 push-403 + apparent silent-fail symptoms).The clearing is sharp and coincident with your fix landing. Continuing to monitor through this week — will reopen or file fresh if anything regresses. Thanks for the quick turnaround.
This issue has been automatically locked since it was closed and has not had any activity for 7 days. If you're experiencing a similar issue, please file a new issue and reference this one if it's relevant.