homelab: v0.1 docs, distribution wiring, and version
Completes v0.1: documentation, build/install path, and version stamping. - cli/VERSION (v0.1.0) stamped into the binary via ldflags. - cli/README.md rewritten as the homelab overview (verbs + tiers, manifest, build, the preserved legacy webhook use-cases). - docs/adr/0004-0006: why homelab exists (grown in place from infra/cli, not a separate repo), v0.1 scope + everything-allowed/tiers-recorded, and the work/tf behaviour (native worktree entry, verification-gated auto-land, presence-coupled apply). - setup-devvm.sh builds cli/ -> /usr/local/bin/homelab each provisioning run (t3-dispatch pattern), so every devvm user gets the current binary. - AGENTS.md: discovery pointer under Common Operations. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
087b415f73
commit
66caa0bf7f
7 changed files with 164 additions and 2 deletions
30
docs/adr/0004-homelab-unified-cli.md
Normal file
30
docs/adr/0004-homelab-unified-cli.md
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
# homelab: a unified infra-ops CLI grown in place from infra/cli
|
||||
|
||||
Agents re-derive the same operational command boilerplate every session — mining
|
||||
51,116 bash commands across 2,225 past sessions showed dense, repeated patterns
|
||||
(the infra inner-loop alone is ~29%). We are building `homelab`, one CLI encoding
|
||||
the deterministic, repeated **actions** (not judgment) agents run — composable in
|
||||
bash, JSON-capable, and discovered progressively via `homelab manifest`. It is
|
||||
grown **in place** in `cli/` (the existing `infra-cli`), absorbing new verb-groups
|
||||
alongside the preserved legacy webhook use-cases. Versioned with a `cli/VERSION`
|
||||
file (the infra repo deploys continuously and does not cut semver tags).
|
||||
|
||||
## Considered options
|
||||
|
||||
- **Its own top-level repo** (the original plan) — rejected in favour of keeping
|
||||
it where the Terraform/Terragrunt and `scripts/tg` it drives already live; the
|
||||
Go source isn't git-crypt-encrypted and a provision-time build is unaffected by
|
||||
GitOps continuous-deploy.
|
||||
- **A fresh CLI ignoring infra-cli** — rejected: strands the VPN/DNS/email
|
||||
webhook use-cases.
|
||||
- **Raw kubectl/tg/ssh + skills + MCP only** — kept for everything outside the
|
||||
recurring action surface (methodology skills; third-party/owned MCP such as
|
||||
phpIPAM, which homelab does NOT duplicate).
|
||||
|
||||
## Consequences
|
||||
|
||||
- The binary is dual-purpose: the agent-facing `homelab` verb surface AND the
|
||||
in-cluster `infra-cli` webhook image. `main()` front-dispatches homelab verbs
|
||||
and falls through to the legacy `-use-case` path verbatim.
|
||||
- Distribution: built from source to `/usr/local/bin/homelab` during devvm
|
||||
provisioning (`t3-dispatch` precedent), refreshed by `t3-autoupdate`.
|
||||
23
docs/adr/0005-homelab-v01-scope.md
Normal file
23
docs/adr/0005-homelab-v01-scope.md
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
# homelab v0.1 scope: the infra inner-loop; everything allowed, tiers recorded
|
||||
|
||||
v0.1 ships only the highest-volume surface — the infra inner-loop: `work`
|
||||
(worktree lifecycle), `tf` (terragrunt via `scripts/tg` + fmt/validate/
|
||||
force-unlock), and `claim`/`release` (presence) — because it is ~29% of all mined
|
||||
commands and where agents lose the most time and leak the most presence claims.
|
||||
|
||||
v0.1 enforces **no** homelab-level permission gating: everything is allowed,
|
||||
relying on existing gates (harness permission mode, presence claims, plan
|
||||
approval). But every verb records a `read|write` tier (visible in `manifest`), so
|
||||
a PreToolUse classifier hook (auto-allow reads / prompt writes) can be added
|
||||
later with zero restructuring.
|
||||
|
||||
## Considered options
|
||||
|
||||
- **Reads-first vertical slice** (top read verb per domain) — lower risk, broad
|
||||
value, but defers the toil that motivated the project.
|
||||
- **One domain deep (k8s)** — cleanest template, narrow day-one value.
|
||||
|
||||
We chose the highest-volume-but-write-heavy infra loop deliberately, accepting
|
||||
the extra complexity (worktree lifecycle, git-crypt flag injection, presence
|
||||
coupling, branch-protection PR fallback) for the biggest immediate toil
|
||||
reduction. k8s/node/secret/net/ci verb-groups are deferred to later versions.
|
||||
29
docs/adr/0006-homelab-work-and-tf.md
Normal file
29
docs/adr/0006-homelab-work-and-tf.md
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
# homelab work/tf behaviour: native worktree entry, gated auto-land, presence-coupled apply
|
||||
|
||||
Four behaviours of the infra-loop verbs are surprising enough to record:
|
||||
|
||||
1. **`work` owns worktree create/land/clean, but session *entry* delegates to the
|
||||
native harness worktree tool.** A CLI is a child process and cannot change the
|
||||
agent's working directory; `EnterWorktree` can. So `homelab work start <topic>`
|
||||
creates the worktree + branch off `<remote>/master` (git-crypt-aware) and
|
||||
prints the path — the agent enters it with native `EnterWorktree({path})`.
|
||||
|
||||
2. **`work land` is auto-land, but gated on verification.** It merges master in →
|
||||
runs verification → pushes `HEAD:master` (fetch+merge+retry on
|
||||
non-fast-forward) → falls back to pushing the feature branch for a PR when the
|
||||
direct push is rejected (branch protection). It **refuses to push when it
|
||||
cannot verify** (no `--verify-cmd` and no auto-detected suite) unless
|
||||
`--no-verify` is passed — added after an accidental smoke-test land pushed
|
||||
unverified WIP to master (benign: the infra CI applied 0 stacks because the
|
||||
diff was `cli/`-only, but an unverified land must be deliberate, not default).
|
||||
|
||||
3. **`tf apply` is first-class despite GitOps, and mandatorily presence-coupled.**
|
||||
Local applies are out-of-band (CI applies canonically on push) but happen
|
||||
constantly (~763× in the corpus). `tf apply <stack>` auto-claims `stack:<name>`,
|
||||
delegates to `scripts/tg apply --non-interactive`, and **always releases on
|
||||
exit** (normal, error, or signal via `sync.Once` + handler) — fixing the
|
||||
documented ~200-claim leak — and prints an out-of-band reminder.
|
||||
|
||||
4. **Known v0.1 limitation:** `work land` does not yet block on CI to green; that
|
||||
arrives with the ci/deploy watch verb-group. It prints a reminder to follow
|
||||
the pipeline manually.
|
||||
Loading…
Add table
Add a link
Reference in a new issue