
Общая информация
В конце 2024г компания Anthropic, создатель LLM-моделей Claude, опубликовала стандарт Model Context Protocol и выпустила статью, посвящённую видению Anthropic того, как строить эффективные системы с AI-агентами: Building effective agents (хорошая вводная статья по паттернам агентских систем).
Прошло всего 3 месяца, и к этому моменту поддержка MCP уже появилась почти во всех AI- вайб-IDE, во многих LLM-интерфейсах, были выпущены тысячи MCP-серверов от компаний и сообщества.
Самое время написать о том, что это такое
Итак, что такое MCP (Model Context Protocol)?
Это открытый протокол от Anthropic, стандартизирующий взаимодействие между LLM и внешними системами и через это упрощающий построение агентских систем.
Какие это внешние системы могут быть?
Любые, с которыми можно либо обмениваться данными, либо вызывать у них какие-то функции:
● базы данных, вики, поисковики, RAG-системы
● таск-трекеры, мессенджеры, репозитории, почта
● файловая система, сервера, контейнеры
● reddit, youtube, прочие соцсети
● умные лампочки дома, кофеварка, кондиционер, кот
Словом, что угодно, что выставляет наружу хоть какой-то интерфейс, с которым можно программно взаимодействовать.
Какие проблемы решает MCP?
● делает универсальной интеграцию внешних систем с LLM — и это, пожалуй, самое важное, что позволило распространиться этому протоколу с такой скоростью
● обеспечивает доступ LLM к тем системам, которые могут быть чисто внутренними, даже не имеющим доступ в Интернет
● позволяет модели оставаться в пределах единого контекста при решении многоэтапной задачи
Конкретные примеры
● находясь в чате Cursor, к примеру, можно получать сведения о фиче не только из кода, но и через поиск в Confluence/Jira, что позволяет модели лучше понять проект и задачу
● можно просить LLM поискать в интернете вылезшую ошибку, её решения и сразу применить фикс в коде
● на основе MCP можно собирать чаты поддержки, которые будут иметь доступ ко всем внутренним системам и смогут консультировать сотрудников или клиентов. К ним же можно прикрутить и вызовы внешних инструментов, таких как Notion, Slack, CRM
● имея подключенную к чату БД, можно на человеческом языке просить выбрать из неё какие-то данные — LLM сама составит SQL-запрос и выполнит его, а потом ещё и уточняющие вопросы можно позадавать
● у меня были захватывающие сессии дебага в Cursor с подключенными MCP, где модель правила код, выполняла его, сверялась с тем, что лежит в БД/Redis, снова правила код и т.д., пытаясь решить проблему
Какие компоненты нужны для работы с MCP?
Помимо внешней системы и LLM:
MCP-хост — программа, в функционал которой входит решение пользовательских задач при помощи LLM и внешней системы — Cursor / Claude Desktop / LibreChat / etc.
Как правило, это та программа, с которой непосредственно общается пользователь в режиме чата
MCP-клиент — программный клиент протокола MCP для связи хоста и сервера, является частью хоста.
Вот тут есть список примеров хостов-клиентов и тех фич протокола, которые они поддерживают: https://modelcontextprotocol.io/clients
MCP-сервер — легковесная программа, выступающая в роли прокси/гейтвея, которая общается с внешней системой, используя её API. Сам же сервер наружу выставляет MCP-специфичный интерфейс, с которым взаимодействует хост.
Тут можно посмотреть на примеры серверов: https://modelcontextprotocol.io/examples
Что входит в интерфейс MCP-сервера?
Из существенного, что экспортирует сервер:
Tools, инструменты — по сути, описания функций, которые могут быть вызваны клиентами, когда их о том попросит LLM.
Cписок инструментов передается LLM, и она сама решает, какой из них и когда вызвать для решения поставленной ей задачи
Resources, ресурсы — описания и сами наборы данных, которые сервер может предоставить клиентам для чтения и включения в контекст для LLM.
К примеру, в случае БД это могут быть схемы таблиц, для файлового хранилища — списки файлов и/или содержимое самих файлов.
Предполагается, что ресурсы должны быть явно выбраны пользователем или клиентом для передачи модели, но не запрещается переложить выбор и на саму модель
Prompts, промпты — заготовки промптов, которые пользователь может выбрать в хост-программе. Промпты могут быть параметризованными и принимать какие-то динамические значения от пользователя или окружения
Какие LLM можно использовать?
Заявляется, что протокол открытый и его можно использовать с любыми LLM, где есть Structured Outputs / Function Calling.
Тут Anthropic, конечно, слегка лукавит, т.к. у них есть преимущество в том плане, что они выпускают лучшие в настоящее время агентские модели, и они вполне могли тюнить тот же Sonnet на работу именно с чем-то MCP-подобным.
Так что пока что для лучших результатов стоит выбирать именно модели Anthropic.
MCP-сервер

Что из себя представляет MCP-сервер?
Как правило — это небольшая программа на любом языке программирования (чаще всего — Python или TypeScript), которая никакой логики в себе не содержит, и просто связывает внешнюю систему и MCP-клиент между собой.
Аутентификация
Довольно часто для доступа к внешней системе MCP-сервер содержит в себе процедуры аутентификации — т.е. именно ему нужно передавать все логины/пароли/токены, и он решает проблему с доступом LLM к каким-то вашим внутренним ресурсам.
Как можно общаться с MCP-сервером?
Есть 2 транспорта из коробки:
● stdio — т.е. через стандартный input/output: MCP-сервер запускается MCP-хостом как консольное приложение и обмен данными идет напрямую.
В этом случае предполагается, что вы скачиваете MCP-сервер в виде кода или готовой к запуску программы на машину, где у вас находится сам хост, и они работают в тесной связке, запускаясь вместе.
● sse — это по имени Server-Sent Events, одного из стандартных (и довольно древних) способов передачи сообщений поверх HTTP, использующего долгоживущее соединение для передачи данных в одном направлении (server -> client).
В случае с MCP нам всё-таки нужен полноценный двусторонний обмен с сервером, и, соответственно, 2 endpoint’а:
-
GET с собственно SSE — по нему будут передаваться сообщения от сервера клиенту в режиме бесконечного стрима
-
обычный POST для передачи сообщений от клиента серверу
Сервер с таким транспортом может быть запущен где угодно и может обслуживать много клиентов одновременно, в отличие от stdio.
В подавляющем большинстве случаев, однако, сервера сделаны именно в варианте stdio, но есть способ конвертить stdio <=> sse, см. ниже, в разделе с полезными инструментами.
Где брать MCP-сервера?
К примеру, тут: https://github.com/modelcontextprotocol/servers или тут: https://github.com/punkpeye/awesome-mcp-servers/
Вообще серверов буквально тысячи уже (https://glama.ai/mcp/servers, https://mcp.so/), но я бы советовал прям глазами проверять код тех, которые вы собираетесь использовать, т.к. порог входа низкий, модерации нет, многие вообще не работают — словом, это дикое поле
Пример сервера
Вот пример кода простого MCP-сервера — это всего лишь ~140 строк TypeScript, которые дают модели возможность просматривать схемы таблиц в вашем PostgreSQL и выполнять read-only запросы к выбранной базе.
Это stdio-сервер, и запускается он как консольное приложение, которому передаются данные для доступа к БД, к примеру, так:node <path>/index.js postgresql://myuser:mypassword@localhost:5432/mydb
Оцените, насколько просто можно сделать сервер под свои задачи, расширив тем самым возможности LLM для работы в вашем окружении.
Полезные инструменты
MCP-inspector
Локальное веб-приложение, с помощью которого можно проверять, работает ли MCP-сервер, узнать, какие сущности он экспортирует и посылать ему тестовые запросы.

Supergateway
Весьма полезная штука для конверсии транспорта MCP-сервера sse <=> stdio.
Я предпочитаю sse в силу большого количества багов вокруг stdio, так что все сервера перевёл на sse с помощью Supergateway, собрав их в docker-compose и развесив контейнеры на разные порты на хост-машине.
Выглядит это примерно так:
docker-compose.yaml
name: mcp services: postgres-gateway: image: supergateway ports: - "${POSTGRES_HOST_PORT:-8001}:8000" command: --port 8000 --stdio "npx -y @modelcontextprotocol/server-postgres ${POSTGRES_CONNECTION_STRING}" atlassian-gateway: image: supergateway-uv build: context: . dockerfile: Dockerfile.uv ports: - "${ATLASSIAN_HOST_PORT:-8002}:8000" command: --port 8000 --stdio "uvx mcp-atlassian --confluence-url=${CONFLUENCE_URL} --confluence-username=${CONFLUENCE_USERNAME} --confluence-token=${CONFLUENCE_TOKEN} --jira-url=${JIRA_URL} --jira-username=${JIRA_USERNAME} --jira-token=${JIRA_TOKEN}" youtube-gateway: image: supergateway-youtube build: context: . dockerfile: Dockerfile.youtube ports: - "${YOUTUBE_HOST_PORT:-8003}:8000" command: --port 8000 --stdio "npx github:anaisbetts/mcp-youtube"
После чего соответствующие MCP-сервера доступны на хост-машине с использованием sse-транспорта по URL’ам вида http://localhost:8001/sse, и их можно вот так добавить в Cursor, к примеру:
sse MCP-сервера в Cursor

Как вариант, для тех же целей преобразования sse <=> stdio можно использовать mcp-proxy
Существующие проблемы
Куда же без проблем — они, конечно, есть, и почти все их можно связать с тем, что технология недавно появилась, но уже произошел взрывной рост её популярности:
Нет официального каталога серверов
… и проверок новых серверов тоже никто не делает. Есть надежда на то, что коммьюнити само постепенно отфильтрует мусор, но пока что надо быть аккуратным.
Реально, во многих случаях может оказаться самому быстрее написать сервер, чем брать чей-то сомнительного качества — благо, сделать свой несложно.
Но есть хорошая новость: сами Anthropic в кулуарах обещаются сделать официальный MCP-registry, так что ждём.
Устанавливать сервера — боль
Нет какого-то общего формата описания того, откуда сервер должен скачиваться, как ставиться и как запускаться, поэтому кто во что горазд, и нас встречает зоопарк из docker / npx / node / uv / uvx / python / pipx / бинарников (и это только самые распространенные варианты).
Да, есть формат списка подключенных MCP-серверов, который используется в Claude Desktop: claude_desktop_config.json (https://modelcontextprotocol.io/quickstart/user#2-add-the-filesystem-mcp-server), и его пытаются копировать другие клиенты, но тоже кто в лес, кто по дрова, т.к. формат не стандартизирован.
Это ж до смешного доходит — Cline ставит MCP-сервера, скармливая LLM-ке README из репозитория устанавливаемого MCP-сервера, чтобы модель сама разобралась, как его поставить и сконфигурировать в проекте
И есть даже такой MCP-сервер, mcp-installer, который ставит другие MCP-сервера по такому же принципу, с помощью LLM, прописывая их в claude_desktop_config.json.
Есть проект https://smithery.ai/, к которому можно присмотреться — по крайней мере, они работают над унификацией конфигурации серверов.
Но мне не нравится их подход в том, что они стараются сервера хостить у себя — возникают вопросы с безопасностью.
Разнобой в поддержке фич протокола
На странице со списком клиентов, которые заявили о поддержке протокола, можно видеть, что далеко не все из них поддерживают все его фичи.
Впрочем, в большинстве случаев Tools хватает, но, тем не менее, надо этот фактор учитывать как при разработке MCP-серверов, так и при их использовании.
Так, к примеру, в Cursor 0.46.9 выпилили поддержку ресурсов, и у меня пропали схемы таблиц из БД, которые экспортировал mcp-postgres. Нейронке теперь через вызов инструмента «sql-запрос» приходится вытаскивать схемы из БД, что не очень оптимально.
Обещают вернуть в будущих версиях и сделать возможным их упоминать в окне чата, что в целом правильно и согласуется с концепцией ресурсов как выбираемых пользователем сущностей для передачи их модели.
А пока что, как вариант, можно откатиться от текущей 0.46.11 на 0.46.8, есть вот такой неофициальный репозиторий со ссылками на старые билды Cursor.
Практики внедрения
Управление контекстом
Одна из целей обращения к внешним системам — обогащение контекста LLM для решения поставленной задачи.
Однако тут важно понимать, что контекст (т.е. токены) стоит денег, он лимитирован по длине, с его ростом LLM начинает медленнее отвечать, и, даже если все ваши данные влезают в контекст, далеко не все LLM одинаково «умны» с коротким и длинным контекстом.
Соответственно, MCP-сервер должен быть точен и лаконичен в возвращаемых данных, а MCP-хост может применять разного рода техники по управлению контекстом, чтобы снизить стоимость работы с ним: суммаризация, кеширование, использование скользящего окна и т.д.
Также не стоит подключать большое количество MCP-серверов к хосту, т.к. список всех сущностей, которые предоставляет MCP-сервер (tools, resources, prompts, etc) с их описаниями передается LLM в контексте, чтобы она про них знала и могла попросить вызвать что-то, что нужно для решения задачи пользователя.
Качество данных
LLM принимает решения на основе тех данных, которые оказались в контексте, и если в него попадает неполная, противоречивая, нерелевантная задаче информация, то ждите проблем: будет путаться, делать не то, что надо, обращать внимание на несущественные детали и т.п.
Соответственно, по возможности нужно следить за качеством данных, которые попадают в контекст из внешних систем через MCP-сервера.
Правило garbage in — garbage out тут всё ещё работает
Это касается и того, насколько хорошо и уникально названы и описаны сущности, которые экспортирует MCP-сервер, чтобы модель вызывала те функции, которые вы от неё ожидаете.
Безопасность
Подключением MCP вы даёте LLM доступ к приватным данным и возможность совершать потенциально деструктивные операции в том окружении, где запущен MCP-сервер.
Встроенного механизма авторизации в протоколе на текущий момент нет, она существует только в виде драфта для следующей версии.
Так что нужно учесть следующие моменты, особенно при работе со сторонними MCP-серверами:
● проверяйте их код на предмет наличия там небезопасных операций
● запускайте сам MCP-сервер под пользователем с минимально необходимым набором прав и, по возможности, в изолированной среде
● если MCP-сервер требует авторизации во внешней системе — у пользователя, который он для этого будет использовать, тоже должны быть только самые необходимые права
● настраивайте MCP-хост на то, чтобы он спрашивал разрешение у пользователя на получение доступа к ресурсам или на вызов инструментов. Да, это довольно быстро станет обузой в работе, но при работе с непроверенным MCP-сервером стоит об этом подумать
Ну и конечно нужно помнить о том, в случае коммерческих LLM данные передаются куда-то в облако, и этот вопрос требует отдельной проработки с учётом ваших политик безопасности.
Этихлид — само собой, ссылка на Telegram-канал, там пишу про AI / техлидство / спорт и всякое околофилософское вокруг всего этого, подключайтесь
ссылка на оригинал статьи https://habr.com/ru/articles/890740/
Добавить комментарий