The Storrito API allows to import images and videos that Storrito will post as Instagram Stories, Instagram Reels or TikTok posts. Furthermore it is possible to define Instagram Stickers that will be added to the story image or video.
The API is designed as 'HTTP API', meaning you can use curl and other HTTP clients to interact with the API and it will return common HTTP status codes. But the API is neither RESTful nor a full-blown remote-procedure-call service (like gRPC). The focus of the API design is to provide a good developer experience. Nowadays the best option might be to follow the OpenAPI specification, which allows to generate client SDKs for the most common programming languages. However, the downside is that OpenAPI and maintaining dozens of client SDKs is quite complex. For the moment we focus on providing a simple 'HTTP API' that is easy to use.
The API offers remote-procedure-calls (RPC) via HTTP. The arguments for the procedure are send as JSON via a HTTP POST request. All API endpoints starts with:
https://ORG_UUID.storrito.com/api/v1/
followed by the name of the procedure. Usually the response will also contain JSON data. The top-level data structure of the request and the response is always a map. This allows us to add more map entries without breaking your code.
Note: The URLs on this page contain ORG_UUID as a placeholder. Log in at storrito.com to see the URLs personalized with your organization's UUID.
No API or website has 100% availability, therefore be prepared to handle the following HTTP status codes and retry the HTTP request:
HTTP 429 'Too Many Requests': the API will return this status code to signal that you run into a rate limit. The default quota allows 60 requests per minute (using a token bucket algorithm). If the procedure has a stricter quota this will be mentioned in its documentation. A rate limit can also happen, when the API servers are too busy to accept further requests.
The API runs behind a HTTPs load balancer. When we deploy an update for the API the load balancer may return a HTTP 502, a HTTP 503 or a HTTP 504.
Retry the HTTP request either with an exponential backoff or just retry it every 2 seconds plus some random milliseconds (between 0-999ms).
Recommended rpc helper (Node.js)
Use this helper function for all API calls. It automatically retries on rate-limit (429) and transient server errors (502, 503, 504):
async function rpc(procedure, params = {}) {
const maxAttempts = 5;
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
const res = await fetch(`${BASE_URL}/${procedure}`, {
method: "POST",
headers: {
"Authorization": `Bearer ${TOKEN}`,
"Content-Type": "application/json",
},
body: JSON.stringify(params),
});
if ([429, 502, 503, 504].includes(res.status)) {
if (attempt === maxAttempts) {
throw new Error(`${procedure} failed after ${maxAttempts} attempts (${res.status})`);
}
const delay = 2000 + Math.random() * 1000;
console.log(`${procedure}: HTTP ${res.status}, retrying in ${Math.round(delay)}ms...`);
await new Promise((r) => setTimeout(r, delay));
continue;
}
if (!res.ok) {
const text = await res.text();
throw new Error(`${procedure} failed (${res.status}): ${text}`);
}
return res.json();
}
}
Web components for building Instagram Stories with HTML.
Use with AI Coding Agents
The Storrito API works great with AI coding agents like Claude Code, Cursor, GitHub Copilot, and others. You can paste the following example prompt into your agent to get started quickly:
Write a Node.js script that posts an image to Instagram Stories using the
Storrito API. Use the first connected Instagram account. Add a hashtag
sticker with "#travel" and a link sticker pointing to "https://example.com".
API docs: https://ORG_UUID.storrito.com/documentation/api/v1/index.md
Story component docs: https://ORG_UUID.storrito.com/documentation/api/v1/story-components.md
Base URL: https://ORG_UUID.storrito.com/api/v1/
Ask me for the bearer token before writing any code.
This is just a starting point. Customize the prompt to match your use case, for example by changing the sticker types, scheduling the post for a specific time, or using a video instead of an image.
Authentication
The API uses Bearer token authentication. You can create API credentials in your account settings under API Credentials.
When you create an API credential, a Bearer token is shown once. The server only stores a hash, so the token cannot be retrieved again.
Include the token in the Authorization header of every request:
Authorization: Bearer YOUR_BEARER_TOKEN
Store your token in a shell variable so you can copy-paste the curl examples below:
Besides an error message (errorMessage) the server will also show you the JSON schema (paramsJsonSchema) and explain why the parameters for the procedure are invalid (validationErrorExplanation). In the example above there is a typo in storyPostUud and the key blah is not defined for the procedure status-instagram-story.
Webhooks
Webhooks let Storrito notify your tools as soon as an Instagram Story post changes status. This is useful for no-code automations in Make, Zapier, n8n, Notion workflows, or your own backend because you do not need to poll status-instagram-story repeatedly for API-created posts.
Configure webhook URLs in the Storrito app under Storrito API → Webhooks. Each organization can configure up to 5 webhook URLs. Webhook URLs must use HTTPS.
Delivery behavior
Storrito sends an HTTP POST request with a JSON body. Your endpoint should return any 2xx HTTP status code to mark the delivery as successful. If the endpoint is unavailable or returns a non-2xx status code, Storrito retries the delivery with backoff and eventually marks it as failed.
For v1, webhook deliveries are intentionally simple and are not signed. Treat webhook payloads as notifications and call the API if your automation needs to verify the latest state.
{
"event": "instagram_story_post.status_changed",
"storyPostUuid": "550e8400-e29b-41d4-a716-446655440000",
"status": "failed",
"errorMessage": "Instagram returned an error.",
"occurredAt": "2026-06-09T12:34:56Z"
}
Errors
All 'expected' errors will return a HTTP 400 status code. Unexpected errors are caused by bugs or downtimes on the server-side, they will return a HTTP 500 status code. These errors should only be retried, if the procedure is idempotent.
Using standard HTTP status codes is the reason why we call the design an 'HTTP API' and one of the reason we do not use JSON-RPC.
Dates
All dates in the API use ISO 8601 format in UTC (e.g. "2025-06-15T14:30:00Z"). Most languages have built-in support for parsing and formatting ISO 8601 date-time strings.
Instagram Limits and Best Practices
Instagram enforces its own limits that are outside of Storrito's control. Violating them can result in temporary posting blocks or automation warnings on your account.
Posting frequency
Instagram allows roughly 15–25 stories per account per day. Exceeding this may trigger a temporary cooldown or a "try again later" error.
Space out your posts. Avoid bursting many stories for the same account within a few minutes.
The Storrito API enforces its own per-account quota (100 story posts per account per 24 hours) as a safety net, but Instagram's limits are lower and less predictable.
Content uniqueness
Do not post the same story design repeatedly. Instagram's systems detect duplicate content and may flag your account for spam or automation.
Each story should have a unique visual — change the background image or video, sticker text, or layout between posts.
If you are testing your integration, preview your story locally using the <insta-story> web components in a browser instead of posting to Instagram repeatedly.
Account health
If Instagram returns an error or blocks a post, back off and wait before retrying. Do not retry failed posts in a tight loop.
Video Requirements
When you upload a video for an Instagram Story, the API validates it before rendering. Videos that do not meet the following requirements are rejected with an HTTP 400 error and a descriptive message.
Codec: H.264 (h264)
Resolution: 1080 x 1920 pixels (9:16 portrait)
Duration: 0.5 – 60 seconds
Bitrate: ≤ 30 Mbps
Converting a video with ffmpeg
Use the following ffmpeg command to convert any video to the required format:
scale=1080:1920:...,pad=1080:1920:... — scales the video to fit within 1080×1920 while keeping the aspect ratio, then pads with black bars to exactly 1080×1920.
-c:v libx264 -crf 18 — encodes with H.264 at high quality. Increase the CRF value (e.g. 23) for a smaller file size.
-r 30 — sets 30 fps.
-c:a aac -b:a 128k — encodes audio as AAC at 128 kbps.
-movflags +faststart — moves the MP4 metadata to the beginning for faster HTTP streaming.
Creates a connect-link: a shareable URL that lets an Instagram account owner connect their account to your Storrito workspace in the browser.
Share the returned connectLinkUrl with the person who owns the Instagram account (for example your customer). They open it, enter their Instagram credentials on the Storrito connect page, and complete any Instagram verification steps there. Their credentials never pass through your integration.
Once the account is connected it appears in list-instagram-users and can be used with schedule-instagram-story.
An organization can have at most 100 connect-links. Delete unused links in the Storrito app.
Generates a random UUID. Useful for creating a storyPostUuid before calling schedule-instagram-story or a tiktokPostUuid before calling schedule-tiktok-post.
Lists all Instagram users connected to your Storrito account.
Returns an array of Instagram users with their username, numeric ID, and linked Facebook destinations. Only active (non-deleted) accounts are included. Use the instagramUsername value when calling schedule-instagram-story. Pass shareToFacebook: true and, when needed, one of the returned facebookDestinationId values to cross-post a Story to Facebook.
Renders a page built with <insta-story> web components and schedules the rendered video as an Instagram reel.
Provide either the url of your hosted page or pass the HTML directly via the html parameter, plus the instagramUsername to post to. Exactly one of url or html must be provided.
When using html, the server injects the web component JavaScript and fonts automatically — just provide the raw HTML containing your <insta-story> markup. The HTML is loaded in a sandboxed context with no origin (about:blank), so it cannot access cookies or session data.
Instagram reels must be videos, so the <insta-story> element needs a src attribute that points to a video. The video can be up to 3 minutes long. Any other components on the page are rendered into the video. Instagram-native sticker metadata is not available for reels.
Optionally provide a date (ISO 8601 string, e.g. "2025-06-15T14:30:00Z") to schedule the reel for a future time. When date is omitted the reel is published as soon as rendering is complete.
Optionally provide a caption, set shareToFeed to also share the reel to the account's main feed, or set aiGenerated to mark the reel as AI-generated content.
The server creates the same editor2-compatible story-media that is used by schedule-instagram-story, so the reel can be opened and edited in the Storrito editor. The Instagram account must be connected in your Storrito dashboard first.
Every request requires a reelPostUuid that you generate on your side. This ensures idempotency — if a reel with that UUID already exists, the same success response is returned without creating a duplicate. This makes it safe to retry requests. Pass the UUID to the status-instagram-reel procedure to poll for the posting status.
curl -X POST https://ORG_UUID.storrito.com/api/v1/schedule-instagram-reel \
-H "Authorization: Bearer $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"html": "<insta-story src=\"https://example.com/my-reel.mp4\"></insta-story>",
"instagramUsername": "YOUR_INSTAGRAM_USERNAME",
"reelPostUuid": "e3be0a9d-6a29-4a2a-9418-32eac624ae8f",
"caption": "My first reel via the Storrito API"
}'
{
"html" : "<insta-story src=\"https://example.com/my-reel.mp4\"></insta-story>",
"instagramUsername" : "YOUR_INSTAGRAM_USERNAME",
"reelPostUuid" : "EXAMPLE_REEL_POST_UUID",
"caption" : "My first reel via the Storrito API"
}
schedule-instagram-story
Renders a page built with <insta-story> web components and schedules it as an Instagram story.
Provide either the url of your hosted story page or pass the HTML directly via the html parameter, plus the instagramUsername to post to. Exactly one of url or html must be provided.
When using html, the server injects the web component JavaScript and fonts automatically — just provide the raw HTML containing your <insta-story> markup. The HTML is loaded in a sandboxed context with no origin (about:blank), so it cannot access cookies or session data.
Optionally provide a date (ISO 8601 string, e.g. "2025-06-15T14:30:00Z") to schedule the story for a future time. When date is omitted the story is posted immediately.
Optionally set aiGenerated to true to mark the story as AI-generated content, so Instagram shows its AI label on the story.
Optionally set shareToFacebook to true to cross-post the Story to a Facebook destination linked to the selected Instagram account. If the account has multiple Facebook destinations, pass facebookDestinationId; otherwise Storrito uses the first linked destination.
Unknown JSON keys are rejected. This prevents typos from being silently ignored.
The server extracts sticker data from the page, builds an editor2-compatible design, and schedules the story for rendering and posting. The resulting story can be opened and edited in the Storrito editor. The Instagram account must be connected in your Storrito dashboard first.
Every request requires a storyPostUuid that you generate on your side. This ensures idempotency — if a story post with that UUID already exists, the same success response is returned without creating a duplicate. This makes it safe to retry requests. Pass the UUID to the status-instagram-story procedure to poll for the posting status.
Request duration: Before the request returns, the server loads your page in a headless browser, extracts the sticker data and uploads the media. Depending on server load and media size (especially for video stories) this can take longer than 30 seconds, so configure a client read timeout of at least 120 seconds. If your client times out anyway, the server usually still finishes the request — retry with the same storyPostUuid: thanks to idempotency the retry returns the success response without creating a duplicate.
Extracting stickers: Any <insta-hashtag>, <insta-mention>, <insta-location>, <insta-link>, or other sticker components on the page are automatically extracted and applied as native Instagram stickers. See the Story Components documentation for all available components.
Video stories: If the <insta-story> element has a src attribute pointing to a video, a video story is created. Otherwise an image story is created.
Renders a page built with <insta-story> web components and schedules the rendered media as a TikTok post.
Provide either the url of your hosted story page or pass the HTML directly via the html parameter, plus the tiktokAccountId to post to. Exactly one of url or html must be provided.
When using html, the server injects the web component JavaScript and fonts automatically — just provide the raw HTML containing your <insta-story> markup. The HTML is loaded in a sandboxed context with no origin (about:blank), so it cannot access cookies or session data.
Optionally provide a date (ISO 8601 string, e.g. "2025-06-15T14:30:00Z") to schedule the TikTok post for a future time. When date is omitted the post is published as soon as rendering is complete.
For rendered image/photo posts, TikTok allows title to be at most 90 characters. Put longer text into description.
The server creates the same editor2-compatible story-media that is used by schedule-instagram-story. TikTok receives the rendered image or video; Instagram-native sticker metadata is not sent to TikTok.
Every request requires a tiktokPostUuid that you generate on your side. This ensures idempotency — if a TikTok post with that UUID already exists, the same success response is returned without creating a duplicate. This makes it safe to retry requests. Pass the UUID to the status-tiktok-post procedure to poll for the posting status.
Use list-tiktok-accounts to find the tiktokAccountId of a connected account.
Returns the current posting status of an Instagram story.
Provide the storyPostUuid that was returned by the schedule-instagram-story procedure. The response includes a status field:
scheduled — the story is queued and will be posted shortly.
executed — the story has been posted to Instagram.
failed — posting failed. The errorMessage field contains details.
canceled — the story post was canceled before it was posted.
Call this procedure repeatedly to poll until the status is executed or failed.
How long a story stays scheduled: After schedule-instagram-story returns, the story is rendered and then posted to Instagram, starting at the scheduled date (or immediately when no date was given). The time from scheduled to executed therefore varies with rendering time and Instagram's availability — typically it is under a couple of minutes, but there is no fixed duration, so keep polling instead of assuming a failure after a short delay. The hard upper bound is 60 minutes: a story that could not be posted within 60 minutes after its scheduled time is never posted late, it is marked as failed instead.