> ## Documentation Index
> Fetch the complete documentation index at: https://docs.runtools.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Run Agent

> Run an agent one-shot or in a persisted thread

`POST /v1/run` is the canonical agent run endpoint. Set `stream: false` for JSON responses. When `stream` is omitted or `true`, the endpoint returns Server-Sent Events for sandbox-backed and managed agents.

Runs can target `in_sandbox`, `managed`, or `local-mac` agents. `in_sandbox` runs wake the linked sandbox when possible. `local-mac` runs either register a thread for the local sidecar caller or dispatch over RunMesh to the bound device.

## Request Body

<ParamField body="agent" type="string" required>
  Agent slug or ID.
</ParamField>

<ParamField body="prompt" type="string">
  User prompt. Either `prompt` or `messages` is required.
</ParamField>

<ParamField body="messages" type="array">
  Caller-managed conversation history. Use this when you do not want server-managed thread history.
</ParamField>

<ParamField body="threadId" type="string">
  Persist the run into a server-managed thread. Reuse the same ID to continue the thread.
</ParamField>

<ParamField body="stream" type="boolean" default="true">
  `false` returns JSON. `true` returns Server-Sent Events.
</ParamField>

<ParamField body="config" type="object">
  Per-run overrides: `maxTokens`, `maxTurns`, and `temperature`.
</ParamField>

<ParamField body="metadata" type="object">
  Caller metadata stored with the run.
</ParamField>

## Response

<ResponseField name="runId" type="string">
  Run ID.
</ResponseField>

<ResponseField name="status" type="string">
  Run status, such as `completed`, `registered`, or `dispatched`.
</ResponseField>

<ResponseField name="result" type="string">
  Final assistant response for non-streaming runs.
</ResponseField>

<ResponseField name="threadId" type="string">
  Thread ID when threading is active.
</ResponseField>

<ResponseField name="rolloutId" type="string">
  Active rollout ID when the run is registered for a cloud thread.
</ResponseField>

<ResponseField name="executionMode" type="string">
  `in_sandbox`, `managed`, or `local-mac`.
</ResponseField>

<ResponseField name="usage" type="object">
  Token usage when available.
</ResponseField>

<RequestExample>
  ```bash cURL theme={null}
  curl -X POST https://api.runtools.ai/v1/run \
    -H "X-API-Key: $RUNTOOLS_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "agent": "code-assistant",
      "prompt": "Run the tests and summarize failures.",
      "stream": false,
      "config": {
        "maxTurns": 12
      }
    }'
  ```

  ```typescript SDK theme={null}
  const result = await rt.agent.run(
    'code-assistant',
    'Run the tests and summarize failures.',
    {
      maxTurns: 12,
    },
  );

  console.log(result.result);
  ```

  ```typescript Threaded SDK theme={null}
  const first = await rt.agent.run('code-assistant', 'Inspect this repo.', {
    thread: true,
  });

  await rt.agent.run('code-assistant', 'Now fix the failing test.', {
    threadId: first.threadId,
  });
  ```
</RequestExample>

<ResponseExample>
  ```json 200 OK theme={null}
  {
    "data": {
      "runId": "run_abc123",
      "sandboxId": "sandbox-abc123",
      "executionMode": "in_sandbox",
      "status": "completed",
      "result": "The test suite is green.",
      "usage": {
        "inputTokens": 1480,
        "outputTokens": 322
      },
      "iterations": 4,
      "threadId": "thr_abc123"
    }
  }
  ```

  ```json 409 Conflict theme={null}
  {
    "error": {
      "code": "THREAD_BUSY",
      "message": "Thread is busy"
    }
  }
  ```
</ResponseExample>

## Thread APIs

Thread history and live updates are exposed through `/v1/threads`, not the run endpoint:

```bash theme={null}
curl "https://api.runtools.ai/v1/threads?limit=25" \
  -H "X-API-Key: $RUNTOOLS_API_KEY"
```

```typescript theme={null}
const { threads } = await rt.threads.list();
const detail = await rt.threads.get(threads[0].id);
await rt.threads.archive(threads[0].id);
```

Use `/v1/threads/{threadId}/events` for durable event history and `wss://api.runtools.ai/v1/threads/{threadId}/events?api_key=...` for live frames.

## Legacy Per-Agent Endpoint

`POST /v1/agents/{slug}/run` still exists, but new code should prefer `POST /v1/run` because it has the same request shape used by the SDK and thread helpers.
