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

# Devices API

> Manage paired devices with pairing, approval, denial, and revocation actions

# Devices API

Manage device pairing for your agent. Devices can be self-paired (auto-approved) or created via a pairing code flow where they start in a `pending` state and can be approved, denied, or revoked.

<Note>All device endpoints require an authenticated session. Unauthenticated requests receive a `401` response.</Note>

## List devices

```http theme={"dark"}
GET /api/devices
```

Returns all pending and approved devices grouped by status.

### Response

```json theme={"dark"}
{
  "pending": [
    {
      "id": "dev_pending_1",
      "name": "iPhone 15 Pro — Atlas Mobile",
      "ip": "86.23.104.12",
      "firstSeen": "2026-03-27T14:22:00Z",
      "lastSeen": "2026-03-27T15:30:00Z",
      "status": "pending"
    }
  ],
  "approved": [
    {
      "id": "dev_approved_1",
      "name": "Docker Container — agentbot-prod",
      "ip": "10.0.1.42",
      "firstSeen": "2026-03-25T09:00:00Z",
      "lastSeen": "2026-03-27T15:29:00Z",
      "status": "approved"
    }
  ]
}
```

| Field      | Type  | Description                     |
| ---------- | ----- | ------------------------------- |
| `pending`  | array | Devices awaiting approval       |
| `approved` | array | Devices that have been approved |

### Device object

| Field       | Type   | Description                                             |
| ----------- | ------ | ------------------------------------------------------- |
| `id`        | string | Unique device identifier                                |
| `name`      | string | Human-readable device name                              |
| `ip`        | string | IP address of the device                                |
| `firstSeen` | string | ISO 8601 timestamp when the device was first detected   |
| `lastSeen`  | string | ISO 8601 timestamp of the device's most recent activity |
| `status`    | string | One of `pending`, `approved`, `denied`, or `revoked`    |

### Errors

| Code | Description                               |
| ---- | ----------------------------------------- |
| 401  | `Unauthorized` — no authenticated session |

***

## Generate a pairing code

```http theme={"dark"}
PUT /api/devices
```

Creates a new device in `pending` status and returns a pairing code. Use this when you want another device to complete the pairing flow via a code or URL.

### Query parameters

| Parameter | Type   | Required | Default     | Description                        |
| --------- | ------ | -------- | ----------- | ---------------------------------- |
| `name`    | string | No       | `My Device` | Human-readable name for the device |

### Response

```json theme={"dark"}
{
  "success": true,
  "deviceId": "dev_abc123",
  "pairingCode": "X7K2M9",
  "pairingUrl": "/dashboard/devices?pair=X7K2M9&id=dev_abc123"
}
```

| Field         | Type    | Description                                       |
| ------------- | ------- | ------------------------------------------------- |
| `success`     | boolean | `true` when the pairing code was generated        |
| `deviceId`    | string  | Identifier of the newly created device            |
| `pairingCode` | string  | Six-character alphanumeric code for pairing       |
| `pairingUrl`  | string  | URL path to complete the pairing in the dashboard |

### Example

```bash theme={"dark"}
curl -X PUT "https://agentbot.sh/api/devices?name=Living+Room+iPad"
```

### Errors

| Code | Description                               |
| ---- | ----------------------------------------- |
| 401  | `Unauthorized` — no authenticated session |

***

## Self-pair a device

```http theme={"dark"}
POST /api/devices/pair
```

Pairs the current device directly with auto-approval. This is used for self-pairing flows such as the "Pair My iPhone" button, where the requesting device is the one being paired.

### Request body

| Field  | Type   | Required | Default     | Description                        |
| ------ | ------ | -------- | ----------- | ---------------------------------- |
| `name` | string | No       | `My iPhone` | Human-readable name for the device |

### Response

```json theme={"dark"}
{
  "success": true,
  "device": {
    "id": "dev_xyz789",
    "name": "My iPhone",
    "status": "approved",
    "pairedAt": "2026-04-09T16:20:00Z"
  }
}
```

| Field             | Type    | Description                                      |
| ----------------- | ------- | ------------------------------------------------ |
| `success`         | boolean | `true` when the device was paired                |
| `device`          | object  | The newly paired device                          |
| `device.id`       | string  | Unique device identifier                         |
| `device.name`     | string  | Human-readable device name                       |
| `device.status`   | string  | Always `approved` for self-paired devices        |
| `device.pairedAt` | string  | ISO 8601 timestamp of when the device was paired |

### Example

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/devices/pair \
  -H "Content-Type: application/json" \
  -d '{
    "name": "My iPhone"
  }'
```

### Errors

| Code | Description                               |
| ---- | ----------------------------------------- |
| 401  | `Unauthorized` — no authenticated session |

***

## Manage a device

```http theme={"dark"}
POST /api/devices
```

Approve, deny, or revoke a device. The action must be valid for the device's current status:

* `approve` — only valid when the device is `pending`
* `deny` — only valid when the device is `pending`
* `revoke` — only valid when the device is `approved`

### Request body

| Field      | Type   | Required | Description                            |
| ---------- | ------ | -------- | -------------------------------------- |
| `deviceId` | string | Yes      | The identifier of the device to act on |
| `action`   | string | Yes      | One of `approve`, `deny`, or `revoke`  |

### Response

```json theme={"dark"}
{
  "success": true,
  "pending": [],
  "approved": [
    {
      "id": "dev_approved_1",
      "name": "iPhone 15 Pro — Atlas Mobile",
      "ip": "86.23.104.12",
      "firstSeen": "2026-03-27T14:22:00Z",
      "lastSeen": "2026-03-27T15:35:00Z",
      "status": "approved"
    }
  ]
}
```

| Field      | Type    | Description                        |
| ---------- | ------- | ---------------------------------- |
| `success`  | boolean | `true` when the action was applied |
| `pending`  | array   | Remaining pending devices          |
| `approved` | array   | Currently approved devices         |

### Errors

| Code | Description                                                                                     |
| ---- | ----------------------------------------------------------------------------------------------- |
| 401  | `Unauthorized` — no authenticated session                                                       |
| 400  | `Missing required fields: deviceId, action` — one or both required fields are missing           |
| 400  | `Invalid action. Must be: approve, deny, or revoke` — the action is not recognized              |
| 400  | `Device is not pending` — attempted to approve or deny a device that is not in `pending` status |
| 400  | `Device is not approved` — attempted to revoke a device that is not in `approved` status        |
| 400  | `Invalid request body` — the request body is not valid JSON                                     |
| 404  | `Device not found` — no device exists with the given identifier                                 |

### Example: approve a device

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/devices \
  -H "Content-Type: application/json" \
  -d '{
    "deviceId": "dev_pending_1",
    "action": "approve"
  }'
```

### Example: revoke a device

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/devices \
  -H "Content-Type: application/json" \
  -d '{
    "deviceId": "dev_approved_1",
    "action": "revoke"
  }'
```

***

## OpenClaw devices proxy (deprecated)

<Warning>These proxy endpoints are deprecated and will be removed in a future release. Device management now uses the local endpoints documented above (`/api/devices` and `/api/devices/pair`) instead of proxying to the agent runtime.</Warning>

The following endpoints previously proxied device management requests to the agent's OpenClaw runtime. They have been replaced by the local device pairing API.

### List paired devices (runtime)

```http theme={"dark"}
GET /api/openclaw/devices
```

Returns the list of devices paired with the agent's runtime. Proxies to the agent's `GET /api/devices` endpoint.

#### Errors

| Code | Description                                                                |
| ---- | -------------------------------------------------------------------------- |
| 401  | `Unauthorized` — no authenticated session                                  |
| 404  | `No agent deployed` — the user has no running agent instance               |
| 502  | `Agent unreachable` — the agent instance did not respond within 10 seconds |

### Manage paired devices (runtime)

```http theme={"dark"}
POST /api/openclaw/devices
```

Perform device actions on the agent's runtime. The `action` field determines the behavior.

#### Request body

| Field      | Type   | Required    | Description                                   |
| ---------- | ------ | ----------- | --------------------------------------------- |
| `action`   | string | Yes         | One of `pair`, `unpair`, or `test-push`       |
| `deviceId` | string | Conditional | Required for `unpair` and `test-push` actions |

#### Actions

| Action      | Description                                      | Proxies to                    |
| ----------- | ------------------------------------------------ | ----------------------------- |
| `pair`      | Generate a QR code for pairing a new device      | `POST /api/devices/pair`      |
| `unpair`    | Unpair an existing device                        | `POST /api/devices/unpair`    |
| `test-push` | Send a test push notification to a paired device | `POST /api/devices/test-push` |

#### Example: pair a new device

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/openclaw/devices \
  -H "Content-Type: application/json" \
  -d '{
    "action": "pair"
  }'
```

#### Example: unpair a device

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/openclaw/devices \
  -H "Content-Type: application/json" \
  -d '{
    "action": "unpair",
    "deviceId": "device_abc123"
  }'
```

#### Example: test push notification

```bash theme={"dark"}
curl -X POST https://agentbot.sh/api/openclaw/devices \
  -H "Content-Type: application/json" \
  -d '{
    "action": "test-push",
    "deviceId": "device_abc123"
  }'
```

#### Errors

| Code | Description                                                                   |
| ---- | ----------------------------------------------------------------------------- |
| 400  | `Invalid action` — the `action` field is not `pair`, `unpair`, or `test-push` |
| 400  | `Invalid request body` — the request body is not valid JSON                   |
| 401  | `Unauthorized` — no authenticated session                                     |
| 404  | `No agent deployed` — the user has no running agent instance                  |
| 502  | `Agent unreachable` — the agent instance did not respond within 15 seconds    |
