Fifteen tools manage the agent's work. They track what it needs to do, hand parts to subagents, ask you for input, and schedule later runs.
Todo lists and plans
A conversation holds one todo checklist and one plan document. They serve different scales of work, and both show up in the chat as you go.
todo_write writes the checklist, which appears above the composer as Todo and expands
to show the items. Every call replaces the whole list. There is no add-one or mark-done operation, so the model has
to restate every item and its status each time, which stops it leaving a finished step marked in progress. Only one
item may be in progress at a time.
plan_write stores a Markdown document of up to 50,000 characters with an optional title.
plan_get reads it back. Writing an empty string clears it. The plan appears in the chat as a
Plan widget showing its revision number and size, and View plan opens the whole
thing.
The split is about lifespan. The todo list is the steps in front of the agent right now. The plan is the reasoning you do not want it to rebuild after the conversation is compacted.
Plan mode can place the finished plan in this document and leave a short summary in chat, while SoAI blocks tools marked destructive in the catalog. Other selected Plan tools can still have external effects. When the plan looks right, Execute plan on the widget switches the conversation to Execute mode and tells the agent to implement it. The plan tools themselves are nondestructive and remain available in Plan mode.
Subagents
subagent_spawn starts a background agent for the current turn and returns an ID. Give it a
task, and optionally context, a mode, a model override, a
workspace_path, a display_name, and a max_iterations cap. Running subagents
show up in the transcript with their own activity stream, so you can watch what each one is doing.
Spawning works from Plan or Execute mode. A Plan-mode parent may only spawn Plan-mode subagents, so delegation cannot bypass the destructive-tool policy.
The tools argument means three different things depending on how it is passed: leave it out for the
default subagent set, pass an empty array for text-only operation with no tools, or pass names to provide only those
tools.
SoAI then removes a fixed set regardless of the requested names. A subagent cannot call
subagent_spawn, subagent_observe, or subagent_cancel, so subagents cannot
nest. It cannot call ask_user or notify_user, so it cannot interrupt you while its parent
is mid-turn. It cannot touch todo_write, plan_write, or plan_get, which
belong to the parent. SoAI also blocks every automation tool. In Plan mode the destructive filter applies to
subagents exactly as it does to the parent. SoAI refuses the spawn if that filtering leaves no tools in Plan or
Execute mode.
subagent_observe checks on one. mode: current returns a snapshot straight away;
mode: terminal blocks until the subagent finishes, is cancelled, fails, or is abandoned.
timeout_ms bounds that wait and defaults to TOOLS.MCP.SUBAGENT.OBSERVE_TIMEOUT_MS, which
is 0 out of the box; pass null to wait with no limit.
subagent_cancel asks one to stop. Cancellation is cooperative and asynchronous, so work already in
flight may still finish before it takes effect.
Talking to you
ask_user pauses the turn and puts questions in the chat, then waits for your answer. One to six
questions per call, and the schema advises one to three with two to four options each, because a wall of questions
is worse than asking twice. The agent can mark confidential free text as secret. Credentials belong in
the vault tools, which keep the value away from the model.
TOOLS.MCP.ELICITATION.WAIT_TIMEOUT_MS
bounds the wait to one hour by default.
notify_user goes the other way and does not wait. It posts to the notification centre in the header
with a type of info, success, warning, or error, a title, a
message, an optional source label, and an optional link. Use it to report that a long job finished. Use
ask_user when the answer changes what the agent does next.
Pausing and stopping
wait sleeps. Give it seconds, up to a week, or an ISO 8601 until timestamp
with an optional timezone when that timestamp carries no offset. A reason labels the pause
in the transcript, so the agent does not spend turns polling.
stop_conversation ends the current model turn cleanly without closing the conversation. Authorized
conversation users, including non-administrators, can select it. It cannot be exposed through MCP server mode.
Automations
An automation is a scheduled agent run with its own conversation. In the SoAI WebUI, create, enable, inspect, and stop it from Automation in the sidebar. Automations covers the WebUI form, recurrence, run history, limits, and approval behavior. The tools below let an agent manage its owner's automations from a conversation.
Automation tools in a conversation
Five tools let an agent manage automations directly, each one limited to the calling user's own.
| Tool | What it does |
|---|---|
automation_create |
Creates one, with the same fields the Create automation form collects |
automation_run_enqueue |
Runs one now, without waiting for its schedule |
automation_run_get |
Fetches one run record by run_id |
automation_run_wait |
Blocks until a run reaches a terminal state. timeout_ms of 0 returns the
current state immediately, null waits indefinitely, and leaving it out uses a 60-second
wait.
|
automation_update |
Changes an existing one by automation_id. Every field except the ID is optional. |
Scheduling takes a timezone, a local start_local of the form
YYYY-MM-DDTHH:mm, and a recurrence of none, hourly,
daily, weekly, monthly, or yearly. Cron expressions are not
accepted, in either the form or the tool.
Run permissions
Automation runs always use Execute mode, and they get no tools at all unless the automation's own model settings switch tools on. An automation created without that is a plain multi-turn prompt.
Administrators have one installation-wide control that an automation cannot override. An administrator with
Configuration changes (CONFIG_PATCH) selects the Settings button at the right of the header,
then Settings. Select Advanced in the Settings page header. The page becomes
Advanced settings and the control changes to Basic. Search for
AUTOMATION.DISALLOWED_UNQUALIFIED_TOOLS. It is an empty list by default. A tool named there is unavailable to every
automation run, whatever its own configuration says. Select Save after editing. Add shell tool
names there when scheduled jobs must never reach the shell.