PostraDocsOpen Postra

Get started

The Postra Public API lets your own code work with your Postra account. You can list your channels, upload media, create and schedule posts, and read analytics.

It is a REST API. You send JSON and get JSON back. File uploads use multipart/form-data.

What you need

Base URL

https://app.postra.co.uk/api/public/v1

Use this address exactly as it is. All paths in these docs are added to the end of it.

Get your API key

  1. Sign in to Postra.
  2. Open Settings, then Developers, then Access.
  3. Click Reveal next to the API key, then Copy.

One key belongs to one organisation. It acts with admin rights in that organisation, so treat it like a password:

Rotate Key on the same page creates a new key. The old key stops working straight away.

Send the key

Put the key in the Authorization header of every request. Send the key on its own, with no Bearer in front of it.

Authorization: YOUR_API_KEY

Authorization: Bearer YOUR_API_KEY is refused with 401 Invalid API key.

Building an app for other Postra users? Ask them to approve your app instead of sharing their key. Their OAuth token (it starts with pos_) goes in the same header. See Sign in with Postra.

Your first request

List the channels connected to your organisation:

curl https://app.postra.co.uk/api/public/v1/integrations \
  -H "Authorization: YOUR_API_KEY"

Response:

[
  {
    "id": "8d3f1c2a-5b6e-4f7a-9c0d-1e2f3a4b5c6d",
    "name": "Northside Bakery",
    "identifier": "instagram",
    "picture": "https://cdn-dev.postra.pl/2026/10/01/avatar.jpg",
    "disabled": false,
    "profile": "northsidebakery"
  }
]

Keep the id. You need it to post to that channel. identifier is the platform, see Platforms and settings.

Next steps:

Rate limits

Limits are counted per organisation. Every key and token of the organisation shares them. Each endpoint below has its own counter.

Endpoint Limit
POST /posts 90 requests per hour
POST /upload, POST /upload-from-url 30 requests per 5 minutes each
POST /integration-trigger/:id 30 requests per 5 minutes
GET /posts/:id/missing 30 requests per 5 minutes
GET /social/:platform 60 requests per 5 minutes
GET /analytics/:id, GET /analytics/post/:postId 60 requests per 5 minutes each

These endpoints send three headers with each answer:

Header Meaning
X-RateLimit-Limit Requests allowed in the window
X-RateLimit-Remaining Requests left in the window
X-RateLimit-Reset Seconds until the window starts again

Over the limit you get 429 Too Many Requests and a Retry-After header with the number of seconds to wait.

Monthly posts

Your plan also sets how many posts you can create each month:

Plan Posts a month
Starter 400
Pro Unlimited
Business Unlimited

Each channel in a request counts as a post, and so does each follow-up part of a thread. Drafts do not count. A post counts in the billing month it is published in. When the allowance is used up, POST /posts answers 402.

Errors

Errors come back as JSON with an HTTP status code.

Status What it means What to do
400 A field is missing or wrong, or the post breaks a platform rule. Read message and fix the request.
401 The key is missing or wrong, or the organisation has no active paid plan. Check the header and your plan.
402 Your plan does not allow this: the monthly posts are used up, the platform is not in your plan, or all channel slots are taken. Upgrade the plan, or wait for the next month.
403 The platform does not take new channels yet. Pick a platform from Platforms and settings.
404 The channel or post does not exist in your organisation. Check the id.
429 Too many requests. Wait for the seconds in Retry-After, then try again.

401 messages

Body Cause
{"msg": "No API Key found"} No Authorization header
{"msg": "Invalid API key"} Unknown key, an old key after a rotation, or the key sent with Bearer
{"msg": "Invalid OAuth token"} The pos_ token is unknown, revoked or expired
{"msg": "No subscription found"} The organisation has no active paid plan

400 examples

A field fails validation:

{
  "statusCode": 400,
  "message": ["posts.0.settings.post_type should not be null or undefined"],
  "error": "Bad Request"
}

A post breaks a rule of its platform. provider is the platform and name is your channel:

{
  "statusCode": 400,
  "provider": "instagram",
  "name": "Northside Bakery",
  "message": "Should have at least one media"
}

402 example

{
  "statusCode": 402,
  "message": "You have reached the maximum number of posts for your subscription. Please upgrade your subscription to add more posts.",
  "url": "https://app.postra.co.uk/billing"
}