plym Docs
    plym.io

    Introduction

    plym ships an MCP server that gives an AI client read and write access to your blog.

    Updated Aug 04, 2026

    On this page

    The plym MCP server runs as a second container built from the same plym image and reaches the api over the internal network. It exposes six tools — create a post, upload an image, list posts, list users, fetch a URL, convert HTML to markdown — over streamable HTTP at /mcp. Unlike the REST API, there is no key to issue: every tool call authenticates with a plym account email and password.

    Enable the server

    Run this in your blog directory:

    plym enable mcp

    The endpoint becomes https://blog.flapico.com/mcp, served through the reverse proxy your blog already uses. No extra domain and no extra certificate are needed. If the blog is not on a domain yet, the endpoint is http://localhost:9173/mcp against the blog's own port.

    A separate hostname

    Use the default above for most setups. Give MCP its own hostname when you want it off the blog's domain, and name the proxy plym should configure:

    plym enable mcp mcp.flapico.com --caddy

    The accepted proxies are --nginx, --caddy, and --traefik. --nginx and --caddy need sudo to write the site config; --traefik writes docker-compose.mcp-traefik.yml for you to finish and needs no sudo.

    What enabling changes

    Key in .env Value
    COMPOSE_PROFILES gains mcp
    PLYM_MCP_PUBLISH_PORT the first free port from 9369 up
    PLYM_MCP_PUBLIC_URL written only when you pass a hostname
    PLYM_MCP_PROXY written only when you pass a hostname

    The published port is bound to 127.0.0.1, so the container is reachable from the machine and through the proxy, never directly from the internet. While the profile is on, plym reload and plym rebuild restart the MCP container along with the api.

    The endpoint path

    /mcp sits at the domain root even when the blog is served under a prefix. With a blog_prefix of /blog, the blog is at https://flapico.com/blog and MCP is at https://flapico.com/mcp. A request to https://flapico.com/blog/mcp returns 405.

    Authentication

    Every request carries two headers:

    Header Value
    X-User-Identity The email address of a plym account
    X-Mcp-Token That account's password

    X-Mcp-Token holds the account password. Despite the name, plym issues no MCP-specific credential. The server trades the pair for a short-lived access token by calling the login endpoint on every tool call, which costs one extra round trip per call.

    What these credentials cannot do

    There is no expiry, no revocation list, and no per-tool scoping. To rotate, change the account password in the admin — every configured client then fails until you update it. A client holding an administrator account can do through the tools everything that account can do.

    Connecting is unauthenticated

    initialize and tools/list succeed with no credentials at all; only tool calls check them. Anyone who can reach /mcp can read the tool list. Put the endpoint behind the same network controls you would put in front of the admin.

    Roles

    Tools that touch content need an account with the editor or administrator role. A reader account can call list_users, get_from_url, and md_from_html, and nothing else. The per-tool table is in Features.

    HTTP is the only usable transport

    Credentials arrive as HTTP headers, so the server needs an HTTP transport to read them. Setting PLYM_MCP_TRANSPORT=stdio starts a stdio server that answers initialize and tools/list, but every tool call fails with Missing credentials: set the X-User-Identity and X-Mcp-Token headers. A client that speaks only stdio needs a bridge — see Client setup.

    Disable the server

    plym disable mcp

    This stops the container, removes the proxy config plym wrote, drops mcp from COMPOSE_PROFILES, and clears PLYM_MCP_PUBLIC_URL and PLYM_MCP_PROXY. PLYM_MCP_PUBLISH_PORT stays, so re-enabling reuses the same port.