docs(#2067): trim choom prose in code, link to docs/tools/hivectl.md
This commit is contained in:
parent
0125fcfae8
commit
2248881be8
1 changed files with 22 additions and 49 deletions
|
|
@ -110,15 +110,11 @@ enum Cmd {
|
|||
},
|
||||
/// Open an interactive Claude session inside an agent container.
|
||||
///
|
||||
/// Execs `machinectl shell <name>@h-<name>` running claude as the
|
||||
/// agent user from its state dir, with the same settings / MCP config
|
||||
/// / system prompt the harness uses. Bare `choom <name>` launches a
|
||||
/// fresh blank session; `choom <name> --continue <id|name>` passes
|
||||
/// `--continue <value>` straight through to claude to rejoin a prior
|
||||
/// session (claude resolves whether the value is a session id or a
|
||||
/// display name). It never collides with the harness's live session —
|
||||
/// the harness pins its own session via `--resume`, so a blank choom
|
||||
/// session is invisible to it. Requires root + a running container.
|
||||
/// Runs claude as the agent user from its state dir with the harness's
|
||||
/// settings / MCP / system prompt. Bare `choom <name>` is a fresh
|
||||
/// session; `--continue <id|name>` rejoins a prior one. Never collides
|
||||
/// with the harness's live session. Requires root + a running
|
||||
/// container. See `docs/tools/hivectl.md` (Choom) for details.
|
||||
Choom {
|
||||
/// Agent name (e.g. `damocles`, `iris`).
|
||||
name: String,
|
||||
|
|
@ -1029,49 +1025,29 @@ fn agent_exists(name: &str) -> Result<bool> {
|
|||
|
||||
/// Drop into an interactive Claude session in the agent container.
|
||||
///
|
||||
/// Execs `machinectl shell <name>@h-<name> /bin/sh -lc '<script>'` where
|
||||
/// the script `cd`s into the agent's state dir and execs claude with the
|
||||
/// same flags the harness uses. Four things matter:
|
||||
///
|
||||
/// 1. **Run as the agent user** (`<name>@` prefix), not root, so claude
|
||||
/// reads the agent's `/home/<name>/.claude` OAuth creds.
|
||||
/// 2. **Start in the agent's state dir** (`/agents/<name>/state`) so the
|
||||
/// session + `CLAUDE.md` resolve against the right project.
|
||||
/// 3. **Pass the harness's flags** (`--settings` / `--mcp-config` /
|
||||
/// `--system-prompt-file` from `/run/hive-config/`), each only if its
|
||||
/// file exists so a half-up container degrades to a bare session.
|
||||
/// 4. **Pick the session explicitly.** Bare choom starts a fresh blank
|
||||
/// session. `--continue <value>` is passed straight through as
|
||||
/// `claude --continue <value>` to rejoin a prior session — claude
|
||||
/// resolves whether the value is a session id or a display name (the
|
||||
/// operator can `/rename` a session in-session for an easy handle).
|
||||
/// Either way choom never clobbers the harness's live session: the
|
||||
/// harness pins its own id via `--resume`, so a blank choom session
|
||||
/// in this shared project dir is invisible to it.
|
||||
///
|
||||
/// Inherits the caller's PTY. Requires root + a running container.
|
||||
/// Execs `machinectl shell <name>@h-<name>` running claude as the agent
|
||||
/// user from its state dir, reproducing the harness's per-turn claude
|
||||
/// invocation (flags, session selection, why it never collides with the
|
||||
/// live harness session). See `docs/tools/hivectl.md` (Choom) for the
|
||||
/// full rationale. Inherits the caller's PTY; requires root + a running
|
||||
/// container.
|
||||
fn choom(name: &str, continue_session: Option<&str>) -> Result<()> {
|
||||
if !agent_exists(name)? {
|
||||
bail!("no such agent: '{name}' (no state dir under /var/lib/hyperhive/agents/)");
|
||||
}
|
||||
let container = hive_c0re::lifecycle::container_name(name);
|
||||
// The agent's unix user name matches its agent name (meta-flake
|
||||
// sets `hyperhive.user.name = <label>`); enter the session as that
|
||||
// user so claude sees the right `$HOME/.claude`.
|
||||
// Enter as the agent's unix user (== agent name) so claude reads the
|
||||
// right `$HOME/.claude`.
|
||||
let target = format!("{name}@{container}");
|
||||
let claude = "/run/current-system/sw/bin/claude";
|
||||
// In-container state dir (host `/var/lib/hyperhive/agents/<name>/state`
|
||||
// is bind-mounted here); matches `hive-ag3nt::paths::state_dir()`.
|
||||
// Bind-mounted state dir; matches `hive-ag3nt::paths::state_dir()`.
|
||||
let state_dir = format!("/agents/{name}/state");
|
||||
// Per-turn config dir the harness writes (RuntimeDirectory
|
||||
// `hive-config`); matches `hive-ag3nt::paths::config_dir()`. These
|
||||
// are the exact files the harness passes to claude each turn.
|
||||
// Per-turn config the harness writes; matches `paths::config_dir()`.
|
||||
let cfg = "/run/hive-config";
|
||||
// `--continue <value>` (if given) is passed straight through to
|
||||
// claude; with none, claude starts a fresh blank session. The value
|
||||
// is single-quoted into the shell script, so reject an embedded
|
||||
// single quote (the only char that breaks single-quoting) to rule
|
||||
// out injection — ids and display names never contain one.
|
||||
// `--continue <value>` passes straight through to claude. The value is
|
||||
// single-quoted into the shell script, so reject an embedded single
|
||||
// quote (the only char that breaks single-quoting) to rule out
|
||||
// injection — session ids / display names never contain one.
|
||||
let session_arg = match continue_session {
|
||||
Some(val) => {
|
||||
if val.contains('\'') {
|
||||
|
|
@ -1081,12 +1057,9 @@ fn choom(name: &str, continue_session: Option<&str>) -> Result<()> {
|
|||
}
|
||||
None => "set --;".to_string(),
|
||||
};
|
||||
// Build the claude argv as the harness does, but only include each
|
||||
// flag when its file is present so a half-up container falls back to
|
||||
// a bare session rather than a hard claude error. `name` is
|
||||
// constrained to `[a-z0-9._-]` so there's nothing to quote. choom
|
||||
// never collides with the harness's live session in this same project
|
||||
// dir: the harness pins its own session id via `--resume`.
|
||||
// Build claude's argv as the harness does, each flag included only
|
||||
// when its file is present so a half-up container degrades to a bare
|
||||
// session. `name` is `[a-z0-9._-]` so there's nothing to quote.
|
||||
let inner = format!(
|
||||
"cd {state_dir} || exit 1; {session_arg} \
|
||||
[ -f {cfg}/claude-settings.json ] && set -- \"$@\" --settings {cfg}/claude-settings.json; \
|
||||
|
|
|
|||
Loading…
Reference in a new issue