aboutsummaryrefslogtreecommitdiff
path: root/docs
diff options
context:
space:
mode:
authorOgulcan Celik <ogulcancelik@gmail.com>2026-07-19 23:52:20 +0300
committerOgulcan Celik <ogulcancelik@gmail.com>2026-07-19 23:56:07 +0300
commit3f80947678a9723434aa7fddfe23750b5393e24c (patch)
tree6f463797132acfc51dfb6e135820a052954b4f13 /docs
parentf76f895efe5b9f19aa9db909354c6c0f2195630b (diff)
feat: make agent automation a first-class cli primitive
Diffstat (limited to 'docs')
-rw-r--r--docs/next/CHANGELOG.md5
-rw-r--r--docs/next/api/herdr-api.schema.json121
-rw-r--r--docs/next/website/src/content/docs/agent-automation.mdx122
-rw-r--r--docs/next/website/src/content/docs/agent-skill.mdx2
-rw-r--r--docs/next/website/src/content/docs/agents.mdx36
-rw-r--r--docs/next/website/src/content/docs/cli-reference.mdx62
-rw-r--r--docs/next/website/src/content/docs/ja/agent-automation.mdx122
-rw-r--r--docs/next/website/src/content/docs/ja/agent-skill.mdx2
-rw-r--r--docs/next/website/src/content/docs/ja/agents.mdx36
-rw-r--r--docs/next/website/src/content/docs/ja/cli-reference.mdx65
-rw-r--r--docs/next/website/src/content/docs/ja/socket-api.mdx10
-rw-r--r--docs/next/website/src/content/docs/socket-api.mdx10
-rw-r--r--docs/next/website/src/content/docs/zh-cn/agent-automation.mdx122
-rw-r--r--docs/next/website/src/content/docs/zh-cn/agent-skill.mdx2
-rw-r--r--docs/next/website/src/content/docs/zh-cn/agents.mdx36
-rw-r--r--docs/next/website/src/content/docs/zh-cn/cli-reference.mdx65
-rw-r--r--docs/next/website/src/content/docs/zh-cn/socket-api.mdx10
17 files changed, 654 insertions, 174 deletions
diff --git a/docs/next/CHANGELOG.md b/docs/next/CHANGELOG.md
index b3d57550..f9805cda 100644
--- a/docs/next/CHANGELOG.md
+++ b/docs/next/CHANGELOG.md
@@ -3,10 +3,13 @@
## Unreleased
### Added
-- Added named-agent `start`, `prompt`, and completion-wait workflows. Agent startup now targets an existing pane without changing topology, validates the requested interactive agent kind, and accepts optional native arguments after `--`.
+- Added a live-agent CLI facade with named `start`, atomic `prompt`, logical `send-keys`, and server-owned `wait` workflows. Agent startup targets an existing pane without changing topology, validates the requested interactive agent kind and strict agent name, and accepts native arguments after `--`.
- Added `ui.sidebar_start_collapsed` to launch Herdr with the sidebar collapsed. (#1463)
- Added macOS support for the `HERDR_AGENT=<agent>` foreground-process hint, allowing agents hidden behind host-visible wrappers such as `nono` to use the named agent's screen manifest. (#679)
+### Changed
+- Agent commands now accept only a unique live agent name or the pane ID currently hosting that agent. Names are cleared when the occupant exits, is released, or is replaced. The old top-level `wait` commands were replaced by `agent wait` and `pane wait-output`, and `agent send` was replaced by `agent send-keys`.
+
### Fixed
- `herdr config check` now reports unknown config keys with their full paths instead of treating ignored typos as valid configuration. (#1573)
- Codex panes with customized static terminal titles now fall back to the live working footer instead of remaining idle, while OSC activity remains preferred. (#1563)
diff --git a/docs/next/api/herdr-api.schema.json b/docs/next/api/herdr-api.schema.json
index cb0c0b72..b066574f 100644
--- a/docs/next/api/herdr-api.schema.json
+++ b/docs/next/api/herdr-api.schema.json
@@ -597,9 +597,22 @@
"null"
]
},
+ "final_status": {
+ "anyOf": [
+ {
+ "$ref": "#/schemas/event/$defs/AgentStatus"
+ },
+ {
+ "type": "null"
+ }
+ ]
+ },
"pane_id": {
"type": "string"
},
+ "released": {
+ "type": "boolean"
+ },
"type": {
"const": "pane_agent_detected",
"type": "string"
@@ -1183,6 +1196,16 @@
},
"text": {
"type": "string"
+ },
+ "wait": {
+ "anyOf": [
+ {
+ "$ref": "#/schemas/request/$defs/AgentPromptWaitOptions"
+ },
+ {
+ "type": "null"
+ }
+ ]
}
},
"required": [
@@ -1191,6 +1214,25 @@
],
"type": "object"
},
+ "AgentPromptWaitOptions": {
+ "properties": {
+ "timeout_ms": {
+ "format": "uint64",
+ "minimum": 0,
+ "type": [
+ "integer",
+ "null"
+ ]
+ },
+ "until": {
+ "items": {
+ "$ref": "#/schemas/request/$defs/AgentStatus"
+ },
+ "type": "array"
+ }
+ },
+ "type": "object"
+ },
"AgentReadParams": {
"properties": {
"format": {
@@ -1239,18 +1281,21 @@
],
"type": "object"
},
- "AgentSendParams": {
+ "AgentSendKeysParams": {
"properties": {
- "target": {
- "type": "string"
+ "keys": {
+ "items": {
+ "type": "string"
+ },
+ "type": "array"
},
- "text": {
+ "target": {
"type": "string"
}
},
"required": [
"target",
- "text"
+ "keys"
],
"type": "object"
},
@@ -1309,6 +1354,31 @@
],
"type": "object"
},
+ "AgentWaitParams": {
+ "properties": {
+ "target": {
+ "type": "string"
+ },
+ "timeout_ms": {
+ "format": "uint64",
+ "minimum": 0,
+ "type": [
+ "integer",
+ "null"
+ ]
+ },
+ "until": {
+ "items": {
+ "$ref": "#/schemas/request/$defs/AgentStatus"
+ },
+ "type": "array"
+ }
+ },
+ "required": [
+ "target"
+ ],
+ "type": "object"
+ },
"ClientWindowTitleSetParams": {
"properties": {
"title": {
@@ -4499,11 +4569,11 @@
{
"properties": {
"method": {
- "const": "agent.send",
+ "const": "agent.send_keys",
"type": "string"
},
"params": {
- "$ref": "#/schemas/request/$defs/AgentSendParams"
+ "$ref": "#/schemas/request/$defs/AgentSendKeysParams"
}
},
"required": [
@@ -4579,6 +4649,22 @@
{
"properties": {
"method": {
+ "const": "agent.wait",
+ "type": "string"
+ },
+ "params": {
+ "$ref": "#/schemas/request/$defs/AgentWaitParams"
+ }
+ },
+ "required": [
+ "method",
+ "params"
+ ],
+ "type": "object"
+ },
+ {
+ "properties": {
+ "method": {
"const": "pane.split",
"type": "string"
},
@@ -6332,9 +6418,22 @@
"null"
]
},
+ "final_status": {
+ "anyOf": [
+ {
+ "$ref": "#/schemas/success_response/$defs/AgentStatus"
+ },
+ {
+ "type": "null"
+ }
+ ]
+ },
"pane_id": {
"type": "string"
},
+ "released": {
+ "type": "boolean"
+ },
"type": {
"const": "pane_agent_detected",
"type": "string"
@@ -8320,11 +8419,6 @@
"agent": {
"$ref": "#/schemas/success_response/$defs/AgentInfo"
},
- "baseline_state_change_seq": {
- "format": "uint64",
- "minimum": 0,
- "type": "integer"
- },
"type": {
"const": "agent_prompted",
"type": "string"
@@ -8332,8 +8426,7 @@
},
"required": [
"type",
- "agent",
- "baseline_state_change_seq"
+ "agent"
],
"type": "object"
},
diff --git a/docs/next/website/src/content/docs/agent-automation.mdx b/docs/next/website/src/content/docs/agent-automation.mdx
new file mode 100644
index 00000000..cbedd8c7
--- /dev/null
+++ b/docs/next/website/src/content/docs/agent-automation.mdx
@@ -0,0 +1,122 @@
+---
+title: Agent automation
+description: Use Herdr's layout, pane, and agent primitives to coordinate coding agents from scripts or other agents.
+---
+
+Herdr can act as an automation layer for coding agents. A script can control them, or one agent can create work for other agents, inspect their state, and collect their results. The important part is choosing the primitive that matches the job.
+
+## Three primitives
+
+| Primitive | Responsibility |
+| --- | --- |
+| Layout (`workspace`, `tab`, and pane topology) | Create and organize terminal locations. |
+| Pane | Control a raw terminal: run commands, send input, read output, and wait for output. |
+| Agent | Control a recognized coding agent by name or pane and lifecycle state. |
+
+A pane exists whether or not it contains an agent. An agent is the recognized process currently running inside a pane. `agent start` therefore requires an existing shell pane and never creates, splits, or moves layout.
+
+Creating a workspace also creates its first tab and root pane; creating a tab creates its root pane. Use the returned pane ID for the first process, and split only when that layout needs another terminal.
+
+Creation commands print JSON. Capture IDs from the response instead of predicting them:
+
+```bash
+created=$(herdr workspace create --cwd ~/project --label api --no-focus)
+pane_id=$(printf '%s\n' "$created" | jq -r '.result.root_pane.pane_id')
+
+split=$(herdr pane split "$pane_id" --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+```
+
+`workspace create` returns `.result.workspace`, `.result.tab`, and `.result.root_pane`. `tab create` returns `.result.tab` and `.result.root_pane`. `pane split` returns the new pane as `.result.pane`.
+
+Moving a pane to another workspace changes its workspace-qualified pane ID. After any `pane move`, continue with `.result.move_result.pane.pane_id`; the response keeps the old value at `.result.move_result.previous_pane_id`. A running process keeps its launch-time Herdr environment, but the old `HERDR_PANE_ID` remains an alias for that terminal, so `--current` stays safe. New commands can still resolve the agent by name after the move, but a wait already in progress ends with `agent_not_running`.
+
+Use pane commands for shells, tests, servers, CI watchers, and other ordinary terminal processes. Use agent commands when Herdr needs to understand which agent is running or whether it is `working`, `blocked`, `done`, `idle`, or `unknown`.
+
+## Agent identity and launch
+
+A pane ID such as `w1:p2` identifies the terminal location. An agent name such as `reviewer` is a convenient alias for the current agent in that pane. Names must match `[a-z][a-z0-9_-]{0,31}` and be unique among live agents. The alias is cleared when that agent exits, is released, or is replaced; it does not permanently rename the pane.
+
+Agent commands accept either a unique live name or the pane ID that currently hosts the agent.
+
+An available shell pane is at its interactive shell prompt: the shell itself owns the foreground, with no foreground command, editor, or agent running. Return the pane to its prompt before calling `agent start`.
+
+`--kind` selects a supported agent and its canonical executable. Supported kinds are `pi`, `claude`, `codex`, `gemini`, `cursor`, `devin`, `agy`, `cline`, `omp`, `mastracode`, `opencode`, `copilot`, `kimi`, `kiro`, `droid`, `amp`, `grok`, `hermes`, `kilo`, `qodercli`, and `maki`. Arguments after `--` are passed unchanged to that executable.
+
+`agent start` returns only after Herdr detects the expected agent in the same terminal and marks it ready for interactive input. Startup waits for 30 seconds by default; `--timeout` must be greater than 3000 and no more than 300000 milliseconds.
+
+```bash
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+```
+
+The equivalent fixed-ID example is:
+
+```bash
+herdr pane split --current --direction right --no-focus
+herdr agent start reviewer --kind codex --pane w1:p2 -- -m gpt-5.4
+```
+
+Agents launched manually are detected automatically and can be addressed by pane ID. Give one a name when a stable human-readable target is useful:
+
+```bash
+herdr agent get w1:p2
+herdr agent rename w1:p2 reviewer
+```
+
+## Choose the control surface
+
+| Goal | Command |
+| --- | --- |
+| Run a shell command and submit it | `pane run` |
+| Send literal text without Enter | `pane send-text` |
+| Send terminal keys or modifier chords | `pane send-keys` |
+| Wait for text or a regular expression | `pane wait-output` |
+| Start a supported agent in an existing pane | `agent start` |
+| Submit a prompt, optionally waiting for it | `agent prompt` |
+| Send keys to an agent's interactive UI | `agent send-keys` |
+| Wait for agent lifecycle state | `agent wait` |
+
+`agent prompt` submits text plus encoded Enter and honors the terminal's live bracketed-paste mode. It can prompt an agent that is already working. Use `agent send-keys` for interactions such as `esc`, `up`, `enter`, or `ctrl+c`; `escape` is accepted as an alias for `esc`. Use the pane input commands when you deliberately want raw terminal control.
+
+Pane input addresses the terminal regardless of its current occupant. Agent input resolves the live agent and rejects the operation if that agent no longer controls the pane.
+
+`agent prompt --wait` submits immediately, then waits for the first matching lifecycle state observed afterward. It does not track individual turns. If the agent is already working, completion of that active turn may satisfy the wait. To run prompts as separate turns, send the next prompt only after the previous wait returns. To steer an active turn with several messages, send those prompts without `--wait`, then use `agent wait` when you want to wait for the next settled state. Standalone `agent wait` observes the current agent and returns immediately if its status already matches. Both commands default to `idle`, `done`, or `blocked`. Repeat `--until` to accept several exact states, for example `--until idle --until done`; use `--until unknown` explicitly when needed. On `agent prompt`, `--until` requires `--wait`.
+
+`idle` means the agent is ready for input and its tab has been seen in the focused Herdr UI. `done` is the same underlying idle state after background work finishes, until that tab is focused or `pane focus` / `agent focus` targets it. Reading through the CLI does not mark it seen. `blocked` means Herdr recognized an approval or question UI. `unknown` means an agent is present but Herdr cannot classify its lifecycle confidently; it does not prove successful completion. Use exact `--until` states when that distinction matters.
+
+`pane wait-output` does not interpret agent lifecycle. It polls the selected terminal snapshot and searches it immediately, so text that was already present can match. The default source name is `recent`; matching treats that source as unwrapped recent output. `--lines` limits the searched snapshot, `--regex` uses Rust regular-expression syntax and matches one line at a time, and `--raw` keeps ANSI escape sequences while matching.
+
+At the CLI, both `pane read` and `agent read` print terminal text directly. The default is UTF-8 text with ANSI escapes stripped; use `--format ansi` or `--ansi` to preserve terminal escapes where the source exposes them. The `detection` source is always plain text. For every read source, `--lines N` returns the last N logical lines. The socket API returns the text at `.result.read.text`.
+
+Successful `agent start`, `agent prompt`, and `agent wait` commands return the current agent at `.result.agent`. `pane wait-output` returns `.result.pane_id`, `.result.matched_line`, and the matched snapshot at `.result.read`.
+
+Wait commands have no default timeout and can wait indefinitely. On timeout or another server error, CLI commands print a JSON error to stderr and exit with status 1; invalid CLI syntax exits with status 2.
+
+## Recipes
+
+Start a helper, give it work, and wait for that work to settle:
+
+```bash
+split=$(herdr pane split --current --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 120
+```
+
+Wait for an agent to ask for input, inspect it, and interact with its UI:
+
+```bash
+herdr agent wait reviewer --until blocked --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 80
+herdr agent send-keys reviewer esc
+```
+
+Run an ordinary process and wait for its output without treating it as an agent:
+
+```bash
+herdr pane run w1:p3 "just test --watch"
+herdr pane wait-output w1:p3 --regex "passed|failed" --timeout 120000
+```
+
+See the [CLI reference](/docs/cli-reference/) for the complete command and option list. Shell completions expose the same command tree interactively.
diff --git a/docs/next/website/src/content/docs/agent-skill.mdx b/docs/next/website/src/content/docs/agent-skill.mdx
index 13a90154..498861f7 100644
--- a/docs/next/website/src/content/docs/agent-skill.mdx
+++ b/docs/next/website/src/content/docs/agent-skill.mdx
@@ -58,7 +58,7 @@ This prevents an agent outside Herdr from trying to control a session it does no
## Agent-facing reference
-The full command guide lives in the skill file itself. It covers pane IDs, `pane split`, `pane run`, `pane read`, `wait output`, `wait agent-status`, workspace and tab commands, and coordination recipes.
+The full command guide lives in the skill file itself. It covers pane IDs, `pane split`, `pane run`, `pane read`, `pane wait-output`, `agent wait`, workspace and tab commands, and coordination recipes.
Read the source file here:
diff --git a/docs/next/website/src/content/docs/agents.mdx b/docs/next/website/src/content/docs/agents.mdx
index 958852fa..ee275d19 100644
--- a/docs/next/website/src/content/docs/agents.mdx
+++ b/docs/next/website/src/content/docs/agents.mdx
@@ -5,6 +5,8 @@ description: See what Herdr can detect, how agent state works, and how integrati
Herdr is built for running more than one coding agent at a time. Each agent stays in a real terminal pane with its shell, logs, prompts, and running processes intact. Herdr tracks which panes contain agents, rolls their state up to tabs and workspaces, and lets you jump straight to the pane that needs attention instead of polling every terminal by hand.
+To coordinate agents from scripts or from another agent, see [Agent automation](/docs/agent-automation/).
+
## Supported agents
Automatic detection works out of the box for common coding agents. The important difference is not whether Herdr can see an agent. It is which signal is allowed to author `idle`, `working`, and `blocked`.
@@ -110,7 +112,7 @@ herdr agent rename w1:p1 reviewer
herdr agent rename reviewer --clear
```
-Targets accept terminal IDs, unique agent names, detected or reported agent labels, and legacy pane IDs.
+Targets accept a unique live agent name or the pane ID that currently hosts the agent. Terminal IDs and bare agent-kind labels are not accepted.
## Custom status labels
@@ -131,38 +133,6 @@ herdr pane report-metadata w1:p1 \
Agent sidebar rows can also opt into `terminal_title` or `terminal_title_stripped`; neither appears in the default rows. The first shows the latest safety-normalized OSC 0/2 terminal title. The second removes one recognized leading activity or spinner glyph and following whitespace. Herdr owns these values on the server; they are ephemeral across a cold restart and remain independent of metadata titles and semantic agent state. Spinner animation can therefore update the raw title without producing a pane update when the stripped text stays the same.
-## Start agents from the CLI
-
-Use workspace, tab, pane, and layout commands to create topology first. Then activate an existing shell pane as a supported interactive agent with a unique name:
-
-```bash
-herdr pane split --current --direction right --no-focus
-herdr agent start reviewer --kind pi --pane w1:p2
-```
-
-`agent start` never creates or splits topology. Herdr chooses the canonical executable for the requested kind, labels the target pane with the unique name, and returns after the expected interactive agent is detected as idle, done, or blocked. Optional native arguments follow `--`:
-
-```bash
-herdr agent start reviewer --kind pi --pane w1:p2 -- --name scratch --no-session
-```
-
-Submit a prompt by name. `--wait` binds the wait to that prompt and returns when the agent finishes or becomes blocked:
-
-```bash
-herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
-```
-
-`agent prompt` honors the terminal's live bracketed-paste mode before sending Enter, so text such as `A != B` reaches agents without triggering input-mode keybindings. Use it for submissions; `agent send` remains a low-level literal-text operation and does not submit a turn.
-
-For an agent that is already working, `agent wait` returns when its status becomes idle, done, or blocked. It returns immediately if one of those statuses is already current.
-
-```bash
-herdr agent wait reviewer --timeout 120000
-herdr agent read reviewer --source recent-unwrapped --lines 120
-```
-
-Use `herdr pane ...` commands for ordinary terminals, servers, tests, shells, topology, and low-level terminal input.
-
## Attach directly to an agent
Attach your current terminal to one agent terminal instead of the full Herdr UI:
diff --git a/docs/next/website/src/content/docs/cli-reference.mdx b/docs/next/website/src/content/docs/cli-reference.mdx
index 4d668df9..88585b8a 100644
--- a/docs/next/website/src/content/docs/cli-reference.mdx
+++ b/docs/next/website/src/content/docs/cli-reference.mdx
@@ -130,6 +130,8 @@ Create a workspace without stealing focus:
herdr workspace create --cwd ~/project --label api --no-focus
```
+A workspace is the top-level project or work context. Creating one also creates its first tab and root pane. The JSON response exposes their IDs as `.result.workspace.workspace_id`, `.result.tab.tab_id`, and `.result.root_pane.pane_id`.
+
## Worktrees
```bash
@@ -154,6 +156,10 @@ herdr tab rename <tab_id> <label>
herdr tab close <tab_id>
```
+A tab is another terminal layout inside a workspace. Without `--workspace`, `tab create` uses the active workspace and fails if none exists. Its JSON response exposes `.result.tab.tab_id` and `.result.root_pane.pane_id`.
+
+Workspace and tab creation, and pane splitting, leave focus unchanged by default. `--focus` selects the new layout; `--no-focus` states the default explicitly. Without `--cwd`, new terminals follow the configured `terminal.new_cwd` policy, which follows the source pane or workspace by default. Each `--env KEY=VALUE` adds or replaces that variable in the new root shell.
+
## Panes
```bash
@@ -181,15 +187,19 @@ For pane commands that accept `--current`, Herdr uses the calling pane's
`HERDR_PANE_ID` when the command runs inside a Herdr pane. For `pane split`,
an explicit pane id or `--pane ID` splits that pane, `--current` splits the
calling pane, and an omitted target keeps using the UI-focused pane.
+The split response exposes the new pane ID as `.result.pane.pane_id`.
+After `pane move`, use `.result.move_result.pane.pane_id` for later commands. A cross-workspace move changes the workspace-qualified pane ID; the prior value remains at `.result.move_result.previous_pane_id`. The running process keeps its launch-time `HERDR_PANE_ID`, `HERDR_TAB_ID`, and `HERDR_WORKSPACE_ID`; Herdr retains the old pane ID as an alias for that terminal, so pane commands using `--current` still resolve it. A live agent name follows the terminal and continues to resolve after the move.
Read output:
```bash
-herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N]
+herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi] [--raw]
herdr pane read <pane_id> --source visible --ansi
herdr pane read <pane_id> --source recent-unwrapped --lines 120
```
+`pane read` prints UTF-8 terminal text directly. ANSI escapes are stripped by default; use `--format ansi` or `--ansi` to preserve them where the source exposes styling. The `detection` source is always plain text. For every source, `--lines N` returns the last N logical lines. `agent read` uses the same output and line behavior.
+
Send input:
```bash
@@ -204,6 +214,7 @@ special keys such as `enter`, `tab`, `esc`, `backspace`, `left`, `right`,
and `shift+tab`, function keys such as `f1`, and named punctuation such as
`minus`, `plus`, and `backtick`. Legacy `C-c` and `c-c` are accepted as
aliases for `ctrl+c`.
+`esc` is the canonical spelling; `escape` is also accepted.
`pane run` honors live bracketed-paste mode and submits text plus Enter atomically. Prefer it over `send-text` plus `send-keys Enter` for commands; the separate send operations remain low-level and non-submitting.
@@ -218,8 +229,23 @@ herdr pane report-agent <pane_id> \
[--seq N] \
[--agent-session-id ID] \
[--agent-session-path PATH]
+
+herdr pane report-agent-session <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N] \
+ [--agent-session-id ID] \
+ [--agent-session-path PATH] \
+ [--session-start-source SOURCE]
+
+herdr pane release-agent <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N]
```
+`report-agent-session` updates native session identity without reporting lifecycle state. `release-agent` ends that source's lifecycle authority when its agent process exits.
+
`pane get`, `pane list`, `agent get`, and `agent list` include a read-only `agent_session` object when an official integration has reported a native session reference. If no native session reference is stored, the field is omitted.
Those commands include `foreground_cwd` when Herdr can resolve the cwd of the foreground process controlling the pane. The existing `cwd` field remains the pane/workspace cwd used for labels and follow-cwd behavior.
@@ -253,26 +279,34 @@ Metadata text is normalized before storage. Herdr trims surrounding whitespace,
## Agents
+For the pane-versus-agent model and complete orchestration examples, see [Agent automation](/docs/agent-automation/).
+
```bash
herdr agent list
herdr agent get <target>
herdr agent read <target> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi]
-herdr agent send <target> <text>
-herdr agent prompt <name> <text> [--wait] [--timeout MS]
+herdr agent send-keys <target> <key> [key ...]
+herdr agent prompt <target> <text> [--wait] [--until STATUS]... [--timeout MS]
herdr agent rename <target> <name>|--clear
herdr agent focus <target>
-herdr agent wait <name> [--timeout MS]
+herdr agent wait <target> [--until STATUS]... [--timeout MS]
herdr agent attach <target> [--takeover]
herdr agent start <name> --kind KIND --pane ID [--timeout MS] [-- <agent-args...>]
herdr agent explain <target> [--json|--verbose]
herdr agent explain --file PATH --agent LABEL [--json|--verbose]
```
-Agent targets can be terminal IDs, unique agent names, detected or reported agent labels, or legacy pane IDs. Names and labels are agent identities. Terminal IDs and legacy pane IDs are low-level escape hatches.
+Agent targets are either a unique live agent name or the pane ID that currently hosts the agent. Terminal IDs and bare agent-kind labels are not agent targets. Agents started through `agent start` require a name; manually launched agents remain unnamed and use their pane ID.
+
+`agent start` activates an existing available shell pane: the pane's interactive shell must own the foreground, with no foreground command, editor, or agent running. Topology must be created separately. Names are unique among live agents and must match `[a-z][a-z0-9_-]{0,31}`. The kind selects Herdr's canonical interactive executable, while arguments after `--` are passed to that executable. Supported kinds are `pi`, `claude`, `codex`, `gemini`, `cursor`, `devin`, `agy`, `cline`, `omp`, `mastracode`, `opencode`, `copilot`, `kimi`, `kiro`, `droid`, `amp`, `grok`, `hermes`, `kilo`, `qodercli`, and `maki`. A name follows the current pane occupant and is cleared when that agent exits, is released, or is replaced. Temporary detection uncertainty does not clear it.
-`agent start` activates an existing available shell pane; topology must be created separately. The kind selects Herdr's canonical interactive executable, while arguments after `--` are passed to that executable. `agent prompt` requires a unique active agent name, honors live bracketed-paste mode, and submits text plus Enter atomically. With `--wait`, it waits for a causally later idle, done, or blocked state. Standalone `agent wait` returns immediately for idle, done, or blocked and otherwise waits while the agent is working.
+Start returns only after the expected agent owns the same terminal and is ready for interactive input. The default startup timeout is 30000 milliseconds; explicit values must be greater than 3000 and no more than 300000.
-`agent read` reads the resolved terminal stream. `agent send` writes literal text without submitting a turn; use `agent prompt` when the text must be protected from input-mode keybindings and followed by Enter. `agent get`, `agent focus`, and `agent attach` accept the broader agent target forms. `agent rename` can assign an identity to an automatically detected agent.
+`agent prompt` honors live bracketed-paste mode and submits text plus encoded Enter atomically, including while the agent is working. With `--wait`, it waits for the first matching lifecycle state observed after submission; it does not track individual turns. If the agent is already working, completion of that active turn may satisfy the wait. Send the next prompt only after the previous wait returns when you need separate turns. Send steering messages without `--wait`, then use `agent wait` when you want the next settled state. `--until` narrows the matching states and is rejected unless `--wait` is also present. Standalone `agent wait` returns immediately when the current status matches. Both default to `idle`, `done`, or `blocked`; use `--until unknown` explicitly when needed. Repeat `--until STATUS` to accept more than one exact state.
+
+`idle` means ready for input after its tab has been seen in the focused Herdr UI; `done` is the same underlying idle state after unseen background work completes. Focusing that tab or targeting it with `pane focus` / `agent focus` marks it seen; reading it through the CLI does not. `blocked` means Herdr recognized an approval or question UI. `unknown` means an agent is present but Herdr cannot classify it confidently, not that its work succeeded.
+
+`agent send-keys` sends logical terminal keys such as `enter`, `up`, `esc`, or `ctrl+c`. Herdr validates every key before writing any bytes. `agent read` reads the resolved terminal stream, and `agent rename` names an already detected agent.
`agent explain` asks the running server to classify the same bottom-buffer detection snapshot used by screen detection, so live output reflects the server's active manifest cache. Because this uses the `agent.explain` socket method, restart or hand off to an updated server after upgrading Herdr before using live explain. Use `--file PATH --agent LABEL` to explain a saved fixture locally instead. The default output shows the agent, final state, manifest source and version, matched rule with its region evidence, and any fallback, skip, or warning reasons. Add `--verbose` for visible evidence flags, cached remote version, local override shadowing, remote update status, and the full evaluated-rules list with matcher and region evidence. Add `--json` for issue reports or tests.
@@ -302,21 +336,19 @@ the server closes the stream. Multiple observers can watch the same terminal
without taking input, resize, scroll, or takeover authority.
`terminal title clear` restores Herdr's default outer terminal window title.
-## Waits
+## Output waits
Wait for output in a pane:
```bash
-herdr wait output <pane_id> --match <text> [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--regex] [--raw]
+herdr pane wait-output <pane_id> (--match <text> | --regex <pattern>) [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--raw]
```
-Wait for pane agent state:
+Use `pane wait-output` for normal commands and servers. Use `agent wait` for coding agents.
-```bash
-herdr wait agent-status <pane_id> --status <idle|working|blocked|done|unknown> [--timeout MS]
-```
+`pane wait-output` checks the selected snapshot immediately, including output that already exists, then polls until it matches. The default source name is `recent`; matching treats it as unwrapped recent output with no line limit. `--match` finds a literal substring on one line; `--regex` uses Rust regular-expression syntax and also matches one line at a time. `--raw` keeps ANSI escape sequences instead of stripping them.
-Use `wait output` for normal commands and servers. Use `wait agent-status` for coding agents.
+`pane wait-output`, `agent wait`, and `agent prompt --wait` wait indefinitely when `--timeout` is omitted. A timeout or server error is emitted as JSON on stderr with exit status 1. CLI usage errors exit with status 2.
## Integrations
@@ -434,6 +466,8 @@ in pane or agent APIs. Native non-terminal plugin panes are a later surface.
| `recent-unwrapped` | Recent scrollback without soft wrapping. Best for logs. |
| `detection` | Bottom-buffer snapshot used by agent screen detection. |
+These meanings apply to reads. For `pane wait-output` only, both `recent` and `recent-unwrapped` search the unwrapped recent snapshot; `recent` remains the default spelling.
+
## Environment variables
| Variable | Purpose |
diff --git a/docs/next/website/src/content/docs/ja/agent-automation.mdx b/docs/next/website/src/content/docs/ja/agent-automation.mdx
new file mode 100644
index 00000000..cd335fb6
--- /dev/null
+++ b/docs/next/website/src/content/docs/ja/agent-automation.mdx
@@ -0,0 +1,122 @@
+---
+title: エージェント自動化
+description: Herdr のレイアウト、ペイン、エージェントの各プリミティブを使い、スクリプトや別のエージェントからコーディングエージェントを連携させます。
+---
+
+Herdr はコーディングエージェントの自動化レイヤーとして使えます。スクリプトから制御することも、ひとつのエージェントから別のエージェントへ作業を渡し、状態を確認して結果を集めることもできます。重要なのは、目的に合うプリミティブを選ぶことです。
+
+## 3 つのプリミティブ
+
+| プリミティブ | 責務 |
+| --- | --- |
+| レイアウト(`workspace`、`tab`、ペイン構成) | ターミナルの場所を作成し、整理する。 |
+| ペイン | 生のターミナルを制御する。コマンド実行、入力送信、出力読み取り、出力待機を行う。 |
+| エージェント | 認識済みコーディングエージェントを、名前またはペインとライフサイクル状態に基づいて制御する。 |
+
+ペインは、エージェントが入っていなくても存在します。エージェントは、ペイン内で現在実行されていると Herdr が認識したプロセスです。そのため `agent start` には既存のシェルペインが必要で、レイアウトの作成、分割、移動は行いません。
+
+ワークスペースを作成すると最初のタブとルートペインも作られ、タブを作成するとそのルートペインも作られます。最初のプロセスには返されたペイン ID を使い、そのレイアウトに別のターミナルが必要なときだけ分割します。
+
+作成コマンドは JSON を出力します。ID を推測せず、レスポンスから取得してください:
+
+```bash
+created=$(herdr workspace create --cwd ~/project --label api --no-focus)
+pane_id=$(printf '%s\n' "$created" | jq -r '.result.root_pane.pane_id')
+
+split=$(herdr pane split "$pane_id" --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+```
+
+`workspace create` は `.result.workspace`、`.result.tab`、`.result.root_pane` を返します。`tab create` は `.result.tab` と `.result.root_pane` を返し、`pane split` は新しいペインを `.result.pane` として返します。
+
+ペインを別のワークスペースへ移動すると、ワークスペース修飾付きのペイン ID が変わります。`pane move` の後は `.result.move_result.pane.pane_id` を使い、以前の値が必要なら `.result.move_result.previous_pane_id` を参照してください。実行中プロセスは起動時の Herdr 環境を保ちますが、以前の `HERDR_PANE_ID` はそのターミナルの別名として残るため、`--current` は引き続き安全に使えます。移動後に始めるコマンドはエージェント名で解決できますが、すでに進行中の待機は `agent_not_running` で終了します。
+
+シェル、テスト、サーバー、CI ウォッチャーなどの通常のターミナルプロセスにはペインコマンドを使います。どのエージェントが動いているか、または状態が `working`、`blocked`、`done`、`idle`、`unknown` のどれかを Herdr に判断させる場合はエージェントコマンドを使います。
+
+## エージェントの識別子と起動
+
+`w1:p2` のようなペイン ID はターミナルの場所を識別します。`reviewer` のようなエージェント名は、そのペインに現在いるエージェントの扱いやすい別名です。名前は `[a-z][a-z0-9_-]{0,31}` に一致し、ライブエージェント間で一意でなければなりません。エージェントが終了、解放、または置換されると別名は消えます。ペイン自体の恒久的な名前ではありません。
+
+エージェントコマンドは、一意なライブ名、または現在そのエージェントをホストしているペイン ID のどちらでも指定できます。
+
+利用可能なシェルペインとは、対話シェルのプロンプトに戻っており、フォアグラウンドをシェル自身が所有し、フォアグラウンドのコマンド、エディタ、エージェントが動いていないペインです。`agent start` の前にプロンプトへ戻してください。
+
+`--kind` は対応済みエージェントとその標準実行ファイルを選びます。対応する kind は `pi`、`claude`、`codex`、`gemini`、`cursor`、`devin`、`agy`、`cline`、`omp`、`mastracode`、`opencode`、`copilot`、`kimi`、`kiro`、`droid`、`amp`、`grok`、`hermes`、`kilo`、`qodercli`、`maki` です。`--` より後の引数は、その実行ファイルへそのまま渡されます。
+
+`agent start` は、同じターミナルで期待したエージェントを検出し、対話入力の準備ができたと Herdr が判断してから返ります。起動待機はデフォルトで 30 秒です。`--timeout` は 3000 より大きく 300000 以下のミリ秒で指定します。
+
+```bash
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+```
+
+固定 ID を使う同等の例:
+
+```bash
+herdr pane split --current --direction right --no-focus
+herdr agent start reviewer --kind codex --pane w1:p2 -- -m gpt-5.4
+```
+
+手動で起動したエージェントも自動検出され、ペイン ID で指定できます。人が読みやすい安定した対象名が必要なら名前を付けます:
+
+```bash
+herdr agent get w1:p2
+herdr agent rename w1:p2 reviewer
+```
+
+## 操作面を選ぶ
+
+| 目的 | コマンド |
+| --- | --- |
+| シェルコマンドを実行して送信する | `pane run` |
+| Enter を付けずに文字列を送る | `pane send-text` |
+| ターミナルキーや修飾キーの組み合わせを送る | `pane send-keys` |
+| 文字列や正規表現を待つ | `pane wait-output` |
+| 既存のペインで対応済みエージェントを起動する | `agent start` |
+| プロンプトを送信し、必要なら完了を待つ | `agent prompt` |
+| エージェントの対話 UI にキーを送る | `agent send-keys` |
+| エージェントのライフサイクル状態を待つ | `agent wait` |
+
+`agent prompt` は文字列とエンコード済み Enter を送信し、ターミナルの現在の bracketed paste モードを尊重します。working 中のエージェントにも送信できます。`esc`、`up`、`enter`、`ctrl+c` のような操作には `agent send-keys` を使います。`escape` も `esc` のエイリアスとして使えます。意図的に生のターミナルを操作したい場合は、ペイン入力コマンドを使ってください。
+
+ペイン入力は、現在のプロセスに関係なくターミナルを指定します。エージェント入力はライブエージェントを解決し、そのエージェントがペインを制御しなくなっていれば操作を拒否します。
+
+`agent prompt --wait` はプロンプトをすぐ送信し、その後に最初に観測された一致ライフサイクル状態を待ちます。個々のターンは追跡しません。エージェントがすでに working の場合、進行中ターンの完了が待機を満たすことがあります。別々のターンとして実行するには、前の待機が返ってから次のプロンプトを送信します。進行中ターンを複数のメッセージで操作する場合は `--wait` なしで送信し、次の安定状態を待つときに `agent wait` を使います。単独の `agent wait` は現在のエージェントを監視し、すでに状態が一致していれば即座に返ります。どちらもデフォルトでは `idle`、`done`、`blocked` を待ちます。複数の正確な状態を許可するには、`--until idle --until done` のように `--until` を繰り返します。`unknown` が必要な場合は `--until unknown` を明示してください。`agent prompt` では `--until` に `--wait` が必要です。
+
+`idle` は、エージェントが入力待ちで、そのタブがフォーカス中の Herdr UI ですでに表示済みであることを示します。`done` は同じ基礎的な idle 状態ですが、バックグラウンド作業が完了してから、そのタブをフォーカスするか `pane focus` / `agent focus` で対象にするまで使われます。CLI で読み取るだけでは表示済みになりません。`blocked` は承認または質問 UI を Herdr が認識した状態です。`unknown` はエージェントが存在するもののライフサイクルを確実に分類できない状態で、成功完了を意味しません。違いが重要なら正確な `--until` を指定してください。
+
+`pane wait-output` はエージェントのライフサイクルを解釈しません。選択したターミナルスナップショットをポーリングし、最初にすぐ検索するため、すでに存在する文字列も一致します。デフォルトのソース名は `recent` で、マッチング時は recent の折り返し前の出力として扱われます。`--lines` は検索範囲を制限し、`--regex` は Rust の正規表現構文で 1 行ずつ一致し、`--raw` は ANSI エスケープシーケンスを残して検索します。
+
+CLI では、`pane read` と `agent read` のどちらもターミナルテキストを直接出力します。デフォルトは ANSI エスケープを除去した UTF-8 テキストです。ソースに装飾が含まれる場合、`--format ansi` または `--ansi` でエスケープを残します。`detection` ソースは常にプレーンテキストです。すべての read ソースで、`--lines N` は末尾の N 論理行を返します。socket API ではテキストを `.result.read.text` に返します。
+
+成功した `agent start`、`agent prompt`、`agent wait` は現在のエージェントを `.result.agent` に返します。`pane wait-output` は `.result.pane_id`、`.result.matched_line`、一致したスナップショット `.result.read` を返します。
+
+wait コマンドにはデフォルトのタイムアウトがなく、無期限に待機できます。タイムアウトやサーバーエラーでは JSON エラーを stderr に出して終了コード 1、CLI 構文エラーでは終了コード 2 を返します。
+
+## レシピ
+
+補助エージェントを起動して作業を渡し、その作業が落ち着くまで待ちます:
+
+```bash
+split=$(herdr pane split --current --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 120
+```
+
+エージェントが入力を求めるまで待ち、内容を確認して対話 UI を操作します:
+
+```bash
+herdr agent wait reviewer --until blocked --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 80
+herdr agent send-keys reviewer esc
+```
+
+通常のプロセスを実行し、エージェントとして扱わずに出力を待ちます:
+
+```bash
+herdr pane run w1:p3 "just test --watch"
+herdr pane wait-output w1:p3 --regex "passed|failed" --timeout 120000
+```
+
+コマンドとオプションの完全な一覧は [CLI リファレンス](/ja/docs/cli-reference/) を参照してください。シェル補完でも同じコマンドツリーを対話的に確認できます。
diff --git a/docs/next/website/src/content/docs/ja/agent-skill.mdx b/docs/next/website/src/content/docs/ja/agent-skill.mdx
index 1fc6405d..97d109f7 100644
--- a/docs/next/website/src/content/docs/ja/agent-skill.mdx
+++ b/docs/next/website/src/content/docs/ja/agent-skill.mdx
@@ -58,7 +58,7 @@ claude
## エージェント向けリファレンス
-コマンドの完全なガイドはスキルファイル自体にあります。ペイン ID、`pane split`、`pane run`、`pane read`、`wait output`、`wait agent-status`、ワークスペースとタブのコマンド、協調動作のレシピを扱っています。
+コマンドの完全なガイドはスキルファイル自体にあります。ペイン ID、`pane split`、`pane run`、`pane read`、`pane wait-output`、`agent wait`、ワークスペースとタブのコマンド、協調動作のレシピを扱っています。
ソースファイルはこちら:
diff --git a/docs/next/website/src/content/docs/ja/agents.mdx b/docs/next/website/src/content/docs/ja/agents.mdx
index 14f61d03..4b08da69 100644
--- a/docs/next/website/src/content/docs/ja/agents.mdx
+++ b/docs/next/website/src/content/docs/ja/agents.mdx
@@ -5,6 +5,8 @@ description: Herdr が何を検出できるか、エージェント状態の仕ç
Herdr は複数のコーディングエージェントを同時に動かすために作られています。各エージェントは、シェル、ログ、プロンプト、実行中プロセスをそのまま保った実際のターミナルペインの中にいます。Herdr はどのペインにエージェントがいるかを追跡し、その状態をタブとワークスペースに集約し、すべてのターミナルを手作業で見回る代わりに、注意が必要なペインへ直接ジャンプできるようにします。
+スクリプトや別のエージェントから連携させる方法は、[エージェント自動化](/ja/docs/agent-automation/) を参照してください。
+
## 対応エージェント
一般的なコーディングエージェントは、追加設定なしで自動検出されます。重要な違いは Herdr がエージェントを見えるかどうかではありません。どのシグナルが `idle`、`working`、`blocked` を決定する権限を持つかです。
@@ -110,7 +112,7 @@ herdr agent rename w1:p1 reviewer
herdr agent rename reviewer --clear
```
-ターゲットにはターミナル ID、一意なエージェント名、検出または報告されたエージェントラベル、レガシーなペイン ID が使えます。
+ターゲットには一意なライブエージェント名、または現在そのエージェントをホストしているペイン ID を使います。ターミナル ID とエージェント kind のラベルだけでは指定できません。
## カスタムステータスラベル
@@ -131,38 +133,6 @@ herdr pane report-metadata w1:p1 \
エージェントサイドバー行では、`terminal_title` または `terminal_title_stripped` も任意で使えます。どちらもデフォルト行には含まれません。前者は安全性のために正規化された最新の OSC 0/2 ターミナルタイトルを表示し、後者は先頭にある認識済みのアクティビティまたはスピナーのグリフ 1 つと、それに続く空白を除去します。これらの値は Herdr サーバーが所有し、コールドリスタートをまたいで保持されません。また、メタデータのタイトルや意味的なエージェント状態から独立しています。そのため、除去後のテキストが同じなら、スピナーのアニメーションで生のタイトルが変わってもペイン更新は発行されません。
-## CLI からエージェントを起動する
-
-まずワークスペース、タブ、ペイン、レイアウトの各コマンドでトポロジーを作成します。次に、既存のシェルペインを一意な名前を持つ対応済み対話型エージェントとして起動します:
-
-```bash
-herdr pane split --current --direction right --no-focus
-herdr agent start reviewer --kind pi --pane w1:p2
-```
-
-`agent start` はトポロジーを作成も分割もしません。要求された kind に対応する標準実行ファイルを Herdr が選び、対象ペインに一意な名前を付け、対話型エージェントが idle、done、または blocked として検出されるまで待ちます。ネイティブ引数は `--` の後に指定できます:
-
-```bash
-herdr agent start reviewer --kind pi --pane w1:p2 -- --name scratch --no-session
-```
-
-名前でプロンプトを送信します。`--wait` はそのプロンプトに待機を結び付け、エージェントが完了または blocked になると返ります:
-
-```bash
-herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
-```
-
-`agent prompt` は Enter を送る前にターミナルの現在の bracketed paste モードを尊重するため、`A != B` のようなテキストも入力モードのキーバインドを発火させずにエージェントへ届きます。送信にはこれを使ってください。`agent send` は低レベルのリテラルテキスト操作のままで、ターンを送信しません。
-
-すでに working のエージェントには `agent wait` を使います。状態が idle、done、または blocked になると返り、すでにその状態なら即座に返ります。
-
-```bash
-herdr agent wait reviewer --timeout 120000
-herdr agent read reviewer --source recent-unwrapped --lines 120
-```
-
-通常のターミナル、サーバー、テスト、シェル、トポロジー、低レベルなターミナル入力には `herdr pane ...` コマンドを使ってください。
-
## エージェントに直接アタッチする
完全な Herdr UI ではなく、ひとつのエージェントターミナルに現在のターミナルをアタッチします:
diff --git a/docs/next/website/src/content/docs/ja/cli-reference.mdx b/docs/next/website/src/content/docs/ja/cli-reference.mdx
index dfa82472..7edfab23 100644
--- a/docs/next/website/src/content/docs/ja/cli-reference.mdx
+++ b/docs/next/website/src/content/docs/ja/cli-reference.mdx
@@ -126,6 +126,8 @@ herdr workspace close <workspace_id>
herdr workspace create --cwd ~/project --label api --no-focus
```
+ワークスペースは最上位のプロジェクトまたは作業コンテキストです。作成時に最初のタブとルートペインも作られます。JSON レスポンスの `.result.workspace.workspace_id`、`.result.tab.tab_id`、`.result.root_pane.pane_id` から各 ID を取得できます。
+
## Worktree
```bash
@@ -150,6 +152,10 @@ herdr tab rename <tab_id> <label>
herdr tab close <tab_id>
```
+タブはワークスペース内の別のターミナルレイアウトです。`--workspace` を省略すると、`tab create` はアクティブなワークスペースを使い、存在しなければ失敗します。JSON レスポンスの `.result.tab.tab_id` と `.result.root_pane.pane_id` から ID を取得できます。
+
+ワークスペースとタブの作成、およびペインの分割は、デフォルトではフォーカスを変えません。`--focus` は新しいレイアウトを選択し、`--no-focus` はデフォルトを明示します。`--cwd` がない場合、新しいターミナルは `terminal.new_cwd` の設定に従い、デフォルトでは元のペインまたはワークスペースを引き継ぎます。各 `--env KEY=VALUE` は新しいルートシェルの環境変数を追加または置換します。
+
## ペイン
```bash
@@ -173,14 +179,20 @@ herdr pane move <pane_id> --new-workspace [--label TEXT] [--tab-label TEXT] [--f
herdr pane close <pane_id>
```
+`--current` を受け付けるペインコマンドは、Herdr ペイン内から実行した場合、呼び出し元の `HERDR_PANE_ID` を使います。`pane split` では、明示したペイン ID または `--pane ID` がそのペインを、`--current` が呼び出し元ペインを分割します。対象を省略すると UI でフォーカス中のペインを使います。分割レスポンスでは、新しいペイン ID は `.result.pane.pane_id` にあります。
+
+`pane move` の後続コマンドには `.result.move_result.pane.pane_id` を使います。別ワークスペースへの移動ではワークスペース修飾付きのペイン ID が変わり、以前の値は `.result.move_result.previous_pane_id` に残ります。実行中プロセスの `HERDR_PANE_ID`、`HERDR_TAB_ID`、`HERDR_WORKSPACE_ID` は起動時の値のままですが、Herdr は以前のペイン ID をそのターミナルの別名として保持するため、`--current` を使うペインコマンドは引き続き解決できます。ライブエージェント名もターミナルに追従します。
+
出力を読む:
```bash
-herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N]
+herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi] [--raw]
herdr pane read <pane_id> --source visible --ansi
herdr pane read <pane_id> --source recent-unwrapped --lines 120
```
+`pane read` は UTF-8 のターミナルテキストを直接出力します。デフォルトでは ANSI エスケープを除去し、ソースに装飾が含まれる場合は `--format ansi` または `--ansi` で保持します。`detection` ソースは常にプレーンテキストです。すべてのソースで `--lines N` は末尾の N 論理行を返します。`agent read` も同じ出力と行数の動作です。
+
入力を送る:
```bash
@@ -191,6 +203,8 @@ herdr pane run <pane_id> <command>
`<key>` は Herdr のキーコンボ構文を使います: `a` のような通常の印字可能キー、`enter`、`tab`、`esc`、`backspace`、`left`、`right`、`up`、`down` のような特殊キー、`ctrl+h`、`control+j`、`alt+x`、`shift+tab` のような修飾キーコード、`f1` のようなファンクションキー、そして `minus`、`plus`、`backtick` のような名前付き記号です。レガシーな `C-c` と `c-c` は `ctrl+c` のエイリアスとして受け付けられます。
+標準表記は `esc` ですが、`escape` も使えます。
+
`pane run` は現在の bracketed paste モードを尊重し、テキストと Enter をアトミックに送信します。コマンドには `send-text` + `send-keys Enter` よりこちらを使ってください。個別の送信操作は低レベルのままで、コマンドを送信しません。
カスタムフックからエージェント状態を報告する:
@@ -204,8 +218,23 @@ herdr pane report-agent <pane_id> \
[--seq N] \
[--agent-session-id ID] \
[--agent-session-path PATH]
+
+herdr pane report-agent-session <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N] \
+ [--agent-session-id ID] \
+ [--agent-session-path PATH] \
+ [--session-start-source SOURCE]
+
+herdr pane release-agent <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N]
```
+`report-agent-session` はライフサイクル状態を報告せずにネイティブセッション識別子を更新します。`release-agent` は、そのエージェントプロセスが終了したときに、そのソースのライフサイクル権限を終了します。
+
公式インテグレーションがネイティブセッション参照を報告している場合、`pane get`、`pane list`、`agent get`、`agent list` は読み取り専用の `agent_session` オブジェクトを含みます。ネイティブセッション参照が保存されていない場合、このフィールドは省略されます。
これらのコマンドは、ペインを制御しているフォアグラウンドプロセスの cwd を解決できる場合に `foreground_cwd` を含みます。既存の `cwd` フィールドは、ラベルと follow-cwd 挙動に使われるペイン/ワークスペースの cwd のままです。
@@ -237,26 +266,34 @@ herdr pane report-metadata <pane_id> \
## エージェント
+ペインとエージェントの使い分けや一連の連携例は、[エージェント自動化](/ja/docs/agent-automation/) を参照してください。
+
```bash
herdr agent list
herdr agent get <target>
herdr agent read <target> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi]
-herdr agent send <target> <text>
-herdr agent prompt <name> <text> [--wait] [--timeout MS]
+herdr agent send-keys <target> <key> [key ...]
+herdr agent prompt <target> <text> [--wait] [--until STATUS]... [--timeout MS]
herdr agent rename <target> <name>|--clear
herdr agent focus <target>
-herdr agent wait <name> [--timeout MS]
+herdr agent wait <target> [--until STATUS]... [--timeout MS]
herdr agent attach <target> [--takeover]
herdr agent start <name> --kind KIND --pane ID [--timeout MS] [-- <agent-args...>]
herdr agent explain <target> [--json|--verbose]
herdr agent explain --file PATH --agent LABEL [--json|--verbose]
```
-エージェントターゲットには、ターミナル ID、一意なエージェント名、検出または報告されたエージェントラベル、レガシーなペイン ID が使えます。名前とラベルはエージェントのアイデンティティです。ターミナル ID とレガシーペイン ID は低レベルな逃げ道です。
+エージェントターゲットは、一意なライブエージェント名、または現在そのエージェントをホストしているペイン ID です。ターミナル ID とエージェント kind のラベルだけでは指定できません。`agent start` で起動するエージェントには名前が必須で、手動で起動したエージェントは名前なしのままペイン ID で指定します。
+
+`agent start` は既存の利用可能なシェルペインを起動対象にします。対話シェル自身がフォアグラウンドを所有し、フォアグラウンドのコマンド、エディタ、エージェントが動いていない必要があります。トポロジーは別に作成します。名前はライブエージェント間で一意で、`[a-z][a-z0-9_-]{0,31}` に一致する必要があります。対応する kind は `pi`、`claude`、`codex`、`gemini`、`cursor`、`devin`、`agy`、`cline`、`omp`、`mastracode`、`opencode`、`copilot`、`kimi`、`kiro`、`droid`、`amp`、`grok`、`hermes`、`kilo`、`qodercli`、`maki` です。名前は現在のペイン占有者に属し、そのエージェントの終了、release、置換で消えます。一時的に検出できないだけでは消えません。
-`agent start` は既存の利用可能なシェルペインを起動対象にし、トポロジーは別に作成します。kind は Herdr の標準対話型実行ファイルを選び、`--` 以降の引数はその実行ファイルへ渡されます。`agent prompt` は一意なアクティブエージェント名を要求し、現在の bracketed paste モードを尊重してテキストと Enter をアトミックに送信します。`--wait` を付けると、その送信より後の idle、done、または blocked 状態まで待ちます。単独の `agent wait` は idle、done、blocked なら即座に返り、それ以外では working の間だけ待ちます。
+start は、期待したエージェントが同じターミナルを所有し、対話入力の準備ができてから返ります。デフォルトの起動タイムアウトは 30000 ミリ秒で、明示する値は 3000 より大きく 300000 以下でなければなりません。
-`agent read` は解決されたターミナルストリームを読みます。`agent send` はターンを送信せずにリテラルテキストを書き込みます。テキストを入力モードのキーバインドから保護して Enter と一緒に送る場合は `agent prompt` を使ってください。`agent get`、`agent focus`、`agent attach` はより広いターゲット形式を受け付けます。`agent rename` は自動検出されたエージェントに名前を割り当てられます。
+`agent prompt` は現在の bracketed paste モードを尊重し、working 中でもテキストとエンコード済み Enter をアトミックに送信します。`--wait` は送信後に最初に観測された一致ライフサイクル状態を待ち、個々のターンは追跡しません。すでに working の場合、進行中ターンの完了が待機を満たすことがあります。別々のターンが必要なら、前の待機が返ってから次を送信します。進行中ターンへの追加メッセージは `--wait` なしで送り、次の安定状態を待つときに `agent wait` を使います。`--until` は一致状態を絞り込み、`--wait` なしでは拒否されます。単独の `agent wait` は現在の状態が一致すれば即座に返ります。どちらもデフォルトは `idle`、`done`、`blocked` です。`unknown` が必要な場合は `--until unknown` を明示してください。複数の正確な状態を許可するには `--until STATUS` を繰り返します。
+
+`idle` は入力待ちで、そのタブがフォーカス中の Herdr UI ですでに表示済みの状態です。`done` は同じ基礎的な idle 状態ですが、表示していないバックグラウンド作業が完了したときに使われます。そのタブをフォーカスするか `pane focus` / `agent focus` で対象にすると表示済みになりますが、CLI で読み取るだけでは変わりません。`blocked` は承認または質問 UI を Herdr が認識した状態です。`unknown` はエージェントが存在するものの確実に分類できない状態で、作業の成功を意味しません。
+
+`agent send-keys` は `enter`、`up`、`esc`、`ctrl+c` などの論理キーを送ります。Herdr は 1 バイトも書き込む前に全キーを検証します。`agent read` は解決されたターミナルストリームを読み、`agent rename` は検出済みエージェントに名前を付けます。
`agent explain` は、スクリーン検出が使うのと同じ下部バッファの検出スナップショットの分類を実行中のサーバーに依頼します。そのためライブの出力はサーバーのアクティブなマニフェストキャッシュを反映します。これは `agent.explain` ソケットメソッドを使うので、Herdr のアップグレード後にライブ explain を使う前に、サーバーを再起動するか更新済みサーバーへハンドオフしてください。保存済みフィクスチャをローカルで説明するには `--file PATH --agent LABEL` を使います。デフォルトの出力には、エージェント、最終状態、マニフェストのソースとバージョン、リージョンの証拠付きでマッチしたルール、そしてフォールバック・スキップ・警告の理由が表示されます。`--verbose` を付けると、可視の証拠フラグ、キャッシュされたリモートバージョン、ローカルオーバーライドのシャドーイング、リモート更新状況、マッチャーとリージョンの証拠付きの評価済みルール全リストが表示されます。issue の報告やテストには `--json` を付けてください。
@@ -273,21 +310,19 @@ herdr terminal title clear
ダイレクトアタッチからは `ctrl+b q` でデタッチします。リテラルの `ctrl+b` は `ctrl+b ctrl+b` で送ります。
`terminal title clear` は Herdr のデフォルトの外側ターミナルウィンドウタイトルを復元します。
-## Wait
+## 出力待機
ペインの出力を待つ:
```bash
-herdr wait output <pane_id> --match <text> [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--regex] [--raw]
+herdr pane wait-output <pane_id> (--match <text> | --regex <pattern>) [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--raw]
```
-ペインのエージェント状態を待つ:
+通常のコマンドやサーバーには `pane wait-output` を使います。コーディングエージェントには `agent wait` を使います。
-```bash
-herdr wait agent-status <pane_id> --status <idle|working|blocked|done|unknown> [--timeout MS]
-```
+`pane wait-output` は選択したスナップショットを最初にすぐ検索するため、すでに存在する出力も一致します。デフォルトのソース名は `recent` で、マッチング時は行数制限なしの recent 折り返し前出力として扱われます。`--match` は 1 行内のリテラル部分文字列を検索し、`--regex` は Rust の正規表現構文で 1 行ずつ一致します。`--raw` は ANSI エスケープシーケンスを除去しません。
-通常のコマンドやサーバーには `wait output` を使います。コーディングエージェントには `wait agent-status` を使います。
+`pane wait-output`、`agent wait`、`agent prompt --wait` は、`--timeout` を省略すると無期限に待ちます。タイムアウトまたはサーバーエラーは JSON として stderr に出力され、終了コード 1 になります。CLI 使用法のエラーは終了コード 2 です。
## インテグレーション
@@ -392,6 +427,8 @@ herdr plugin pane close <pane_id>
| `recent-unwrapped` | ソフト折り返しなしの直近のスクロールバック。ログに最適。 |
| `detection` | エージェントのスクリーン検出が使う下部バッファのスナップショット。 |
+この表は読み取り時の意味です。`pane wait-output` に限り、`recent` と `recent-unwrapped` はどちらも recent の折り返し前スナップショットを検索し、デフォルト表記は `recent` です。
+
## 環境変数
| 変数 | 目的 |
diff --git a/docs/next/website/src/content/docs/ja/socket-api.mdx b/docs/next/website/src/content/docs/ja/socket-api.mdx
index be2ad285..b1a2f201 100644
--- a/docs/next/website/src/content/docs/ja/socket-api.mdx
+++ b/docs/next/website/src/content/docs/ja/socket-api.mdx
@@ -77,7 +77,7 @@ herdr pane split w1:p1 --direction right --ratio 0.333
エージェントを待つ:
```bash
-herdr wait agent-status w1:p1 --status done
+herdr agent wait w1:p1 --until done
```
ペインの出力を読む:
@@ -102,12 +102,12 @@ herdr pane read w1:p2 --source recent --lines 50
| ペイン | `pane.split`、`pane.swap`、`pane.move`、`pane.zoom`、`pane.layout`、`pane.process_info`、`pane.neighbor`、`pane.edges`、`pane.focus_direction`、`pane.resize`、`pane.list`、`pane.current`、`pane.get`、`pane.rename`、`pane.send_text`、`pane.send_keys`、`pane.send_input`、`pane.read`、`pane.graphics.info`、`pane.graphics.set`、`pane.graphics.clear`、`pane.graphics.stream`、`pane.report_agent`、`pane.report_agent_session`、`pane.report_metadata`、`pane.clear_agent_authority`、`pane.release_agent`、`pane.close`、`pane.wait_for_output` |
| ポップアップ | `popup.close` |
| レイアウト | `layout.export`、`layout.apply`、`layout.set_split_ratio` |
-| エージェント | `agent.list`、`agent.get`、`agent.read`、`agent.explain`、`agent.send`、`agent.prompt`、`agent.rename`、`agent.focus`、`agent.start` |
+| エージェント | `agent.list`、`agent.get`、`agent.read`、`agent.explain`、`agent.send_keys`、`agent.prompt`、`agent.wait`、`agent.rename`、`agent.focus`、`agent.start` |
| イベント | `events.subscribe`、`events.wait` |
| インテグレーション | `integration.install`、`integration.uninstall` |
| プラグイン | `plugin.link`、`plugin.list`、`plugin.unlink`、`plugin.enable`、`plugin.disable`、`plugin.action.list`、`plugin.action.invoke`、`plugin.log.list`、`plugin.pane.open`、`plugin.pane.focus`、`plugin.pane.close` |
-一部の CLI コマンドは、これらのメソッドの便利ラッパーです。たとえば `herdr agent wait` は、エージェントターゲットを解決してからペインのエージェント状態イベントを購読します。
+`agent.wait` はサーバー所有でイベント駆動です。解決したペイン占有者に固定されるため、置換されたエージェントが待機を満たすことはありません。`agent.prompt` は `until` と `timeout_ms` を持つ省略可能な `wait` オブジェクトを受け付けます。これにより、プロンプト送信と待機開始を 1 つのリクエストで行い、別々の呼び出し間の競合を避けられます。
`session.snapshot` は、独自のローカルランタイムキャッシュを持つクライアント向けに、一度限りのブートストラップスナップショットを返します。レスポンスには、バージョン/プロトコルメタデータ、フォーカス中のワークスペース/タブ/ペイン id、ワークスペース、タブ、ペイン、タブレイアウト、エージェントの各レコードが含まれます。これは購読ではありません。取得後はリソースイベントを購読し、そのイベントでローカルキャッシュを更新してください。再接続後やキャッシュが古い可能性がある場合は、`session.snapshot` を再度呼び出します。ワークスペースレコードには、関連付けられた worktree の出自情報も含まれます。リポジトリ全体の worktree 検出には引き続き `worktree.list` を使います。
@@ -589,8 +589,8 @@ herdr pane read w1:p1 --source detection
エージェントとスクリプトの協調には wait を使います。
```bash
-herdr wait agent-status w1:p1 --status done
-herdr wait agent-status w1:p1 --status blocked
+herdr agent wait w1:p1 --until done
+herdr agent wait w1:p1 --until blocked
```
エージェントの wait は、任意のコマンドの完了ではなく意味的な状態を観測します。
diff --git a/docs/next/website/src/content/docs/socket-api.mdx b/docs/next/website/src/content/docs/socket-api.mdx
index 82778d5b..66072d3c 100644
--- a/docs/next/website/src/content/docs/socket-api.mdx
+++ b/docs/next/website/src/content/docs/socket-api.mdx
@@ -81,7 +81,7 @@ herdr pane split w1:p1 --direction right --ratio 0.333
Wait for an agent:
```bash
-herdr wait agent-status w1:p1 --status done
+herdr agent wait w1:p1 --until done
```
Read pane output:
@@ -106,12 +106,12 @@ Raw socket method names use dot notation:
| Pane | `pane.split`, `pane.swap`, `pane.move`, `pane.zoom`, `pane.layout`, `pane.process_info`, `pane.neighbor`, `pane.edges`, `pane.focus_direction`, `pane.resize`, `pane.list`, `pane.current`, `pane.get`, `pane.rename`, `pane.send_text`, `pane.send_keys`, `pane.send_input`, `pane.read`, `pane.graphics.info`, `pane.graphics.set`, `pane.graphics.clear`, `pane.graphics.stream`, `pane.report_agent`, `pane.report_agent_session`, `pane.report_metadata`, `pane.clear_agent_authority`, `pane.release_agent`, `pane.close`, `pane.wait_for_output` |
| Popup | `popup.close` |
| Layout | `layout.export`, `layout.apply`, `layout.set_split_ratio` |
-| Agent | `agent.list`, `agent.get`, `agent.read`, `agent.explain`, `agent.send`, `agent.prompt`, `agent.rename`, `agent.focus`, `agent.start` |
+| Agent | `agent.list`, `agent.get`, `agent.read`, `agent.explain`, `agent.send_keys`, `agent.prompt`, `agent.wait`, `agent.rename`, `agent.focus`, `agent.start` |
| Events | `events.subscribe`, `events.wait` |
| Integrations | `integration.install`, `integration.uninstall` |
| Plugins | `plugin.link`, `plugin.list`, `plugin.unlink`, `plugin.enable`, `plugin.disable`, `plugin.action.list`, `plugin.action.invoke`, `plugin.log.list`, `plugin.pane.open`, `plugin.pane.focus`, `plugin.pane.close` |
-Some CLI commands are conveniences around these methods. For example, `herdr agent wait` resolves an agent target and then subscribes to pane agent state events.
+`agent.wait` is server-owned and event-driven. It pins the resolved pane occupant so a replacement cannot satisfy the wait. `agent.prompt` accepts an optional `wait` object with `until` and `timeout_ms`; this submits the prompt and starts the wait in one request, avoiding a race between separate calls.
`session.snapshot` returns a one-time bootstrap snapshot for clients that keep
their own local runtime cache. The response includes version/protocol metadata,
@@ -721,8 +721,8 @@ herdr pane read w1:p1 --source detection
Use waits to coordinate agents and scripts.
```bash
-herdr wait agent-status w1:p1 --status done
-herdr wait agent-status w1:p1 --status blocked
+herdr agent wait w1:p1 --until done
+herdr agent wait w1:p1 --until blocked
```
Agent waits observe semantic state, not arbitrary command completion.
diff --git a/docs/next/website/src/content/docs/zh-cn/agent-automation.mdx b/docs/next/website/src/content/docs/zh-cn/agent-automation.mdx
new file mode 100644
index 00000000..b25aadf0
--- /dev/null
+++ b/docs/next/website/src/content/docs/zh-cn/agent-automation.mdx
@@ -0,0 +1,122 @@
+---
+title: 智能体自动化
+description: 使用 Herdr 的布局、窗格和智能体原语,从脚本或其他智能体协调编码智能体。
+---
+
+Herdr 可以作为编码智能体的自动化层。脚本可以控制智能体,一个智能体也可以给其他智能体分配工作、检查状态并收集结果。关键是为任务选择正确的原语。
+
+## 三种原语
+
+| 原语 | 职责 |
+| --- | --- |
+| 布局(`workspace`、`tab` 和窗格拓扑) | 创建和组织终端位置。 |
+| 窗格 | 控制原始终端:运行命令、发送输入、读取输出和等待输出。 |
+| 智能体 | 按名称或窗格以及生命周期状态控制已识别的编码智能体。 |
+
+无论是否包含智能体,窗格都可以存在。智能体是 Herdr 在窗格中识别出的当前进程。因此,`agent start` 需要一个现有 shell 窗格,绝不会创建、拆分或移动布局。
+
+创建工作区时也会创建第一个标签页和根窗格;创建标签页时会创建它的根窗格。第一个进程应使用返回的窗格 ID,只有布局需要另一个终端时才进行拆分。
+
+创建命令输出 JSON。请从响应中读取 ID,不要猜测:
+
+```bash
+created=$(herdr workspace create --cwd ~/project --label api --no-focus)
+pane_id=$(printf '%s\n' "$created" | jq -r '.result.root_pane.pane_id')
+
+split=$(herdr pane split "$pane_id" --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+```
+
+`workspace create` 返回 `.result.workspace`、`.result.tab` 和 `.result.root_pane`;`tab create` 返回 `.result.tab` 和 `.result.root_pane`;`pane split` 把新窗格返回为 `.result.pane`。
+
+把窗格移动到另一个工作区会改变带工作区前缀的窗格 ID。执行 `pane move` 后,请继续使用 `.result.move_result.pane.pane_id`;旧值保留在 `.result.move_result.previous_pane_id`。运行中的进程会保留启动时的 Herdr 环境,但旧的 `HERDR_PANE_ID` 会继续作为该终端的别名,所以 `--current` 仍可安全使用。移动后发起的新命令仍可通过智能体名称解析,但已经进行中的等待会以 `agent_not_running` 结束。
+
+对于 shell、测试、服务器、CI 监视器和其他普通终端进程,使用窗格命令。当 Herdr 需要理解正在运行的是哪个智能体,或它处于 `working`、`blocked`、`done`、`idle`、`unknown` 中的哪个状态时,使用智能体命令。
+
+## 智能体身份与启动
+
+`w1:p2` 这样的窗格 ID 标识终端位置。`reviewer` 这样的智能体名称是该窗格中当前智能体的便捷别名。名称必须匹配 `[a-z][a-z0-9_-]{0,31}`,并在实时智能体中唯一。智能体退出、被释放或被替换时,别名会被清除;它不会永久重命名窗格。
+
+智能体命令既可以接受唯一的实时名称,也可以接受当前托管该智能体的窗格 ID。
+
+可用的 shell 窗格必须停在交互式 shell 提示符,由 shell 自身占用前台,没有正在前台运行的命令、编辑器或智能体。调用 `agent start` 前先让窗格回到提示符。
+
+`--kind` 选择受支持的智能体及其标准可执行文件。支持的 kind 是 `pi`、`claude`、`codex`、`gemini`、`cursor`、`devin`、`agy`、`cline`、`omp`、`mastracode`、`opencode`、`copilot`、`kimi`、`kiro`、`droid`、`amp`、`grok`、`hermes`、`kilo`、`qodercli` 和 `maki`。`--` 后的参数会原样传给该可执行文件。
+
+`agent start` 只有在 Herdr 于同一终端检测到预期智能体,并确认它可接受交互输入后才返回。默认等待启动 30 秒;`--timeout` 必须大于 3000 且不超过 300000 毫秒。
+
+```bash
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+```
+
+使用固定 ID 的等价示例:
+
+```bash
+herdr pane split --current --direction right --no-focus
+herdr agent start reviewer --kind codex --pane w1:p2 -- -m gpt-5.4
+```
+
+手动启动的智能体也会被自动检测,可以用窗格 ID 指定。当需要一个稳定、易读的目标时,给它命名:
+
+```bash
+herdr agent get w1:p2
+herdr agent rename w1:p2 reviewer
+```
+
+## 选择控制界面
+
+| 目标 | 命令 |
+| --- | --- |
+| 运行并提交 shell 命令 | `pane run` |
+| 发送不带 Enter 的纯文本 | `pane send-text` |
+| 发送终端按键或修饰键组合 | `pane send-keys` |
+| 等待文本或正则表达式 | `pane wait-output` |
+| 在现有窗格中启动受支持的智能体 | `agent start` |
+| 提交提示,并可选择等待 | `agent prompt` |
+| 向智能体交互界面发送按键 | `agent send-keys` |
+| 等待智能体生命周期状态 | `agent wait` |
+
+`agent prompt` 会提交文本和编码后的 Enter,并遵循终端当前的 bracketed paste 模式。即使智能体正在 working 也可以提交。使用 `agent send-keys` 进行 `esc`、`up`、`enter`、`ctrl+c` 等交互;`escape` 也是 `esc` 的别名。只有在明确需要原始终端控制时才使用窗格输入命令。
+
+窗格输入直接指定终端,不关心当前进程。智能体输入会解析实时智能体;如果该智能体已不再控制此窗格,操作会被拒绝。
+
+`agent prompt --wait` 会立即提交提示,然后等待此后首次观察到的匹配生命周期状态。它不会跟踪单独的轮次。如果智能体已经处于 working,当前轮次的完成可能满足等待。要把提示作为独立轮次运行,请等前一次等待返回后再发送下一条。要用多条消息引导当前轮次,请不带 `--wait` 发送,再在需要等待下一个稳定状态时使用 `agent wait`。独立的 `agent wait` 观察当前智能体;如果状态已经匹配,会立即返回。两者默认都匹配 `idle`、`done` 或 `blocked`。要接受多个精确状态,重复写 `--until`,例如 `--until idle --until done`;需要 `unknown` 时请明确使用 `--until unknown`。在 `agent prompt` 中,`--until` 必须与 `--wait` 一起使用。
+
+`idle` 表示智能体正等待输入,且其标签页已在聚焦的 Herdr 界面中显示。`done` 是相同的底层 idle 状态,但用于后台工作完成后,直到该标签页获得焦点或 `pane focus` / `agent focus` 指向它。仅通过 CLI 读取不会把它标记为已查看。`blocked` 表示 Herdr 识别到了审批或提问界面。`unknown` 表示智能体存在,但 Herdr 无法可靠判断其生命周期;它不代表工作成功完成。区别重要时,请指定精确的 `--until` 状态。
+
+`pane wait-output` 不解释智能体生命周期。它轮询选定的终端快照并立即进行第一次搜索,所以已经存在的文本也会匹配。默认来源名是 `recent`;匹配时会把它作为 recent 的未折行输出来处理。`--lines` 限制搜索范围;`--regex` 使用 Rust 正则表达式语法并逐行匹配;`--raw` 在匹配时保留 ANSI 转义序列。
+
+在 CLI 中,`pane read` 和 `agent read` 都直接打印终端文本。默认输出去除 ANSI 转义的 UTF-8 文本;来源包含样式时,使用 `--format ansi` 或 `--ansi` 保留终端转义。`detection` 来源始终是纯文本。对所有 read 来源,`--lines N` 都返回末尾 N 个逻辑行。socket API 在 `.result.read.text` 返回文本。
+
+成功的 `agent start`、`agent prompt` 和 `agent wait` 会在 `.result.agent` 返回当前智能体。`pane wait-output` 返回 `.result.pane_id`、`.result.matched_line` 以及位于 `.result.read` 的匹配快照。
+
+等待命令没有默认超时,可能无限等待。超时或服务器错误会把 JSON 错误写到 stderr 并以状态 1 退出;CLI 语法错误以状态 2 退出。
+
+## 示例
+
+启动辅助智能体,分配工作,并等待该工作结束:
+
+```bash
+split=$(herdr pane split --current --direction right --no-focus)
+review_pane=$(printf '%s\n' "$split" | jq -r '.result.pane.pane_id')
+herdr agent start reviewer --kind codex --pane "$review_pane" -- -m gpt-5.4
+herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 120
+```
+
+等待智能体请求输入,检查内容,再操作其交互界面:
+
+```bash
+herdr agent wait reviewer --until blocked --timeout 120000
+herdr agent read reviewer --source recent-unwrapped --lines 80
+herdr agent send-keys reviewer esc
+```
+
+运行普通进程并等待输出,而不把它当作智能体:
+
+```bash
+herdr pane run w1:p3 "just test --watch"
+herdr pane wait-output w1:p3 --regex "passed|failed" --timeout 120000
+```
+
+完整命令和选项列表见 [CLI 参考](/zh-cn/docs/cli-reference/)。Shell 补全也能以交互方式显示同一命令树。
diff --git a/docs/next/website/src/content/docs/zh-cn/agent-skill.mdx b/docs/next/website/src/content/docs/zh-cn/agent-skill.mdx
index a7657053..f905f347 100644
--- a/docs/next/website/src/content/docs/zh-cn/agent-skill.mdx
+++ b/docs/next/website/src/content/docs/zh-cn/agent-skill.mdx
@@ -58,7 +58,7 @@ claude
## 面向智能体的参考
-完整的命令指南就在技能文件本身。它涵盖窗格 ID、`pane split`、`pane run`、`pane read`、`wait output`、`wait agent-status`、工作区和标签页命令,以及协作配方。
+完整的命令指南就在技能文件本身。它涵盖窗格 ID、`pane split`、`pane run`、`pane read`、`pane wait-output`、`agent wait`、工作区和标签页命令,以及协作配方。
在这里阅读源文件:
diff --git a/docs/next/website/src/content/docs/zh-cn/agents.mdx b/docs/next/website/src/content/docs/zh-cn/agents.mdx
index ba6e96b7..fb478081 100644
--- a/docs/next/website/src/content/docs/zh-cn/agents.mdx
+++ b/docs/next/website/src/content/docs/zh-cn/agents.mdx
@@ -5,6 +5,8 @@ description: 了解 Herdr 能检测什么、智能体状态如何工作,以及é›
Herdr 为同时运行多个编程智能体而生。每个智能体都待在一个真实的终端窗格里,shell、日志、提示符和运行中的进程都完好无损。Herdr 跟踪哪些窗格里有智能体,把它们的状态汇总到标签页和工作区,让你直接跳到需要关注的窗格,而不是手动轮询每个终端。
+要从脚本或另一个智能体协调它们,请参阅[智能体自动化](/zh-cn/docs/agent-automation/)。
+
## 受支持的智能体
常见编程智能体开箱即用地支持自动检测。重要的区别不在于 Herdr 能不能看到某个智能体,而在于允许哪个信号来决定 `idle`、`working` 和 `blocked`。
@@ -110,7 +112,7 @@ herdr agent rename w1:p1 reviewer
herdr agent rename reviewer --clear
```
-目标可以是终端 ID、唯一的智能体名称、检测到或上报的智能体标签,以及旧式窗格 ID。
+目标使用唯一的实时智能体名称,或当前承载该智能体的窗格 ID。终端 ID 和单独的智能体 kind 标签不能作为目标。
## 自定义状态标签
@@ -131,38 +133,6 @@ herdr pane report-metadata w1:p1 \
智能体侧边栏行也可以选择使用 `terminal_title` 或 `terminal_title_stripped`;两者都不在默认行中。前者显示经过安全规范化的最新 OSC 0/2 终端标题,后者会移除开头一个已识别的活动或旋转指示符字形及其后的空白。这些值由 Herdr 服务器所有,冷重启后不会保留,并且独立于元数据标题和语义智能体状态。因此,如果移除后的文本不变,旋转动画可以改变原始标题而不触发窗格更新。
-## 从 CLI 启动智能体
-
-先用工作区、标签页、窗格和布局命令创建拓扑,再把一个现有 shell 窗格启动为具有唯一名称的受支持交互式智能体:
-
-```bash
-herdr pane split --current --direction right --no-focus
-herdr agent start reviewer --kind pi --pane w1:p2
-```
-
-`agent start` 不会创建或拆分拓扑。Herdr 为请求的 kind 选择标准可执行文件,用唯一名称标记目标窗格,并等待交互式智能体被检测为 idle、done 或 blocked。原生参数可以放在 `--` 之后:
-
-```bash
-herdr agent start reviewer --kind pi --pane w1:p2 -- --name scratch --no-session
-```
-
-按名称提交提示。`--wait` 会把等待绑定到该提示,并在智能体完成或变为 blocked 时返回:
-
-```bash
-herdr agent prompt reviewer "Review the current diff" --wait --timeout 120000
-```
-
-`agent prompt` 会在发送 Enter 前遵循终端当前的 bracketed paste 模式,因此 `A != B` 之类的文本不会触发智能体的输入模式快捷键。提交提示时请使用它;`agent send` 仍是底层的字面文本操作,不会提交一轮对话。
-
-对于已经处于 working 的智能体,`agent wait` 会在状态变为 idle、done 或 blocked 时返回;如果当前已经是这些状态之一,则立即返回。
-
-```bash
-herdr agent wait reviewer --timeout 120000
-herdr agent read reviewer --source recent-unwrapped --lines 120
-```
-
-普通终端、服务器、测试、shell、拓扑和底层终端输入请使用 `herdr pane ...` 命令。
-
## 直接附加到智能体
把当前终端附加到某一个智能体终端,而不是完整的 Herdr UI:
diff --git a/docs/next/website/src/content/docs/zh-cn/cli-reference.mdx b/docs/next/website/src/content/docs/zh-cn/cli-reference.mdx
index 61666ba8..a4facb32 100644
--- a/docs/next/website/src/content/docs/zh-cn/cli-reference.mdx
+++ b/docs/next/website/src/content/docs/zh-cn/cli-reference.mdx
@@ -126,6 +126,8 @@ herdr workspace close <workspace_id>
herdr workspace create --cwd ~/project --label api --no-focus
```
+工作区是顶层项目或工作上下文。创建工作区也会创建第一个标签页和根窗格。JSON 响应中的 `.result.workspace.workspace_id`、`.result.tab.tab_id` 和 `.result.root_pane.pane_id` 是对应 ID。
+
## Worktree
```bash
@@ -150,6 +152,10 @@ herdr tab rename <tab_id> <label>
herdr tab close <tab_id>
```
+标签页是工作区内的另一个终端布局。不指定 `--workspace` 时,`tab create` 使用活动工作区;如果没有活动工作区则失败。JSON 响应中的 `.result.tab.tab_id` 和 `.result.root_pane.pane_id` 是对应 ID。
+
+创建工作区、标签页和拆分窗格默认不改变焦点。`--focus` 选择新布局;`--no-focus` 显式表达默认行为。不指定 `--cwd` 时,新终端遵循 `terminal.new_cwd` 设置,默认跟随来源窗格或工作区。每个 `--env KEY=VALUE` 在新的根 shell 中添加或替换一个环境变量。
+
## 窗格
```bash
@@ -173,14 +179,20 @@ herdr pane move <pane_id> --new-workspace [--label TEXT] [--tab-label TEXT] [--f
herdr pane close <pane_id>
```
+接受 `--current` 的窗格命令在 Herdr 窗格内运行时使用调用方的 `HERDR_PANE_ID`。对 `pane split` 而言,显式窗格 ID 或 `--pane ID` 拆分该窗格,`--current` 拆分调用方窗格,省略目标则使用 UI 当前聚焦的窗格。拆分响应中的新窗格 ID 位于 `.result.pane.pane_id`。
+
+执行 `pane move` 后,后续命令应使用 `.result.move_result.pane.pane_id`。跨工作区移动会改变带工作区前缀的窗格 ID;旧值保留在 `.result.move_result.previous_pane_id`。运行中进程的 `HERDR_PANE_ID`、`HERDR_TAB_ID` 和 `HERDR_WORKSPACE_ID` 保持启动时的值,但 Herdr 会把旧窗格 ID 保留为该终端的别名,所以使用 `--current` 的窗格命令仍能解析它。实时智能体名称也会跟随终端。
+
读取输出:
```bash
-herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N]
+herdr pane read <pane_id> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi] [--raw]
herdr pane read <pane_id> --source visible --ansi
herdr pane read <pane_id> --source recent-unwrapped --lines 120
```
+`pane read` 直接打印 UTF-8 终端文本。默认去除 ANSI 转义;来源包含样式时,使用 `--format ansi` 或 `--ansi` 保留。`detection` 来源始终是纯文本。对所有来源,`--lines N` 都返回末尾 N 个逻辑行。`agent read` 使用相同的输出和行数行为。
+
发送输入:
```bash
@@ -191,6 +203,8 @@ herdr pane run <pane_id> <command>
`<key>` 使用 Herdr 的组合键语法: `a` 这类普通可打印键,`enter`、`tab`、`esc`、`backspace`、`left`、`right`、`up`、`down` 这类特殊键,`ctrl+h`、`control+j`、`alt+x`、`shift+tab` 这类修饰组合键,`f1` 这类功能键,以及 `minus`、`plus`、`backtick` 这类命名标点。旧式的 `C-c` 和 `c-c` 作为 `ctrl+c` 的别名被接受。
+标准拼写是 `esc`;也接受 `escape`。
+
`pane run` 会遵循当前的 bracketed paste 模式,并把文本和 Enter 作为一个原子操作提交。发送命令时优先用它,而不是 `send-text` 加 `send-keys Enter`;单独的发送操作仍是底层操作,不会提交命令。
从自定义钩子上报智能体状态:
@@ -204,8 +218,23 @@ herdr pane report-agent <pane_id> \
[--seq N] \
[--agent-session-id ID] \
[--agent-session-path PATH]
+
+herdr pane report-agent-session <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N] \
+ [--agent-session-id ID] \
+ [--agent-session-path PATH] \
+ [--session-start-source SOURCE]
+
+herdr pane release-agent <pane_id> \
+ --source ID \
+ --agent LABEL \
+ [--seq N]
```
+`report-agent-session` 只更新原生会话身份,不上报生命周期状态。`release-agent` 在智能体进程退出时结束该来源的生命周期权威。
+
当官方集成上报了原生会话引用时,`pane get`、`pane list`、`agent get` 和 `agent list` 会包含一个只读的 `agent_session` 对象。没有存储原生会话引用时,该字段被省略。
当 Herdr 能解析控制窗格的前台进程的 cwd 时,这些命令会包含 `foreground_cwd`。已有的 `cwd` 字段仍然是用于标签和 follow-cwd 行为的窗格/工作区 cwd。
@@ -237,26 +266,34 @@ herdr pane report-metadata <pane_id> \
## 智能体
+窗格与智能体的模型和完整协调示例见[智能体自动化](/zh-cn/docs/agent-automation/)。
+
```bash
herdr agent list
herdr agent get <target>
herdr agent read <target> [--source visible|recent|recent-unwrapped|detection] [--lines N] [--format text|ansi] [--ansi]
-herdr agent send <target> <text>
-herdr agent prompt <name> <text> [--wait] [--timeout MS]
+herdr agent send-keys <target> <key> [key ...]
+herdr agent prompt <target> <text> [--wait] [--until STATUS]... [--timeout MS]
herdr agent rename <target> <name>|--clear
herdr agent focus <target>
-herdr agent wait <name> [--timeout MS]
+herdr agent wait <target> [--until STATUS]... [--timeout MS]
herdr agent attach <target> [--takeover]
herdr agent start <name> --kind KIND --pane ID [--timeout MS] [-- <agent-args...>]
herdr agent explain <target> [--json|--verbose]
herdr agent explain --file PATH --agent LABEL [--json|--verbose]
```
-智能体目标可以是终端 ID、唯一的智能体名称、检测到或上报的智能体标签,以及旧式窗格 ID。名称和标签是智能体的身份。终端 ID 和旧式窗格 ID 是底层的逃生舱。
+智能体目标只能是唯一的实时智能体名称,或当前承载该智能体的窗格 ID。终端 ID 和单独的智能体 kind 标签不能作为目标。通过 `agent start` 启动的智能体必须有名称;手动启动的智能体保持未命名,通过窗格 ID 寻址。
+
+`agent start` 会在现有可用 shell 窗格中启动智能体:交互式 shell 必须占用前台,不能有正在前台运行的命令、编辑器或智能体。拓扑必须单独创建。名称在实时智能体中必须唯一,并匹配 `[a-z][a-z0-9_-]{0,31}`。支持的 kind 是 `pi`、`claude`、`codex`、`gemini`、`cursor`、`devin`、`agy`、`cline`、`omp`、`mastracode`、`opencode`、`copilot`、`kimi`、`kiro`、`droid`、`amp`、`grok`、`hermes`、`kilo`、`qodercli` 和 `maki`。名称属于当前窗格占用者,在该智能体退出、release 或被替换时清除;短暂的检测不确定不会清除它。
-`agent start` 会在现有可用 shell 窗格中启动智能体;拓扑必须单独创建。kind 选择 Herdr 的标准交互式可执行文件,`--` 之后的参数会传给该程序。`agent prompt` 要求唯一的活动智能体名称,遵循当前的 bracketed paste 模式,并原子地提交文本和 Enter。加上 `--wait` 后,它会等待该提交之后的 idle、done 或 blocked 状态。单独的 `agent wait` 在当前为 idle、done 或 blocked 时立即返回,否则只在智能体处于 working 时等待。
+start 只有在预期智能体占用同一终端并可接受交互输入后才返回。默认启动超时是 30000 毫秒;显式值必须大于 3000 且不超过 300000。
-`agent read` 读取解析出的终端流。`agent send` 只写入字面文本,不会提交一轮对话;需要保护文本不触发输入模式快捷键并发送 Enter 时,请使用 `agent prompt`。`agent get`、`agent focus` 和 `agent attach` 接受更广泛的目标形式。`agent rename` 可以为自动检测到的智能体分配名称。
+`agent prompt` 遵循当前的 bracketed paste 模式,即使智能体处于 working 也会原子地提交文本和编码后的 Enter。`--wait` 会等待提交后首次观察到的匹配生命周期状态,但不会跟踪单独的轮次。如果智能体已经处于 working,当前轮次的完成可能满足等待。需要独立轮次时,请等前一次等待返回后再发送下一条。向当前轮次发送附加消息时不要带 `--wait`,并在需要等待下一个稳定状态时使用 `agent wait`。`--until` 用于缩小匹配状态,不带 `--wait` 时会被拒绝。单独的 `agent wait` 在当前状态匹配时立即返回。两者默认匹配 `idle`、`done` 或 `blocked`;需要 `unknown` 时请明确使用 `--until unknown`。重复 `--until STATUS` 可接受多个精确状态。
+
+`idle` 表示智能体在等待输入,且其标签页已在聚焦的 Herdr 界面中显示。`done` 是相同的底层 idle 状态,用于未查看的后台工作完成后。聚焦该标签页或用 `pane focus` / `agent focus` 指向它会标记为已查看;仅通过 CLI 读取不会改变它。`blocked` 表示 Herdr 识别到审批或提问界面。`unknown` 表示智能体存在但无法可靠分类,不代表工作成功。
+
+`agent send-keys` 发送 `enter`、`up`、`esc`、`ctrl+c` 等逻辑按键。Herdr 会在写入任何字节前验证所有按键。`agent read` 读取解析出的终端流,`agent rename` 为已检测到的智能体命名。
`agent explain` 请求运行中的服务器对屏幕检测所用的同一份底部缓冲区检测快照进行分类,因此实时输出反映服务器生效的清单缓存。因为它使用 `agent.explain` socket 方法,升级 Herdr 后,请先重启或交接到更新后的服务器,再使用实时 explain。用 `--file PATH --agent LABEL` 可以改为在本地解释一份保存的样本。默认输出显示智能体、最终状态、清单来源和版本、匹配的规则及其区域证据,以及任何回退、跳过或警告原因。加 `--verbose` 可以看到可见证据标志、缓存的远程版本、本地覆盖的遮蔽情况、远程更新状态,以及带匹配器和区域证据的完整已评估规则列表。提交问题报告或写测试时加 `--json`。
@@ -273,21 +310,19 @@ herdr terminal title clear
从直接附加中用 `ctrl+b q` 分离。用 `ctrl+b ctrl+b` 发送字面的 `ctrl+b`。
`terminal title clear` 恢复 Herdr 默认的外层终端窗口标题。
-## 等待
+## 输出等待
等待窗格中的输出:
```bash
-herdr wait output <pane_id> --match <text> [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--regex] [--raw]
+herdr pane wait-output <pane_id> (--match <text> | --regex <pattern>) [--source visible|recent|recent-unwrapped] [--lines N] [--timeout MS] [--raw]
```
-等待窗格的智能体状态:
+普通命令和服务器用 `pane wait-output`。编程智能体用 `agent wait`。
-```bash
-herdr wait agent-status <pane_id> --status <idle|working|blocked|done|unknown> [--timeout MS]
-```
+`pane wait-output` 会立即检查所选快照,所以已经存在的输出也能匹配。默认来源名是 `recent`;匹配时会把它作为不限制行数的 recent 未折行输出。`--match` 在单行中查找字面子串;`--regex` 使用 Rust 正则表达式语法并逐行匹配。`--raw` 保留 ANSI 转义序列。
-普通命令和服务器用 `wait output`。编程智能体用 `wait agent-status`。
+`pane wait-output`、`agent wait` 和 `agent prompt --wait` 在省略 `--timeout` 时会无限等待。超时或服务器错误以 JSON 写到 stderr,退出状态为 1。CLI 用法错误的退出状态为 2。
## 集成
@@ -392,6 +427,8 @@ herdr plugin pane close <pane_id>
| `recent-unwrapped` | 不带软折行的最近回滚内容。最适合日志。 |
| `detection` | 智能体屏幕检测使用的底部缓冲区快照。 |
+此表描述读取时的含义。仅对 `pane wait-output` 而言,`recent` 和 `recent-unwrapped` 都搜索 recent 的未折行快照,默认写法仍是 `recent`。
+
## 环境变量
| 变量 | 用途 |
diff --git a/docs/next/website/src/content/docs/zh-cn/socket-api.mdx b/docs/next/website/src/content/docs/zh-cn/socket-api.mdx
index 89c2e771..543aeb39 100644
--- a/docs/next/website/src/content/docs/zh-cn/socket-api.mdx
+++ b/docs/next/website/src/content/docs/zh-cn/socket-api.mdx
@@ -77,7 +77,7 @@ herdr pane split w1:p1 --direction right --ratio 0.333
等待智能体:
```bash
-herdr wait agent-status w1:p1 --status done
+herdr agent wait w1:p1 --until done
```
读取窗格输出:
@@ -102,12 +102,12 @@ herdr pane read w1:p2 --source recent --lines 50
| 窗格 | `pane.split`、`pane.swap`、`pane.move`、`pane.zoom`、`pane.layout`、`pane.process_info`、`pane.neighbor`、`pane.edges`、`pane.focus_direction`、`pane.resize`、`pane.list`、`pane.current`、`pane.get`、`pane.rename`、`pane.send_text`、`pane.send_keys`、`pane.send_input`、`pane.read`、`pane.graphics.info`、`pane.graphics.set`、`pane.graphics.clear`、`pane.graphics.stream`、`pane.report_agent`、`pane.report_agent_session`、`pane.report_metadata`、`pane.clear_agent_authority`、`pane.release_agent`、`pane.close`、`pane.wait_for_output` |
| 弹窗 | `popup.close` |
| 布局 | `layout.export`、`layout.apply`、`layout.set_split_ratio` |
-| 智能体 | `agent.list`、`agent.get`、`agent.read`、`agent.explain`、`agent.send`、`agent.prompt`、`agent.rename`、`agent.focus`、`agent.start` |
+| 智能体 | `agent.list`、`agent.get`、`agent.read`、`agent.explain`、`agent.send_keys`、`agent.prompt`、`agent.wait`、`agent.rename`、`agent.focus`、`agent.start` |
| 事件 | `events.subscribe`、`events.wait` |
| 集成 | `integration.install`、`integration.uninstall` |
| 插件 | `plugin.link`、`plugin.list`、`plugin.unlink`、`plugin.enable`、`plugin.disable`、`plugin.action.list`、`plugin.action.invoke`、`plugin.log.list`、`plugin.pane.open`、`plugin.pane.focus`、`plugin.pane.close` |
-一些 CLI 命令是这些方法的便捷包装。比如 `herdr agent wait` 先解析智能体目标,然后订阅窗格智能体状态事件。
+`agent.wait` 由服务器拥有并由事件驱动。它会固定到已解析的窗格占用者,因此替换后的智能体不能满足该等待。`agent.prompt` 接受可选的 `wait` 对象,其中包含 `until` 和 `timeout_ms`;这样可在一个请求中提交提示并开始等待,避免两个独立调用之间的竞态。
`session.snapshot` 为维护本地运行时缓存的客户端返回一次性引导快照。响应包含版本/协议元数据、当前聚焦的工作区/标签页/窗格 id、工作区记录、标签页记录、窗格记录、标签页布局快照和智能体记录。它不是订阅;读取后应订阅资源事件,并根据事件更新本地缓存。重新连接后或本地缓存可能已过期时,再次调用 `session.snapshot`。工作区记录也包含关联 worktree 的来源信息。完整的仓库 worktree 发现仍使用 `worktree.list`。
@@ -589,8 +589,8 @@ herdr pane read w1:p1 --source detection
用等待来协调智能体和脚本。
```bash
-herdr wait agent-status w1:p1 --status done
-herdr wait agent-status w1:p1 --status blocked
+herdr agent wait w1:p1 --until done
+herdr agent wait w1:p1 --until blocked
```
智能体等待观察的是语义状态,不是任意命令的完成。