D173 — kb commands: bounded clone, correct local target, read-only list¶
Decision. gitx.Clone takes a context and a non-interactive environment;
kb create/kb clone accept --config and refuse to act on the local data dir
when this machine's client points at a remote server (--local opts out); kb
list reports what is on disk and what the server serves, writing nothing.
Context. Three defects in the same family: a command that can hang with no output, one that silently acts on the wrong directory, and a state nothing on the CLI could observe.
- Bounded execution over a diagnosis.
Clonewasexec.Command+CombinedOutput(): no deadline, no progress, nothing stopping git from opening a credential or host-key prompt against a stdin that cannot answer. A hang was observed; which prompt fired is not asserted, because the remedy is the same either way —GIT_TERMINAL_PROMPT=0,BatchMode=yes -o ConnectTimeout=10for ssh remotes,--timeout(default 120s), and streamed progress. - Never force host-key acceptance.
StrictHostKeyChecking=accept-newwould trade a hang for a silent trust-on-first-use decision on an operator's machine. Git fails quickly and says why; the operator accepts the key themselves. - An operator's
GIT_SSH_COMMANDwins. Someone who configured a proxy command, an identity file or a jump host has said how to reach their forge. Overwriting that breaks a working setup to prevent a hypothetical one, so the default is added only when neither the process environment nor the caller provides one. - Cleanup removes only what the command created. The destination is checked
not to exist before the clone, so anything under it afterwards is ours. An
interrupt now cancels the context — killing git and waiting for it to exit —
before removing the tree: deleting a directory a running git is still writing
produces a second, more confusing failure, and the previous
defernever ran on SIGINT at all. - The wrong target is an error, not a warning.
resolveServerDataDirread the standard service config path whileservice install --configaccepts another, so a service installed at a custom path was invisible and the command reportedKB "x" mounted at …about a directory nothing reads.--configfixes the resolution; the guard covers the other half — a client pointed at a remote server means these commands would act on a server nobody is talking to. A command that claims to have mounted something it did not is the worst outcome available, so it fails, with--localas the declared opt-out and no opinion at all when--dataalready names the target or no client config exists. kb listis strictly read-only. It must not callkb.Open, which self-migrates the local git-exclude entry of every repository it touches: a listing command that mutates what it lists is not one. Validity is read directly fromdata/index.md, which is whatOpenitself checks. A missing data dir is reported, never created — that isserve's job, not a listing's.- "Not mounted" and "could not ask" are different answers. When
/healthdoes not respond theMOUNTEDcolumn disappears and the reason is printed. Rendering an unreachable server as "nothing is mounted" would invent a fact.
Consequences. A new subcommand, new flags (--config, --local,
--timeout), and a guard that starts failing a usage which is silently
ineffective today — worth naming in the release notes together with --local.
kb create --remote stays mandatory (D134); this changes nothing about it.