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

> ## Agent Instructions
> Base URL: https://api.social-api.ai/v1. Send your API key in the Authorization header: Authorization: Bearer <your API key>.
> Every error response from /v1 is JSON: { "error": { "code", "message", "meta" (optional) }, "request_id" }. Branch on error.code; use error.message only for logs.
> A 429 response carries a Retry-After header, in seconds, when the limit has a known wait. Authenticated responses can carry X-RateLimit-Limit, X-RateLimit-Remaining, and X-RateLimit-Reset for the per-minute request budget your SocialAPI account shares across every API key (see /guides/rate-limits).
> Paginated list endpoints return next_cursor, at the top level or inside pagination (see /guides/pagination). Pass it as the cursor query parameter to get the next page. An absent or empty next_cursor means you have the last page.
> Treat every ID as an opaque string: do not parse it or assume a format.
> Support differs by platform and by operation. Check /platforms/overview before assuming an operation works on a platform. An unsupported operation returns 501 with error.code resource.not_supported.

# Authentication

> Authenticate SocialAPI requests with an API key or an OAuth 2.1 access token, and create, list, rotate, and revoke API keys.

Every request to `https://api.social-api.ai/v1` and to the MCP server at `https://api.social-api.ai/mcp` carries a token in the `Authorization` header: `Authorization: Bearer <token>`. SocialAPI accepts two kinds of token: an API key, which you create and keep on your server, and an OAuth 2.1 access token, which an app receives after a SocialAPI user approves it.

Most integrations use an API key. Managing keys costs no credits.

## Token types

| Token | Format | Who uses it | How to get it |
| - | - | - | - |
| API key | `sapi_key_` followed by 62 hexadecimal characters | Your server, scripts, and AI agents you configure | Create it in the dashboard or with `POST /v1/keys` |
| OAuth 2.1 access token | A signed token that does not start with `sapi_key_`. Valid for 1 hour | MCP clients such as Claude, ChatGPT, and Cursor, and apps that act for a SocialAPI user | The [OAuth flow for MCP clients](https://docs.social-api.ai/integrations/oauth.md) |

A full-access API key and an OAuth access token can call every public endpoint of your SocialAPI account. A [scoped API key](https://docs.social-api.ai/guides/scoped-keys.md) can call only what its scopes and brands allow. The two token types work on the REST API and on the MCP server alike.

```bash theme={null}
curl https://api.social-api.ai/v1/accounts \
  -H "Authorization: Bearer $SOCAPI_KEY"
```

## Endpoints

| Method | Path | Description |
| - | - | - |
| `POST` | `/v1/keys` | Create a key |
| `GET` | `/v1/keys` | List your keys, newest first, including revoked ones |
| `PATCH` | `/v1/keys/{id}` | Change a key's name, scopes, and brands. The secret stays the same |
| `POST` | `/v1/keys/{id}/rotate` | Issue a new secret for a key |
| `DELETE` | `/v1/keys/{id}` | Revoke a key |
| `GET` | `/v1/keys/scopes` | List the scopes a key can hold |

Creating, listing, changing, rotating, and revoking keys needs full access: a full-access key, an OAuth access token, or the dashboard. A scoped key, including a key restricted only to brands, that calls these endpoints gets `403 auth.insufficient_scope`. `GET /v1/keys/scopes` is the exception: any valid key can call it.

## Create a key

Create a key in the SocialAPI dashboard, or with the API:

```bash theme={null}
curl -X POST https://api.social-api.ai/v1/keys \
  -H "Authorization: Bearer $SOCAPI_KEY" \
  -H "Content-Type: application/json" \
  -d '{"name": "Production server"}'
```

Response (HTTP 201):

```json theme={null}
{
  "id": "5b0e6f3a-8c2d-4e1f-9a7b-3c4d5e6f7a8b",
  "name": "Production server",
  "raw_key": "sapi_key_cd27569b0823266d6431e5431c09fd746edd48faa40aeb43e5e7ccd9a34fee",
  "message": "Store this key securely. It will not be shown again.",
  "scopes": [],
  "brand_ids": []
}
```

`raw_key` is shown once, in this response. Store it in a secret manager or an environment variable such as `SOCAPI_KEY`. `GET /v1/keys` shows only a preview afterwards, and no endpoint returns the secret again: a lost secret needs a [rotation](#rotate-a-key).

| Field | Type | Required | Description |
| - | - | - | - |
| `name` | string | Yes | A label for the key. A missing or empty name returns `400 validation.field_required` |
| `scopes` | string\[] | No | Scopes the key holds. Empty or absent: every scope. An unknown scope returns `400 validation.scope_invalid`. See [Scoped API keys](https://docs.social-api.ai/guides/scoped-keys.md) |
| `brand_ids` | string\[] | No | Brands the key can reach. Empty or absent: every brand. An ID that is not a UUID, or not one of your brands, returns `400 validation.brand_invalid` |

## List keys

```bash theme={null}
curl https://api.social-api.ai/v1/keys \
  -H "Authorization: Bearer $SOCAPI_KEY"
```

Response (HTTP 200):

```json theme={null}
{
  "data": [
    {
      "id": "5b0e6f3a-8c2d-4e1f-9a7b-3c4d5e6f7a8b",
      "name": "Production server",
      "preview": "sapi_key_cd275...",
      "is_active": true,
      "last_used_at": "2026-10-12T16:04:00Z",
      "created_at": "2026-09-30T08:15:00Z",
      "scopes": [],
      "brand_ids": []
    }
  ],
  "count": 1
}
```

| Field | Description |
| - | - |
| `preview` | `sapi_key_` and the first 5 characters after it, followed by `...` |
| `is_active` | `false` once the key is revoked. Revoked keys stay in the list |
| `last_used_at` | The time of the key's latest request, up to 1 minute out of date. Absent when the key was never used or was rotated since |
| `scopes`, `brand_ids` | The key's restrictions. Two empty arrays mean full access |

## Rotate a key

Rotation issues a new secret and keeps the key's `id`, `name`, `scopes`, and `brand_ids`:

```bash theme={null}
curl -X POST https://api.social-api.ai/v1/keys/5b0e6f3a-8c2d-4e1f-9a7b-3c4d5e6f7a8b/rotate \
  -H "Authorization: Bearer $SOCAPI_KEY"
```

Response (HTTP 200): the same fields as when you create a key, with the new `raw_key`. The old secret stops working at once, so update every service that uses it. `last_used_at` is cleared. Rotating a revoked key, or an ID that is not one of your keys, returns `404 resource.not_found`.

To replace a secret with no downtime, create a second key with the same scopes and brands, deploy it to your services, then revoke the first key. Rotation cuts over at once and has no overlap.

To change a key's name, scopes, or brands without a new secret, use `PATCH /v1/keys/{id}`, described in [Scoped API keys](https://docs.social-api.ai/guides/scoped-keys.md#change-the-restrictions-on-a-key).

## Revoke a key

```bash theme={null}
curl -X DELETE https://api.social-api.ai/v1/keys/5b0e6f3a-8c2d-4e1f-9a7b-3c4d5e6f7a8b \
  -H "Authorization: Bearer $SOCAPI_KEY"
```

Response (HTTP 200):

```json theme={null}
{ "ok": true }
```

> [!WARNING]
>
> Revoking cannot be undone. The key stops working at once, and every request with it returns `401 auth.invalid_key`. Revoking a key that is already revoked returns `404 resource.not_found`.

## Authentication errors

* No `Authorization` header returns `401 auth.missing_header`.
* `Authorization: Bearer ` followed by nothing returns `401 auth.empty_token`.
* A `sapi_key_` token that is unknown or revoked returns `401 auth.invalid_key`.
* Any other token that is invalid or expired returns `401 auth.invalid_token`.
* An OAuth access token whose user no longer exists returns `401 auth.user_not_found`.
* A scoped key outside its scopes or brands, or calling key management, returns `403 auth.insufficient_scope`.
* A failed payment on your SocialAPI account returns `402 billing.past_due` on every endpoint except every method of `/v1/users/me` and every `/v1/billing/*` endpoint. See [Plans](https://docs.social-api.ai/guides/plans.md).

Match on `error.code`, never on `error.message`. Every code is in [Errors](https://docs.social-api.ai/guides/errors.md). The MCP server at `/mcp` answers the same failures with HTTP 401 (or 402 for a past-due account) and a body of the form `{"error": "invalid or inactive API key"}`, without the error envelope. The past-due 402 body also carries `code`: `billing.past_due`.

## Keep keys safe

* **Use keys only on a server.** A key in a browser, a mobile app, or a public repository can be copied and used by anyone.
* **Load keys from the environment.** Read `SOCAPI_KEY` from an environment variable or a secret manager, never from source code.
* **Create one key per service.** Revoke one service's key without stopping the others.
* **Give each key only what it needs.** Restrict keys to the [scopes and brands](https://docs.social-api.ai/guides/scoped-keys.md) the service uses, so a leaked key cannot reach other clients or actions.
* **Guard full-access keys most.** A full-access key can create more keys, including other full-access keys.
* **Rotate a key you think leaked.** `POST /v1/keys/{id}/rotate` ends the old secret at once and keeps the key's restrictions.
* **Revoke keys you no longer use.** Check `last_used_at` to find them.

## Use from an AI agent

| Tool | What it does |
| - | - |
| `social_api_list_keys` | Lists your API keys |
| `social_api_revoke_key` | Revokes an API key |

See [MCP tools](https://docs.social-api.ai/integrations/tools.md) for every tool.

## Related

* [Scoped API keys](https://docs.social-api.ai/guides/scoped-keys.md) for keys limited to some scopes and brands
* [OAuth for MCP clients](https://docs.social-api.ai/integrations/oauth.md) for the OAuth 2.1 flow and its tokens
* [The MCP server](https://docs.social-api.ai/integrations/overview.md) for connecting AI clients with a key or OAuth
* [Errors](https://docs.social-api.ai/guides/errors.md) for the full `auth.*` list
* [Rate limits](https://docs.social-api.ai/guides/rate-limits.md) for how many requests you can send


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