Compare commits
4 changed files with 24 additions and 24 deletions
|
|
@ -123,8 +123,8 @@ somebody already thought of.
|
||||||
## Reachability
|
## Reachability
|
||||||
|
|
||||||
The receiver is socket-activated, and the socket binds **this host's
|
The receiver is socket-activated, and the socket binds **this host's
|
||||||
mesh address**, never a wildcard. The module asserts two things: the
|
mesh address**, never a wildcard. Both the mesh being enabled and the
|
||||||
mesh is on, and the address isn't empty --- neither is just documentation: bound to
|
address being set are assertions, not documentation --- bound to
|
||||||
`0.0.0.0` this socket is an unauthenticated remote write into agent
|
`0.0.0.0` this socket is an unauthenticated remote write into agent
|
||||||
state.
|
state.
|
||||||
|
|
||||||
|
|
@ -161,7 +161,7 @@ The boundary is the machine. The intended deployments are:
|
||||||
The second is worth keeping deliberately, and not only for
|
The second is worth keeping deliberately, and not only for
|
||||||
convenience: it means every local deployment exercises the confined
|
convenience: it means every local deployment exercises the confined
|
||||||
path. The usual failure mode for an isolated variant is that
|
path. The usual failure mode for an isolated variant is that
|
||||||
nobody runs it day to day, so it rots and turns up broken in
|
nobody runs it day to day, so it rots and is discovered broken in
|
||||||
production.
|
production.
|
||||||
|
|
||||||
⚠️ **The assumption to keep true over time:** the store host runs
|
⚠️ **The assumption to keep true over time:** the store host runs
|
||||||
|
|
@ -175,8 +175,8 @@ Which makes it the highest-value target in the swarm by a wide margin,
|
||||||
and means it should get the treatment a backup host gets --- restricted
|
and means it should get the treatment a backup host gets --- restricted
|
||||||
access, and a decision (rather than an omission) on encryption at rest.
|
access, and a decision (rather than an omission) on encryption at rest.
|
||||||
|
|
||||||
The trap is the label: this box holds backup-grade data while nobody
|
The trap is the label: this box holds backup-grade data while not being
|
||||||
calls it a backup, so it can end up with backup-grade _exposure_ and
|
called a backup, so it can end up with backup-grade _exposure_ and
|
||||||
non-backup-grade _controls_. Nobody puts a migration staging area on
|
non-backup-grade _controls_. Nobody puts a migration staging area on
|
||||||
the access-review list.
|
the access-review list.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -185,8 +185,8 @@ it directly as a bulleted list, no follow-up fetch needed.
|
||||||
rows, on both the agent and manager sockets alike (the manager, `ruth`,
|
rows, on both the agent and manager sockets alike (the manager, `ruth`,
|
||||||
is a normal agent here, just deployed automatically with different
|
is a normal agent here, just deployed automatically with different
|
||||||
default capabilities). `Approval` rows only appear when the calling agent is
|
default capabilities). `Approval` rows only appear when the calling agent is
|
||||||
the manager (sub-agents don't submit approvals). `Reminder` rows always
|
the manager (sub-agents don't submit approvals). `Reminder` rows are
|
||||||
carry `owner == self`.
|
scoped to `owner == self`.
|
||||||
|
|
||||||
Per-variant fields:
|
Per-variant fields:
|
||||||
|
|
||||||
|
|
@ -242,8 +242,8 @@ status_text, status_set_at, hive_name, swarm_name, matrix_accounts }`:
|
||||||
currently pinned at.
|
currently pinned at.
|
||||||
- `running`: whether the target's container is currently up. When
|
- `running`: whether the target's container is currently up. When
|
||||||
`false`, the host clears `status_text` / `status_set_at` —
|
`false`, the host clears `status_text` / `status_set_at` —
|
||||||
on-disk values from before the stop are stale snapshots, not
|
on-disk values from before the stop are stale snapshots and
|
||||||
live status. Defaults to `true` on the
|
shouldn't be shown as live status. Defaults to `true` on the
|
||||||
wire (older harnesses never serialised it, and the host only
|
wire (older harnesses never serialised it, and the host only
|
||||||
knew how to ask about live containers — keeps backwards-compat
|
knew how to ask about live containers — keeps backwards-compat
|
||||||
with pre-running-field payloads).
|
with pre-running-field payloads).
|
||||||
|
|
@ -321,7 +321,7 @@ being able to report its status chip, and the server-side `SetStatus` handler
|
||||||
has no tool-group check (only length validation), so gating it would only
|
has no tool-group check (only length validation), so gating it would only
|
||||||
desync the `--allowedTools` list from what the host actually accepts.
|
desync the `--allowedTools` list from what the host actually accepts.
|
||||||
Revoking `meta` therefore drops `get_agent_meta` but never `set_status`.
|
Revoking `meta` therefore drops `get_agent_meta` but never `set_status`.
|
||||||
`mark_todos_done` is here because producers push todos to an agent independent of
|
`mark_todos_done` is here because todos are pushed to an agent independent of
|
||||||
whether it holds `inbox` — an agent without that group still needs a way to
|
whether it holds `inbox` — an agent without that group still needs a way to
|
||||||
clear them.
|
clear them.
|
||||||
|
|
||||||
|
|
@ -427,7 +427,7 @@ Anything that changes per-container state on the host should be
|
||||||
re-applied here so a manual `↻ R3BU1LD` from the dashboard is
|
re-applied here so a manual `↻ R3BU1LD` from the dashboard is
|
||||||
sufficient to recover.
|
sufficient to recover.
|
||||||
|
|
||||||
## Actions live in one place
|
## Actions are factored
|
||||||
|
|
||||||
`approve` / `deny` / `destroy` (and the lifecycle helper) live in
|
`approve` / `deny` / `destroy` (and the lifecycle helper) live in
|
||||||
`actions.rs` / `hive-c0re/src/dashboard/`. The admin socket and the dashboard
|
`actions.rs` / `hive-c0re/src/dashboard/`. The admin socket and the dashboard
|
||||||
|
|
|
||||||
|
|
@ -52,8 +52,8 @@ and every client sees a name mismatch.
|
||||||
It's deliberately not an assertion: this module can see what _it_ is
|
It's deliberately not an assertion: this module can see what _it_ is
|
||||||
able to issue, but not an operator-installed sub-CA in
|
able to issue, but not an operator-installed sub-CA in
|
||||||
`swarm.ca.stateDir`, an external ACME setup, or a certificate delivered
|
`swarm.ca.stateDir`, an external ACME setup, or a certificate delivered
|
||||||
by any other means. If you have arranged one, expect the warning and
|
by any other means. If you have arranged one, the warning is expected
|
||||||
ignore it. Otherwise either install the sub-CA, or pin the
|
and can be ignored. Otherwise either install the sub-CA, or pin the
|
||||||
names back under the hive domain — a supported migration, since the
|
names back under the hive domain — a supported migration, since the
|
||||||
sub-CA carries a name constraint on the _configured_ names and the
|
sub-CA carries a name constraint on the _configured_ names and the
|
||||||
swarm root carries no name constraints at all.
|
swarm root carries no name constraints at all.
|
||||||
|
|
@ -62,8 +62,8 @@ swarm root carries no name constraints at all.
|
||||||
|
|
||||||
The root's private key never reaches the nix store: the store is
|
The root's private key never reaches the nix store: the store is
|
||||||
world-readable and content-addressed, so a key committed to a flake is a
|
world-readable and content-addressed, so a key committed to a flake is a
|
||||||
key published to everyone who builds it. The swarm distributes only
|
key published to everyone who builds it. Only certificates are
|
||||||
certificates.
|
distributed.
|
||||||
|
|
||||||
Each hive CA is **name-constrained** (X.509 `nameConstraints`) to that
|
Each hive CA is **name-constrained** (X.509 `nameConstraints`) to that
|
||||||
hive's own domain, so a hive CA that leaks can only mint names inside
|
hive's own domain, so a hive CA that leaks can only mint names inside
|
||||||
|
|
@ -161,7 +161,7 @@ The root **certificate** is a runtime file as a _consequence_ — it lives
|
||||||
beside the key under `swarm.ca.stateDir` — and that has a cost worth
|
beside the key under `swarm.ca.stateDir` — and that has a cost worth
|
||||||
naming, because it's subtle and it bites at a distance:
|
naming, because it's subtle and it bites at a distance:
|
||||||
|
|
||||||
> **Nothing whose trust store nix assembles at build time can reference
|
> **Nothing whose trust store is assembled at build time can reference
|
||||||
> the swarm root.** The derivation reads `security.pki.certificateFiles`
|
> the swarm root.** The derivation reads `security.pki.certificateFiles`
|
||||||
> inside itself; the root doesn't exist there.
|
> inside itself; the root doesn't exist there.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -43,7 +43,7 @@ hivectl forge reconcile-config iris --verbose # include the full diff, not
|
||||||
`create-user` persists the token to `<state>/forge-token`. Re-running refreshes the
|
`create-user` persists the token to `<state>/forge-token`. Re-running refreshes the
|
||||||
token (idempotent — scope always matches current `TOKEN_SCOPES`).
|
token (idempotent — scope always matches current `TOKEN_SCOPES`).
|
||||||
- For **non-agents** (humans): creates the account and prints the token to
|
- For **non-agents** (humans): creates the account and prints the token to
|
||||||
stdout, creating no state dir. Re-running after account already exists
|
stdout; no state dir is created. Re-running after account already exists
|
||||||
re-mints the token and prints it again — safe for password resets.
|
re-mints the token and prints it again — safe for password resets.
|
||||||
- Without `--password` / `--password-stdin` `create-user` uses a random
|
- Without `--password` / `--password-stdin` `create-user` uses a random
|
||||||
throwaway password (fine for agents — they auth by token).
|
throwaway password (fine for agents — they auth by token).
|
||||||
|
|
@ -133,8 +133,8 @@ username updates the password hash in place.
|
||||||
|
|
||||||
Container lifecycle shortcuts that go through the host admin socket.
|
Container lifecycle shortcuts that go through the host admin socket.
|
||||||
Requires the `hive-c0re` daemon to be running. Everything scoped to a
|
Requires the `hive-c0re` daemon to be running. Everything scoped to a
|
||||||
single agent lives under `hivectl agent <name> <verb>` — `hivectl` hoists
|
single agent lives under `hivectl agent <name> <verb>` — the name is
|
||||||
the name onto the parent command, so none of the verbs below repeat it.
|
hoisted onto the parent command, so none of the verbs below repeat it.
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
hivectl list-agents # roster: every agent's status + technical state
|
hivectl list-agents # roster: every agent's status + technical state
|
||||||
|
|
@ -221,8 +221,8 @@ granting that group the one action `machinectl shell` needs); `choom`
|
||||||
checks this itself and refuses up front with a message naming the
|
checks this itself and refuses up front with a message naming the
|
||||||
requirement rather than letting systemd reject the exec later with an
|
requirement rather than letting systemd reject the exec later with an
|
||||||
opaque polkit prompt. Same caveat as the socket grant: a shell opened
|
opaque polkit prompt. Same caveat as the socket grant: a shell opened
|
||||||
before the operator added you to `hive-admin` won't see it until you log
|
before you were added to `hive-admin` won't see it until you log back in
|
||||||
back in — secondary group membership applies at login.
|
— secondary group membership applies at login.
|
||||||
|
|
||||||
It also needs the daemon socket, unlike the other exec-into-a-container
|
It also needs the daemon socket, unlike the other exec-into-a-container
|
||||||
paths: the "is this actually an agent?" pre-flight reads the agents root,
|
paths: the "is this actually an agent?" pre-flight reads the agents root,
|
||||||
|
|
@ -241,9 +241,9 @@ through as `claude --resume <value>` to rejoin a prior session by its
|
||||||
session id — the flag name deliberately matches the claude flag it maps
|
session id — the flag name deliberately matches the claude flag it maps
|
||||||
to. (choom never uses claude's `--continue`: that's a bare flag that
|
to. (choom never uses claude's `--continue`: that's a bare flag that
|
||||||
takes no argument and resumes the cwd's _latest_ session, that is, the
|
takes no argument and resumes the cwd's _latest_ session, that is, the
|
||||||
harness's; claude would consume a value after it as the first prompt,
|
harness's; a value after it would be consumed as the first prompt,
|
||||||
silently poking the live harness session.) A value is required when you
|
silently poking the live harness session.) A value is required when the
|
||||||
pass the flag. Either way choom never collides with the harness's live
|
flag is given. Either way choom never collides with the harness's live
|
||||||
session in the same project dir: the harness pins its own id via
|
session in the same project dir: the harness pins its own id via
|
||||||
`--resume`, so a blank choom session is invisible to it. The container
|
`--resume`, so a blank choom session is invisible to it. The container
|
||||||
must be running.
|
must be running.
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue