MCP Server Hub
Hosts multiple Model Context Protocol servers (fetch, memory, GitHub, Postgres, utils) behind a single authenticated gateway, giving AI agents instant access via one Bearer token.
README
<p align="center"> <img src="https://cdn.jsdelivr.net/gh/KbnCodes/mcp-server-hub@main/assets/logo.svg" alt="MCP Server Hub logo" width="140" height="140" /> </p>
<h1 align="center">MCP Server Hub</h1>
<p align="center"><strong>Host multiple Model Context Protocol servers behind one authenticated gateway — in one click.</strong></p>
<p align="center">
</p>
A production-ready, stateless Streamable HTTP hub that gives your AI agents (Claude, Cursor, LibreChat, custom clients) instant access to web fetching, shared memory, GitHub, Postgres and utility tools — all from a single Railway service with a single Bearer token.
Built for the 2026-07-28 MCP spec revision: no sessions, no sticky routing, any replica serves any request.
Deploy it, or run it locally:
# ...or try it on your machine in one command (auto-generates a dev token):
npx @kbncodes/mcp-server-hub --dev
Why this hub?
| This template | Typical MCP templates | |
|---|---|---|
| Servers per deploy | 5 in one service | 1 |
| Authentication | Bearer token (timing-safe compare), spec-compliant 401 + WWW-Authenticate + RFC 9728 metadata |
None, optional, or hardcoded defaults |
| Transport | Stateless Streamable HTTP (2026-07-28-ready) | Often deprecated SSE or sessionful |
| Admin UI | Built-in status dashboard at / |
None |
| Healthcheck | /health wired into Railway |
Usually missing |
| Horizontal scaling | Yes — stateless, no session store | Rarely |
What's inside
| Server | Endpoint | Tools | Requires |
|---|---|---|---|
| Utils | /mcp/utils |
current_time, convert_timezone, generate_uuid, hash_text, base64, calculate |
— |
| Fetch | /mcp/fetch |
fetch_url (HTML→clean text), fetch_json |
— |
| Memory | /mcp/memory |
memory_set/get/list/delete/search — shared agent notes |
— (volume optional) |
| GitHub | /mcp/github |
search_repositories, get_repo, get_file, list_issues |
GITHUB_TOKEN |
| Postgres | /mcp/postgres |
list_tables, describe_table, query (READ ONLY transactions) |
DATABASE_URL |
Plus:
- Admin dashboard at
/— server status, tool inventory, copy-paste client config /healthhealthcheck endpoint (configured inrailway.json)/.well-known/oauth-protected-resource— RFC 9728 Protected Resource Metadata
Deploy on Railway
- Click Deploy on the template page (or deploy this repo).
- Railway auto-generates a strong
AUTH_TOKENfor you. - Open your service URL — the dashboard walks you through connecting a client.
That's it. Optionally:
- Add a GitHub token (
GITHUB_TOKEN) to enable the GitHub server. - Attach a Postgres database and set
DATABASE_URL=${{Postgres.DATABASE_URL}}to enable read-only SQL. - Mount a volume at
/dataand setMEMORY_FILE=/data/memory.jsonto persist agent memory.
Railway is the recommended home for this template: it lists in the marketplace for discovery and pays template authors via the 25% Template Kickback Program.
Run locally with npx
Want to try it on your machine first? The hub is published to npm — no clone, no build:
npx @kbncodes/mcp-server-hub --dev
--dev (or any interactive terminal) auto-generates an ephemeral AUTH_TOKEN, prints it, and serves the dashboard at http://localhost:8080/. For a stable token, set it yourself:
AUTH_TOKEN=$(openssl rand -hex 32) npx @kbncodes/mcp-server-hub
The published binary stays production-safe: in a non-interactive environment (containers, CI) it still fails closed and refuses to start without
AUTH_TOKENunless you setALLOW_NO_AUTH=true.
Deploy on Render
This repo ships a render.yaml blueprint, so Render provisions everything (Docker build, /health check, auto-generated AUTH_TOKEN) in one click:
After the first deploy, set PUBLIC_URL to your Render URL (e.g. https://mcp-server-hub.onrender.com) so the auth challenge and RFC 9728 metadata advertise the correct address. To persist memory, add a Render disk mounted at /data and set MEMORY_FILE=/data/memory.json (see the commented block in render.yaml).
Deploy on Manufact Cloud
Manufact is an MCP-native host that can also distribute your server to the ChatGPT Apps Store, Claude Connectors, and Gemini. Because this hub uses the official @modelcontextprotocol/sdk, you can deploy it as-is:
- Push this repo to GitHub and connect it in Manufact Cloud (every push auto-deploys), or use the CLI:
npm install -g @mcp-use/cli mcp-use login mcp-use deploy - Set
AUTH_TOKEN(plus any optionalGITHUB_TOKEN/DATABASE_URL) in the Manufact environment settings. - Set
PUBLIC_URLto the assigned Manufact URL.
Note: Manufact is usage-based hosting that you pay for — it does not offer template revenue sharing. Use it for reach (ChatGPT/Claude/Gemini distribution); use Railway's 25% Template Kickback for earnings.
Connect a client
Any MCP client that speaks Streamable HTTP works. Point it at a server endpoint and pass your token:
{
"mcpServers": {
"hub-fetch": {
"url": "https://YOUR-APP.up.railway.app/mcp/fetch",
"headers": { "Authorization": "Bearer YOUR_AUTH_TOKEN" }
},
"hub-memory": {
"url": "https://YOUR-APP.up.railway.app/mcp/memory",
"headers": { "Authorization": "Bearer YOUR_AUTH_TOKEN" }
}
}
}
Quick smoke test with curl:
curl -X POST https://YOUR-APP.up.railway.app/mcp/utils \
-H "Authorization: Bearer YOUR_AUTH_TOKEN" \
-H "Content-Type: application/json" \
-H "Accept: application/json, text/event-stream" \
-d '{"jsonrpc":"2.0","id":1,"method":"tools/list","params":{}}'
Configuration
| Variable | Required | Default | Description |
|---|---|---|---|
AUTH_TOKEN |
Yes | — | Bearer token for /mcp/* and /api/*. Auto-generated by the Railway template. |
ENABLED_SERVERS |
No | all |
Comma-separated server ids (utils,fetch,memory,github,postgres) or all. |
GITHUB_TOKEN |
No | — | GitHub PAT; activates the github server. |
DATABASE_URL |
No | — | Postgres connection string; activates the postgres server (read-only). |
MEMORY_FILE |
No | — | File path (on a volume) to persist the memory server, e.g. /data/memory.json. |
FETCH_MAX_BYTES |
No | 1000000 |
Max bytes fetched per request by the fetch server. |
STRICT_HEADER_VALIDATION |
No | false |
Reject Mcp-Method header/body mismatches (2026-07-28 behavior) instead of warning. |
RATE_LIMIT_RPM |
No | 120 |
Requests per minute per IP on /mcp/* and /api/*; 429 beyond. |
MAX_BODY_BYTES |
No | 1000000 |
Max JSON request body size in bytes. |
ALLOW_NO_AUTH |
No | false |
Explicit opt-in to run without authentication (the hub refuses to start otherwise when AUTH_TOKEN is unset). |
PUBLIC_URL |
No | — | Canonical scheme://host used in auth challenges and RFC 9728 metadata. |
AUDIT_LOG |
No | false |
Log one structured JSON line per MCP request (ip, server, method, tool, status). |
FETCH_ALLOW_HOSTS |
No | — | Comma-separated hostname allowlist for the fetch server. |
PORT |
No | 8080 |
Listen port (Railway injects this). |
Spec compliance & the 2026-07-28 revision
This hub is stateless by design, which is exactly the model the 2026-07-28 MCP revision standardizes:
- No sessions — no
Mcp-Session-Id, no sticky routing; a fresh MCP server instance handles each request (sessionIdGenerator: undefined). Scale replicas freely. MCP-Protocol-Versionvalidation — unsupported versions get a clean400(per spec since 2025-03-26). Accepted:2024-11-05→2026-07-28.Mcp-Methodheader awareness (SEP-2243) — mismatches between the new routing header and the JSON-RPC body are logged, or rejected withSTRICT_HEADER_VALIDATION=true.- Authorization done right —
Authorization: Bearerverified with a timing-safe compare; failures return401with aWWW-Authenticatechallenge pointing at RFC 9728 resource metadata. - No deprecated surfaces — no HTTP+SSE legacy transport, no Roots/Sampling/Logging reliance (deprecated in the new revision).
When the v2 SDK (@modelcontextprotocol/server 2.x) goes stable alongside the final spec, migration is isolated to src/index.ts (transport) and the per-server factories — the stateless architecture carries over unchanged.
Local development
cp .env.example .env # set AUTH_TOKEN
npm install
npm run dev # hot-reload dev server
npm run build && npm start
Releasing
Publishing to npm is fully automated via GitHub Actions OIDC trusted publishing — no tokens, secrets, 2FA prompts or passkeys required. The workflow authenticates to npm using GitHub's OIDC identity and attaches build provenance.
To cut a release:
npm version patch # or: minor / major — bumps package.json + creates a git tag
git push --follow-tags
Then, on GitHub, Releases → Draft a new release, pick the tag you just pushed, and Publish release. That fires the Publish to npm workflow, which builds and publishes the new version automatically. (You can also trigger it manually from the Actions tab via Run workflow.)
One-time setup: the package must have this repo registered as a Trusted Publisher on npm (package Settings → Trusted Publisher → GitHub Actions, workflow file
publish.yml).
Architecture
src/
index.ts Express gateway: auth, protocol validation, stateless MCP handling
config.ts Env configuration + supported protocol versions
registry.ts Server catalog (id → factory); fresh McpServer per request
admin.ts Self-contained dashboard (no build step)
servers/
utils.ts Time/UUID/hash/base64/calculator (safe expression parser)
fetch.ts Bounded web fetch with SSRF guards + HTML cleanup
memory.ts Shared notes store, optional volume persistence
github.ts Read-only GitHub REST tools
postgres.ts READ ONLY transaction SQL tools
Security posture:
- Authentication — mandatory Bearer token (fail-closed: the hub refuses to start without
AUTH_TOKENunlessALLOW_NO_AUTH=true), timing-safe comparison, brute-force lockout (10 failed attempts/min per IP → 429). - Rate limiting — per-IP limits on
/mcp/*and/api/*(RATE_LIMIT_RPM), standardRateLimitheaders. - SSRF defense — the fetch server resolves every hostname via DNS and blocks all private/reserved ranges (IPv4 + IPv6, incl. cloud metadata
169.254.169.254); redirects are followed manually with every hop re-validated; embedded credentials rejected; optionalFETCH_ALLOW_HOSTSallowlist. - SQL isolation — Postgres queries run single-statement over the extended query protocol inside
READ ONLYtransactions with statement + idle timeouts; multi-statement strings (e.g.COMMIT; DROP …) are rejected by the database itself. - No code execution — hand-written arithmetic parser, no
eval/codegen anywhere. - Hardened HTTP surface — helmet security headers, strict CSP with per-request nonces on the dashboard,
X-Frame-Options: DENY,Cache-Control: no-storeon token-bearing routes, sanitized JSON-RPC error responses (no stack traces or paths), body-size limits, slowloris timeouts. - Input validation — zod schemas with length caps on every tool input; server ids, GitHub owner/repo names and file paths validated against strict patterns; memory store capped (1000 entries / 10 MB) with atomic persistence.
- Least privilege — runs as non-root
nodeuser in Docker; secrets only via environment variables; API error messages scrubbed of tokens. - Auditability — optional structured request log (
AUDIT_LOG=true).
See SECURITY.md for the vulnerability reporting policy.
Adding your own server
- Create
src/servers/myserver.tsexportingcreateMyServer(config): McpServerand register tools withserver.registerTool(...). - Add an entry to
src/registry.tswith an id, description, tool list and factory. - Redeploy — it appears in the dashboard and at
/mcp/myserver.
License
MIT
推荐服务器
Baidu Map
百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。
Playwright MCP Server
一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。
Magic Component Platform (MCP)
一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。
Audiense Insights MCP Server
通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。
VeyraX
一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。
graphlit-mcp-server
模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。
Kagi MCP Server
一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。
e2b-mcp-server
使用 MCP 通过 e2b 运行代码。
Neon MCP Server
用于与 Neon 管理 API 和数据库交互的 MCP 服务器
Exa MCP Server
模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。