The MCP Registry: What It Is and How Clients Use It
The official MCP Registry is a public catalogue of server metadata, not of code. What an entry contains, how names are verified, the API, how to publish, and how GitHub, VS Code and private registries build on it.
8 min read
The MCP Registry is the official public catalogue of MCP servers, at registry.modelcontextprotocol.io. It stores metadata, not code: for each server, a server.json that says what it is called, where to get it (an npm or PyPI package, a container image, or a remote URL) and how to run it. Names are namespaced and verified, so io.github.alice/weather can only be published by that GitHub account, and com.example/tool only by whoever controls example.com. It is read through a public REST API, is still in preview, and is meant to be consumed mainly by other registries and marketplaces rather than straight by your editor. Those downstream registries, including private ones a company runs, speak the same API, which is how GitHub Copilot and VS Code can be pointed at a list of approved servers.
One thing a registry is not is an approval. That argument is made in MCP governance; this piece is about how the registry works.
What the registry stores
The registry’s own overview (opens in a new tab) describes it as the official centralised metadata repository for publicly accessible MCP servers, backed by contributors including Anthropic, GitHub, PulseMCP and Microsoft. Each entry is a server.json with:
- A unique name in reverse-DNS form, such as
io.github.user/server-name. - Where to find the server:
packagesfor something you install and run locally,remotesfor a hosted server at a URL, or both. - How to run it: the transport, command-line arguments, environment variables, and for remotes any headers or URL variables the user must supply.
- Discovery data such as the description, version and repository.
{
"$schema": "https://static.modelcontextprotocol.io/schemas/2025-12-11/server.schema.json",
"name": "com.example/acme-analytics",
"title": "ACME Analytics",
"description": "Real-time business intelligence and reporting platform",
"version": "2.0.0",
"remotes": [
{ "type": "streamable-http", "url": "https://analytics.example.com/mcp" }
]
}The code itself stays where it already lives: npm, PyPI, NuGet, crates.io, a container registry, or a GitHub or GitLab release for MCPB bundles. The registry only points to it. It accepts only public servers: the installation method must be publicly available, or the remote server publicly reachable. A server on a private network or a private package feed does not belong there.
Namespaces and verification
The name’s prefix decides how you must prove you own it. The authentication guide (opens in a new tab) offers three routes:
- GitHub sign-in, for names under
io.github.username/orio.github.orgname/. - DNS, for names under your own domain in reverse form (
com.example/): you publish a TXT record holding a public key and sign in with the private key. - HTTP, the same idea with the key in a file at
/.well-known/mcp-registry-authon your domain.
The registry then checks that the package really belongs to the name. The registry’s package types page lists the check for each: an mcpName field in package.json for npm; an mcp-name: line in the README for PyPI, NuGet and Cargo; an io.modelcontextprotocol.server.name label on a container image; and for MCPB bundles, a SHA-256 hash that clients check before installing.
Be clear about what that proves. It proves the entry was published by whoever controls that GitHub account or domain, and that the package names the same server. It does not prove the code is safe. The registry says so itself: it delegates security scanning to the package registries and to downstream aggregators, and its maintainers remove spam and malicious entries by hand under a moderation policy.
The API
The API is unauthenticated and read-only. The aggregators guide (opens in a new tab) documents three endpoints under https://registry.modelcontextprotocol.io: list servers, list the versions of one server, and get one version, where the version latest gives the newest. The list takes a limit, a cursor for the next page and updated_since to fetch only what changed; the publishing quickstart also uses a search parameter. Server names in a path must be URL-encoded.
# Search by name curl "https://registry.modelcontextprotocol.io/v0.1/servers?search=io.github.github/github-mcp-server" # Page through everything, 100 at a time curl "https://registry.modelcontextprotocol.io/v0.1/servers?limit=100" # The newest version of one server (note the encoded slash) curl "https://registry.modelcontextprotocol.io/v0.1/servers/io.github.github%2Fgithub-mcp-server/versions/latest"
Each result wraps the server.json with registry metadata under _meta, including a status, when it was published and when it last changed. Published versions are immutable; only the status moves, to deprecated or deleted. Deleted usually means the entry broke the moderation policy, so anything that copies the registry should keep statuses up to date. The registry promises no uptime or durability, and expects consumers to copy the data on a regular but infrequent schedule, such as hourly, rather than query it live.
Publishing a server
The publishing quickstart (opens in a new tab) uses the official mcp-publisher command-line tool. For an npm package the steps are:
- Add
mcpNametopackage.json, set to the name you will publish under, and publish the package to npm. The registry only hosts metadata, so the package has to exist first. - Install
mcp-publisher(a release binary, or Homebrew) and runmcp-publisher initto generate aserver.jsonfrom your project. - Edit it: the
namemust matchmcpName, and both version fields should match the package version. For a hosted server, add aremotesentry instead of or as well aspackages. - Sign in:
mcp-publisher login github, orlogin dnsorlogin httpfor a domain name. - Run
mcp-publisher publish, then search the API to confirm it is there.
Two rules to know before you start. You update an entry by publishing a new version with a new version string; you cannot edit one in place. And at the time of writing you cannot unpublish a server at all; that is still under discussion. Publishing can also be automated from GitHub Actions.
Sub-registries, GitHub and private registries
The official registry is deliberately unopinionated, and it is not meant to be read directly by host applications such as your editor. Hosts are meant to read other registries: marketplaces and aggregators that pull from the official one, add curation, ratings or security scan results, and serve it all through the same OpenAPI interface. A registry that does that is called a sub-registry, and it may add its own data under _meta.
- GitHub MCP Registry. GitHub’s catalogue at github.com/mcp lists servers with their READMEs and an Install in VS Code button that opens VS Code with the configuration filled in. GitHub’s guide to the registry (opens in a new tab) describes publishing to it with
mcp-publisher, with updates flowing downstream. - VS Code’s gallery. The
@mcpview in the Extensions panel is VS Code’s gallery of servers. An organisation can use its own registry for it with theMcpGalleryServiceUrlpolicy, and setchat.mcp.accesstoregistryso only servers from that registry run. - GitHub Copilot for organisations. On Copilot Business and Enterprise, an admin can enter an MCP registry URL (opens in a new tab) and choose Allow all or Registry only. The URL must be the registry’s base, because Copilot appends the API path itself; Azure API Center is given as one way to host it.
- Your own private registry. The official registry does not take private servers and suggests running your own for them. Its code is not designed for self-hosting, so the documented route is a registry that implements the same OpenAPI spec, rather than a fork of the official service.
How clients use a registry
From the host’s side, a registry is a lookup table that turns a name into a configuration. The flow in practice:
- The host reads a registry that implements the standard API: a marketplace, GitHub’s, or your company’s.
- It shows the entries in a gallery, with name, publisher namespace, description and any ratings the registry added.
- You pick one. The host reads its
packagesorremotes, asks you for the variables marked required or secret, and writes the server into its configuration. For VS Code that ismcp.json; VS Code mcp.json step by step shows the result. - On first use, a remote server with OAuth opens your browser to sign in; a package is downloaded and started.
- If an admin set a registry-only policy, a server that is not in the registry does not run.
Notice where the registry stops. It can tell the host what a server is and where it lives. It cannot tell the host whether the server should be trusted with your data, which scopes it should get, or who on your team owns it. Those are decisions, covered in MCP governance and checked with an MCP security scanner.
Keeping track of what you approved
A registry-only policy works best with a short, reviewed list behind it, and the reviews are work like any other. One way to run it: keep each “add this server” request as a task on the team’s board, with the decision recorded against it. fenbs, a task board where people and AI assistants are members with roles, is itself a remote MCP server at https://fenbs.ai/api/mcp with a browser sign-in; the assistant you connect holds your role on the board, narrowed by the scopes you tick, and every change it makes is recorded in History with its name.
Related
The architecture a registry feeds into: MCP client, host and server. Which apps can install from a registry: MCP clients compared. Connecting fenbs by URL: MCP docs.