Skip to main content
Glama
BEST_PRACTICES_EN.mdβ€’6.09 kB
# BEST_PRACTICES.md > πŸ›  **Objective**: Production-oriented FastMCP (SDK v1.10.1) server best practices. Clarify project structure, deployment recommendations, and bypass capabilities all at once to avoid the embarrassment of "runs but hard to maintain". ------ ## 1 Β· Transport Layer Selection | Scenario | Recommended Transport | Description | | ----------------------- | -------------------------- | ----------------------------------------------- | | Local CLI / IDE Debug | **stdio** | No ports, shortest path | | Web / Multi-client | **Streamable HTTP** | Best compatibility with LB / auth middleware; supports HTTP2 / H2C | | Long connection push | Streamable HTTP + built-in SSE | Auto-upgrade on same path, no additional /sse endpoint needed | ⚠️ Public deployments must implement Host validation or bind to `127.0.0.1` at gateway to prevent DNS rebinding attacks. ------ ## 2 Β· Directory Structure (Production Template) ```text mcp-server/ β”œβ”€β”€ server/ # Core Python package (import server) β”‚ β”œβ”€β”€ __init__.py β”‚ β”œβ”€β”€ main.py # FastMCP instance & app entry β”‚ β”œβ”€β”€ config.py # Pydantic Settings / env parsing β”‚ β”œβ”€β”€ resources/ # All @mcp.resource β”‚ β”‚ β”œβ”€β”€ __init__.py β”‚ β”‚ └── greeting.py β”‚ β”œβ”€β”€ tools/ # All @mcp.tool β”‚ β”‚ β”œβ”€β”€ __init__.py β”‚ β”‚ └── math.py β”‚ β”œβ”€β”€ prompts/ # All @mcp.prompt β”‚ β”‚ β”œβ”€β”€ __init__.py β”‚ β”‚ └── echo.py β”‚ β”œβ”€β”€ routes/ # Bypass REST API β”‚ β”‚ β”œβ”€β”€ __init__.py β”‚ β”‚ β”œβ”€β”€ health.py β”‚ β”‚ └── convert.py β”‚ └── static/ # Static resources directory (mounted by StaticFiles) β”œβ”€β”€ tests/ # pytest & httpx β”‚ β”œβ”€β”€ __init__.py β”‚ β”œβ”€β”€ conftest.py β”‚ β”œβ”€β”€ unit/ # Pure function unit tests β”‚ └── integration/ # End-to-end Streamable HTTP calls β”œβ”€β”€ scripts/ # Local ops scripts β”‚ β”œβ”€β”€ start.sh # Unified entry (uvicorn / gunicorn) β”‚ └── migrate.sh # DB / KV migration example β”œβ”€β”€ configs/ # Config & secret templates (not in Git) β”‚ β”œβ”€β”€ logging.yml # Structured logging config β”‚ └── .env.example # Environment variable example (.env ➜ docker-compose) β”œβ”€β”€ deploy/ # Unified deployment directory β”‚ β”œβ”€β”€ docker/ # Containerization β”‚ β”‚ β”œβ”€β”€ Dockerfile β”‚ β”‚ └── entrypoint.sh β”‚ β”œβ”€β”€ kubernetes/ # K8s / Helm Chart β”‚ β”‚ β”œβ”€β”€ deployment.yaml β”‚ β”‚ └── service.yaml β”‚ └── ci/ # CI/CD (GitHub Actions / GitLab CI) β”‚ └── github/ β”‚ └── workflows/ β”‚ └── ci.yml β”œβ”€β”€ pyproject.toml # Poetry / PEP 621; lock mcp==1.10.1 β”œβ”€β”€ README.md # Project overview & quick start └── docs/ # Development / ops documentation β”œβ”€β”€ QUICKSTART.md β”œβ”€β”€ BEST_PRACTICES.md └── API_REFERENCE.md ``` ### Directory Key Points | Directory | Purpose / Highlights | | ------------------- | ------------------------------------------------------------ | | **server/** | Code as protocol, layered by resources / tools / prompts; `config.py` unified loading of `os.environ`, avoiding scattered `os.getenv()` | | **routes/** | Only bypass HTTP; keep MCP core clean. | | **tests/** | Unit tests cover pure functions; integration tests directly connect `/mcp` Streamable HTTP, ensuring tools & resources are callable under real protocol. | | **deploy/** | Unified deployment directory containing all deployment configs including containerization, K8s, CI/CD. | | **deploy/docker/** | Independent of source code, any container changes don't pollute server package; `entrypoint.sh` reads `/configs/.env` ➜ generates final config. | | **deploy/kubernetes/** | Decoupled from CI, avoiding Helm over-coupling early projects; add Helm Chart in production. | | **docs/** | Separate **running (QUICKSTART)**, **development (BEST_PRACTICES)**, **interface (API_REFERENCE)** for targeted reading by newcomers. | > βœ… **Practice Rule**: All variable content unrelated to business logic (config / logs / secrets) should always be placed in `configs/` or external volumes. ------ ## 3 Β· Bypass Capabilities | Need | Approach | | --------------- | ------------------------------------------------------------ | | Health Check | `GET /health`: Return 200 & build sha | | RESTful API | `POST /api/v1/xxx`: Other RESTful API entries | | Static Files | `StaticFiles(directory=server.static)` ➜ `/static` | | Sub-microservice | `from fastapi import APIRouter`; mount `router` to `app.mount("/sub", sub_app)` | > **Naming Suggestion**: Unified bypass routes in `routes/`, filename consistent with HTTP path, search cost = 0. ------ ## 4 Β· Deployment Tips 1. **Process Model**: Uvicorn Worker β‰₯ *4* (`--worker-class=uvicorn.workers.UvicornWorker`); IO-intensive suggests 2 Γ— CPU Core. 2. **Logging**: Unified structured JSON ➜ ELK / Loki; no `print()`. 3. **Version Locking**: `mcp==1.10.1`, `fastapi~=0.115.14`; regression test in staging before upgrade. 4. **Security**: - Streamable HTTP endpoint at `/mcp`, other custom APIs don't share cookies; - Public only expose 443 TLS, internal `ClusterIP` communication via H2C. 5. **Monitoring**: Prometheus + OpenTelemetry Exporter; key metrics: `tool_invocation_total`, `tool_latency_seconds`, `resource_hit_total`.

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/WW-AI-Lab/Awesome-MCP-Scaffold'

If you have feedback or need assistance with the MCP directory API, please join our Discord server