Skip to content

Policy and Invocation

How CompozyOS validates tool input, applies daemon policy, handles approvals, redacts sensitive fields, and records invocation evidence.

For people running agent work4 pages in this section

Tool invocation is a runtime operation, not a direct function call from an agent. CompozyOS validates the input, applies policy, dispatches the tool, redacts sensitive fields, and returns a structured result.

Invocation lifecycle

Rendering diagram…

Tool invocation flows through validation, policy, dispatch, redaction, and audit instead of bypassing the daemon.

CLI invocation

Invoke with inline JSON:

compozy tool invoke compozy__tool_info --input '{"tool_id":"compozy__skill_view"}' -o json

Invoke with a file:

compozy tool invoke compozy__tool_info --input-file ./input.json -o json

Invoke with stdin:

echo '{"tool_id":"compozy__skill_view"}' | compozy tool invoke compozy__tool_info -o json

What happened: the CLI sent JSON input to the daemon, the daemon validated and dispatched the tool, and the response came back as structured output.

Scoped diagnostics

Some tools depend on workspace, session, or agent context. Pass scope when you need diagnostics for the same view a managed session would receive:

compozy tool info compozy__skill_view --workspace ws-1 --session sess-1 --agent reviewer -o json

Use scoped diagnostics when:

  • a tool is visible globally but unavailable inside a session
  • a workspace-specific resource should appear but does not
  • an agent-specific toolset is narrower than the operator view
  • a policy decision depends on the active session context

Approval-gated tools

Some tools may require approval before execution. When a tool requires approval, the descriptor and diagnostics should tell the caller what is missing. The invocation path accepts a single-use approval token:

compozy tool invoke <tool-id> \
  --approval-token "$APPROVAL_TOKEN" \
  --input '{"target":"example"}' \
  -o json

Do not persist approval tokens in memory, docs, logs, or task descriptions. Treat them as short-lived credentials.

Pending command-palette approvals

A palette invocation can return approval_pending with an approval_id. In the Web palette, choose Approve or Deny and wait for the displayed execution result. For an invocation from the CLI or API, use the profile that originally created the approval:

compozy approvals show <approval-id> --profile <owner> -o json
compozy approvals resolve <approval-id> --decision approved --profile <owner> -o json
compozy approvals show <approval-id> --profile <owner> -o json

Use --decision denied to refuse execution, or compozy approvals cancel <approval-id> with the same profile to cancel. A successful decision can still report execution_status: dispatching; only the later status read confirms completion or failure. Expired and resolved approvals cannot run again. Selecting another profile does not transfer ownership.

HTTP and UDS expose POST /api/tools/approvals/{id}/resolve?profile=<owner> with {"decision":"approved"} or {"decision":"denied"}. HTTP decisions require a loopback listener. The daemon checks profile availability and session binding again before accepting the decision, and the deferred tool call rechecks current tool policy under the recorded owner.

Remembered native-tool decisions

When a managed session answers a native-tool approval prompt with allow-always or reject-always, CompozyOS remembers the decision in the workspace database. The remembered key is exact: workspace, agent, tool ID, and the SHA-256 digest of the authored input must all match. A different agent or input prompts again.

Operators and managed agents can also set an explicit wider decision. Agent scope matches one agent and tool across every input; tool scope matches the tool across every agent and input in the workspace. This management path never accepts an input digest, so it cannot fabricate an exact prompt-origin decision.

CompozyOS checks a supplied single-use approval token first. Without one, it checks the remembered decision before opening another prompt. A remembered allow continues to dispatch; a remembered reject blocks the invocation. These decisions survive daemon restarts and remain workspace-scoped. They do not broaden ACP or workspace policy.

Set, list, or revoke remembered decisions from any management surface:

compozy tool approvals set compozy__workspace_list \
  --workspace <workspace> \
  --decision allow \
  --scope agent \
  --agent claude-code \
  -o json
compozy tool approvals set compozy__workspace_list \
  --workspace <workspace> \
  --decision reject \
  --scope tool \
  -o json
compozy tool approvals list --workspace <workspace> -o json
compozy tool approvals revoke <grant-id> --workspace <workspace> -o json

The matching HTTP and UDS routes are PUT /api/tool-approval-grants, GET /api/tool-approval-grants, and DELETE /api/tool-approval-grants/:grant_id, all with workspace_id. The PUT body is {tool_id, decision, scope, agent_name?}; agent_name is required for agent scope and forbidden for tool scope. Managed agents can use compozy__tool_approvals_set, compozy__tool_approvals_list, and compozy__tool_approvals_revoke. Web Settings → General exposes the same wider set, workspace list, and revoke actions.

An explicit wider allow only skips the prompt when the workspace tool policy already permits the invocation. It does not change the configured tool mode or broaden ACP, capability, or workspace boundaries.

Sensitive input fields

If input contains sensitive values, mark the field path so invocation evidence can redact it:

compozy tool invoke <tool-id> \
  --input '{"secret_ref":"vault://provider/token"}' \
  --sensitive-input-field secret_ref \
  -o json

What happened: CompozyOS still received the input needed by the handler, but the specified field is treated as sensitive in diagnostic and event surfaces.

Retired tool IDs

The removed memory tool IDs and the two removed memory toolsets stay reserved and are never reused. A tool policy that still names one of them by its exact ID is never an error. CompozyOS drops the entry and applies the rest of the policy:

  • in an agent definition's tools, toolsets, or deny_tools;
  • in the tool list of a spawned or coordinator session's permission policy, or in a session's allowed-tools override.

CompozyOS logs one tools.retired_ids_ignored warning per policy owner (agent:<source path or name> or session:<session id>) for the life of the daemon process, with the owner and the dropped ids. A wildcard pattern in tools or deny_tools is not a retired entry. It is kept and matches no tool because the memory tools no longer exist. An allow-list that held only retired entries stays enforced, so it grants no tools; it never becomes an unrestricted policy. The filter is removed in v0.6.0. See the migration guide.

Common failures

SymptomLikely causeFirst check
Tool is not foundWrong ID or tool not registered in the current runtime.compozy tool search <query> -o json
Tool is visible but unavailableMissing workspace/session/agent scope or prerequisite configuration.compozy tool info <tool-id> --session <id> -o json
Invocation rejects inputJSON does not match the tool schema.compozy tool info <tool-id> -o json
Invocation needs approvalPolicy requires an approval token.Descriptor diagnostics
Result omits expected secret valueSecrets are write-only or redacted by design.Vault and policy docs

On this page