Child-Agent Jobs
Magent uses durable child-agent jobs for collaborative agent work. This replaces the old one-shot delegate tool with a small lifecycle that the root agent can coordinate explicitly.
Tool Surface
The public child-agent tool surface is:
| Tool | Purpose |
|---|---|
spawn_agent |
Start a child-agent job and return a stable job id. |
send_agent_message |
Send follow-up input to an existing child job. |
wait_agent |
Wait for one or more jobs and return status/result data. |
list_agents |
List child jobs for the current parent session. |
close_agent |
Close a job and abort its live request when present. |
These tools share the agent permission key. The old delegate tool is not kept as a compatibility wrapper.
Data Model
magent-agent-job.el defines magent-agent-job, the durable record for a child job. Each job stores:
idparent-session-idagent-nametask-namestatuspromptcreated-atupdated-attranscriptresulterrormetadata
Valid statuses are queued, running, waiting, completed, failed, closed, and cancelled.
The parent magent-session persists child jobs in its agent-jobs slot. Runtime-only state for active loops lives in magent-agent-job--runtimes, keyed by job id. This keeps parent session JSON sufficient for resume/inspection while avoiding serializing live request handles.
magent-agent-job.el also owns status observers. wait_agent subscribes to
those transitions and uses one deadline timer; it does not poll. Child
transitions schedule parent-session persistence through the session’s deferred
save queue, so tool callbacks do not synchronously rewrite session JSON.
Runtime Flow
spawn_agentcreates amagent-agent-jobin the parent session.- The child request starts through the Magent-owned loop in
magent-agent-loop.el. - The child runs with summary-only UI so it does not write its full transcript into the parent conversation body.
- Completion, failure, and close transitions notify wait observers and update the durable job record.
- Tool results return model-visible JSON summaries to the root agent.
A successful spawn_agent result includes a machine-readable next_action
that calls wait_agent with the returned job id. It deliberately omits a
timeout so host policy remains authoritative. When wait_agent omits its
timeout, it uses a positive magent-request-timeout or a finite 300-second
fallback. Timing out one wait does not cancel or close the child job.
The provider boundary remains gptel-request through magent-llm-gptel.el. Magent owns orchestration, tool dispatch, persistence, abort behavior, and child-job coordination.
Inheritance
Child jobs inherit the parent request context where practical:
- project root and session scope
- backend/model names
- temperature, top-p, and reasoning effort
- active skill names and capability context
- effective permission profile bounded by the parent and child agent
- request depth for recursive spawn guards
magent-child-agent-max-depth controls recursive spawning. The default allows direct children and blocks recursive child spawning.
UI And Resume
The supported agent-shell frontend renders compact child-agent lifecycle
updates. Full child prompt, metadata, result/error, and transcript state remain
persisted under the parent session’s agent-jobs data.
When agent-shell resumes a persisted parent session, its agent-jobs data is
restored with it. Active request handles are not restored after Emacs restart,
but saved job metadata, result/error state, and transcripts remain persisted.
Boundaries
This lifecycle intentionally preserves Magent’s Emacs-native workflow:
- live Emacs buffers
emacs_eval- agent-shell UI
- project-scoped sessions
- gptel transport
Codex sandbox, seatbelt, bubblewrap, and shell-isolation parity are out of scope.