# Postally API overview

The Postally API is a REST, JSON-over-HTTPS interface for programmatic access to
your brand's social accounts. It's designed for server-to-server use. Every
request must include an API key you mint in your dashboard settings, plus the
brand it acts on.

Anything you can do in the Postally dashboard — upload media, draft, schedule,
publish, reschedule, delete, and read analytics — you can drive from your own
code across X, Instagram, LinkedIn, Facebook, Threads, TikTok, YouTube, and
Bluesky.

> **Prefer to drive Postally from an AI assistant?** The MCP server
> (https://postally.io/features/mcp) exposes the same capabilities to Claude,
> Codex, and other MCP clients as conversational tools — same account, same
> brands, nothing new to provision.

## What you can build

- Upload media — local files or remote URLs
- Schedule posts, publish immediately, or save drafts with `type`
- Fan one call out to several platforms by adding an entry to `posts[]` per
  connected account
- List, reschedule, and delete posts
- Read profile and per-post analytics

## Base URL

```
https://app.postally.io/api/public/v1
```

Every path in these docs is relative to this base URL, e.g.
`POST https://app.postally.io/api/public/v1/posts`.

## Content type

Requests and responses use `application/json`, with one exception:
`POST /media/upload` takes `multipart/form-data` so you can stream a file.
Authentication travels in two headers on every request:

```
Authorization: Bearer pst_live_xxxxxxxxxxxxxxxxxxxx
x-brand-id: <your_brand_id>
Content-Type: application/json
```

## Versioning

The API is versioned in the path (`/api/public/v1`). Breaking changes ship under
a new major version, so an integration built against `v1` keeps working on `v1`.

## Responses

Successful responses return the resource itself — there is no wrapper envelope.
Creating a post returns one entry per targeted account:

```json
[
  {
    "postId": "post_...",
    "integration": "integration_x_123",
    "group": "group_..."
  }
]
```

Errors return a machine-readable `code` next to a human-readable `message`:

```json
{
  "statusCode": 403,
  "code": "INSUFFICIENT_SCOPE",
  "message": "This API key is missing the required scope."
}
```

Requests are throttled per API key at roughly 60 requests per minute; over that
you get `429 Too Many Requests`. Media uploads beyond your plan's storage
allowance return `402`. See the API reference for the full error table.

## Next steps

- Getting started — https://postally.io/docs/getting-started
- API reference — https://postally.io/docs/api
- Examples — https://postally.io/docs/examples
- OpenAPI reference — https://app.postally.io/api/public/v1/docs
