feat(docker): opt-in gh + az CLIs with git credential helpers for private repos

Add Case -> Clone Repo could only reach public repositories in the Docker
deployment. This lets a deployment opt in to the GitHub CLI and the Azure
CLI (+ azure-devops extension) as git credential helpers. Codeman itself
still collects no credentials.

- server.Dockerfile / agent.Dockerfile: CODEMAN_INSTALL_GH /
  CODEMAN_INSTALL_AZ build args (0 or 1, default 0; anything else stops the
  build). Off leaves no apt repository, package, extension, helper script
  or credential entry, so a default build is unchanged. On installs from
  the vendors' apt repositories and configures system gitconfig helpers:
  github.com / gist.github.com -> `gh auth git-credential`, dev.azure.com /
  *.visualstudio.com -> new docker/git-credential-azure-cli (an Entra ID
  token from `az account get-access-token`, or AZURE_DEVOPS_EXT_PAT).
  A helper whose CLI is not signed in prints nothing, so a private clone
  still fails fast.
- The extension lives in AZURE_EXTENSION_DIR outside HOME
  (/opt/codeman-az-extensions, runtime-owned; /opt/az-extensions, gid-0
  group-writable in the agent image).
- Hosts turn them on in docker-compose.override.yml: `build: args:` for the
  server image, `environment:` CODEMAN_AGENT_IMAGE_INSTALL_GH / _AZ for the
  agent image. build-agent-image.mjs and the in-app auto-build share one
  env -> ARG table (pinned by the parity test) and pass nothing when unset.
  docker-compose.yaml is untouched; .env.example only gains a comment, so
  the self-updater's environment gate sees no new keys.
- Docker cases seed the gh sign-in (~/.config/gh/hosts.yml, config.yml) and
  the az sign-in files from ~/.azure per file, read-only, like pi/grok.
- The Clone Repo AUTH_REQUIRED message says how to sign the server's git
  in instead of claiming private repositories cannot be cloned.
- Docs: docker/README.md "Private repositories", docker-compose.md,
  docker-cases.md, the Quick-Start / Core-Concepts / Docker-Cases wiki
  pages, security-architecture.md, architecture-invariants.md, changeset.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0167CiuzLrmjYWxwKp3rMWjw
This commit is contained in:
Devvyn
2026-09-23 08:57:09 +08:00
co-authored by Claude Opus 5.5
parent 9466acfc1a
commit 5cf5a45438
18 changed files with 501 additions and 14 deletions
+1 -1
View File
@@ -579,7 +579,7 @@ export function classifyGitFailure(stderr: string, timedOut: boolean, spawnError
return {
code: 'AUTH_REQUIRED',
message:
'That repository needs authentication. Codeman clones without credentials, so private repositories have to be cloned outside Codeman and added with Link Existing.',
"That repository needs authentication. Codeman never asks for credentials, so sign this server's git in first (for example `gh auth login` or `az login` from a shell session; the Docker image can include both, see docker/README.md), or clone it outside Codeman and add it with Link Existing.",
stderr: clean,
};
}