Из чего состоит MCP-сервер#
Внутри у сервера всего три вида умений, и для первого своего сервера хватит одного из трёх:
| Умение | Как устроено | Как это выглядит на практике |
|---|---|---|
| Инструмент (tool) | Функция, которую вызывает сама модель, когда решит, что она нужна | «Сохрани заметку», «отправь письмо», «посчитай сумму» |
| Ресурс (resource) | Данные, которые Claude может прочитать напрямую, как файл | Содержимое конфига, список последних заметок |
| Промпт (prompt) | Готовый шаблон запроса, который предлагается вам | «Составь отчёт по этим данным» одной командой |
Инструменты — это то, ради чего обычно и пишут свой сервер. У вас есть своя задача: например, свой файл на диске, своя база данных, свой внутренний сервис компании. У Claude Code доступа к этому нет, а у обычного кода на Python есть: он умеет открывать файлы, читать и записывать в них, отправлять запросы в базу или в сервис, как и любая другая программа. Вы пишете такой код и через @mcp.tool() объявляете его инструментом: после этого Claude может вызвать его сам, когда решит, что он нужен. Дальше в статье соберём сервер с двумя инструментами: этого достаточно, чтобы понять принцип и расширять его самостоятельно.
Что понадобится и как всё установить#
Писать будем на Python и официальном SDK (это готовый набор кода, который Anthropic выпустила именно под такую задачу): пакет называется mcp, ставится через менеджер uv. Актуальные на 14 августа 2026 требования из официального гайда по сборке сервера (полная ссылка в источниках): Python 3.10 или новее и версия SDK не ниже 2.0.0.
Все команды ниже выполняются в обычном терминале: подойдёт и системный (Terminal на macOS, PowerShell на Windows), и встроенный терминал VS Code (Вид → Терминал) — это то же самое окно, просто внутри редактора. Через чат Claude Code эти команды тоже можно попросить выполнить за вас, но дальше в статье мы печатаем их сами: так видно, что происходит на каждом шаге.
- Поставьте
uv— менеджер пакетов и окружений для Python: на macOS и Linux командойcurl -LsSf https://astral.sh/uv/install.sh | sh, на Windows командойirm https://astral.sh/uv/install.ps1 | iexв PowerShell. После установки перезапустите терминал. - Создайте папку проекта:
uv init notes-server && cd notes-server && uv add 'mcp[cli]'. Эта команда сама создаёт папкуnotes-serverв том месте, где вы сейчас находитесь в терминале — если запускали её из папки «Документы», там она и появится. - Создайте пустой файл для кода сервера: на macOS и Linux командой
touch server.py, на Windows —ni server.pyв PowerShell. Файл появится внутри той же папкиnotes-server.
Команда uv add 'mcp[cli]' ставит не только сам SDK, но и утилиту mcp с флагом dev — она понадобится, чтобы проверить сервер до подключения к Claude.
Пишем первый инструмент#
Соберём сервер заметок: Claude сможет сохранять текстовые заметки в обычный файл на вашем диске и потом показывать их вам по запросу. Это не встроенная память Claude — просто текстовый файл у вас на компьютере, который вы в любой момент можете открыть и посмотреть сами.
Откройте VS Code (или любой другой редактор кода). В меню нажмите «Файл → Открыть папку» и выберите папку notes-server — ту самую, которую вы только что создали в терминале и куда положили пустой server.py. Слева появится список файлов: кликните по server.py, он откроется в редакторе, и можно писать код.
1from mcp.server import MCPServer2 3mcp = MCPServer("notes")4 5NOTES_FILE = "notes.txt"6 7 8@mcp.tool()9def add_note(text: str) -> str:10 """Save a new note to the notes file.11 12 Args:13 text: The text of the note to save14 """15 with open(NOTES_FILE, "a", encoding="utf-8") as f:16 f.write(text + "\n")17 return f"Заметка сохранена: {text}"
Декоратор @mcp.tool() над функцией превращает обычную функцию в инструмент для Claude. Вот как: он смотрит на имя функции (add_note), на её аргумент (text: str, то есть аргумент называется text и в нём лежит текст) и на строку в тройных кавычках под def — это и есть докстрока, короткое описание того, что функция делает. Из этих трёх вещей декоратор сам собирает всё, что нужно объяснить Claude: вам не нужно ничего писать отдельно.
Докстрока в примере написана по-английски специально: её читает не только человек, но и сама модель, и по-английски она понимает эту строку так же хорошо, как по-русски.
Добавляем второй инструмент и проверяем сервер#
Один инструмент только пишет — добавим второй, который читает, и запустим файл целиком:
1@mcp.tool()2def list_notes() -> str:3 """Return all notes saved so far."""4 try:5 with open(NOTES_FILE, encoding="utf-8") as f:6 notes = f.read().strip()7 except FileNotFoundError:8 return "Заметок пока нет."9 return notes or "Заметок пока нет."10 11 12if __name__ == "__main__":13 mcp.run(transport="stdio")
Последние две строки — точка входа: transport='stdio' включает режим, в котором сервер и Claude Code обмениваются сообщениями через тот же терминал, где сервер запущен. Это и называется локальным транспортом.
Прежде чем звать Claude, проверьте сервер сами: пакет mcp[cli], который вы уже поставили, приносит с собой MCP Inspector — можно вызвать оба инструмента прямо в браузере, ещё до подключения к Claude:
- Запустите
uv run mcp dev server.pyиз папки проекта. - Дождитесь, пока в терминале появится адрес, и откройте его в браузере — это и есть Inspector.
- Найдите инструмент
add_note, впишите в полеtextлюбую строку и нажмите вызов — рядом появится ответ сервера. - Вызовите
list_notesбез аргументов и убедитесь, что заметка вернулась обратно.
Если оба инструмента отвечают в Inspector — сервер рабочий, и ошибка на следующем шаге будет уже не в коде, а в подключении.
Подключаем сервер к Claude Code#
Локальный сервер добавляется той же командой, что и любой другой stdio-сервер: claude mcp add. Отличие только в том, что вместо готовой программы вы указываете запуск через uv:
1claude mcp add notes -- uv --directory /path/to/notes-server run server.py
Путь после --directory — не сокращённый вроде ./notes-server, а полный, от корня диска. Узнать его можно командой pwd, стоя внутри папки notes-server: она распечатает путь целиком. Двойной дефис перед uv обязателен: без него Claude Code попытается разобрать --directory как одну из своих собственных настроек, а не передать её серверу. Подробно про эту границу и про то, чем локальный транспорт отличается от удалённого, я писала в статье про MCP в Claude Code.
Проверьте, что сервер подключился:
1claude mcp list
Рядом с именем notes должно появиться ✔ Connected. Дальше — обычный диалог, без специальных команд:
- Запустите
claudeи напишите: «Сохрани заметку: купить молоко». - Разрешите вызов инструмента, когда Claude спросит, — в первый раз он спрашивает про каждый новый сервер.
- Напишите: «Покажи мои заметки» — и Claude вызовет
list_notesсам, без напоминания, каким инструментом это делается.
Что дальше: расширяем сервер#
Два инструмента на чтение и запись — это шаблон, который переносится на любую свою задачу: вместо текстового файла может быть ваша база данных, внутренний API компании или чужой сервис без готового MCP-сервера под него. Меняется только код внутри функции, декоратор и вызов через Claude Code остаются те же.
Если задача разрастается настолько, что одной функции мало и нужно несколько шагов подряд с решениями по ходу дела, это уже не про MCP-сервер, а про агента, который его вызывает: как устроен такой цикл и из чего он состоит, я показывала на примере Claude API в отдельной статье.
Готовый сервер можно оставить только для себя, а можно показать другим: выложить код на GitHub или, если он достаточно общий и полезен не только вам, предложить в каталог Anthropic — тогда его смогут подключить командой claude mcp add те же люди, что подключают готовые серверы. SDK для этого пути на Python есть такие же официальные, как для TypeScript, Java, Kotlin, C# и Ruby: все они опубликованы в организации modelcontextprotocol на GitHub.
Частые вопросы#
Обязательно ли хорошо знать Python, чтобы написать MCP-сервер?
@mcp.tool() берёт на себя всё, что связано с самим протоколом, вам остаётся обычная логика внутри функции. Асинхронный код в SDK тоже поддержан, но для первого сервера он не нужен: обычная функция работает так же.Можно ли написать MCP-сервер не на Python?
modelcontextprotocol на GitHub, там же лежат примеры серверов на каждом языке для сравнения.Чем свой сервер отличается от готовых, которые просто подключаются командой?
Опасно ли давать Claude инструмент с доступом к файлам?
- Model Context Protocol — официальный гайд по сборке первого сервера, требования и код примера
- Model Context Protocol — README Python SDK, установка, класс MCPServer, версия 2.0.0
- PyPI — страница пакета mcp, актуальная версия и дата релиза
- Anthropic — полный справочник по MCP в Claude Code: команды, транспорты, scope
- Model Context Protocol — три типа возможностей сервера: ресурсы, инструменты, промпты
Больше цифр и разборов — в Telegram-канале
Черновики, промежуточные результаты и то, что не дошло до блога