description: "Global send_message, interrupt_agent, and list_agents tools for users and maintainers composing or debugging continuable-child control."
English | 中文
dsh-tool-subagent-control adds the global control tools for continuable children: send_message delivers a follow-up message that becomes the child's next turn, interrupt_agent stops a child's current turn while keeping its queue and descendants intact, and list_agents (from the separately loadable list-agents plugin) lists continuable children by durable id and label. The tools are global, so any number of delegation tools never duplicates them. These tools cover only the parent-to-child direction; the child-to-parent direction belongs to the independently installed dsh-tool-subagent-report. No tool's presence decides whether a delegation tool starts continuable work.
Mount this package in any composition with continuable children the model should message, interrupt, or list. The root plugin needs only the subagent service; the list tool is a separate plugin a deployment can omit.
Load the subagent service, a backend, the delegation tool, and this package. Adding the separate list plugin exposes all three tools:
- name: '@deepseek-ai/dsh-subagent'
- name: '@deepseek-ai/dsh-subagent-spawn-in-process'
- name: '@deepseek-ai/dsh-tool-subagent'
config:
provider: spawn
backgroundMode: continuable
- name: '@deepseek-ai/dsh-tool-subagent-control'
- name: '@deepseek-ai/dsh-tool-subagent-control/list-agents'
This package takes no configuration: the root plugin provides send_message and interrupt_agent, and the list plugin provides list_agents.
Sends a message that becomes the child's next FIFO turn: a working child finishes its current turn first, so a message cannot redirect work already underway. The call returns only acceptance (the accepted message's stable messageId), never the child's reply — the child's transcript by its id is the source of what it did. A failure — an unauthorized or unknown child, a descriptor-less child that cannot be resumed, or rejected admission — states the message was not delivered.
Stops only the target's current turn: queued messages stay parked until a later send_message, descendants keep running, and the child stays available for follow-ups. The call returns when the stop request is accepted, not when the target is quiet; interrupting an already-finished agent is an accepted no-op, and self, sibling, stale, and non-ancestor callers get errored results.
Lists the continuable children below the calling agent: children (default) shows direct children, descendants walks the whole tree in stable pre-order, annotating each entry with its durable direct-parent session id and depth. Status comes from the live Agent registry — running, idle, or ready. One-shot children are intentionally absent because they cannot accept send_message, and unreadable candidates appear as diagnostics.
Read these pages when the package-level contract is not enough; they move from the tool schemas to the continuation service behind them.
The generated schemas: send_message takes subagent_id and message; interrupt_agent takes agent_id; list_agents takes the optional scope enum.
Fixed schema cost per parent request.
Prefix-stable; the schema does not change at runtime.
interrupt requested for agent <agent_id> on acceptance. An unauthorized caller — self, sibling, stale, or non-ancestor — is an errored result naming the rejection; an absent or settled target still renders the acceptance line.
One short acknowledgement per call; the interrupted turn's abort is visible only in the child's own transcript.
Append-only; each result follows the reusable request prefix.
message queued as the next turn for subagent <subagent_id> on acceptance; the canonical output carries the accepted messageId. A failure — an unauthorized or unknown child, a descriptor-less child that cannot be resumed, or admission rejected — is an errored result whose message states the message was not delivered.
One short acknowledgement per call; the child's response never returns through this call. A separately granted report may append selected content to parent history.
Append-only; newly visible content follows the reusable request prefix and does not invalidate existing KV-cache entries.
One line per continuable child in stable catalog order: <id> [<status>] — <label> (running = active driver, idle = resident between turns, ready = storage only, resumable rather than terminal), plus <id> [diagnostic: <reason>] for a candidate that could not be read. The descendants scope inserts parent=<id> depth=<n> before the label dash on every line, in pre-order. One-shot children are intentionally absent; (no subagents) means no continuable child or diagnostic survived the projection.
Grows linearly with the listed continuable children — the whole tree under the descendants scope; there is no cursor or cap, so long-lived parents with many persisted children pay the full list each call.
Append-only; each result follows the reusable request prefix.
These limits define what the control tools cannot observe or steer; they are current package constraints.
messageId; the child's work lands in the durable child Session and is never collected through this tool. A child granted report may send selected content back separately, but that message is not this call's result.ready; cross-process accuracy requires a shared lease. interrupt_agent performs the authoritative live-lineage check itself, so discovery staleness cannot grant authority.