How to submit an MCP server to Official MCP Registry

By Jonah EasePublished Last checked

The official registry has no form and no reviewer in the route. You write a server.json, prove you own the package it points to, sign in with the mcp-publisher tool, and publish[1]. It stores metadata only, and the packages stay on npm, PyPI, Docker Hub or wherever you put them[7]. Most of the work is getting the name and the proof to agree.

A server.json that validates

Three fields are required: name, description and version. The schema caps the description at 100 characters and requires the name to look like namespace/server[8]. This is the quickstart's file after its edit[1]:

server.json
{
  "$schema": "https://static.modelcontextprotocol.io/schemas/2025-12-11/server.schema.json",
  "name": "io.github.my-username/weather",
  "description": "An MCP server for weather information.",
  "repository": {
    "url": "https://github.com/my-username/mcp-weather-server",
    "source": "github"
  },
  "version": "1.0.1",
  "packages": [
    {
      "registryType": "npm",
      "identifier": "@my-username/mcp-weather-server",
      "version": "1.0.1",
      "transport": { "type": "stdio" }
    }
  ]
}

For a hosted server, replace packages with a remotes entry holding type (streamable-http is the one to use) and a public url[4].

Your namespace decides how you sign in

Sign-inName must start with
GitHubio.github.username/ or io.github.orgname/
Your own domain (DNS or HTTP proof)com.example.*/, your domain written backwards

Registry docs, read [2]

Proof you own the package

PackageProof, inside the published package
npm"mcpName" in package.json, equal to the server name
PyPI, NuGet, Cargomcp-name: your-server-name in the README. Crates.io strips HTML comments, so a Cargo README needs it as visible text.
Docker / OCILABEL io.modelcontextprotocol.server.name="your-server-name"
MCPBA URL containing "mcp", and a fileSha256 in server.json
Remote URLNone named in the docs; the server must be publicly reachable.

[3][4]. Publish the package version first: the registry hosts metadata only, and the quickstart publishes the package before the server.

Sign in and publish

The three commands, then a check
mcp-publisher init
mcp-publisher login github
mcp-publisher publish

curl "https://registry.modelcontextprotocol.io/v0.1/servers?search=io.github.my-username/weather"

login github prints a code and the page github.com/login/device; you enter the code there yourself[2]. Every change after that needs a new version. Published metadata is immutable, and there is no way to unpublish today[6][5]. Version ranges such as ^1.2.3 or 1.x are refused.

Errors people hit

  • "Registry validation failed for package": the proof is missing from the published version. Add mcpName or the README line, publish the package again, then retry[1].
  • "You do not have permission to publish this server": your sign-in method and the name's namespace do not match[1]. For an organisation namespace a user reported a 403 as an organisation owner, and a maintainer called it a bug on the registry's side[11].
  • "cannot publish duplicate version". In one reported case the cause was a server.json that still said the old version, and the fix was to put the new one in it[9].
  • "Expected mcpName X, got x": a casing mismatch between the organisation name and the namespace. This report was still open on [10].
  • "Invalid or expired Registry JWT token": run mcp-publisher login github again[1].
The duplicate-version response, from issue 1615
Error: publish failed: server returned status 400:
{"title":"Bad Request","status":400,"detail":"Failed to publish server",
 "errors":[{"message":"invalid version: cannot publish duplicate version"}]}

By hand or with help

Everything above is the by-hand route: three commands and one approval in your browser. The registry expects downstream aggregators to pull from it[7], and two of them have their own pages: PulseMCP and the GitHub MCP Registry.

Current status,

The registry's own pages still call it a preview, where breaking changes or data resets may occur[7]. The latest release of the registry software was v1.8.1, published [12].

Sources

  1. MCP Registry docs: Quickstart · checked
  2. MCP Registry docs: How to authenticate when publishing · checked
  3. MCP Registry docs: Supported package types · checked
  4. MCP Registry docs: Publishing remote servers · checked
  5. MCP Registry docs: Versioning · checked
  6. MCP Registry docs: Frequently asked questions · checked
  7. MCP Registry docs: About the registry (preview notice) · checked
  8. server.json schema, 2025-12-11 · checked
  9. Registry issue 1615: publish rejected as a duplicate version · checked
  10. Registry issue 1525: mcpName rejected for a casing mismatch · checked
  11. Registry issue 1468: 403 publishing under an organisation namespace · checked
  12. Registry repository: releases · checked

ManyCP is not affiliated with, endorsed by or sponsored by any directory, Docker, OpenAI, Anthropic or GitHub named here. Names are used to say which service a fact is about.

Or skip all of that

Or let ManyCP do it in one click

ManyCP builds the server.json, checks it with the registry, and publishes with your GitHub sign-in. If your package is missing the mcpName proof, it opens a pull request on your own repo to add it.

Guides

More directories