-
Notifications
You must be signed in to change notification settings - Fork 7
Description
Bug
Polecat agents fail to git push because git credentials are never set up. The agent clones successfully (using credentials embedded in the clone URL) but subsequent push operations fail with authentication errors.
Root Cause
The git credential flow has a gap: no code path ever writes git_auth.github_token to the town config.
The intended flow:
- User creates a rig with a git URL (e.g.,
https://github.com/user/repo.git) - Town config should have
git_auth.github_tokenset (from the user's GitHub integration or manually) container-dispatch.tsreadstownConfig.git_auth.github_tokenand maps it toenvVars.GIT_TOKEN- Container's
cloneRepoembeds the token in the clone URL:https://x-access-token:<token>@github.com/... - Container's
configureGitCredentialswrites a credential-store file for push operations - Agent's
git pushuses the credential-store helper
What actually happens:
- Step 2 never occurs. The tRPC
createRigmutation sendsgitUrlbut no git token - The tRPC
createTownmutation setskilocode_tokenandowner_user_idbut notgit_auth - The town config settings page (
/api/towns/:townId/configPATCH) supportsgit_authbut no UI flow populates it during rig creation - Result:
git_auth.github_tokenis alwaysundefined,envVars.GIT_TOKENis never set, clone uses unauthenticated URL (works for public repos), push fails
Secondary issues:
startMergeInContainerdoesn't mapGITLAB_INSTANCE_URLto envVars (breaks self-hosted GitLab merges)- The credential-store file is written to
/tmp/with a unique suffix per agent, but the SDK subprocess (opencode serve) may not inherit the worktree's git config ifprocess.chdirchanges before the subprocess reads it
Fix Requirements
1. Populate git credentials on rig creation
When a rig is created via createRig tRPC mutation:
- If the rig uses a GitHub integration (
platform_integration_id), fetch an installation token from the GitHub API and store it ingit_auth.github_token - If the rig uses a GitLab integration, fetch an access token and store it in
git_auth.gitlab_token - If the rig has no integration (manual git URL), the user must provide credentials via the town config settings page
2. Token refresh
GitHub installation tokens expire (typically 1 hour). The token needs to be refreshed:
- Before each
startAgentInContainercall, check if the token is expired and refresh - Or: use a long-lived personal access token / fine-grained token instead of installation tokens
- Or: configure the container's git credential helper to call back to the worker for fresh tokens on demand
3. Fix startMergeInContainer
Map GITLAB_INSTANCE_URL in the merge dispatch path (same as the agent dispatch path).
4. Verify credential-store propagation to SDK subprocess
The configureGitCredentials function writes to /tmp/.git-credentials-<suffix> and sets credential.helper in the worktree's git config. Verify that when opencode serve spawns and the agent runs git push, the git config is found and the credential-store file is readable.
Acceptance Criteria
- Polecat agent can
git pushto a GitHub repo after being dispatched - Polecat agent can
git pushto a GitLab repo (including self-hosted) after being dispatched - Deterministic merge (
/git/merge) can push to both GitHub and GitLab repos - Credentials are refreshed before they expire for long-running agents
- E2E test: create town → create rig with GitHub repo → sling bead → agent clones, makes changes, pushes successfully