# Как собрать свой MCP-сервер 2026: FastMCP + Claude Code за один файл

Готовые MCP-серверы закрывают почти всё — GitHub, Postgres, Sentry, файловая система. Но рано или поздно упираешься в задачу, которой нет в каталоге: дёрнуть внутренний API компании, посчитать что-то по вашей бизнес-логике, прочитать данные из системы, о которой знаете только вы. Это те самые 10%, ради которых и пишут свой сервер.

Хорошая новость: свой MCP-сервер — это не проект на неделю. На библиотеке FastMCP рабочий сервер помещается в один Python-файл: функция, декоратор, одна строка запуска. Дальше показываю весь путь — от пустого файла до инструмента, который Claude Code вызывает сам. Если только осваиваете Claude Code, держите под рукой [обзор, что это за инструмент](/claude-code/).

## Зачем вообще свой сервер, если есть готовые

MCP (Model Context Protocol) — это стандартный «разъём», через который агент получает инструменты: не текстовые подсказки, а реальные функции, которые он вызывает и получает результат. Если вы ещё не подбирали готовые серверы под свои задачи, начните с обзора [15 MCP-серверов для Claude Code](/guides/mcp-servers-claude-code/) — часто своё писать и не нужно.

Свой сервер оправдан, когда:

- **инструмента нет в каталоге** — внутренний сервис, закрытый API, ваша база с нестандартной схемой;
- **нужна ваша логика** — не «сходи в API», а «посчитай маржу по нашим правилам и верни число»;
- **вы отлаживаете свою систему** — MCP-сервер как обёртка над вашими скриптами: агент видит функции `run_migration`, `check_health`, `read_logs` и оперирует ими напрямую, а не через `bash`.

Последний пункт — частый мотив запроса «mcp для дебага»: вместо того чтобы агент вслепую дёргал команды в терминале, вы даёте ему набор именованных функций с понятными аргументами. Меньше ошибок, больше контроля.

## Что понадобится

- Claude Code (тариф Pro или Max).
- Python 3.10 или новее — FastMCP требует минимум 3.10.
- Умение написать функцию с типами аргументов (`def f(a: int) -> str`). Типы — не косметика: из них FastMCP строит схему инструмента, которую видит агент.

## Шаг 1: Установите FastMCP

FastMCP — самостоятельная библиотека (репозиторий `github.com/PrefectHQ/fastmcp`, автор Jeremiah Lowin). Ставится одной командой:

```bash
pip install fastmcp
```

Документация рекомендует `uv` — он быстрее и изолирует зависимости:

```bash
uv add fastmcp
```

Проверьте, что установилось:

```bash
python -c "import fastmcp; print(fastmcp.__version__)"
```

На момент написания актуальная версия — 3.x. Если команда напечатала номер без ошибок — библиотека на месте.

## Шаг 2: Напишите минимальный сервер

Создайте файл `server.py`. Вот полный рабочий сервер с одним инструментом:

```python
from fastmcp import FastMCP

mcp = FastMCP("My First Server")


@mcp.tool
def greet(name: str) -> str:
    """Поздороваться с человеком по имени."""
    return f"Привет, {name}!"


if __name__ == "__main__":
    mcp.run()
```

Что здесь происходит:

- `FastMCP("My First Server")` — создаёт сервер. Строка внутри — его человекочитаемое имя.
- `@mcp.tool` — регистрирует функцию `greet` как инструмент. Имя инструмента FastMCP берёт из имени функции, описание — из докстринга, схему аргументов — из аннотаций типов (`name: str`). Поэтому докстринг и типы обязательны: по ним агент понимает, что и как вызывать.
- `mcp.run()` — запускает сервер. Без аргументов транспорт по умолчанию — **stdio** (общение через стандартный ввод/вывод). Именно его ждёт Claude Code от локального сервера.

Декоратор пишется **без скобок** — `@mcp.tool`. Скобки нужны только когда переопределяете имя или описание вручную:

```python
@mcp.tool(name="say_hello", description="Приветствие на русском")
def greet(name: str) -> str:
    return f"Привет, {name}!"
```

## Шаг 3: Запустите и проверьте сервер локально

Перед подключением к Claude Code убедитесь, что сервер вообще стартует:

```bash
python server.py
```

Процесс запустится и будет ждать ввода по stdio — это нормально, он «висит» молча. Остановите его через Ctrl+C. Если Python не выдал traceback — сервер рабочий.

Есть и второй способ запуска, без блока `if __name__`: CLI-команда самой библиотеки. Она сама находит в файле инстанс с именем `mcp`, `server` или `app`:

```bash
fastmcp run server.py
```

Для подключения к Claude Code достаточно любого из вариантов — оба поднимают stdio-сервер.

## Шаг 4: Подключите сервер к Claude Code

Claude Code добавляет локальный stdio-сервер командой `claude mcp add`. Синтаксис: сначала опции Claude, потом `--`, потом команда запуска вашего сервера. Всё после `--` уходит серверу как есть.

```bash
claude mcp add my-server -- python /абсолютный/путь/server.py
```

Разберём флаги, которые пригодятся:

- **`--scope`** — где хранить конфиг. `local` (по умолчанию, только у вас), `user` (для всех ваших проектов), `project` (кладётся в `.mcp.json` в корне проекта и коммитится в git — для команды).
- **`--env KEY=value`** — переменные окружения серверу (например, ключ API). Важная деталь из доков: между `--env` и именем сервера должна стоять ещё одна опция, иначе CLI примет имя за очередную пару.

Пример с переменной окружения и project-областью:

```bash
claude mcp add --env API_TOKEN=xxx --scope project my-server -- python /путь/server.py
```

Если предпочитаете конфиг руками — тот же сервер в `.mcp.json` в корне проекта:

```json
{
  "mcpServers": {
    "my-server": {
      "command": "python",
      "args": ["/абсолютный/путь/server.py"],
      "env": {}
    }
  }
}
```

Project-серверы из `.mcp.json` Claude Code спрашивает подтвердить при первом запуске — это защита от чужих команд в чекнутом репозитории.

Полезная деталь для переносимых конфигов: Claude Code кладёт в окружение сервера переменную `CLAUDE_PROJECT_DIR` с корнем проекта. Внутри Python-сервера её читаете как `os.environ["CLAUDE_PROJECT_DIR"]` — и не привязываетесь к рабочей директории.

## Шаг 5: Убедитесь, что инструмент виден агенту

Проверьте, что сервер зарегистрирован:

```bash
claude mcp list
```

Ваш `my-server` должен быть в списке. Детали по одному серверу:

```bash
claude mcp get my-server
```

Теперь запустите Claude Code и внутри сессии откройте панель:

```
/mcp
```

Там виден статус подключения и список инструментов сервера. Если `greet` на месте — попросите агента: «поздоровайся с Даши через инструмент greet». Он вызовет функцию и вернёт `Привет, Даши!`. С этого момента ваша логика — часть арсенала агента.

## Типичные грабли

- **Относительный путь к серверу.** `claude mcp add ... -- python server.py` сработает только из той же папки. Всегда указывайте абсолютный путь — сервер запускается не там, где вы ожидаете.
- **Забыли `--` перед командой.** Без двойного дефиса CLI попытается разобрать `python server.py` как свои опции. Разделитель обязателен для stdio.
- **Нет типов или докстринга у tool-функции.** Без аннотаций FastMCP не построит схему аргументов, без докстринга агент не поймёт назначение инструмента. И то и другое — не стиль, а контракт.
- **Сервер печатает в stdout.** Транспорт stdio использует стандартный вывод для протокола. Любой ваш `print()` в сервере ломает обмен сообщениями — для отладки пишите в `stderr` (`print(..., file=sys.stderr)`) или в лог-файл.
- **Python не тот.** Если `python` в системе указывает на 3.9 или старше, сервер не поднимется. Проверьте `python --version` и при необходимости укажите в команде `python3.12`.

## FAQ

### Что такое MCP-сервер простыми словами?
Это программа, которая даёт AI-агенту набор функций-инструментов по стандартному протоколу. Агент не пишет код и не гадает — он видит список именованных функций с описанием и аргументами, вызывает нужную и получает результат. MCP-сервер — «переходник» между агентом и вашей системой: API, базой, скриптами.

### Нужно ли знать протокол MCP, чтобы написать сервер?
Нет. В этом и смысл FastMCP: она берёт на себя весь протокол (регистрацию инструментов, схемы, обмен сообщениями по stdio). Вы пишете обычную Python-функцию, вешаете декоратор `@mcp.tool` — библиотека сама превращает её в валидный MCP-инструмент. Знать спецификацию MCP не требуется.

### На каком языке писать MCP-сервер?
MCP-серверы бывают на разных языках (есть SDK для TypeScript, Python и других), но для быстрого старта на Python FastMCP — самый короткий путь: рабочий сервер в один файл. Если ваша логика уже на Python, оборачивать её в MCP логичнее всего тоже на Python.

### Можно ли сделать MCP-сервер для дебага своего проекта?
Да, и это популярный сценарий. Оборачиваете свои операции — прогон миграций, чтение логов, health-check — в tool-функции. Агент получает их как именованные инструменты и оперирует ими осознанно, а не дёргает команды в терминале вслепую. Меньше ошибок, чётче контроль над тем, что агенту разрешено.

### Чем свой сервер лучше готового?
Ничем, если готовый закрывает задачу — тогда пишите свой только зря. Свой оправдан, когда инструмента нет в каталоге, либо нужна именно ваша бизнес-логика (не «сходи в API», а «посчитай по нашим правилам»), либо вы даёте агенту доступ к закрытой внутренней системе. Сначала проверьте каталог готовых, потом пишите своё.

## Дальше — не в одиночку

Первый свой сервер вы поднимете за вечер. Дальше начинаются вопросы, которых нет в документации: какие функции стоит отдавать агенту, а какие опасно; как не дать ему сломать прод через ваш же инструмент; как выстроить набор серверов под реальный рабочий процесс, а не один демо-`greet`. Это уже не про синтаксис — про архитектуру работы с агентами.

В сообществе EdgeLab это ровно то, что разбираем на практике: участники приносят свои задачи — от внутреннего API до дебаг-обёрток — и собирают серверы под них вместе, а не по чужим туториалам. Если хотите пройти путь от «работает у меня в файле» до «агент делает это в моём проекте каждый день» с обратной связью, а не в одиночку упираться в грабли — заходите. Свой первый сервер вы уже умеете написать; дальше интереснее.
