Use the Email API when an agent needs to send a notification, confirmation, or batch of personalized messages. Messages go through your own SMTP mail server, connected to the workspace as an email-smtp connector. Robots Center checks the agent's permissions and approval policies before sending and records a trace you can inspect afterward.
Authorization is part of every send
The endpoint evaluates grants and approval policies using the recipient payload plus optional top-level environment, amount, risk_score, and contains_phi. A separate auth check is informative only and does not reserve a later decision.
Idempotency protects the SMTP side effect
Supply one Idempotency-Key for each logical single or bulk send. Conflict detection hashes the connector, action, and validated SMTP payload; changing one of those under the same key conflicts. Policy-only environment, amount, risk_score, and contains_phi inputs are evaluated again on every request but are not part of that hash, so keep them stable for a predictable logical retry.
Approval is not queued by email routes
A requires_approval result is returned as HTTP 400 problem JSON, just like a policy denial; the email is not sent and no approval workflow is automatically resumed. Use the Gateway tool-action approval flow when an operator-approved execution is required.
Before you begin
The command-line examples require curl and jq; any exception is identified in its introduction.
An operator-configured active connector whose slug is email-smtp and whose SMTP host, port, username, password, and from address are valid.
A permission grant binding the calling service agent to that connector and permitting the exact email action.
A machine credential with email:send; add gateway:check only if the client will preflight the policy decision.
How it works
Prepare connector access
Have an operator create the SMTP connector and grant the service agent send_email and, if needed, send_bulk_email. Confirm the connector is active and the relay is allowed by outbound network policy.
Optionally preflight policy
POST /api/v1/auth_checks with the same connector, action name, payload characteristics, and policy fields. Treat the result as a point-in-time explanation, not proof the subsequent send must succeed.
Send once and retain the receipt
Use a stable idempotency key, then record the returned SMTP message_id, runtime trace_id, connector identity, and duration. A bulk response reports totals and can succeed with a nonzero failed count.
Examples
These examples are illustrative. Replace the sample values with your own.
Keep credentials in environment variables or a secret manager, never in client-side code.
Preflight the send policy
This endpoint does not send email. Use the same policy fields that the later send will carry.
When authentication, validation, and connector lookup succeed, all policy outcomes return HTTP 200 with decision: allowed, denied, or requires_approval. Check the decision as well as the HTTP status; malformed or unauthorized requests can still return errors.
Send one email with safe retry
Keep the key stable only while retrying this logical send. Connector, action, recipient, subject, body, HTML, and attachments determine an idempotency conflict; keep policy inputs stable even though they are re-evaluated rather than hashed.
bash
export AGENTOPS_BASE_URL="https://robotscenter.net"
export AGENT_TOKEN="machine_token_with_email_send"
export EMAIL_IDEMPOTENCY_KEY="receipt-ord-example-1042-v1"
curl --fail-with-body --silent --show-error \
-X POST \
-H 'content-type: application/json' \
-H "Authorization: Bearer $AGENT_TOKEN" \
-H "Idempotency-Key: $EMAIL_IDEMPOTENCY_KEY" \
--data '{"connector_slug":"email-smtp","to":"customer@example.com","subject":"Your receipt","body":"Thank you for order ord-example-1042.","environment":"production","contains_phi":false}' \
"$AGENTOPS_BASE_URL/api/v1/email/send" | jq .
What to expect
HTTP 200 returns status: sent, the SMTP message_id, connector ID and slug, action, trace ID, and duration in milliseconds.
Send a bounded bulk request
One idempotency key protects the whole array, not each recipient independently.
HTTP 200 returns status: completed, total, sent, failed, connector details, a trace ID, and duration. Inspect the counts rather than assuming every recipient was delivered.
Troubleshooting
The send returns denied or requires_approval
Both are HTTP 400 problem responses on the email routes and no SMTP action runs. Check the connector grant and policy inputs; use the Gateway approval flow instead if execution truly must wait for a human decision.
The connector is 404 or the wrong type
Connector lookups are workspace-scoped and return only active, non-archived rows. Email endpoints additionally require slug email-smtp; another connector type produces invalid_connector_type.
An idempotency retry conflicts
The key was reused with a changed connector, action, or validated SMTP payload, or a prior attempt is still in progress or failed indeterminately. Policy-only inputs do not produce this hash conflict, but they are re-authorized. Do not generate a new key merely to force a second SMTP side effect.
An attachment is rejected
Send inline base64 only: at most 10 files, 2 MiB decoded per file, and 5 MiB decoded in total. URL and filesystem-path attachments are intentionally refused.
Endpoint reference
Ready to integrate? Open an endpoint for its required permissions, request fields,
response format, and status codes. The examples above explain the workflow;
these details define each individual request.
POST
/api/v1/email/send
API key / access token
Send a single email via SMTP connector
email:send
Description
Sends a single transactional email using an Email (SMTP) connector. Requires a connector with slug 'email-smtp' bound to the service agent with send_email action permitted. Idempotency-Key enables safe retry; the same key and request replay the first result, while changed input returns 409.
Auth
API key / access token
Required Scopes
email:send
Request Body
Field
Type
Required
Description
body
string
Yes
Plain text email body
to
string
Yes
Recipient email address
amount
number
No
Fintech policy amount (top-level PDP input)
html
string
No
Optional HTML email body
subject
string
Yes
Email subject line
environment
string
No
Environment for approval-policy conditions (top-level)
attachments
array<object>
No
Up to 10 inline objects with filename, content_type, and content_base64. URL/path attachments are rejected. Each decoded file is limited to 2 MiB and all decoded files to 5 MiB. Only basename/type/size/SHA-256 metadata is persisted.
connector_id
string
No
Email connector UUID
connector_slug
string
No
Email connector slug (alternative to connector_id)
contains_phi
boolean
No
Healthcare policy input. Hoisted into payload.contains_phi for the same PDP envelope as /gateway/execute.
risk_score
number
No
Risk score for approval-policy conditions (top-level)
Parameters
Name
In
Type
Required
Description
Idempotency-Key
header
string
No
Optional key of at most 200 visible ASCII bytes. Blank, duplicated, non-visible ASCII, or overlong values return 422; exact retries replay the prior result.
Problem JSON. Denied, requires_approval, and invalid_connector_type fall through FallbackController as 400 with detail denied, requires_approval, or invalid_connector_type. SMTP/executor failures also use this status.
401
Invalid or missing token
403
Missing email:send scope or workspace write gate
404
Connector not found
409
Problem JSON: Idempotency-Key conflicts with changed input, is in progress, or a prior execution failed and cannot safely retry
422
Validation failed: missing to/subject/body or connector ref, invalid email, or invalid connector UUID
POST
/api/v1/email/bulk
API key / access token
Send bulk emails via SMTP connector
email:send
Description
Sends multiple emails to different recipients using an Email (SMTP) connector. Each recipient can have individual to, subject, body, html, and bounded inline attachment fields. Idempotency-Key protects the whole bulk side effect.
Auth
API key / access token
Required Scopes
email:send
Request Body
Field
Type
Required
Description
amount
number
No
Fintech policy amount (top-level PDP input)
environment
string
No
Environment for approval-policy conditions (top-level)
recipients
array<object>
Yes
Array of at most 100 recipient objects with to, subject, body, html fields
connector_id
string
No
Email connector UUID
connector_slug
string
No
Email connector slug (alternative to connector_id)
contains_phi
boolean
No
Healthcare policy input. Hoisted into payload.contains_phi for the same PDP envelope as /gateway/execute.
risk_score
number
No
Risk score for approval-policy conditions (top-level)
Parameters
Name
In
Type
Required
Description
Idempotency-Key
header
string
No
Optional key of at most 200 visible ASCII bytes. Blank, duplicated, non-visible ASCII, or overlong values return 422; exact retries replay the prior result.
Problem JSON. Denied, requires_approval, and invalid_connector_type fall through FallbackController as 400 with detail denied, requires_approval, or invalid_connector_type.
401
Invalid or missing token
403
Missing email:send scope or workspace write gate
404
Connector not found
409
Problem JSON: Idempotency-Key conflicts with changed input, is in progress, or a prior execution failed and cannot safely retry
422
Validation failed: missing or more than 100 recipients, missing connector ref, or invalid connector UUID