Skip to main content
Platforms

Instagram

Publish feed posts, stories, reels, and carousels to Instagram via the PostPeer API.

Overview

Publish feed posts, stories, reels, and carousels to Instagram through PostPeer's unified API. PostPeer handles the Instagram Graph API complexity, including the async media publishing flow.

Note: Instagram feed posts and Reels require a professional Business or Creator account. Story publishing requires a Business account. PostPeer uses Instagram Login, so a linked Facebook Page is not required.

Quick Start

1. Connect an Instagram Account

curl https://api.postpeer.dev/v1/connect/instagram \
  -H "x-access-key: YOUR_API_KEY"

Returns an Instagram authorization URL. The user must have an Instagram professional account. See Connect Accounts for the full OAuth flow.

2. Get the Account ID

curl https://api.postpeer.dev/v1/connect/integrations \
  -H "x-access-key: YOUR_API_KEY"

Find the integration with "platform": "instagram" and note the id.

3. Publish a Post

curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "New product launch! #startup #launch",
    "platforms": [
      { "platform": "instagram", "accountId": "ig_456" }
    ],
    "mediaItems": [
      { "type": "image", "url": "https://cdn.example.com/photo.jpg" }
    ],
    "publishNow": true
  }'
import PostPeer from '@postpeer/node';

const client = new PostPeer();
const { data } = await client.posts.create({
	body: {
		content: 'New product launch! #startup #launch',
		platforms: [{ platform: 'instagram', accountId: 'ig_456' }],
		mediaItems: [{ type: 'image', url: 'https://cdn.example.com/photo.jpg' }],
		publishNow: true,
	},
});
from postpeer import PostPeer

with PostPeer() as client:
    post = client.posts.create(
        content="New product launch! #startup #launch",
        platforms=[{"platform": "instagram", "accountId": "ig_456"}],
        media_items=[
            {"type": "image", "url": "https://cdn.example.com/photo.jpg"},
        ],
        publish_now=True,
    )

Response:

{
	"success": true,
	"status": "published",
	"postId": "post_def456",
	"platforms": [
		{
			"platform": "instagram",
			"success": true,
			"platformPostUrl": "https://www.instagram.com/p/ABC123/"
		}
	]
}

Features

Feed Posts

Single image or video posts with captions and hashtags. Instagram requires at least one media item — text-only posts are not supported.

Stories

Set platformSpecificData.contentType to "story" to publish one image or video as an Instagram Story:

curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "",
    "platforms": [
      {
        "platform": "instagram",
        "accountId": "ig_456",
        "platformSpecificData": {
          "contentType": "story"
        }
      }
    ],
    "mediaItems": [
      { "type": "image", "url": "https://cdn.example.com/story.jpg" }
    ],
    "publishNow": true
  }'
import PostPeer from '@postpeer/node';

const client = new PostPeer();
const { data } = await client.posts.create({
	body: {
		content: '',
		platforms: [
			{
				platform: 'instagram',
				accountId: 'ig_456',
				platformSpecificData: {
					contentType: 'story',
				},
			},
		],
		mediaItems: [{ type: 'image', url: 'https://cdn.example.com/story.jpg' }],
		publishNow: true,
	},
});
from postpeer import PostPeer

with PostPeer() as client:
    story = client.posts.create(
        content="",
        platforms=[
            {
                "platform": "instagram",
                "accountId": "ig_456",
                "platformSpecificData": {
                    "contentType": "story",
                },
            },
        ],
        media_items=[
            {"type": "image", "url": "https://cdn.example.com/story.jpg"},
        ],
        publish_now=True,
    )

Story publishing requires an Instagram Business account and exactly one image or video. Stories disappear after 24 hours. Instagram does not display the request's content as a Story caption, and its publishing API does not support interactive stickers such as links, polls, music, locations, or mentions.

Reels

Upload short-form vertical videos as Instagram Reels:

curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "Quick tutorial #reels",
    "platforms": [
      { "platform": "instagram", "accountId": "ig_456" }
    ],
    "mediaItems": [
      { "type": "video", "url": "https://cdn.example.com/reel.mp4" }
    ],
    "publishNow": true
  }'

Custom Reel cover (thumbnail)

By default Instagram auto-picks a frame from the video as the Reel cover. To override, pass a public image URL via platformSpecificData.coverUrl, or a timestamp via platformSpecificData.thumbOffset. coverUrl takes precedence when both are set.

curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "Quick tutorial #reels",
    "platforms": [
      {
        "platform": "instagram",
        "accountId": "ig_456",
        "platformSpecificData": {
          "coverUrl": "https://cdn.example.com/reel-cover.jpg"
        }
      }
    ],
    "mediaItems": [
      { "type": "video", "url": "https://cdn.example.com/reel.mp4" }
    ],
    "publishNow": true
  }'

Requirements:

  • coverUrl must be a publicly accessible HTTPS URL. JPEG or PNG.
  • The image aspect ratio should match the video (9:16 for Reels) — Instagram rejects mismatches.
  • thumbOffset is an integer in milliseconds. Instagram extracts the video frame at that timestamp.
  • Both fields are ignored on non-video posts.

Share Reel to feed

Reels default to also appearing in the account's main feed grid. To publish to Reels only, pass shareToFeed: false:

"platformSpecificData": { "shareToFeed": false }

Reel audio name

Pass audioName to set the name shown for the Reel's audio:

"platformSpecificData": { "audioName": "Original audio - yourbrand" }

Instagram does not allow selecting a track from its music library through the API. the audio has to already be in the video file. audioName only labels it.

Trial Reels

Trial Reels are shown to non-followers first, so you can test a Reel before sharing it with your existing audience. Pass trialParams.graduationStrategy with one of these values:

  • MANUAL — keep the Reel as a trial until you choose to share it with followers in Instagram.
  • SS_PERFORMANCE — let Instagram automatically share the Reel with followers when it performs well.
curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "Testing this tutorial with a new audience #reels",
    "platforms": [
      {
        "platform": "instagram",
        "accountId": "ig_456",
        "platformSpecificData": {
          "trialParams": {
            "graduationStrategy": "MANUAL"
          }
        }
      }
    ],
    "mediaItems": [
      { "type": "video", "url": "https://cdn.example.com/reel.mp4" }
    ],
    "publishNow": true
  }'

Trial Reels require exactly one video and cannot be used with Stories, images, or carousels. Availability also depends on the connected Instagram professional account being eligible for Trial Reels.

Carousels

Create carousel posts with up to 10 images or videos by passing multiple mediaItems:

curl -X POST "https://api.postpeer.dev/v1/posts" \
  -H "x-access-key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "content": "Swipe through our latest designs",
    "platforms": [
      { "platform": "instagram", "accountId": "ig_456" }
    ],
    "mediaItems": [
      { "type": "image", "url": "https://cdn.example.com/slide1.jpg" },
      { "type": "image", "url": "https://cdn.example.com/slide2.jpg" },
      { "type": "image", "url": "https://cdn.example.com/slide3.jpg" }
    ],
    "publishNow": true
  }'

Media Requirements

TypeRequirement
ImageJPG or PNG; aspect ratio from 4:5 through 1.91:1
CarouselUp to 10 JPG, PNG, MP4, or MOV items; use one aspect ratio throughout

Reel specifications

SpecificationInstagram requirement
ContainerMOV or MP4; no edit lists; moov atom at the front
VideoH.264 or HEVC; progressive scan; closed GOP; 4:2:0 chroma subsampling
AudioAAC; 48 kHz maximum; mono or stereo; 128 kbps
Frame rate23-60 FPS
Picture sizeMaximum 1,920 px wide; aspect ratio from 0.01:1 through 10:1
Video bitrateVariable bitrate, 25 Mbps maximum
Duration3 seconds-15 minutes
File size300 MB maximum

Instagram recommends 9:16 video to avoid cropping or blank space. See Meta's Instagram Reel specifications for current requirements.

Platform-Specific Data

Pass this object in platformSpecificData when posting to Instagram. Use contentType to publish Stories; the remaining fields customize feed posts and Reels.

FieldTypeRequiredValues and constraintsDescription
contentTypestringNostorySet to "story" to publish an Instagram Story. Omit for the existing behavior: images publish to Feed and videos publish as Reels.
shareToFeedbooleanNoReels-only. When true (default), the Reel also appears in the account's main feed grid. Set false to publish to Reels only.
trialParamsobjectNoReels-only. Publishes a single video as a Trial Reel, initially shown to non-followers.
trialParams.graduationStrategystringYes, when trialParams is providedMANUAL, SS_PERFORMANCEControls how a Trial Reel is shared with followers. MANUAL keeps graduation manual; SS_PERFORMANCE lets Instagram share it automatically when it performs well.
coverUrlstringNoFormat: uriVideo-only. Public URL of an image Instagram will use as the cover frame for the Reel/video post. Ignored for image posts.
thumbOffsetintegerNoRange: 0–unboundedVideo-only. Timestamp in milliseconds Instagram extracts as the cover frame. Ignored when coverUrl is set or for image posts.
audioNamestringNoLength: 1–100Reels-only. Sets the name shown for the Reel audio. Instagram does not allow selecting a track from its music library via the API, so the audio must already be in the video file; this only labels it.
collaboratorsstring[]NoItems: 1–3Feed posts, carousels, and Reels only. Up to three Instagram usernames to invite as collaborators. Each account must accept the invitation in Instagram.

On this page