API reference
Gateway
One tag: method, path, summary, auth, and scopes. Request and response fields ship in this page — expand a row to read the contract.
Endpoints
4
POST
/api/v1/auth_checks
Agent Token
Check if an action is authorized
gateway:check
/api/v1/auth_checks
Agent Token
Check if an action is authorized
Description
Evaluates whether a service agent is authorized to perform a specific action on a connector. Prerequisite: A connector must exist in the workspace (create via operator dashboard).
Auth
Agent TokenRequired Scopes
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
| amount | number | No | Numeric amount for approval-policy conditions (top-level) |
| payload | object | No | Action input parameters used by approval-policy conditions |
| action_name | string | Yes | Name of the action to check |
| environment | string | No | Environment for approval-policy conditions (top-level) |
| connector_id | string | No | Connector UUID |
| connector_slug | string | No | Connector slug (alternative to connector_id) |
| contains_phi | boolean | No | Healthcare policy input. Merged into payload.contains_phi for the same PDP envelope as execute and email. |
| risk_score | number | No | Risk score for approval-policy conditions (top-level) |
Responses
200
Authorization decision. denied and requires_approval are also 200 — this route never executes.
Authorization decision. denied and requires_approval are also 200 — this route never executes.
Response Body
| Field | Type | Required | Description |
|---|---|---|---|
| connector | object | Yes | Resolved connector |
| connector.id | string | Yes | Connector UUID |
| connector.slug | string | Yes | Connector slug |
| decision | string (allowed, denied, requires_approval) | Yes | PDP outcome |
| policy | object | No | Matched approval policy, or null |
| policy.id | string | Yes | Policy UUID |
| policy.name | string | Yes | Policy name |
Example
{
"connector": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"slug": "email-smtp"
},
"decision": "allowed",
"policy": null
}
401
Invalid or missing token
Invalid or missing token
403
Missing required scope
Missing required scope
404
Connector not found
Connector not found
422
Validation failed: missing connector_id/connector_slug or action_name, invalid connector UUID, or non-numeric amount/risk_score
Validation failed: missing connector_id/connector_slug or action_name, invalid connector UUID, or non-numeric amount/risk_score
POST
/api/v1/tool_actions
Agent Token
Authorize a tool action
gateway:execute
/api/v1/tool_actions
Agent Token
Authorize a tool action
Description
Authorizes a tool action, writes an audit row, and optionally creates an approval request. GatewayExecutor is not called. Allowed returns 200 {status:"ok", decision, connector_id}. requires_approval returns 202 with approval_request_id, status_url, Location and Retry-After: 2; poll status_url until execution completes. Indeterminate execution is never retried automatically and requires review. Prerequisite: a connector must exist in the workspace.
Auth
Agent TokenRequired Scopes
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
| amount | number | No | Numeric amount for approval-policy conditions (top-level) |
| payload | object | No | Action input parameters |
| action_name | string | Yes | Name of the action to authorize (this route does not execute it) |
| environment | string | No | Environment for approval-policy conditions (top-level) |
| connector_id | string | No | Connector UUID |
| connector_slug | string | No | Connector slug (alternative to connector_id) |
| contains_phi | boolean | No | Healthcare policy input. Merged into payload.contains_phi for the same PDP envelope as execute and email. |
| risk_score | number | No | Risk score for approval-policy conditions (top-level) |
| input_payload | object | No | Alternative key for payload |
Responses
200
Authorized. No connector action ran. Body is {status:"ok", decision, connector_id}.
Authorized. No connector action ran. Body is {status:"ok", decision, connector_id}.
Example
{
"status": "ok",
"connector_id": "550e8400-e29b-41d4-a716-446655440000",
"decision": "allowed"
}
202
Policy requires approval. Body includes status_url; poll it with the same gateway:execute token. Location points to the same URL, Retry-After is 2 seconds, and Cache-Control is no-store.
Policy requires approval. Body includes status_url; poll it with the same gateway:execute token. Location points to the same URL, Retry-After is 2 seconds, and Cache-Control is no-store.
Example
{
"status": "pending_approval",
"connector_id": "550e8400-e29b-41d4-a716-446655440000",
"decision": "requires_approval",
"approval_request_id": "9c1d2e3f-4a5b-6c7d-8e9f-0a1b2c3d4e5f",
"status_url": "/api/v1/tool_actions/9c1d2e3f-4a5b-6c7d-8e9f-0a1b2c3d4e5f"
}
401
Invalid or missing token
Invalid or missing token
403
Denied by policy. Body is {error:"denied", decision, connector_id}, not problem JSON.
Denied by policy. Body is {error:"denied", decision, connector_id}, not problem JSON.
404
Connector not found
Connector not found
422
Validation failed: missing connector ref or action_name, invalid UUID, or non-numeric amount/risk_score
Validation failed: missing connector ref or action_name, invalid UUID, or non-numeric amount/risk_score
POST
/api/v1/gateway/execute
Agent Token
Execute connector action with full trace recording
gateway:execute
/api/v1/gateway/execute
Agent Token
Execute connector action with full trace recording
Description
Runs a connector action after PDP authorization, records a runtime trace, and returns the event timeline. SMTP (email-smtp) handles send_email and send_bulk_email; those actions accept Idempotency-Key for safe replay and bounded inline attachments (filename, content_type, content_base64), while URL/path attachments are rejected. HTTPExecutor already runs slack, github, jira, linear, internal-api, stripe, salesforce, and twilio (events http_request/http_response; actions such as messages.post). Policy-only slugs have no executor and fail as EXECUTION_ERROR (:not_executable). AuthorizationSnapshot is stored only in execution metadata/audit — it is not a top-level 200 field.
Auth
Agent TokenRequired Scopes
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
| metadata | object | No | Optional metadata including trace_id, campaign_id, etc. |
| metadata.trace_id | string | No | Custom trace ID |
| metadata.campaign_id | string | No | Campaign identifier |
| action | string | Yes | Action to execute (e.g. send_email, send_bulk_email, messages.post) |
| amount | number | No | Fintech policy amount. Hoisted into the same PDP envelope as auth_checks/tool_actions. |
| payload | object | No | Action-specific input parameters |
| action_name | string | No | Alternative key for action (alias) |
| environment | string | No | Environment label for approval-policy conditions (top-level) |
| service_agent_id | string | No | Optional service agent ID for audit trail |
| connector_id | string | No | Connector UUID |
| connector_slug | string | No | Connector slug (alternative to connector_id) |
| contains_phi | boolean | No | Healthcare policy input. Cast is skipped; the controller hoists this into the PDP payload.contains_phi envelope. |
| risk_score | number | No | Risk score for approval-policy conditions (top-level) |
| input_payload | object | No | Alternative key for payload |
Responses
200
Action executed successfully
Returns: GatewayExecuteResponse
Action executed successfully
Returns: GatewayExecuteResponse
Response Body
| Field | Type | Required | Description |
|---|---|---|---|
| output | object | No | Action-specific output data |
| status | string | Yes | Execution status |
| events | array<object> | Yes | Array of execution events with timestamps |
| events[].timestamp | datetime (ISO 8601) | Yes | ISO 8601 timestamp |
| events[].type | string | Yes | Event type (e.g. smtp_connecting, email_sent, http_request, http_response) |
| events[].details | object | No | Event-specific details |
| action | string | No | Executed action name |
| message_id | string | No | Message identifier (for email actions) |
| connector_id | string | Yes | Connector UUID |
| connector_slug | string | Yes | Connector slug |
| duration_ms | integer | Yes | Total execution time in milliseconds |
| trace_id | string | Yes | Trace ID for observability lookup |
Example
{
"output": {
"delivered": true,
"recipient": "[email protected]",
"message_id": "<[email protected]>",
"duration_ms": 245
},
"status": "success",
"events": [
{
"timestamp": "2026-03-18T10:00:00Z",
"type": "smtp_connecting",
"details": {
"port": 587,
"host": "smtp.example.com"
}
},
{
"timestamp": "2026-03-18T10:00:00Z",
"type": "smtp_connected",
"details": {
"port": 587,
"host": "smtp.example.com"
}
},
{
"timestamp": "2026-03-18T10:00:01Z",
"type": "smtp_authenticating",
"details": {
"user": "[email protected]"
}
},
{
"timestamp": "2026-03-18T10:00:01Z",
"type": "smtp_authenticated",
"details": {
"user": "[email protected]"
}
},
{
"timestamp": "2026-03-18T10:00:02Z",
"type": "email_sent",
"details": {
"from": "[email protected]",
"to": [
"[email protected]"
],
"subject": "Test Email",
"message_id": "<[email protected]>"
}
},
{
"timestamp": "2026-03-18T10:00:02Z",
"type": "smtp_disconnected",
"details": {}
}
],
"action": "send_email",
"message_id": "<[email protected]>",
"connector_id": "550e8400-e29b-41d4-a716-446655440000",
"connector_slug": "email-smtp",
"duration_ms": 245,
"trace_id": "a1b2c3d4e5f6"
}
400
Execution failed - includes events up to failure point
Returns: GatewayExecuteErrorResponse
Execution failed - includes events up to failure point
Returns: GatewayExecuteErrorResponse
Response Body
| Field | Type | Required | Description |
|---|---|---|---|
| message | string | Yes | Human-readable error message |
| status | string | Yes | Always 'error' |
| events | array<object> | No | Partial events recorded before failure |
| details | object | No | Error details |
| details.action | string | No | Action name |
| details.provided_fields | array<string> | No | List of provided field names |
| error_code | string (UNSUPPORTED_ACTION, INVALID_EMAIL, SMTP_ERROR, ACCESS_DENIED, REQUIRES_APPROVAL, EXECUTION_ERROR) | Yes | Error code. Paused or missing connectors are 404 Problem JSON, not CONNECTOR_PAUSED/CONNECTOR_NOT_FOUND. :http_error, :not_executable, :http_not_configured, and outbound URL-policy atoms collapse to EXECUTION_ERROR. |
| trace_id | string | No | Trace ID for debugging |
Example
{
"message": "Failed to send email via SMTP",
"status": "error",
"events": [
{
"timestamp": "2026-03-18T10:00:00Z",
"type": "smtp_connecting",
"details": {
"port": 587,
"host": "smtp.example.com"
}
},
{
"timestamp": "2026-03-18T10:00:00Z",
"type": "smtp_connected",
"details": {
"port": 587,
"host": "smtp.example.com"
}
},
{
"timestamp": "2026-03-18T10:00:01Z",
"type": "smtp_authentication_failed",
"details": {
"error": "Invalid credentials",
"user": "[email protected]"
}
},
{
"timestamp": "2026-03-18T10:00:01Z",
"type": "smtp_disconnected",
"details": {}
}
],
"details": {
"action": "send_email",
"provided_fields": [
"action",
"connector_id",
"payload"
]
},
"error_code": "SMTP_ERROR",
"trace_id": "a1b2c3d4e5f6"
}
401
Invalid or missing token
Invalid or missing token
403
Missing gateway:execute scope
Missing gateway:execute scope
404
Connector not found. get_connector only returns active, non-archived connectors, so paused and missing connectors are this 404 Problem JSON — not a 400 CONNECTOR_PAUSED body.
Connector not found. get_connector only returns active, non-archived connectors, so paused and missing connectors are this 404 Problem JSON — not a 400 CONNECTOR_PAUSED body.
422
Validation error (missing action or connector)
Validation error (missing action or connector)
GET
/api/v1/tool_actions/:id
Agent Token
Poll a tool approval and execution
gateway:execute
/api/v1/tool_actions/:id
Agent Token
Poll a tool approval and execution
Description
Returns the requesting service agent's approval and execution state. This read never executes, retries, or enqueues the connector action. A pending request may expire without being mutated; an interrupted execution is indeterminate and requires operator review.
Auth
Agent TokenRequired Scopes
Parameters
| Name | In | Type | Required | Description |
|---|---|---|---|---|
| id | path | string | Yes | Approval request UUID returned by POST /api/v1/tool_actions |
Responses
200
Approval and execution state
Approval and execution state
Response Body
| Field | Type | Required | Description |
|---|---|---|---|
| id | string | Yes | Approval request UUID |
| state | string (pending_approval, queued, running, succeeded, failed, rejected, expired, indeterminate, not_requested) | Yes | Current combined state for a polling client |
| expires_at | datetime (ISO 8601) | Yes | Approval expiry |
| retry_after_seconds | integer (2, ) | Yes | Polling delay or null for a terminal/review state |
| approval_status | string (pending, approved, rejected, expired) | Yes | Recorded approval state |
| automatic_retry | boolean (false) | Yes | Always false |
| execution_completed_at | datetime (ISO 8601) | Yes | Execution completion |
| execution_started_at | datetime (ISO 8601) | Yes | Execution start |
| execution_status | string (not_requested, queued, running, succeeded, failed) | Yes | Durable execution state |
| execution_trace_id | string | Yes | Execution trace correlation only; confers no read access |
| next_action | string (poll, continue, stop, review) | Yes | Continue the caller's workflow only after success; never resubmit this action |
| reviewed_at | datetime (ISO 8601) | Yes | Operator decision time |
Example
{
"id": "9c1d2e3f-4a5b-6c7d-8e9f-0a1b2c3d4e5f",
"state": "pending_approval",
"expires_at": "2026-09-08T12:05:00Z",
"retry_after_seconds": 2,
"approval_status": "pending",
"automatic_retry": false,
"execution_completed_at": null,
"execution_started_at": null,
"execution_status": "not_requested",
"execution_trace_id": null,
"next_action": "poll",
"reviewed_at": null
}
401
Invalid or missing token
Invalid or missing token
403
Missing gateway:execute scope
Missing gateway:execute scope
404
Approval request not found for this service agent
Approval request not found for this service agent