Skip to main content
Experimental version.This is the latest in-development version of AI-Implement. Features may change without notice and behavior is not guaranteed. Switch to the latest stable version here.
If your repo needs tools or language runtimes that aren’t in the default runner image, you can point AI-Implement at a custom image by committing .ai-implement/image.yml to the default branch of your target repo. When AI-Implement starts a session for your repo, it reads this file and runs your image instead of the default.

How it works

Create a file at .ai-implement/image.yml in the default branch of your target repo:
Whether a private image works depends on the execution mode. In Fly Machines mode the session machine boots on your image with no registry credentials, so the image must be publicly pullable. In GitHub Actions mode the workflow pulls your image with the implementation job’s own token, so a private image on GitHub Container Registry works. How much setup that needs depends on where the image lives:
  • Published by the target repository itself — no configuration. A package is linked to the repository that publishes it, so that repository’s workflows inherit access.
  • A sibling repository’s, or one in another organization — the package must grant that repository access, or a personal access token must be swapped into the workflow’s registry credentials.
If the file is absent, malformed, or its image: value isn’t a well-formed image reference, the orchestrator falls back to the default runner image automatically — but that check only looks at the file itself. A syntactically valid reference that can’t actually be pulled (deleted, the wrong tag, or private where the execution mode has no credentials for it) passes this check and fails later, when the session tries to start, with a manifest/unauthorized error.
The file is always read from the default branch, never from a pull request’s head — so editing image.yml in an open PR won’t change which image that PR’s runs use. Merge the change first.
The default base image is:

Codex compatibility

Configured Codex runs need a compatible shared runner with the Codex CLI and the selected-agent execution support. The published runner includes a pinned Codex CLI. A custom image must retain that support and the runner entrypoint. Installing a Codex binary alone does not make an older runner compatible. Use Sync workflows on the project and merge its target-repository PR when workflow readiness reports incompatibility. Then retry project opt-in. Check the image and selected agent in the actual run evidence. Publishing a new tag does not prove an existing run used it. Ordinary Fly or local Codex runs are separate from managed Restate review-fix, which currently requires GitHub Actions. See local feedback for a repeatable source and image check.

Setup steps

1

Create a Dockerfile

Build FROM the published base image so you inherit the tools and configuration the default runner provides, then add the tools or runtimes your repo requires.
2

Build and push the image

Build the image and push it to a registry AI-Implement can pull from. GitHub Container Registry (ghcr.io), under your own namespace, is the usual choice.
In GitHub Actions mode the image must also sit under a trusted prefix — your own ghcr.io/<owner>/ namespace, or one you add to the image allowlist. A public image is no exception, and one outside every trusted prefix fails the run rather than falling back to the default image. Fly Machines mode has no such restriction.Whether a private image works differs by mode as well — see the per-mode rules above.
3

Commit .ai-implement/image.yml

Create the file in your target repo pointing at the image you just pushed:
Commit this to your default branch. AI-Implement reads it from there on the next run.
Common use cases for a custom runner image include repos that need Terraform, Ruby, Go, or a specific language version that isn’t available in the default image.

Alternative: GitHub Actions variable

Repos using GitHub Actions execution mode have a second image-override mechanism: the AI_IMPLEMENT_RUNNER_IMAGE repository variable. When set, the synced claude-implement.yml workflow uses that image as the container for its job.
Resolution order when the orchestrator dispatches a GHA-mode run:
  1. The orchestrator’s resolved image (from .ai-implement/image.yml or its own AI_IMPLEMENT_RUNNER_IMAGE — the deprecated SESSION_IMAGE env var name is still honored as a fallback) is forwarded as the workflow’s runner_image input, if either is explicitly set
  2. Otherwise the workflow falls back to AI_IMPLEMENT_RUNNER_IMAGE if that variable is set
  3. Otherwise the built-in default (ghcr.io/builddownai/ai-implement-runner:latest) is used
Most repos use .ai-implement/image.yml because it gives you one mechanism for both execution modes. Reach for AI_IMPLEMENT_RUNNER_IMAGE when you want an org-level default that applies across all your repos without committing a file to each one.