Model Context Protocol
WordPress MCP server (for AI agents)
OAuth sign-in, no API key. One URL, click Authorize, done. Your agent publishes markdown as real Gutenberg posts — images re-hosted, categories and tags by name, SEO fields where your site supports them — and you approve what goes live.
MCP server URL
https://mcp.pressbotics.com/mcpAdd as a custom MCP server. Static pb_live_ keys remain available for custom or self-hosted agents.
Connect your agent
Works with any MCP agent, including Claude, ChatGPT, Cursor and n8n. Copy the URL, add it as a custom connector, authorize once.
Pressbotics MCP server URL
https://mcp.pressbotics.com/mcpOne connection. Your favourite agent. Copy this URL into your agent’s custom MCP connections.
Connect Claude
Verified agent- 1Copy the Pressbotics MCP server URL above.
- 2In Claude, open Settings → Connectors and choose Add custom connector.
- 3Name it Pressbotics, paste the URL, and click Add.
- 4Click Connect — Claude opens Pressbotics in your browser. Sign in and click Authorize.
- 5Back in Claude, start a new chat and ask it to list your sites.
The 27 tools
This is the whole surface. Nothing else is exposed.
| Tool | What it does |
|---|---|
| create_connect_link | Creates a one-time link the site owner opens to connect a WordPress site. |
| get_connect_status | Reports whether a connect link has been completed and which site it produced. |
| list_sites | Lists the connected sites the caller is allowed to publish to. |
| get_site_context | Returns a site's handle, capabilities, categories, tags, brand voice notes and approval policy. |
| site_health | Re-probes a site and reports WordPress version, plugin detection and SEO capability. |
| list_content | Lists and filters existing posts on a site so an agent can find something to update. |
| list_media | Lists attachments already in the site's media library, so an existing image can be reused. |
| create_media_upload | Creates an upload link the person opens to hand over a file the agent cannot forward itself. |
| get_media_upload | Polls an upload until it is ready and returns the media_ref to pass to a publish call. |
| update_media | Updates an existing media library item's alt text, title, caption or description. |
| publish_post | Creates a post from markdown and publishes it (or queues it for approval). |
| schedule_post | Same as publish_post, plus a future publish_at timestamp. |
| update_post | Updates an existing post by id with new content, taxonomy, media or SEO fields. |
| get_post_status | Returns the current state of a submitted action, including per-component outcomes. |
| list_scheduled | Lists scheduled posts across the caller's sites with their times and current state. |
| reschedule_post | Moves a scheduled post to a new time, on WordPress as well as in Pressbotics. |
| cancel_scheduled | Cancels a scheduled post before it runs, reverting it to a draft on WordPress. |
| schedule_batch | Schedules several posts in one call — a week of content at a time. |
| create_recurrence | Creates a standing cadence that generates empty scheduled slots. It does not write content. |
| list_recurrences | Lists the cadences on a site, with their pattern, timezone and next slots. |
| cancel_recurrence | Stops a cadence generating further slots. Slots already created remain. |
| get_account | Returns the connected account: workspace, masked owner email, plan, plan limits, posts used and remaining this month, and when the count resets. |
| get_site_insights | Returns a site's (or all sites') output, on-time reliability, live-page quality scores, weekly trend and plain-English readings for 7d, 30d or 90d. Search and traffic are null until connected. |
| get_site_profile | Returns what Pressbotics has learned about a site — niche, audience, voice, topics, actual and wanted cadence, formats, approval and recommendation behaviour — each marked inferred or confirmed. |
| get_recommendations | Lists open recommendation cards (fill the calendar, improve, attention, write, series) with reasoning and confidence. Cards are briefs; Pressbotics does not write content. |
| accept_recommendation | Accepts a card and returns the full brief and a ready agent_prompt. Accepting a series also launches its campaign and holds weekly empty calendar slots (paid plans). |
| dismiss_recommendation | Dismisses a card with an optional reason; that type and topic stay hidden for 30 days. |
Publish parameters
Shared by publish_post, schedule_post and update_post. publish_at applies to schedule_post only; post_id to update_post only.
| Parameter | Type | Notes |
|---|---|---|
| site | string | Site handle or URL. Required. |
| title | string | Post title — the on-page headline. Required. |
| markdown | string | Post body in markdown. Converted to Gutenberg blocks. Required. |
| excerpt | string | WordPress excerpt. Does NOT set the meta description. |
| categories | string[] | Category names (not ids). Matched by name or created. |
| tags | string[] | Tag names (not ids). Matched by name or created. |
| featured_image_url | string (URL) | Public URL. Downloaded and sideloaded as the featured image. |
| featured_image_id | number | An attachment id already in the media library. Find one with list_media. |
| featured_media_ref | string | A file the person uploaded through the media handoff. From get_media_upload. |
| seo_title | string | The title tag. Max 70 characters. Needs the companion plugin + an SEO plugin (Yoast verified; Rank Math supported, untested). |
| meta_description | string | The search-result description. Max 200 characters. Same plugin requirement. |
| focus_keyword | string | Max 120 characters. Same plugin requirement. |
| canonical_url | string (URL) | Canonical link for the post. |
| request_review | boolean | Force the post into the approval queue regardless of site policy. |
| idempotency_key | string | Required. Repeat calls with the same key return the original action instead of duplicating. |
| publish_at | ISO 8601 | schedule_post only. Future publish time. |
| post_id | number | update_post only. The WordPress post to update. Required there. |
Three featured-image inputs, mutually exclusive
Supplying more than one is rejected — never silently resolved.
| Parameter | Source | Behaviour |
|---|---|---|
| featured_image_url | A publicly reachable URL | Pressbotics downloads it and sideloads it into the media library, then sets it as the featured image. |
| featured_image_id | An attachment already on the site | Reuse something in the media library. Find the id with list_media. |
| featured_media_ref | A file the person just uploaded | Produced by the media upload handoff: create_media_upload, the person uploads, get_media_upload returns the ref. |
list_content filters
Every post comes back with date and modified, so an agent can find the post you published last Tuesday.
| Filter | Type | Meaning |
|---|---|---|
| search | string | Free-text search across post titles and content. |
| category | string | Category name. |
| tag | string | Tag name. |
| status | publish | draft | future | pending | private | any | Defaults to published posts. Drafts, scheduled (future), pending and private posts are read with the site's own credential, so they are listed too. |
| published_after | ISO 8601 or YYYY-MM-DD | Only posts published on or after this moment. |
| published_before | ISO 8601 or YYYY-MM-DD | Only posts published before this moment. |
| order_by | date | title | modified | Sort field. |
| order | asc | desc | Sort direction. |
| page | number | 1-based page number. |
| limit | number | Results per page. |
Markdown becomes Gutenberg blocks
- Paragraphs
- Headings H1–H6
- Bold, italic and links
- Bulleted lists
- Numbered lists
- Blockquotes
- Pullquotes (:::pullquote)
- Fenced code blocks
- Tables
- Horizontal rules / separators
- Images, with an optional caption
- Galleries (:::gallery)
- Cover blocks (:::cover)
- Columns (:::columns)
- Groups (:::group)
- Embeds from supported providers
- Self-hosted video files
- Self-hosted audio files
Composite blocks with ::: directives
Some Gutenberg blocks have no markdown equivalent. Write them as fence directives inside the markdown parameter — :::name on its own line, closed by ::: on its own line.
| Directive | Block | What it does |
|---|---|---|
| :::cover <image-url> | wp:cover | Full-bleed hero with the enclosed content overlaid. The hero image is uploaded to the media library like any other image. |
| :::pullquote | wp:pullquote | A large decorative quote, distinct from a normal > blockquote. A second paragraph inside becomes the citation. |
| :::gallery | wp:gallery | One image per line — markdown image syntax or a bare URL. Produces a gallery with nested images, all uploaded. |
| :::columns | wp:columns | Columns separated by a line containing only ---. Markdown inside each column is compiled normally. |
| :::group | wp:group | A grouped section. |
:::cover https://cdn.example.com/hero.jpg
# Inside the launch of Orbit 2.0
A year of work, in one release.
:::
Orbit 2.0 is the biggest release we have shipped.
:::pullquote
We stopped optimising the old thing and rebuilt the loop.
Ana Reyes, Head of Product
:::

:::gallery

https://cdn.example.com/g2.jpg

:::
:::columns
### Faster
Builds are 3x quicker.
---
### Simpler
One screen instead of four.
:::
https://www.youtube.com/watch?v=dQw4w9WgXcQ
https://cdn.example.com/walkthrough.mp4Image captions
Markdown's title argument becomes a real WordPress figcaption. Without a title argument no caption is rendered — this is the only way to caption an image.
Video, audio and embeds
A bare link on its own line to a media file becomes a real player, not a link or an embed card.
| Kind | Extensions | Block |
|---|---|---|
| Video | .mp4 .webm .ogv .mov .m4v | wp:video |
| Audio | .mp3 .wav .m4a .ogg .oga .flac | wp:audio |
A bare link to a supported provider becomes wp:embed: YouTube, Vimeo, TikTok, Spotify, SoundCloud, Wistia. Any other URL stays an ordinary paragraph or link — embedding is not universal.
Partial success is reported, not hidden
A post can publish while one component fails — an unreachable image, a term that couldn't be created. Every publish response carries per-component outcomes, so your agent knows exactly what landed. Read them before reporting success to your user: a post can go live without its featured image, and the response will say so.
| Field | Values | Meaning |
|---|---|---|
| state | queued | published | scheduled | failed | rejected | reverted | What happened to the post itself. Everything below describes its components. |
| partial | boolean | True when the post landed but at least one component did not. |
| image_status | none | ok | failed | Featured image outcome. |
| image_error | string | Why the featured image failed, when it did. |
| taxonomy_status | none | ok | partial | failed | Categories and tags outcome. |
| taxonomy_error | string | Which terms could not be applied. |
| seo_status | none | ok | unsupported | Whether SEO meta was actually written. |
| seo_error | string | Which piece is missing when seo_status is "unsupported". |
| embed_status | none | ok | partial | failed | Whether provider embeds resolved. A provider that will not embed stays a plain link and the post still publishes. |
| embeds | array | The embed URLs found and what each became. |
| inline_images | { total, failed, errors } | Inline image re-hosting. An image that cannot be fetched is REMOVED from the post body and listed in errors; the post still publishes. |
| post_url | string (URL) | The live post URL, once it exists. |
| alt_text_warnings | array | Images in the post (featured or inline) that have no alt text. The post still publishes; fix them with update_media. |
| warnings | array of { code, message } | Advisory, never a refusal. no_taxonomy: the post has no categories and no tags, so WordPress files it under Uncategorized — resend with categories or tags from get_site_context, or fix it with update_post. |
| publish_at_utc | string (ISO 8601, Z) | Scheduled posts only. The exact instant the post is due, in UTC, stored beside the timezone you sent so the record is unambiguous. |
| preview_url | string (URL) | A signed-in Pressbotics page showing the saved post before it goes live. Present only when there is a saved body to preview. |
| render_check | pass | fail | not_yet | pass: the live post was fetched and rendered correctly. fail: it did not, and the post was reverted to draft. not_yet: a scheduled post that is not public yet — the scheduler verifies it when it goes live and writes pass or fail then. |
The SEO status contract
Every publish, schedule and update response returns seo_status.
| seo_status | Meaning | Detail |
|---|---|---|
| none | No SEO fields were requested on the call. | Nothing to write. |
| unsupported | SEO fields were requested but the site cannot write them. | seo_error names the missing piece: the Pressbotics companion plugin, or a supported SEO plugin. |
| ok | The site is capable and the SEO meta was actually written. | Requires the companion plugin AND an SEO plugin. Yoast is verified end to end on a live site; Rank Math is supported but has not been tested. Only the active plugin's meta keys are written. |
"ok" requires both the free Pressbotics companion plugin and an SEO plugin. Yoast is verified end to end on a live site; Rank Math is supported but has not been tested. Only the active plugin's meta keys are written. Other SEO plugins are not supported and return "unsupported". Note the distinctions: the post title is the headline, seo_title is the title tag (max 70), the excerpt is the on-site summary, and meta_description is the search-result description (max 200). The excerpt does not set the meta description.
What it can and cannot do
It can
- Create, schedule and update posts from markdown
- Set a featured image and re-host inline images
- Assign categories and tags by name
- Set SEO title, meta description, focus keyword and canonical URL (plugin + Yoast; Rank Math supported, untested)
- Read a site's context, content list and health
- Hold every post for your approval
It cannot
- Managing WordPress users
- Changing site settings
- Installing, activating or configuring plugins
- Changing or editing themes
- Running WordPress core updates
By design. A compromised agent can post something you can revert — one click in Activity unpublishes it and keeps the content as a draft, or puts an earlier version back. It cannot take over the site.
Further reading: What is a WordPress MCP server? · The WordPress MCP plugin guide


