Agent definitions API
An agent definition is the saved recipe for an agent: which Amara model it runs on, the instructions it follows, the tools, skills and MCP servers it may use, and the limits it works within. The Agent definitions API lets you create, read, change and retire these recipes with an API key, so agents can live in source control and be deployed from CI the same way the rest of your stack is.
The API uses the same schema the Console’s AI Agents area uses. An agent created through the API appears in the Console, and an edit made in the Console shows up in the API as a new version. There is one source of truth, not two copies kept in sync.
A definition does nothing on its own. To put an agent to work you start a session with it, or schedule one with a deployment.
When to use it
| Use the API when | Use the Console when |
|---|---|
| Agents are defined in code and reviewed like code | A non-developer is shaping the agent’s personality and instructions |
| You run many similar agents (one per customer, per region, per product line) | You are creating a single agent by hand |
| A CI pipeline should promote a tested version to production | You want to try changes interactively in Live activity |
| You need a reproducible version number to pin sessions to | You only need the latest settings |
Endpoints
| Method | Path | Purpose |
|---|---|---|
POST | /v1/agents | Create an agent. Its first version is 1. |
GET | /v1/agents | List agents in the workspace. |
GET | /v1/agents/{agent_id} | Read an agent’s current version. |
PATCH | /v1/agents/{agent_id} | Change fields. Every successful change creates a new version. |
GET | /v1/agents/{agent_id}/versions | List all versions, newest first. |
GET | /v1/agents/{agent_id}/versions/{version} | Read one version exactly as it was. |
POST | /v1/agents/{agent_id}/archive | Stop new sessions from using the agent. Existing sessions finish normally. |
DELETE | /v1/agents/{agent_id} | Delete an archived agent and all its versions. |
Base URL: https://app.syntic.ai/v1 (see API host).
Authentication: a private inference key, Authorization: Bearer sk_live_.... Keys belong to one workspace; an agent belongs to the workspace of the key that created it, and keys from other workspaces cannot see it.
Headers while in preview: syntic-beta: agents-2026-11-01. Requests without it get 400 invalid_request with code beta_required. See Versioning and beta flags.
Who may write: any key in the workspace may read agents. Creating, changing, archiving and deleting need a key whose creator holds the Developer role or higher in the organization. Turning on tools marked approval required follows the same rule as the Console: only Administrators and Owners may enable them.
The agent object
{
"id": "agt_01JC4R8W6Q2N9X3T5V7Y",
"type": "agent",
"name": "refund-desk",
"description": "Handles refund requests from the support inbox.",
"version": 4,
"status": "active",
"model": "Amara S1.2",
"instructions": "You handle refund requests for Acme Store. ...",
"tools": [
{ "type": "function", "function": { "name": "lookup_order", "description": "...", "parameters": { "type": "object", "properties": { "order_id": { "type": "string" } }, "required": ["order_id"] } } },
{ "type": "syntic_web_search", "max_uses": 3 }
],
"tool_policy": {
"default": "allow",
"require_approval": ["issue_refund"]
},
"mcp_servers": [
{ "name": "crm", "url": "https://mcp.example.com/crm", "vault_secret": "crm-token", "allowed_tools": ["find_customer"] }
],
"skills": [{ "skill_id": "skl_01JB9...", "version": "latest" }],
"environment_id": null,
"memory_store_ids": ["mem_01JC1..."],
"vault_ids": ["vlt_01JC2..."],
"limits": {
"max_turns": 40,
"max_output_tokens_per_turn": 4096,
"session_token_budget": 400000,
"session_cost_budget_usd": 2.0
},
"metadata": { "team": "support" },
"created_at": "2026-11-03T09:14:22Z",
"updated_at": "2026-11-05T16:02:10Z"
}| Field | Type | Description |
|---|---|---|
id | string | Starts with agt_. Stable across versions. |
type | string | Always agent. |
name | string | Unique within the workspace. 1 to 64 characters: lowercase letters, digits, - and _. |
description | string | Free text shown in the Console. Up to 500 characters. |
version | integer | The version this object describes. Starts at 1. |
status | string | active or archived. |
model | string | An Amara model name from GET /v1/models. Unknown names are rejected (400, code unknown_model); there is no silent fallback here. |
instructions | string | The system instructions. Up to 100,000 characters. |
tools | array | Function tools in the same format as tool calling, plus built-in tool entries such as syntic_web_search. Up to 128 entries. |
tool_policy | object | Which tools run without asking. default is allow or ask; require_approval and deny list tool names that override the default. |
mcp_servers | array | Remote MCP servers the agent may use, as in the MCP connector. Tokens come from a vault by name, never inline. |
skills | array | Skills by id, pinned to a version or latest. |
environment_id | string or null | The environment the agent’s code tools run in. null means no code execution. |
memory_store_ids | array | Memory stores available to the agent. |
vault_ids | array | Vaults whose secrets tools may use. |
limits | object | Default limits applied to every session. A session may lower them, never raise them. |
metadata | object | Up to 16 string keys and values, each value up to 512 characters. Returned as sent; Syntic does not read it. |
created_at, updated_at | string | RFC 3339 UTC timestamps. |
Versions
Each PATCH that changes at least one field produces a new version with the next integer. A PATCH that changes nothing returns the current version and does not create a new one.
- New sessions use the latest version unless they name one with
agent_version. - Running sessions keep the version they started with until they end.
- Versions are immutable. You cannot edit or delete a single version, only the whole agent.
Pinning sessions to a version and moving the pin in a deploy step gives you a clean rollback: point back to the previous number.
Create an agent
POST /v1/agents
Request body
| Field | Required | Notes |
|---|---|---|
name | Yes | See the object table. |
model | Yes | |
instructions | Yes | |
description | No | |
tools | No | Default []. Tool schemas are validated on save; see Errors. |
tool_policy | No | Default {"default": "allow"}. |
mcp_servers, skills, memory_store_ids, vault_ids | No | Default []. Every id must exist in the same workspace. |
environment_id | No | Default null. |
limits | No | Missing fields take the workspace defaults. |
metadata | No |
Send an Idempotency-Key header to make retries safe: a repeated key within 24 hours returns the first result instead of creating a second agent.
Response
201 Created with the agent object, version: 1.
curl -sS https://app.syntic.ai/v1/agents \
-H "Authorization: Bearer $SYNTIC_API_KEY" \
-H "Content-Type: application/json" \
-H "syntic-beta: agents-2026-11-01" \
-H "Idempotency-Key: create-refund-desk-001" \
-d '{
"name": "refund-desk",
"model": "Amara S1.2",
"instructions": "You handle refund requests for Acme Store. Look the order up before answering.",
"tools": [{
"type": "function",
"function": {
"name": "lookup_order",
"description": "Fetch an order by its id.",
"parameters": {"type": "object", "properties": {"order_id": {"type": "string"}}, "required": ["order_id"]}
}
}],
"limits": {"max_turns": 30}
}'Update an agent
PATCH /v1/agents/{agent_id}
Include just the fields being changed. Arrays (tools, skills, mcp_servers and so on) are replaced whole, not merged. metadata is merged key by key; set a key to null to remove it.
To avoid overwriting someone else’s change, send if_version with the version you last read. If the agent has moved on, the call fails with 409 and code version_conflict; read it again and reapply your change.
curl -sS -X PATCH https://app.syntic.ai/v1/agents/agt_01JC4R8W6Q2N9X3T5V7Y \
-H "Authorization: Bearer $SYNTIC_API_KEY" \
-H "Content-Type: application/json" \
-H "syntic-beta: agents-2026-11-01" \
-d '{"if_version": 4, "model": "Amara Deep"}'The response is the agent object at its new version (200 OK).
List agents
GET /v1/agents
| Query parameter | Default | Notes |
|---|---|---|
limit | 20 | 1 to 100. |
after_id, before_id | Cursor pagination, see conventions. | |
status | active | active, archived or all. |
name | Exact name match. |
{
"data": [{ "id": "agt_01JC4R8W6Q2N9X3T5V7Y", "type": "agent", "name": "refund-desk", "version": 4, "status": "active", "...": "..." }],
"has_more": false,
"first_id": "agt_01JC4R8W6Q2N9X3T5V7Y",
"last_id": "agt_01JC4R8W6Q2N9X3T5V7Y"
}Archive and delete
POST /v1/agents/{agent_id}/archivesetsstatustoarchived. New sessions and deployments referencing the agent are refused with409 agent_archived.POST /v1/agents/{agent_id}/unarchivereverses it.DELETE /v1/agents/{agent_id}only works on an archived agent with no running sessions, and removes every version. Execution records keep the agent id and name so history stays readable. Returns{"id": "...", "type": "agent_deleted"}.
Errors
All errors use the error envelope:
{
"error": {
"type": "invalid_request",
"code": "invalid_tool_schema",
"message": "tools[0].function.parameters is not a valid JSON Schema object.",
"param": "tools[0].function.parameters"
},
"request_id": "req_6f1c2a9e0b7d4c3a8e5f1b2d"
}| Status | type | code | When |
|---|---|---|---|
| 400 | invalid_request | beta_required | The syntic-beta header is missing. |
| 400 | invalid_request | invalid_name | Name has disallowed characters or is too long. |
| 400 | invalid_request | unknown_model | model is not in the catalogue. |
| 400 | invalid_request | invalid_tool_schema | A tool’s parameters is not a valid JSON Schema object, a name repeats, or a limit below is exceeded. |
| 400 | invalid_request | unknown_reference | A skill, vault, memory store or environment id does not exist in this workspace. |
| 401 | authentication | invalid_api_key | As for every endpoint. |
| 403 | permission | role_required | The key’s creator lacks the role for this change. |
| 404 | not_found | agent_not_found | No such agent in this workspace. |
| 409 | invalid_request | name_taken | Another agent in the workspace has this name. |
| 409 | invalid_request | version_conflict | if_version is not the current version. |
| 409 | invalid_request | agent_has_running_sessions | Delete attempted while sessions are running. |
| 429 | rate_limit | rate_limited | See rate-limit headers. |
Limits
| Limit | Value |
|---|---|
| Agents per workspace | 500 active |
| Versions kept per agent | All of them |
| Tools per agent | 128 |
Size of one tool’s parameters schema | 16 KB |
| Total serialized definition | 512 KB |
| MCP servers per agent | 20 |
| Rate limit for these endpoints | 60 writes and 600 reads per minute per workspace |
Creating and editing definitions is free. Tokens are billed when sessions run.
Build notes for the platform team
- Reuse the Console’s agent table; add a
versioncolumn and an append-only versions table rather than a second schema. - Every write produces an audit event (
agent.created,agent.updated,agent.archived,agent.deleted) with the key id as actor. - Validate tool schemas with the same validator used by strict tools so both paths reject the same inputs.
- Never return vault secret values or MCP tokens in any agent response.
Related
- Sessions: run an agent.
- Scheduled and triggered runs
- Environments, Memory stores, Credential vaults
- Tool calling