Tools & Sandbox
Build custom tools with the Tool Builder and execute code in isolated sandbox environments with resource limits and security controls.
Tool Builder
List Tools
GET /v1/tools The organization is taken from the authenticated session.
Query Parameters
| Parameter | Type | Description |
|---|---|---|
status | string | Filter: draft, testing, deployed, disabled |
page | integer | 1-based page number |
page_size | integer | Results per page (default: 25, max: 100) |
Response
{
"data": {
"items": [
{
"id": "...",
"name": "Cost Estimator",
"description": "Estimate construction costs based on materials and labor",
"tool_type": "api",
"status": "deployed",
"created_at": "2026-03-01T10:00:00Z",
"updated_at": "2026-04-10T14:30:00Z"
}
],
"total": 5,
"page": 1,
"page_size": 25
}
} Create Tool
POST /v1/tools The organization is taken from the authenticated session and must not be sent in the body (unknown fields are rejected).
Request Body
{
"name": "Cost Estimator",
"description": "Estimate construction costs based on materials and labor",
"tool_type": "api",
"schema_def": {
"input": {
"type": "object",
"properties": {
"materials": {
"type": "array",
"items": {
"type": "object",
"properties": {
"name": { "type": "string" },
"quantity": { "type": "number" },
"unit_cost": { "type": "number" }
}
}
},
"labor_hours": { "type": "number" }
}
},
"output": {
"type": "object",
"properties": {
"total_cost": { "type": "number" },
"breakdown": { "type": "object" }
}
}
},
"endpoint_url": "https://api.example.com/estimate",
"auth_config": {
"type": "bearer",
"token_env": "ESTIMATOR_API_KEY"
}
} Tool Schema Fields
| Field | Type | Description |
|---|---|---|
name | string | Display name for the tool |
description | string | What the tool does (shown to AI assistant) |
tool_type | string | Tool type: api, function, script |
schema_def | object | JSON Schema defining input and output |
endpoint_url | string | URL to invoke for API tools |
auth_config | object | Authentication configuration for the endpoint |
Do not send id, created_at, updated_at,
or org_id in the request body; these are assigned by the
server and any unknown field is rejected.
Response
A successful create returns 201 Created with the complete tool
record inside the standard envelope. New tools start in draft
status at version 1.
{
"success": true,
"data": {
"id": "...",
"org_id": "...",
"name": "Cost Estimator",
"description": "Estimate construction costs based on materials and labor",
"tool_type": "api",
"schema_def": { },
"endpoint_url": "https://api.example.com/estimate",
"auth_config": { "type": "bearer", "token_env": "ESTIMATOR_API_KEY" },
"status": "draft",
"version": 1,
"created_by": "...",
"created_at": "2026-03-01T10:00:00Z",
"updated_at": "2026-03-01T10:00:00Z"
}
} Response Codes
| Status | Meaning |
|---|---|
201 Created | Tool created; the full record is returned |
400 Bad Request | Request body failed validation, contained an unknown field, was not valid JSON, or carried a blocked endpoint_url |
401 Unauthorized | Missing or invalid authentication |
403 Forbidden | Caller lacks the permission to create tools |
409 Conflict | A tool with the same name already exists in the organization |
500 Internal Server Error | Unexpected server error |
Get Tool
GET /v1/tools/:id Update Tool
PUT /v1/tools/:id Delete Tool
DELETE /v1/tools/:id Tool Status Lifecycle
| Status | Description |
|---|---|
draft | Under development, not available to the AI assistant |
testing | Available in test mode for validation |
deployed | Live and available to the AI assistant |
disabled | Temporarily disabled, not available |
Sandbox
Provision Sandbox
POST /v1/sandbox The organization is taken from the authenticated session. A session id is minted automatically when one is not supplied. An optional Git repository can be cloned into the workspace on provision.
Request Body
{
"sessionId": "...",
"size": "standard-1",
"gitRepo": "owner/repo",
"gitBranch": "main",
"envVars": {
"DATA_DIR": "/workspace/data"
}
} Sandbox Sizes
Sandboxes run on named instance types. standard-1 is
the default. The legacy tokens small, standard,
and large are still accepted and map to standard-2,
standard-3, and standard-4 respectively.
| Size | Description |
|---|---|
basic | Smallest instance for lightweight tasks |
standard-1 | General-purpose execution (default) |
standard-2 | Larger general-purpose workloads |
standard-3 | Compute-heavy tasks |
standard-4 | Largest instance for the heaviest workloads |
A sandbox is an ephemeral, isolated runtime session rather than a stored
record, so the request body carries only provisioning inputs. Do not send
org_id; it is taken from the authenticated session.
Response
A successful provision returns 201 Created with the session
handle inside the standard envelope.
{
"success": true,
"data": {
"sessionId": "...",
"sandboxId": "...",
"size": "standard-1",
"status": "ready"
}
} Response Codes
| Status | Meaning |
|---|---|
201 Created | Sandbox provisioned and ready |
400 Bad Request | Provisioning inputs failed validation (size, git repo, or branch) |
401 Unauthorized | Missing or invalid authentication |
403 Forbidden | Caller lacks sandbox access (no active plan or compute credits) |
409 Conflict | The supplied sessionId is already in use |
500 Internal Server Error | Provisioning failed before the sandbox started |
502 Bad Gateway | The sandbox runtime failed to initialize |
Get Sandbox Status
GET /v1/sandbox/status/:sessionId Response
{
"data": {
"active": true,
"status": "ready",
"canResume": false
}
}
A stopped sandbox reports active: false with
canResume: true; resume it with
POST /v1/sandbox/resume/:sessionId.
Run Shell Commands
POST /v1/sandbox/terminal/:sessionId
Drive an interactive shell inside the sandbox. The action
selects the operation: create a shell session,
write input, read the buffer, or exec
a command and capture its output.
Request Body (exec example)
{
"action": "exec",
"command": "python -c 'print(42)'",
"timeout": 30000,
"workdir": "/workspace"
} Security Restrictions
Each sandbox runs in a fully isolated, per-session environment with strict per-organization isolation, so one tenant can never reach another tenant’s sandbox. Shell output returned to callers is scrubbed to avoid persisting credentials into client transcripts.
Tear Down Sandbox
POST /v1/sandbox/teardown/:sessionId
Stops the sandbox and releases its compute resources. The session record is
retained so the same sessionId can later be resumed from its
saved snapshot; to start completely fresh, provision with a new
sessionId.