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

# Build with AI

> Skill and context prompt for building Deck integrations with AI coding agents.

AI coding tools write better Deck integration code when they have the right context. This page provides a skill and system prompt you can load into your tool of choice so it understands the Deck v2 API, follows correct patterns, and avoids common mistakes.

## Deck skill

The Deck skill is a [SKILL.md](https://docs.deck.co/skill.md) file your agent can load to learn how to build Deck integrations. It bundles a product summary, API quick reference, decision rules, common gotchas, and a verification checklist.

Download it from [https://docs.deck.co/skill.md](https://docs.deck.co/skill.md) and drop it in your agent's skills directory.

## Prompt

If you'd rather use a prompt than the skill, paste the prompt below into your project's context file so it loads in every session. Common locations:

| Tool               | How to load                                                                            |
| ------------------ | -------------------------------------------------------------------------------------- |
| **Cursor**         | Add to your [project rules](https://cursor.com/docs/context/rules) in `.cursor/rules/` |
| **Claude Code**    | Add to your `CLAUDE.md` file in the project root                                       |
| **Codex**          | Add to your `AGENTS.md` file in the project root                                       |
| **GitHub Copilot** | Save to `.github/copilot-instructions.md`                                              |
| **Other**          | Paste into your tool's system prompt or project context                                |

Copy the full prompt below, or combine sections that are relevant to your integration.

````markdown theme={null}
# Deck v2 API Context

Deck is a platform that connects to external websites on behalf of your users. You make REST API calls, Deck handles authentication, navigation, and data extraction, and returns structured JSON results. You never interact with websites directly.

## API Basics

- Base URL: `https://api.deck.co/v2`
- Auth: `Authorization: Bearer sk_live_...`
- Content type: `application/json`
- All work is asynchronous. API calls return immediately. Results arrive via events.
- There is no sandbox or test environment. All calls are live.

## Core Integration Flow

1. Create a **Source** (an external website, defined by type and URL)
2. Store a **Credential** (encrypted auth details for a user on a source)
3. Create a **Task** (defines what to do on the source)
4. Run the **Task** with a credential (Deck creates a session, authenticates, and executes)
5. Receive results via **Events** pushed to your webhook or queue

## Resource ID Prefixes

Every resource ID is prefixed by type:

| Prefix | Resource |
| --- | --- |
| `agt_` | Agent |
| `src_` | Source |
| `cred_` | Credential |
| `sess_` | Session |
| `task_` | Task |
| `trun_` | Task Run |
| `stor_` | Storage Item |
| `evt_` | Event |
| `evtd_` | Event Destination |
| `edlv_` | Event Delivery |
| `req_` | Request ID |

## Key Endpoints

| Action | Method | Path |
| --- | --- | --- |
| Create source | POST | `/v2/sources` |
| Store credential | POST | `/v2/credentials` |
| Delete credential | DELETE | `/v2/credentials/{credential_id}` |
| Create task | POST | `/v2/tasks` |
| Run task | POST | `/v2/tasks/{task_id}/run` |
| Submit interaction | POST | `/v2/task-runs/{run_id}/interaction` |
| List task runs | GET | `/v2/task-runs` |
| Get task run | GET | `/v2/task-runs/{run_id}?include=input,storage,artifacts` |
| Create event destination | POST | `/v2/event-destinations` |

## Credential Authentication

Most sources use `username_password`:

```json
{
  "source_id": "src_...",
  "auth_method": "username_password",
  "auth_credentials": { "username": "...", "password": "..." }
}
```

Valid `auth_method` values: `username_password`, `source_fields`, `none`.

## Credential Statuses

`unverified` → `verified` → (optionally `invalid`) → `deleted`

- `unverified` means stored but not yet used in a successful authentication
- `verified` means successfully authenticated at least once
- `invalid` means the source rejected the credentials
- `deleted` means permanently removed from the vault

## Session Statuses

Sessions are created automatically when a task runs: `queued` → `running` → `idle` (no active tasks) → `completing` → `completed` | `failed`

You can reuse a session by passing `session_id` when running a task.

## Interactions

When a task run needs user input (MFA, security question, account selection), status becomes `interaction_required`. The response includes an `interaction` object with `type`, `message`, and `fields`. Each field has a `name`, `type`, and `label`. Submit the response to:

- Task runs: `POST /v2/task-runs/{run_id}/interaction`

Body: `{ "input": { "<field_name>": "<value>" } }`

## Events and Webhooks

Deck pushes events to destinations you configure (webhooks, AWS SQS, Kinesis, S3, GCP Pub/Sub, Azure Service Bus, RabbitMQ, Hookdeck).

Event format:
```json
{
  "id": "evt_...",
  "type": "task_run.completed",
  "data": { ... },
  "created_at": "2025-01-15T09:30:00Z"
}
```

Key event types:
- `credential.verified`, `credential.invalid`, `credential.deleted`
- `session.queued`, `session.running`, `session.idle`, `session.completing`, `session.completed`, `session.failed`
- `task_run.queued`, `task_run.running`, `task_run.pending`, `task_run.completed`, `task_run.failed`
- `task_run.interaction_required`

Webhook signatures follow the Standard Webhooks specification. Use the `standardwebhooks` SDK to verify with your `whsec_` signing secret.

## Pagination

All list endpoints use cursor-based pagination:
- Query params: `limit` (default 20, max 100), `cursor`
- Response: `{ "data": [...], "has_more": true, "next_cursor": "eyJ..." }`
- Loop until `has_more` is `false`

## Idempotency

All POST, PATCH, and DELETE endpoints accept an `Idempotency-Key` header (max 256 chars, expires after 24h). Same key + same params returns the original response. Same key + different params returns HTTP 409.

## Error Format

```json
{
  "errors": [{ "type": "request", "code": "input_missing", "field": "name", "message": "..." }],
  "request_id": "req_..."
}
```

Always branch on `type` and `code`, never on `message`. Always log `request_id` for debugging.

Common error codes:
- `rate_limit_exceeded` (429) - back off with exponential delay
- `auth_invalid` (401) - credentials are wrong
- `interaction_timeout` (408) - interaction expired, resubmit the task run
- `input_missing` (400) - check the `field` property
- `source_not_available` (503) - external website is down, retry later
- `idempotency_error` (409) - same key with different params

## CRITICAL RULES FOR AI MODELS

### Always do

1. Use event destinations (webhooks, queues) to receive results. Never poll.
2. Use `Idempotency-Key` on all create requests.
3. Handle `interaction_required` status on task runs.
4. Paginate with `cursor` and `has_more`, never offsets.
5. Verify webhook signatures using the Standard Webhooks SDK.
6. Handle errors by `type` and `code`, never by `message`.
7. Write task prompts as high-level, source-agnostic goals. A task runs across every source that supports it, so never reference a specific website or UI. The prompt is combined with Deck's agent harness, which handles navigation, authentication, and tool use. Example: "Log in and fetch the latest bill." not "Click the sign-in button, enter credentials, navigate to billing..."
8. Design task input schemas with only the fields that change between runs. Keep them source-agnostic. Do not add fields tied to a specific source.
9. Design task output schemas with generic fields any supporting source can populate. Optional fields return `null` when the source doesn't contain that information; if the source doesn't contain a `required` field, the run fails with a `task_not_supported` error. Do not mirror a single source's data model.
10. Reference task inputs by name in the prompt, never inline values: "Download bills between {start_date} and {end_date}".

### Never do

1. Do not poll `/v2/task-runs/{id}` in a loop. Use events.
2. Do not hardcode source IDs. Create sources via the API or look them up.
3. Do not ignore `interaction_required`. Users may need to complete MFA.
4. Do not assume task runs complete synchronously. They are always async.
5. Do not send credentials from the client. Always proxy through your server.
6. Do not branch on error `message` strings. They can change without notice.
7. Do not include detailed navigation steps in task prompts. They conflict with the agent harness and can restrict tools the agent needs.
8. Do not add source-specific fields to task schemas. A task must work across all sources that support it.
9. Do not put credentials or login instructions in task prompts. Deck authenticates the session with the stored credential.
````

## MCP server

If your tool supports MCP, connect the [Deck Docs MCP server](/integrations/mcp) at `https://docs.deck.co/mcp`. It gives your agent live search over this site, so answers come from the current docs instead of training data. It also exposes the Deck skill as an MCP resource.

## Raw files

Point your AI assistant at these URLs to give it canonical source data:

| File                                                                   | Purpose                                           |
| ---------------------------------------------------------------------- | ------------------------------------------------- |
| [`/api-reference/v2.json`](https://docs.deck.co/api-reference/v2.json) | OpenAPI 3.1 spec for the Deck v2 API              |
| [`/llms.txt`](https://docs.deck.co/llms.txt)                           | Index of all docs pages, formatted for LLMs       |
| [`/llms-full.txt`](https://docs.deck.co/llms-full.txt)                 | Full docs content concatenated into a single file |
