Documentation
¶
Overview ¶
Package installer is the transport-agnostic core of the ten-step zero-touch bootstrap that `clawtool install` runs.
It exists so two surfaces can drive the SAME sequence without duplicating orchestration:
- the CLI (`clawtool install`), which executes each step in-process via the App dispatch surface and renders progress as stderr status lines; and
- the GUI installer (cmd/clawtool-installer, a separate Wails binary), which executes each step by shelling out to the clawtool binary and renders progress as a native splash.
The orchestration (which steps run, in what order, which are hard-required vs best-effort, the idempotency contract) lives here as the single source of truth. HOW a step executes (Exec) and HOW progress is surfaced (Emit) are injected, so this package imports neither internal/cli nor any GUI framework — both callers depend on it, not the reverse.
Scope note: steps 1–9 are the cross-surface core. The CLI's step 7.5 (tmux auto-spawn) and --attach handoff are terminal-only and stay in internal/cli; the GUI has no use for them.
Index ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type Actions ¶
type Actions struct {
StartDaemon DaemonStart
VerifyDaemon DaemonVerify
DetectHosts HostDetect
Run Exec
PeerRegister PeerRegisterFn
InitAll InitAllFn
AfterPeerRegister func()
}
Actions bundles the injected executors so Run stays transport- and framework-agnostic.
Run, StartDaemon, VerifyDaemon and DetectHosts are required. The remaining fields are optional hooks the CLI uses to route two steps through its dedicated seams instead of shelling the verb through Exec — the GUI leaves them nil and those steps fall back to Exec:
- PeerRegister (step 7): the CLI's seam carries display-name logic the bare `peer register` verb argv can't express.
- InitAll (step 8): the CLI's seam returns the applied-recipe count that feeds the install summary; a bare `init --all` verb reports only an exit code.
- AfterPeerRegister: a flow hook fired immediately after step 7 and before step 8, so the CLI can inject its terminal-only tmux auto-spawn (step 7.5) at the correct position without the core knowing tmux exists. The GUI has no use for it.
type DaemonStart ¶
DaemonStart ensures the daemon is up and returns its listen port. Bound to daemon.Ensure in production.
type DaemonVerify ¶
DaemonVerify probes daemon health. Returns "" when healthy, or a short diagnostic describing why the probe failed.
type Emit ¶
type Emit func(Event)
Emit is the progress sink. It is called once per status line, in step order, on the calling goroutine — callers that marshal to a UI thread are responsible for their own hand-off.
type Event ¶
type Event struct {
Step int `json:"step"`
Label string `json:"label"`
Level Level `json:"level"`
Message string `json:"message"`
DurationMs int64 `json:"duration_ms"`
}
Event is a single progress update emitted as a step runs. The CLI renders it to a stderr status line; the GUI pushes it to the frontend over a Wails binding. DurationMs is the wall-clock cost of the step's action (0 for steps that emit without timing).
type Exec ¶
Exec runs a single `clawtool <args...>` verb and returns the verb's exit code plus a trimmed one-line tail of its output (for the status message on failure). The CLI binds this to in-process App dispatch with captured stderr; the GUI binds it to a subprocess self-exec of the clawtool binary. A non-nil error is reserved for failures that prevented the verb from running at all (couldn't spawn); a verb that ran and exited non-zero reports via rc.
type HostDetect ¶
type HostDetect func() []string
HostDetect probes for installed agent CLIs and returns their family names (claude / codex / gemini / opencode).
type InitAllFn ¶
InitAllFn applies the Core recipes to workdir and returns the count of recipes applied (or a negative sentinel when the count is unknown). Optional override for step 8 (see Actions).
type Level ¶
type Level int
Level discriminates a step's outcome on its progress event. The three states mirror the operator-facing precedent (the onboard wizard's summary rows use the same ✓ / ⚠ / ✗ glyphs).
type Options ¶
type Options struct {
// Workdir is the directory step 8 (init --all) targets. When it
// is not inside a git repo, step 8 is skipped with a warning.
Workdir string
// SkipInit suppresses step 8 entirely.
SkipInit bool
}
Options tune a run.
type PeerRegisterFn ¶
PeerRegisterFn registers the current shell as a peer under the given backend label. Optional override for step 7 (see Actions).
type Summary ¶
type Summary struct {
Port int
AgentsClaimed int
RecipesApplied int
BridgesInstalled int
PeersRegistered int
StepsOK int
StepsWarn int
StepsFailed int
}
Summary is the running tally Run maintains across the steps so a caller can render a closing one-liner.
func Run ¶
Run executes steps 1–9 of the bootstrap, emitting one Event per status line via emit, and returns the Summary. A non-nil error is returned only when a HARD-REQUIRED step fails: step 1 (daemon health) or step 9 (verify). Steps 2–8 are best-effort — their failures land as LevelWarn events and increment Summary.StepsWarn but never abort the run. The sequence is idempotent: each verb short-circuits when its target state already exists.