Pi Durable Platformdocs

API overview and authentication

Reaching Pi Durable Platform agents from your own app: the three kinds of credentials, which routes take which, the response envelope, revisions, and choosing between a service account and OAuth Connect.

Your app reaches Pi Durable Platform's agents through its HTTP API, at the platform's APP_URL (here https://agents.example.com). The app never talks to an agent's runtime: it sends messages to the platform and follows the conversation as server-sent events.

# Send a message (202), then follow the thread
curl -X POST https://agents.example.com/v1/agents/$AGENT/threads/conv-1/messages \
  -H "Authorization: Bearer $PDP_KEY" -H "Content-Type: application/json" \
  -d '{"text": "Hello", "requestId": "m1"}'
curl -N https://agents.example.com/v1/agents/$AGENT/threads/conv-1/events \
  -H "Authorization: Bearer $PDP_KEY"

Credentials

Send one as Authorization: Bearer <credential>.

CredentialPrefixActs asGet it from
Service account keypdp_sa_The team's service account, in its own team, with its role (member or editor)A team owner or admin: Service accounts
Personal API keypdp_A person, with their accessThe person: API keys
OAuth Connect access tokenpdpat_A person who connected your app, without their platform roleOAuth Connect

Which to use

  • Your app acts for itself, for example giving each of its users an agent of their own inside your team: a service account. The conversations belong to the app; see Agents by key.
  • Your app acts for a person (their personal workspace, their teams' agents, their private threads): OAuth Connect. The person signs in to the platform once and allows your app.
  • A person's own script: a personal API key.

Both service-account mode and OAuth Connect are supported; an app can offer both, and use OAuth Connect where the platform advertises it (connect in GET /v1/auth/config).

Which routes take which credentials

Bearer credentials reach the agent routes and a few readings:

  • agents, threads, messages, events and thread MCP servers (/v1/agents…, /v1/teams/{team}/agents…);
  • template listings (GET /v1/agent-templates, the team's templates);
  • a team's models, usage, limits and MCP servers;
  • GET /v1/me, GET /v1/teams and GET /v1/teams/{team}, for people only: a service account key gets 403 person_required.

Everything else (administration, members, invites, creating keys, service accounts, connected apps, consent) needs a browser session. PUT …/agents/by-key/… is for service accounts only.

Conventions

  • Envelope: success is {"data": …}; an error is {"error": {"code": "…", "message": "…"}} with an HTTP status. See Errors and limits.
  • Request IDs: every response has X-Request-ID. Quote it when you report a problem; it's in the platform's logs and audit log.
  • Not allowed looks like not found: an agent or thread the caller may not use answers 404, the same as one that doesn't exist.
  • Revisions: objects that can be edited carry a revision, returned as ETag. PATCH sends it back as If-Match: missing is 428 revision_required, stale is 412 revision_conflict.
  • IDs are UUIDs. Teams also have slugs; routes with {team} take either.
  • Times are RFC 3339 strings in resources, and Unix milliseconds in conversations (at, createdAt of threads, …).
  • Browser sessions also need X-CSRF-Token (from GET /v1/me) and a same-origin Origin on writes. Bearer requests need neither.

Checking a credential

curl https://agents.example.com/v1/me -H "Authorization: Bearer $TOKEN"

For a person, it returns who they are, their groups, their teams and their capabilities (always false for an app's token). It wakes no agent. For a service account, use GET /v1/agents instead.

Next

The full reference is generated from the OpenAPI document: see API reference. The API may change between releases before 1.0.

On this page