Agent Confessions
A secure steering loop: an uncertain cloud agent reports its concerns, a human gives guidance, and the agent resumes safely.
What it does
Confessions let an agent ask a human to choose a direction when it lacks enough confidence to proceed. Creation persists the item, returns a one-time review URL, and asynchronously queues email notification. A reviewer approves or rejects it; the agent polls or receives a signed confession.resolved callback to resume.
Endpoint
Method: POST
Path: POST /v1/confessions
Auth: x-agent-id + x-api-key (creation and polling); x-admin-key, X-Approval-Key, or a short-lived review token (resolution)
Request shape
- •title: string — the decision or uncertainty that needs human review (required, max 256 characters)
- •summary?: string — optional concise context for the reviewer (max 4096 characters)
- •context?: JSON — private supporting context, maximum 50 KB
- •urgency?: normal | high | blocking; reviewer_email?: string
- •callback_url: HTTPS URL (required); callback_payload?: JSON up to 100 KB
- •expires_in_seconds?: integer (300–604800; defaults to 24 hours)
Example requests
Copy-pasteable examples for agents and automation.
cURL
curl -X POST https://www.agent-utils.com/v1/confessions \
-H "x-agent-id: worker" -H "x-api-key: agutil_agt_…" \
-H "content-type: application/json" \
-d '{
"title":"Which migration should we ship?",
"summary":"Both schemas are active; I need a reviewer decision.",
"urgency":"high",
"callback_url":"https://your-app.example/confessions/resolved"
}'Python
import requests
resp = requests.post(
"https://www.agent-utils.com/v1/confessions",
headers={"x-agent-id": "worker", "x-api-key": "agutil_agt_…"},
json={
"title": "Which migration should we ship?",
"summary": "Both schemas are active; I need a reviewer decision.",
"urgency": "high",
"callback_url": "https://your-app.example/confessions/resolved",
},
)
review_url = resp.json()["data"]["review_url"]JavaScript
const res = await fetch("https://www.agent-utils.com/v1/confessions", {
method: "POST",
headers: { "x-agent-id": "worker", "x-api-key": "agutil_agt_…", "content-type": "application/json" },
body: JSON.stringify({
title: "Which migration should we ship?",
summary: "Both schemas are active; I need a reviewer decision.",
urgency: "high",
callback_url: "https://your-app.example/confessions/resolved",
}),
});
const { data } = await res.json();
console.log(data.review_url);How agents use it
When to use it
- ✓The agent finds competing valid approaches and needs a human to choose the business or technical direction.
- ✓Proceeding with a guess could be costly, unsafe, or difficult to reverse.
- ✓A long-running cloud agent needs help without losing its current context or workflow state.
When not to use it
- •You only need approval or rejection for one proposed, well-defined action; use a checkpoint instead.
- •The task has already failed and needs retry or inspection; use the dead letter queue instead.
- •The agent can safely apply a deterministic fallback without human input.
Failure modes
- •An agent key can create, list, poll, and cancel only its own tenant’s Confessions; it cannot resolve one.
- •Resolution is terminal. A second resolution returns a conflict, so consumers must handle the callback idempotently.
- •An expired unanswered Confession is marked expired; pending notification work is cancelled and callback delivery failure is recoverable through the DLQ.
- •Email notification is asynchronous and non-blocking. If no reviewer email is configured, creation still succeeds and the agent can distribute review_url itself.
Machine-readable summary
This JSON block is stable for crawlers, agents, and downstream documentation pipelines.
{
"slug": "confession",
"title": "Agent Confessions",
"canonical": "/docs/confessions",
"endpoint": "POST /v1/confessions",
"method": "POST",
"auth": "x-agent-id + x-api-key (creation and polling); x-admin-key, X-Approval-Key, or a short-lived review token (resolution)",
"machine_readable": true,
"request_shape": [
"title: string — the decision or uncertainty that needs human review (required, max 256 characters)",
"summary?: string — optional concise context for the reviewer (max 4096 characters)",
"context?: JSON — private supporting context, maximum 50 KB",
"urgency?: normal | high | blocking; reviewer_email?: string",
"callback_url: HTTPS URL (required); callback_payload?: JSON up to 100 KB",
"expires_in_seconds?: integer (300–604800; defaults to 24 hours)"
],
"agent_workflows": [
"Create a Confession with a title, optional summary/context, urgency, required callback URL, and optional reviewer email.",
"Use the returned one-time review_url or tenant email notification to bring an authorized reviewer to /c/{id}.",
"Poll GET /v1/confessions/{id}, or verify the signed confession.resolved callback, then resume according to the approved or rejected decision."
],
"failure_modes": [
"An agent key can create, list, poll, and cancel only its own tenant’s Confessions; it cannot resolve one.",
"Resolution is terminal. A second resolution returns a conflict, so consumers must handle the callback idempotently.",
"An expired unanswered Confession is marked expired; pending notification work is cancelled and callback delivery failure is recoverable through the DLQ.",
"Email notification is asynchronous and non-blocking. If no reviewer email is configured, creation still succeeds and the agent can distribute review_url itself."
]
}