JSON over HTTPS
One endpoint to send products and tags, a few to read status, limits and tagged products. No SDK required.
Developers
When your systems know best what the catalog looks like, send products straight to FeedManager instead of exporting a file for us to fetch. Available on Pro and above.
One endpoint to send products and tags, a few to read status, limits and tagged products. No SDK required.
Batches are validated, queued and applied in order by a worker.
An idempotency key makes a repeated request return the same batch instead of duplicating work.
One bad product doesn't fail the batch — it is reported with its id and reason.
Keys are only accepted over HTTPS and never in a query string. The API host sets no cookies and answers JSON only.
OpenAPI descriptioncurl -X POST https://api.feedmanager.org/v1/sources/42/products/batch \
-H "Authorization: Bearer $FEEDMANAGER_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: 2026-09-20-0001" \
-d '{
"operation": "upsert",
"products": [
{"id": "SKU-1042", "title": "Trail Runner GTX",
"price": "74.90 EUR", "availability": "in_stock",
"link": "https://store.example/p/1042"}
]
}'import os, httpx
key = os.environ["FEEDMANAGER_KEY"]
products = [{"id": "SKU-1042", "title": "Trail Runner GTX",
"price": "74.90 EUR", "availability": "in_stock"}]
response = httpx.post(
"https://api.feedmanager.org/v1/sources/42/products/batch",
headers={"Authorization": f"Bearer {key}",
"Idempotency-Key": "2026-09-20-0001"},
json={"operation": "upsert", "products": products},
timeout=30,
)
batch = response.json()
print(batch["batch_id"], batch["status"])const response = await fetch(
"https://api.feedmanager.org/v1/sources/42/products/batch",
{
method: "POST",
headers: {
Authorization: `Bearer ${process.env.FEEDMANAGER_KEY}`,
"Content-Type": "application/json",
"Idempotency-Key": "2026-09-20-0001",
},
body: JSON.stringify({
operation: "upsert",
products: [{ id: "SKU-1042", title: "Trail Runner GTX",
price: "74.90 EUR", availability: "in_stock" }],
}),
},
);
const batch = await response.json();
console.log(batch.batch_id, batch.status);Reference
Base address https://api.feedmanager.org/v1. Every response is JSON and is
never cached.
| Endpoint | What it does |
|---|---|
POST
/sources/{id}/products/batch |
Send up to 1,000 products. operation is upsert or delete. Answers 202 with a batch id; a repeated Idempotency-Key returns the first batch with 200. |
POST
/sources/{id}/products/batch |
With operation tag: add, remove or set static tags by name on up to 1,000 products of any source — store, file or API. create_missing creates new tags within your plan's limit. |
GET
/batches |
List recent batches, newest first. Filter by source, status or date; page with a cursor, up to 100 per page. |
GET
/batches/{batch_id} |
One batch: counts, status and the per-item errors. |
GET
/sources/{id}/products/{product_id} |
Read one product back, as FeedManager stored it after mapping. |
GET
/tags |
Your tags with their product counts; ?kind=static or dynamic. |
GET
/tags/{tag_id} |
One tag: name, kind, colour, description and how many products carry it. |
GET
/tags/{tag_id}/products |
The products a tag holds — for a storefront's best-seller block or your ERP. Up to 1,000 per page, with the fields you ask for. |
GET
/limits |
Your plan's limits and what you have used: products, requests left this minute, queued batches. |
GET
/openapi.json |
The API description for Postman, Insomnia and code generators. Public, no key needed. |
AI agents
FeedManager is an MCP server: Claude, Cursor and other AI agents that speak the Model Context Protocol can read your catalog, feeds and builds, find out why a product is disapproved or missing from a feed, start a sync, a build or a page check, and tag products.
POST https://api.feedmanager.org/mcp — Streamable HTTP, one JSON
answer per request, with an API key as the bearer token. It speaks protocol revision
2026-07-28 and the three before it (2025-11-25, 2025-06-18,
2025-03-26).mcp scope plus the scopes of what the agent may do; an agent only sees the tools its
key allows. Pro and above; every call counts toward your API requests per minute and is
logged.ai:read to see runs and suggestions, ai:write to ask the AI about one
product, ai:approve to accept a suggestion. Asking spends your AI credits, up to a
daily limit you set per key (500 credits unless you change it); accepting changes what your
feeds send. With ai:write alone, the agent proposes and a person decides.claude mcp add --transport http feedmanager \
https://api.feedmanager.org/mcp \
--header "Authorization: Bearer YOUR_API_KEY"{
"mcpServers": {
"feedmanager": {
"url": "https://api.feedmanager.org/mcp",
"headers": {
"Authorization": "Bearer YOUR_API_KEY"
}
}
}
}MCP tools
Each row needs the mcp scope plus the scope shown. A tool for a module your plan doesn't
include says so instead of returning data.
| Tools | Key scope | What the agent gets |
|---|---|---|
Read
catalog_overview search_products get_product catalog_health |
products:read |
Product counts, search by text and filters (also by Merchant Center status and issue), every field of one product, and the catalog health score with its field gaps. |
Read
list_sources get_source |
sources:read |
Your sources with their schedule, status and product count, and a source's last five syncs. |
Read
merchant_center |
sources:read |
Google's own product statuses today and over 14 days, the most common item issues with an explanation, and account issues with a checklist. |
Read
list_feeds get_feed list_feed_runs get_channel list_promotions |
feeds:read |
Feeds and their builds: rejected products with the reasons, what each rule and filter group did, channel and AI readiness, a channel's field specification, and promotions. |
Read
explain_product_in_feed |
products:read + feeds:read |
Why one product is or isn't in each feed: the filter group that left it out, the fields the channel rejects, or the row the channel gets. |
Read
page_checks_overview list_page_checks |
feeds:read |
Page checks: the daily pass per feed, and per page what the feed sends, what the page shows, the likely cause and what the store answered. |
Read
list_alerts |
sources:read + feeds:read |
The alerts that are open now, with their numbers and text; the recently resolved ones on request. |
Read
list_tags |
tags:read |
Static and dynamic tags with their product counts. |
Read
list_reports get_report |
reports:read |
Weekly and monthly reports with the numbers behind every section. |
Read
list_activity |
activity:read |
Who changed what, newest first. People appear by name; no email or IP addresses. |
Read
list_ai_runs get_ai_run get_product_ai |
ai:read |
AI runs and their suggestions; for one product, which AI actions would do something and what each costs in credits. |
Read
list_creative_sets |
creatives:read |
Creative Studio's creative sets with their template, sizes and last render. |
Action
sync_source build_feed check_page check_issue_pages evaluate_tag render_creative_set |
runs:write |
Start a sync, a build, a check of one product's page or of the pages behind a Merchant Center issue, a dynamic tag's rule, or a creative set's render. |
Action
tag_products |
tags:write |
Add or remove a static tag on up to 1,000 products per call. |
Action
improve_product |
ai:write |
Ask FeedManager's AI about one product: Google category, missing attributes, title, description or an image check. Spends AI credits; the answer is a suggestion. |
Action
decide_suggestion |
ai:approve |
Accept or discard a suggestion. An accepted value is what your feeds send from their next build. |
429 with Retry-After.Set up your feeds and rules for free, then upgrade to Pro when you want to push products through the API.
Private beta — accounts by invitation.