Description
n8n-nodes-meta-publisher
Publish to Instagram, Facebook Pages, and Threads from n8n — including Images, Videos, Reels, Stories, and Carousels — with a single, DRY node.
> Built from the official n8n community node starter structure so you can develop, lint, and ship confidently.
—
#### Workflows
#### Nodes and Operations
!Meta Publisher Operations
!Meta Publisher Operations
#### JSON Generator Output
Table of contents
- Features
- Supported resources & operations
- Installation
- Credentials
- Quick start (Fields mode)
- JSON payload mode (optional)
- Outputs
- Rate limits & retries
- Development
- Testing locally
- Contributing
- License
- One node to publish across Instagram / Facebook Pages / Threads
- Create → poll → publish workflow handled for you
- Reels, Stories, Carousels (IG) + Photos/Videos (FB) + Text/Image/Video/Carousel (Threads)
- Two input styles:
- Consistent JSON output (status, IDs, permalinks-ready payloads)
- Friendly polling with jitter; configurable timeouts
- Publish Image, Publish Video (optional cover image)
- Publish Reel (thumb offset, share to feed)
- Publish Story (image/video)
- Publish Carousel (2–10 items)
- Publish Photo
- Publish Video (status polled until ready)
- Publish Reel (status polled until ready)
- Publish Story (image/video)
- ~~Publish Multi-Photo~~ (work in progress…)
- Publish Text
- Publish Image (optional alt text)
- Publish Video (optional alt text)
- Publish Carousel (2–20 items)
- Install
n8n-node-meta-publishervia n8n Community Nodes. - Resource: Instagram
- Operation: Publish Image
- IG User ID:
1789… - Image URL:
https://…/photo.jpg - Caption:
Hello from n8n 🚀 - Set Input Source →
From JSON Property - Set JSON Property Path → the field in your input JSON where the job(s) are stored.
resource:"instagram" | "facebook" | "threads"operation: one of the supported operations- Required fields for that operation (see below)
resource– platform to publish tooperation– type of publish actionpollSec(optional) – polling interval (default:2)maxWaitSec(optional) – max wait before timeout (default:300)igUserId– Instagram Business User IDautoPublish(default: true)publishImage→mediaUrl,caption?publishVideo→mediaUrl,caption?,coverUrl?publishReel→videoUrl,caption?,thumbOffsetMs?,shareToFeed?publishStory→mediaUrl,storyKind("image"|"video"),caption?publishCarousel→items[]({ type: "image|video", url: "..." }),caption?
—
Features
– Fields mode (simple UI fields)
– JSON payload mode for programmatic/batch posting
—
Supported resources & operations
Facebook Pages
Threads
—
Installation
Community Nodes (recommended for users)
Credentials
Add a credential in n8n called Meta Graph API with an Access Token (prefer long-lived).
The node will also attempt OAuth2 if configured in your instance, then fall back to the access token.
> Keep tokens in Credentials, not in node fields. This keeps secrets secure and reusable across workflows.
—
Quick start (Fields mode)
1. Drag Meta Publisher into your workflow.
2. Choose Resource:
– Instagram / Facebook Page / Threads
3. Choose Operation (e.g., Publish Reel).
4. Fill required fields (e.g., IG User ID, Media URL, Caption).
5. Optionally adjust Polling Interval and Max Wait.
6. Run the workflow.
Example (IG → Publish Image)
—
JSON payload mode (optional)
Instead of filling parameters in the node UI, you can set Input Source = JSON Property.
This allows you to feed one or more publishing jobs from the incoming item JSON.
1. Configure the Node
– Use $json to pass the entire input item.
– Use a path like data.post if your jobs are nested inside {"data": { "post": {...}}}.
2. JSON Job Format
Each job must be an object with at least:
—
#### Common Fields
—
All Instagram jobs require:
Operations:
#### Instagram User Tags
You can tag users in supported Instagram posts using:
{
"userTags": [
{
"username": "someuser",
"x": 0.5,
"y": 0.5
}
]
}
—
#### Facebook Page
All Facebook jobs require:
pageId – Page IDOperations:
publishFbPhoto → imageUrl, caption?publishFbVideo → videoUrl, title?, description?—
#### Threads
All Threads jobs require:
thUserId (or userId alias) – Threads User IDOperations:
threadsPublishText → textthreadsPublishImage → imageUrl, text?, altText?threadsPublishVideo → videoUrl, text?, altText?threadsPublishCarousel → items[] ({ type: "image|video", url: "...", altText? }), text?You can also pass an array of jobs to publish multiple posts in one execution.
3. Example: Multiple Jobs
[
{
"resource": "instagram",
"operation": "publishStory",
"igUserId": "112233445566",
"mediaUrl": "https://www.example.com/video.mp4",
"caption": "This is an example caption.",
"storyKind": "video",
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishStory",
"igUserId": "112233445566",
"mediaUrl": "https://www.example.com/image.jpg",
"caption": "This is an example caption.",
"storyKind": "image",
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishImage",
"igUserId": "112233445566",
"mediaUrl": "https://www.example.com/image.jpg",
"caption": "This is an example caption.",
"userTags": [{ "username": "someuser", "x": 0.5, "y": 0.5 }],
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishVideo",
"igUserId": "112233445566",
"mediaUrl": "https://www.example.com/video.mp4",
"caption": "This is an example caption.",
"coverUrl": "https://www.example.com/image.jpg",
"userTags": [{ "username": "someuser", "x": 0.5, "y": 0.5 }],
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishReel",
"igUserId": "112233445566",
"videoUrl": "https://www.example.com/video.mp4",
"caption": "This is an example caption.",
"userTags": [{ "username": "someuser", "x": 0.5, "y": 0.5 }],
"thumbOffsetMs": 0,
"shareToFeed": true,
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishCarousel",
"igUserId": "112233445566",
"items": [
{
"type": "image",
"url": "https://www.example.com/image.jpg",
"caption": "This is an example caption.",
"userTags": [{ "username": "someuser", "x": 0.1, "y": 0.8 }]
},
{
"type": "video",
"url": "https://www.example.com/video.mp4",
"caption": "This is an example caption.",
"userTags": [{ "username": "someuser", "x": 0.1, "y": 0.8 }]
}
],
"caption": "This is an example caption.",
"autoPublish": true
},
{
"resource": "facebook",
"operation": "publishFbPhoto",
"pageId": "112233445566",
"imageUrl": "https://www.example.com/image.jpg",
"caption": "This is an example caption."
},
{
"resource": "facebook",
"operation": "publishFbVideo",
"pageId": "112233445566",
"videoUrl": "https://www.example.com/video.mp4",
"title": "This is an example title.",
"description": "This is an example description."
},
{
"resource": "facebook",
"operation": "publishFbStoryPhoto",
"pageId": "112233445566",
"imageUrl": "https://www.example.com/image.jpg"
},
{
"resource": "facebook",
"operation": "publishFbStoryVideo",
"pageId": "112233445566",
"videoUrl": "https://www.example.com/video.mp4"
},
{
"resource": "facebook",
"operation": "publishFbReel",
"pageId": "112233445566",
"videoUrl": "https://www.example.com/video.mp4",
"description": "FB Reel Description"
},
{
"resource": "threads",
"operation": "threadsPublishText",
"thUserId": "112233445566",
"text": "This is an example text."
},
{
"resource": "threads",
"operation": "threadsPublishImage",
"thUserId": "112233445566",
"imageUrl": "https://www.example.com/image.jpg",
"text": "This is an example caption.",
"altText": "This is an example alt text."
},
{
"resource": "threads",
"operation": "threadsPublishVideo",
"thUserId": "112233445566",
"videoUrl": "https://www.example.com/video.mp4",
"text": "This is an example caption.",
"altText": "This is an example alt text."
},
{
"resource": "threads",
"operation": "threadsPublishCarousel",
"thUserId": "112233445566",
"items": [
{
"type": "image",
"url": "https://www.example.com/image.jpg",
"altText": "This is an example alt text.",
"caption": "This is an example caption."
},
{
"type": "video",
"url": "https://www.example.com/video.mp4",
"altText": "This is an example alt text.",
"caption": "This is an example caption."
}
],
"text": "This is an example caption."
}
]
4. Example: Single Job
{
"resource": "instagram",
"operation": "publishImage",
"igUserId": "112233445566",
"mediaUrl": "https://example.com/image.jpg",
"caption": "My first IG post",
"autoPublish": true
}
—
Outputs
Every successful publish returns a consistent JSON shape (fields may vary slightly by resource/operation):
{
"resource": "instagram|facebook|threads",
"type": "image|video|reel|story|carousel|text",
"creationId": "1789...", // IG/Threads container or parent (when applicable)
"children": ["childId1"], // for carousels
"status": "FINISHED|PUBLISHED|READY|ERROR|...",
"published": true,
"publishResult": { "id": "1790..." }, // media/thread object
"videoId": "1234567890" // FB video id when relevant
}
Use this to chain downstream steps (e.g., fetch permalink, store IDs).
—
Rate limits & retries
—
Meta Publisher Utils — how to use
The Meta Publisher Utils node generates a ready-to-run JSON payload for the Meta Publisher node. It’s perfect for assembling multiple posts (IG/FB/Threads) from a single set of inputs, templates, or upstream data.
—
What it does
– Resources (Instagram, Facebook Page, Threads)
– Operations per resource (checkboxes; only relevant options appear)
imageUrl, videoUrl, caption, IDs)json.data is an array of jobs ready for the Meta Publisher node’s JSON input mode.—
Basic wiring
1. Meta Publisher Utils → Meta Publisher
– Set Input Source = From JSON Property
– Set JSON Property Path = data
That’s it—Meta Publisher will execute each generated job in the array.
—
Quick start (example)
1. Drop Meta Publisher Utils.
2. In Resources, tick Instagram and Threads.
3. In Instagram Operations, tick Publish Image and Publish Reel.
4. Fill:
– IG User ID: 1789…
– Image URL: https://example.com/image.jpg
– Video URL: https://example.com/reel.mp4
– Caption: Hello from n8n
5. In Threads Operations, tick Publish Text:
– Threads User ID: 9876…
– Threads Text: Posting from n8n 💚
6. (Optional) Leave Skip Missing enabled to silently skip incomplete jobs.
7. Connect to Meta Publisher (JSON mode as above) and run.
The Utils node will output something like:
{
"data": [
{
"resource": "instagram",
"operation": "publishImage",
"igUserId": "1789...",
"mediaUrl": "https://example.com/image.jpg",
"caption": "Hello from n8n",
"userTags": [{ "username": "someuser", "x": 0.1, "y": 0.8 }],
"autoPublish": true
},
{
"resource": "instagram",
"operation": "publishReel",
"igUserId": "1789...",
"videoUrl": "https://example.com/reel.mp4",
"caption": "Hello from n8n",
"userTags": [{ "username": "someuser", "x": 0.1, "y": 0.8 }],
"thumbOffsetMs": 0,
"shareToFeed": true,
"autoPublish": true
},
{
"resource": "threads",
"operation": "threadsPublishText",
"thUserId": "9876...",
"text": "Posting from n8n 💚"
}
],
"count": 3
}
—
Editable fields (high level)
– Instagram / Facebook Page / Threads
– Instagram: publishStory, publishImage, publishVideo, publishReel, publishCarousel
– Facebook Page: publishFbPhoto, publishFbVideo
– Threads: threadsPublishText, threadsPublishImage, threadsPublishVideo, threadsPublishCarousel
imageUrl, videoUrl, captionigUserId, pageId, thUserId – IG: coverUrl (video), reelVideoUrl, thumbOffsetMs, shareToFeed, igItems (carousel)
– IG Story: storyImageUrl, storyVideoUrl (if omitted, falls back to common URLs)
– Threads: text, altText, thItems (carousel: image/video entries with altText, optional caption)
– Skip Missing: Whether to skip incomplete jobs instead of throwing errors.
– Include Example Set: Whether to include example URLs/IDs when you don’t have real ones yet (for demos).
> Tip: When building carousels, supply at least 2 items; the Utils node will warn/skip otherwise (depending on Skip Missing).
—
Feeding dynamic data
Upstream nodes (e.g., Set, Spreadsheet File, HTTP Request) can provide per-item fields like igUserId, imageUrl, etc. Use n8n expressions in the Utils node (e.g., ={{$json.imageUrl}}) to populate the payload dynamically.
—
Minimal recipes
Instagram → Image
{
"resource": "instagram",
"operation": "publishImage",
"igUserId": "1789...",
"mediaUrl": "https://example.com/photo.jpg",
"caption": "My IG post",
"userTags": [{ "username": "someuser", "x": 0.1, "y": 0.8 }],
"autoPublish": true
}
Instagram → Story (video)
{
"resource": "instagram",
"operation": "publishStory",
"igUserId": "1789...",
"mediaUrl": "https://example.com/story.mp4",
"caption": "Story time",
"storyKind": "video",
"autoPublish": true
}
Facebook Page → Photo
{
"resource": "facebook",
"operation": "publishFbPhoto",
"pageId": "112233445566",
"imageUrl": "https://example.com/photo.jpg",
"caption": "FB photo caption"
}
Threads → Image
{
"resource": "threads",
"operation": "threadsPublishImage",
"thUserId": "987654321",
"imageUrl": "https://example.com/thread.jpg",
"text": "Threads image caption",
"altText": "Alt text for accessibility"
}
—
Common pitfalls & tips
– Instagram → igUserId
– Facebook Page → pageId
– Threads → thUserId
platform internally, but we accept resource and normalize it—your Utils output uses resource as shown here (works with our Publisher).—
Chaining to Meta Publisher
1. Meta Publisher Utils (outputs { data: [...] })
2. Meta Publisher
– Input Source = From JSON Property
– JSON Property Path = data
3. Optional: add If / Switch nodes to route successes vs errors (use status, published, etc.).
—
With this utility in front of your Publisher, you can define one compact set of inputs and instantly generate all the platform-specific jobs your workflow needs.
Development
This repo uses the same conventions as the n8n node starter:
dist/build, lint, lintfixTypical loop:
npm i
npm run dev # tsc --watch
In another terminal, run n8n and test
Refer to n8n’s “Using this starter” steps (generate repo, install deps, lint, test locally, publish) for overall workflow.
—
Testing locally
n8n documents how to run your node locally; follow those instructions to link your development build and iterate quickly.
—
Contributing
Issues and PRs are welcome! Please:
npm run lint / npm run lintfix)—
License
MIT — same as the official starter.
—
Notes
graph.threads.net) under the Meta umbrella; this node handles it internally — you just choose Threads in the UI.