Git options
Every environment gets its own git setup, and a handful of settings decide what that setup looks like: whether git is involved at all, what the branch is based on, whether the agent may publish, and whose name ends up on the commits. This page walks through them in the order you'll meet them. The exhaustive key list lives in the config reference.
git_mode — how git is wired up
--git-mode auto|worktree|off|clone (config key git_mode, env var
GIT_MODE; default auto).
worktree— the isolated default. Forge Fleet creates a git worktree on a fresh branch off your source repo and mounts it into the container. Your main checkout is never touched, and environments can be stacked: start a new one from a branch that itself came from another environment.off— no git integration at all. The agent works directly in the mounted directory: no worktree, no branch, and no git repository required. This is how you point Forge Fleet at a plain folder — notes, a data directory, a scratch project.auto— resolves toworktreein a normal repo, and falls back tooffwhen there's nothing to branch from: no git repo, or a directory that is the repository's primary checkout rather than a linked worktree.clone— reserved, not implemented yet. The value passes validation but the container's init script rejects it, so the environment fails to start. Useworktreeorauto.
$ ffleet up my-feature --git-mode worktree # explicit isolation
$ cd ~/notes && ffleet up braindump --here # in-place, no worktree
--here is the per-run form of off: it starts an agent over your current
directory. Setting git_mode = "off" makes that the project's default and points
it at the project root from any subdirectory, so you don't pass --here each
time.
git_mode is an identity setting — pinned when the environment is created.
Changing it means ffleet remove SLUG and starting again.
Choosing what the branch is based on
By default a new worktree's branch forks from your remote's default branch:
ffleet fetches, then takes the first of origin/HEAD, origin/main, local
main, origin/master, local master, HEAD that resolves.
--from BRANCH overrides that for a first-time worktree — base the work
on an existing branch instead of the default one:
$ ffleet up hotfix --from release-2.3 -p "Cherry-pick the logging fix"
It's ignored once the environment exists (the branch is already created), and a
branch you brought in with --from is left alone by ffleet remove — only
branches Forge Fleet created itself get deleted.
git_local_main — stay off the network
--git-local-main (config key git_local_main, env var GIT_LOCAL_MAIN;
default false) bases the branch on your local refs/heads/main and nothing
else — if that ref doesn't exist, the environment fails rather than quietly
falling back to a remote branch.
git_local_main = true
Use it when the work should stay local: you merge on your own machine, with no
push and no PR. It pairs naturally with git_allow_origin_writes = false below,
but neither implies the other — set both for a genuinely local-only environment.
git_allow_origin_writes — let the agent commit but not publish
git_allow_origin_writes (env var GIT_ALLOW_ORIGIN_WRITES; default true,
no CLI flag). Agents inside the container run with their own approval prompts
disabled, so once push credentials are present nothing but the agent's judgement
stops it publishing work you haven't reviewed. Setting it to false denies the
outward-facing commands at the agent's own permission layer:
git_allow_origin_writes = false
git push · gh pr create · gh pr merge · gh release create ·
gh workflow run · gh api with a mutating method
The agent can still commit locally; it just cannot publish. Matching is by command prefix, so the coverage has real edges — read the caveats before you rely on it. It raises the bar; it is not a sandbox.
It is sticky per environment. Once an environment has been created or started
with a value, later starts keep it even if you delete the key from ffleet.toml
— dropping the line does not quietly re-open remote writes. To re-enable them,
set git_allow_origin_writes = true explicitly; an explicit value always wins.
Push credentials and git_https_rewrite
The container gets no SSH key and no host git config, so it has no push auth
until you give it some. What it does have is an HTTPS transport: at every start
the init script writes a rewrite into the container's own gitconfig, derived
from your origin host —
[url "https://github.com/"]
insteadOf = git@github.com:
insteadOf = ssh://git@github.com/
— so an SSH origin URL still fetches and pushes with nothing but a token. The
repository's git config is never modified; it is shared with your host and every
other environment.
Supply the token as a fine-grained personal access token scoped to that one
repository, through docker_env_file.
Prefer that to mounting ~/.ssh: a mounted key is your real, long-lived
credential, valid everywhere it can reach for as long as the environment lives.
git_https_rewrite = false (env var
GIT_HTTPS_REWRITE; default true, no CLI flag) turns the rewrite off — for
example when you deliberately mount your own SSH agent socket. Unlike
git_allow_origin_writes it is not sticky: every start re-reads it from your
config.
Commit identity
Commits made inside the container need a user.name / user.email. Set a
project-specific pair in ffleet.toml:
[git]
user_name = "Jane Developer"
user_email = "jane@example.com"
Those two keys are bridged into FORGE_FLEET_GIT_USER_NAME /
FORGE_FLEET_GIT_USER_EMAIL, which is also where a shell or dotenv value lands —
and an already-set variable wins, so the environment overrides the config file.
From there Forge Fleet takes the first complete pair:
FORGE_FLEET_GIT_USER_NAME+FORGE_FLEET_GIT_USER_EMAIL— from[git], your shell, or.env.forge-fleet.- The identity recorded for this environment when it was created, so a revived environment keeps signing commits the way it always has.
- Your source repository's git config.
- Your global git config.
If none of them yields a pair, ffleet up fails and tells you to set the
variables or configure git — the container never starts without an identity.
Both or neither. Half a pair is not a partial override: setting exactly one
of the two variables — including a [git] table with only user_name — is a
hard error rather than a fall-through to the next source.
Environment-variable equivalents
Every git setting has a dotenv/env-var form, useful for a machine-specific value
you don't want in a shared ffleet.toml:
# .env.forge-fleet
GIT_MODE=worktree
GIT_LOCAL_MAIN=false
GIT_ALLOW_ORIGIN_WRITES=false
GIT_HTTPS_REWRITE=true
FORGE_FLEET_GIT_USER_NAME=Jane Developer
FORGE_FLEET_GIT_USER_EMAIL=jane@example.com
A CLI flag beats an env var, which beats ffleet.toml, which beats the default —
see config precedence.
Related
- Starting an environment — where git-mode fits among the
other
ffleet upchoices. - Completing / cleanup — landing the work and what
removedeletes. - Secrets & keys — getting the push token into the container.
- Config reference — the full key table.