mcp-instagram
mcp-instagram
Instagram 发布 MCP server —— 走官方 Graph API,同时支持 stdio 与 streamable-http 两种传输。
为飞雁(feiyan)而写,但不依赖飞雁:任何 MCP 客户端都能用。AGPL-3.0-only。
为什么自己写
Meta 没有官方 Instagram MCP(唯一的官方连接器是 Meta Ads,只管广告投放)。社区实现有几个,但全是 Graph API 的薄封装、star 个位到二十几、维护弱。既然是薄封装,与其依赖一个随时会停更的仓库,不如自己维护一份。
先决条件
这三件是 Meta 的硬门槛,不是本项目能绕开的:
专业账号(Business / Creator)。个人号在 API 层面被结构性排除。
Meta 应用 + Advanced Access:
instagram_business_content_publish权限要过 App Review 与企业验证,每次提交 2–4 周。长期访问令牌(60 天)与
IG_USER_ID。短期令牌可以用exchangeForLongLived()换一次;之后本服务会在剩余 7 天内自动续期。
平台硬限制(工具描述里也写了一遍)
项 | 限制 |
图片格式 | 仅 JPEG |
图片大小 | ≤ 8 MB |
图片尺寸 | 宽 320–1440 px |
宽高比 | 4:5 ~ 1.91:1 |
轮播 | 2–10 张;所有图按第一张的比例裁剪,顺序即展示顺序 |
caption | ≤ 2200 字符,≤ 30 个话题标签,不渲染 Markdown |
发布配额 | 100 条 / 24 小时滚动窗口(轮播算 1 条) |
媒体必须是 https 公网地址 —— Instagram 由服务端主动拉取,本地路径和内网地址它都取不到。把图片放到公网(对象存储 / CDN / 图床)再把 URL 交给本服务。
配置
环境变量 | 必填 | 说明 |
| ✅ | 专业账号的 user id(不是用户名) |
| ✅ | 长期访问令牌 |
| 仅「短期换长期」时需要;续期用不到 | |
| 默认 | |
| 令牌缓存目录。容器里挂卷,续期结果才能跨重启保留 | |
| http 模式的 Bearer 令牌。不设 = 不鉴权 | |
|
|
运行
# stdio(默认):客户端拉起本进程,一进程一账号
IG_USER_ID=... IG_ACCESS_TOKEN=... npx @feiyan/mcp-instagram
# streamable-http:常驻服务 / 容器
IG_USER_ID=... IG_ACCESS_TOKEN=... AUTH_TOKEN=$(openssl rand -hex 24) \
npx @feiyan/mcp-instagram --http --port 18080
# 端点 http://<host>:18080/mcp,健康检查 http://<host>:18080/healthz(不鉴权)Claude Desktop 之类的客户端配置:
{
"mcpServers": {
"instagram": {
"command": "npx",
"args": ["-y", "@feiyan/mcp-instagram"],
"env": { "IG_USER_ID": "...", "IG_ACCESS_TOKEN": "..." }
}
}
}工具
工具 | 说明 |
| 1 张 → 单图帖,2–10 张 → 轮播。唯一的发布入口 |
| 24 小时配额用了多少、还剩多少 |
| 令牌剩余有效天数 |
| 立即续期(通常不必手动调,快过期会自动续) |
失败一律以 isError: true 返回,并把 Graph API 的错误码翻成可执行的话(例如 190 → 「重新走一次授权」,10 → 「缺 instagram_business_content_publish,去 App Review 申请 Advanced Access」)。
开发
pnpm install
pnpm build # stdio 子进程用例测的是 dist/index.js,跑测试前先 build
pnpm test
pnpm check # tsc --noEmit
pnpm lint测试不打真实网络:起一个真的 node:http 假 Graph API 当夹具(mock fetch 只能证明「我以为的请求」是对的),并用真的 MCP 客户端 SDK 连 stdio 与 streamable-http 各跑一遍。