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

> ## Agent Instructions
> H Platform has four products: the Agents API (managed computer-use agents, base URL https://agp.eu.hcompany.ai/api/v2 or https://agp.hcompany.ai/api/v2 for the US), the Models API (OpenAI-compatible Holo vision-language models at https://api.hcompany.ai/v1), HoloDesktop CLI (Holo on the user's own desktop), and HoloTab (a free no-code Chrome extension that runs Holo in the user's browser, with recordable routines and schedules).
> Authenticate with a bearer API key from the HAI_API_KEY environment variable. SDKs: `pip install hai-agents` (Python, `from hai_agents import Client`) and `npm install hai-agents` (TypeScript, `import { HaiAgentsClient } from "hai-agents"`). CLI: `hai`.
> Agents do work in a browser or on a desktop; describe the task as an imperative instruction. To run a task quickly, prefer the pre-built agent `h/web-surfer-flash`. Read results from the session's `latest_answer` after it reaches a terminal status.
> Sessions are the unit of work; wait for a terminal status (completed, failed, timed_out, interrupted) before reading the answer. Use webhooks or the `changes` long-poll endpoint to follow progress.

# Sessions

> A session is one run of an agent on a task: how to wait for the result, lifecycle states, the session object, overrides, listing and filtering.

A session is one run of an agent on a task. Create it, wait for the result, and steer it while it runs. Every follow-up call (message, pause, cancel) uses the session's `id`. Optional [`max_steps` and `max_time_s`](/agents-api/sessions/create) caps bound the run before the agent is asked for a final answer.

<CodeGroup>
  ```bash CLI theme={"system"}
  hai run "Open Hacker News and list the top 3 stories with their URLs." \
    --agent h/web-surfer-flash
  ```

  ```bash cURL theme={"system"}
  curl -X POST https://agp.eu.hcompany.ai/api/v2/sessions \
    -H "Authorization: Bearer $HAI_API_KEY" -H "Content-Type: application/json" \
    -d '{"agent": "h/web-surfer-flash", "messages": "Open Hacker News and list the top 3 stories with their URLs."}' | jq -r .id
  ```

  ```python Python theme={"system"}
  from hai_agents import Client

  client = Client()
  session = client.sessions.create_session(
      agent="h/web-surfer-flash",
      messages="Open Hacker News and list the top 3 stories with their URLs.",
  )
  print(session.id)
  ```

  ```typescript TypeScript theme={"system"}
  import { HaiAgentsClient } from "hai-agents";

  const client = new HaiAgentsClient();
  const session = await client.sessions.createSession({
    body: {
      agent: "h/web-surfer-flash",
      messages: "Open Hacker News and list the top 3 stories with their URLs.",
    },
  });
  console.log(session.id);
  ```
</CodeGroup>

`messages` takes a plain string (one user message) or message objects like `[{"type": "user_message", "message": "..."}]`. The CLI blocks until the run ends. The create calls return at once with the `id`.

## Wait for the result

The final answer is `answer` on the result object and on `changes`, and `latest_answer` on the session object.

| Way | Use when | You get back |
| - | - | - |
| `client.run_session(...)` / `runSession` ([Quickstart](/agents-api/quickstart#run-a-pre-built-agent)) | One call: create, block, read | The final result: `status`, `answer`, `outcome`, `error_code` |
| `client.start_session(...)` then `session.wait_for_completion()` ([Watch and steer](/agents-api/observe-and-steer#watch-a-run)) | Read or steer while it runs, then block | A handle bound to the `id`, then the same final result |
| `session.stream()` ([Watch and steer](/agents-api/observe-and-steer#stream-events-as-they-arrive)) | A live, read-only event feed | Each event in order until the session settles |
| `wait_for_session(client, id)` / `waitForSession` ([Changes](/agents-api/sessions/changes#long-polling-pattern)) | You hold an `id` created elsewhere | Drains `changes`, returns the final result |
| [`GET /sessions/{id}/changes`](/agents-api/sessions/changes) long-poll | Raw HTTP, any language | New events plus `answer` once it lands |
| [Webhooks](/agents-api/webhooks/overview) | Batches and queued runs, without polling | `session.completed` and the other status events |
| [`GET /sessions/{id}`](/agents-api/sessions/retrieve) | Read a settled run any time | `latest_answer`, no cursor needed |

Polling `changes` by hand has gotchas: see its [polling rules](/agents-api/sessions/changes#polling-rules).

## Lifecycle

Every session moves through the same states, whichever agent runs it.

| Status | Meaning | Terminal |
| - | - | - |
| `queued` | Accepted above your [concurrency limit](/agents-api/plans-and-limits#concurrent-sessions). Starts automatically, oldest first, as slots free up. | No |
| `pending` | Created, agent is launching. | No |
| `running` | Agent is working on the task. | No |
| `paused` | [Paused](/agents-api/sessions/pause) via the API. State is preserved. | No |
| `idle` | Interactive agent finished a task and waits for your next message. | No |
| `awaiting_tool_results` | Blocked on [custom tool](/agents-api/custom-tools) calls your code must answer. | No |
| `completed` | Finished the task. | Yes |
| `timed_out` | Exceeded the maximum allowed time. | Yes |
| `interrupted` | Cancelled via [`DELETE`](/agents-api/sessions/cancel). | Yes |
| `failed` | An unrecoverable error occurred. | Yes |

## Session object

| Field | Description |
| - | - |
| `id` | The session's UUID, used by every follow-up call. |
| `request` | What you submitted, with `agent` resolved to its full spec even if you passed a catalog id. |
| `status` | The live `status`, step count, per-model token usage (`usage_per_model`), any `error` and `error_code`, the agent's self-assessed `outcome`, and `subagent_session_ids`. See [Session status](/agents-api/sessions/status). |
| `agent_view_url` | The session's [Agent View](/agents-api/observe-and-steer) page, for live viewing and replay. |
| `latest_answer` | The agent's latest final answer, mirrored from [`changes`](/agents-api/sessions/changes). `null` until it first answers. |
| `created_at` / `started_at` / `finished_at` | The run's timeline. The last two are `null` until they happen. |

## Overrides

`overrides` adjusts a catalog agent for one run, without defining a new agent. It is a map on the [create-session](/agents-api/sessions/create) body: each key is a dotted path into the resolved request, and its value replaces what the path points to. Paths apply after `agent` is expanded from its catalog id.

| Path syntax | Example |
| - | - |
| Dots walk into objects | `agent.instructions`, `agent.model`, `agent.answer_format` ([structured answer](/agents-api/structured-output)) |
| `[field=value]` picks a list member | `agent.environments[kind=web].start_url`, `agent.environments[kind=web].mode` |

Each value must match the type of the field it targets. An unknown path or a wrong type returns `422` at creation, before the agent runs.

For example, send a catalog web surfer to a chosen start page:

<CodeGroup>
  ```bash CLI theme={"system"}
  hai run "Summarize the top discussion right now" \
    --agent h/web-surfer-flash \
    --override 'agent.environments[kind=web].start_url=https://news.ycombinator.com'
  ```

  ```bash cURL theme={"system"}
  curl -X POST https://agp.eu.hcompany.ai/api/v2/sessions \
    -H "Authorization: Bearer $HAI_API_KEY" -H "Content-Type: application/json" \
    -d '{
      "agent": "h/web-surfer-flash",
      "messages": "Summarize the top discussion right now",
      "overrides": {"agent.environments[kind=web].start_url": "https://news.ycombinator.com"}
    }'
  ```

  ```python Python theme={"system"}
  session = client.sessions.create_session(
      agent="h/web-surfer-flash",
      messages="Summarize the top discussion right now",
      overrides={"agent.environments[kind=web].start_url": "https://news.ycombinator.com"},
  )
  ```

  ```typescript TypeScript theme={"system"}
  const session = await client.sessions.createSession({
    body: {
      agent: "h/web-surfer-flash",
      messages: "Summarize the top discussion right now",
      overrides: { "agent.environments[kind=web].start_url": "https://news.ycombinator.com" },
    },
  });
  ```
</CodeGroup>

## Listing and filtering

[`GET /api/v2/sessions`](/agents-api/sessions/list) pages through your sessions, newest first. Combine filters, for example `?status=running&status=queued&agent=web-price-finder`.

| Filter | Type | Description |
| - | - | - |
| `status` | string (repeatable) | Session status. |
| `agent` | string (repeatable) | Agent identifier, like `h/web-surfer-flash`. |
| `group_id` | string | Group, for multi-session workflows. |
| `parent_session_id` | string | [Child sessions](/agents-api/multi-agent) of a parent. |
| `schedule_id` | string | Sessions created by a [schedule](/agents-api/schedules/overview). |
| `search` | string | Case-insensitive match on the first message or answer. |
| `created_before` / `created_after` | string | Creation time bounds (ISO 8601). |
| `finished_before` / `finished_after` | string | Finish time bounds (ISO 8601). |
| `owner` | string | Access scope. Default `me-in-organization`. |

Responses use the standard [page envelope](/agents-api/api-reference#pagination). The SDKs expose it as `client.sessions.list_sessions(...)` / `listSessions`. See [List sessions](/agents-api/sessions/list) for `size`, `sort`, and every parameter.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.