- Base URL:
https://api.postbreeze.ai/api/v1 - Auth:
Authorization: Bearer pb_live_… - Content type:
application/jsonrequest and response bodies - Errors: standard HTTP status codes; bodies are
{ "statusCode", "code", "message", "requestId" }(see Errors) - Rate limits: 60 req/min burst, 1000 req/15min sustained per key (see Rate limits)
Workspace resolution
API keys are issued in one of two modes:- Full access (default) — the key can act on every workspace its owner is a member of.
- Scoped — the key is restricted to an explicit allow-list of workspaces.
| Endpoint shape | Source of workspaceId | |||
|---|---|---|---|---|
GET /posts/{id}, PATCH /posts/{id}, DELETE /posts/{id} | Derived from Post.workspaceId | |||
| `POST /posts//schedule | reschedule | retry | cancel` | Derived from Post.workspaceId |
POST /posts | Derived from the first account in platforms[] / targets[] | |||
GET /social-accounts/{id}, DELETE /social-accounts/{id} | Derived from SocialAccount.workspaceId | |||
POST /comments/{id}/reply, POST /comments/{id}/read | Derived from Comment.workspaceId | |||
GET /media/{id}, PATCH /media/{id}, DELETE /media/{id} | Derived from the media’s owner workspace | |||
GET /posts, GET /social-accounts, GET /comments | Optional ?workspaceId= — omit to fan out across every workspace the key can act on | |||
GET /media | Required ?workspaceId= (media is account-global) | |||
POST /media/presign, POST /media/from-url, POST /comments/refresh | Required ?workspaceId= |
403.
Endpoints in v1
| Resource | Methods |
|---|---|
| Workspaces | GET /workspaces, GET /workspaces/{id}, POST /workspaces (create) |
| Posts | GET /posts, POST /posts, GET /posts/{id}, PATCH /posts/{id}, DELETE /posts/{id}, POST /posts/{id}/schedule, POST /posts/{id}/cancel, POST /posts/{id}/retry, POST /posts/{id}/targets/{tid}/retry-first-comment |
| Social accounts | GET /social-accounts, GET /social-accounts/{id}, DELETE /social-accounts/{id} |
| Media | GET /media, POST /media/presign, POST /media/from-url, POST /media/{id}/complete, GET /media/{id}, PATCH /media/{id}, DELETE /media/{id} |
| Comments | GET /comments, POST /comments/refresh, POST /comments/{id}/reply, POST /comments/{id}/read |
Two body shapes for POST /posts
The post-create + post-update endpoints accept a discriminated body —
send exactly one of platforms (flat) or targets (nested).
Sending both returns 400 MUST_SPECIFY_EXACTLY_ONE.
- Flat (
{ content, platforms: [{ accountId }] }) — Zernio-style, recommended for most calls. Same caption for every platform. - Nested (
{ caption, targets: [{ socialAccountId, platformOptions }] }) — full control over per-platform options, per-target media overrides, and platform-specifickinddiscriminators.
URL ingest for media
POST /media/from-url accepts a public HTTPS URL and fetches the bytes
server-side. The fetch is SSRF-guarded — private IPs, link-local
addresses, metadata-IMDS hostnames, and DNS-rebinding tricks are
rejected. Redirects are not followed (redirect: manual). By the time
the call returns, the bytes live in R2; the source URL is never
re-fetched at publish time.
Dashboard-internal routes
A second set of routes under/api/v1/me/media/* powers the dashboard
UI — they take an x-workspace-id header instead of inferring from a
key. SDK and MCP callers should ignore these; they’re not part of the
public surface.
OpenAPI spec
The full machine-readable spec lives at/openapi.json on this site
and is regenerated on every Postbreeze deploy. The TypeScript SDK
@postbreeze/node is generated from this spec.