Bitrix24 MCP Bridge
A bridge between Claude (MCP) and Bitrix24 CRM/Tasks, enabling natural language interaction with leads, deals, contacts, companies, and tasks via a custom MCP server using incoming webhooks.
README
Bitrix24 MCP Bridge
Мост между Claude (MCP) и Bitrix24 CRM/Задачами. Развёрнут на хостинге
Beget по адресу mcp-bitrix.karpovpartners-it.ru.
1. Зачем это понадобилось
Изначально пытались подключить Claude к Bitrix24 через встроенный в Bitrix24
коннектор «МСР-подключения» (приложение aiassistant.bitrix_mcp /
кнопка «Б24» в маркетплейсе). Оказалось, что эта функция не работает:
эндпоинты /authorize, /.well-known/oauth-authorization-server,
/.well-known/oauth-protected-resource отдают голый nginx 404, хотя все
настройки и подписка в порядке. Это баг/недокат фичи на стороне Bitrix24,
а не ошибка в настройках.
В качестве обходного пути был написан собственный MCP-сервер («мост»), который:
- принимает MCP-запросы от Claude по протоколу Streamable HTTP;
- транслирует их в вызовы обычного REST API Bitrix24 через входящий вебхук (создан в Bitrix24 с правами только на CRM + Задачи);
- отдаёт результат обратно в Claude в виде MCP tool-ответов.
2. Архитектура и файлы
| Файл | Назначение |
|---|---|
server.mjs |
Основной код моста (ES-модуль). Поднимает Express-сервер, разбирает MCP-запросы через @modelcontextprotocol/sdk, дергает REST API Bitrix24. |
app.js |
Тонкая CommonJS-обёртка для запуска server.mjs. Нужна из-за особенности Passenger на Beget (см. ниже). |
package.json |
Зависимости: @modelcontextprotocol/sdk, express, zod, undici. |
.htaccess.example |
Шаблон конфигурации Phusion Passenger + переменные окружения. Реальный .htaccess с боевыми секретами не хранится в репозитории (см. .gitignore) — он развёрнут напрямую на сервере и сохранён отдельно у владельца проекта. |
Какие инструменты (tools) доступны в Claude
bitrix24_call— вызов любого методаcrm.*,task.*,tasks.*,user.current,profileнапрямую (эскейп-люк).bitrix24_list_crm/bitrix24_get_crm/bitrix24_add_crm/bitrix24_update_crm— список/чтение/создание/обновление записей CRM (lead,deal,contact,company).bitrix24_list_tasks/bitrix24_add_task/bitrix24_update_task/bitrix24_complete_task— работа с задачами.
Сервер жёстко ограничивает вызываемые методы Bitrix24 префиксами crm.,
task., tasks., user.current, profile (см. ALLOWED_METHOD_PREFIXES
в server.mjs) — это защита на случай, если у вебхука когда-нибудь
появятся более широкие права.
3. Аутентификация / безопасность
У кастомных MCP-коннекторов в интерфейсе Claude нет поля для
произвольных HTTP-заголовков — только URL (+ опционально OAuth
Client ID/Secret). Поэтому вместо заголовка Authorization секрет
зашит в путь URL:
https://mcp-bitrix.karpovpartners-it.ru/mcp/<секрет>
Секрет и адрес вебхука Bitrix24 хранятся только в боевом .htaccess
на сервере и в приватной копии у владельца проекта — они намеренно не
закоммичены в этот репозиторий (см. .gitignore). Любой, кто узнает
секрет из URL, получит доступ к CRM и задачам Bitrix24 в рамках прав
вебхука.
4. Как это работает по шагам
- Claude открывает MCP-коннектор → POST на
/mcp/<секрет>с телом{"method":"initialize", ...}. - Express-роут в
server.mjsсоздаёт новыйMcpServer(StreamableHTTPServerTransport,sessionIdGenerator: undefined— сервер без сохранения сессии, каждый запрос независим). - Claude вызывает
tools/list, затемtools/callс конкретным инструментом (напримерbitrix24_list_crm). server.mjsвызываетbitrixCall(method, params), которая делаетfetch()наhttps://<портал>.bitrix24.ru/rest/<id>/<вебхук>/<метод>.json.- Ответ Bitrix24 оборачивается в MCP-формат и уходит обратно в Claude.
5. Развёртывание с нуля
- Создать входящий вебхук в Bitrix24: Настройки → Разработчикам → Другое → Входящий вебхук. Права — минимум CRM + Задачи.
- Склонировать репозиторий на сервер, в директорию сайта (
public_htmlвашего домена/поддомена). npm installв этой директории (поставитexpress,zod,@modelcontextprotocol/sdk,undici).- Скопировать
.htaccess.exampleв.htaccessи прописать реальныеBITRIX_WEBHOOK_URLиMCP_PATH_SECRET. - На Beget:
mkdir tmp && touch tmp/restart.txt— команда Passenger на перезапуск приложения после любых изменений в коде. - В панели Beget: «Сайты» → у нужного сайта → «⋮» → «Прикрепить домен» — без этого шага Apache даже не пытается достучаться до вашего кода (см. раздел 6.2 — легко забыть, ошибка неочевидная).
6. Проблемы, с которыми столкнулись при разворачивании на Beget, и как их решили
Журнал отладки — пригодится при повторном развёртывании на Beget или другом shared-хостинге со старым Node.js.
6.1. Node.js на Beget — версия 16.20.2, слишком старая
На стороне Beget (Ubuntu 18.04, glibc 2.27) официальные сборки Node 18+ не
запускаются (GLIBC_2.28' not found). Пришлось остаться на Node 16.20.2 и
вручную подложить недостающие в Node 16 глобальные объекты, которые нужны
современным зависимостям (@modelcontextprotocol/sdk, Express 5):
fetch,Headers,Request,Response— через пакетundici.crypto(Web Crypto API,crypto.randomUUID()) — через встроенныйnode:crypto(webcrypto).ReadableStream,WritableStream,TransformStream— через встроенныйnode:stream/web.structuredClone,MessageChannel/MessagePort— на всякий случай, черезnode:v8иnode:worker_threads.
Всё это — в самом начале server.mjs, до импорта Express и MCP SDK
(сделано через await import(...), а не через обычный import сверху
файла — см. следующий пункт, почему).
6.2. Домен не был «приклеен» к папке сайта
После загрузки кода на сервер сайт отдавал фирменную страницу Beget «Домен не привязан к директории на сервере» вместо приложения. Просто создать папку сайта и залить туда файлы недостаточно — домен нужно отдельно «прикрепить» через панель: Сайты → нужный сайт → ⋮ → «Прикрепить домен». Неочевидный шаг, который легко пропустить.
6.3. ERR_REQUIRE_ESM: Passenger не умеет грузить ES-модули
Passenger на Beget (старая версия, passenger40) запускает стартовый файл
через require(), а require() в Node принципиально не умеет грузить
ES-модули (import/export, type: module в package.json). server.mjs
использует await на верхнем уровне файла — а это возможно только в
ES-модуле.
Решение: в package.json нет "type": "module" (по умолчанию .js —
CommonJS), сам код лежит в файле с расширением .mjs (расширение .mjs —
это всегда ES-модуль, вне зависимости от package.json), а точкой входа
для Passenger сделан app.js — крошечный CommonJS-файл:
// app.js
import('./server.mjs').catch((err) => {
console.error('Failed to start server:', err);
process.exit(1);
});
require() спокойно загружает app.js (это обычный CommonJS), а внутри
него динамический import() (это функция, а не декларация) уже может
асинхронно загрузить ES-модуль server.mjs.
6.4. Секрет в пути URL
MCP_PATH_SECRET — случайная строка (например, secrets.token_urlsafe(32)
в Python, или crypto.randomUUID() + crypto.randomUUID() в консоли
браузера). Если нужно перевыпустить секрет — сгенерировать новый и
обновить в .htaccess на сервере и в настройках коннектора в Claude.
7. Как подключить в Claude
- claude.ai → Настройки → Connectors → Add custom connector.
- Name:
Bitrix24(любое). - Remote MCP server URL:
https://mcp-bitrix.karpovpartners-it.ru/mcp/<секрет> - OAuth Client ID / Secret — оставить пустыми, они не нужны (авторизация уже зашита в URL).
- Сохранить, включить коннектор в чате.
8. Открытый вопрос — родной MCP-коннектор Bitrix24
Стоит написать в поддержку Bitrix24 про сломанный нативный MCP-коннектор
(«Б24» в маркетплейсе): /authorize и стандартные OAuth-discovery
эндпоинты отдают голый nginx 404 при включённых настройках и активной
подписке. Когда/если Bitrix24 это починит, можно будет переключиться на
официальный коннектор — либо оставить этот мост, он тоже рабочий и даёт
больше контроля (например, ограничение методов до CRM+Задачи прямо в
коде).
Recommended Servers
playwright-mcp
A Model Context Protocol server that enables LLMs to interact with web pages through structured accessibility snapshots without requiring vision models or screenshots.
Audiense Insights MCP Server
Enables interaction with Audiense Insights accounts via the Model Context Protocol, facilitating the extraction and analysis of marketing insights and audience data including demographics, behavior, and influencer engagement.
Magic Component Platform (MCP)
An AI-powered tool that generates modern UI components from natural language descriptions, integrating with popular IDEs to streamline UI development workflow.
VeyraX MCP
Single MCP tool to connect all your favorite tools: Gmail, Calendar and 40 more.
graphlit-mcp-server
The Model Context Protocol (MCP) Server enables integration between MCP clients and the Graphlit service. Ingest anything from Slack to Gmail to podcast feeds, in addition to web crawling, into a Graphlit project - and then retrieve relevant contents from the MCP client.
Kagi MCP Server
An MCP server that integrates Kagi search capabilities with Claude AI, enabling Claude to perform real-time web searches when answering questions that require up-to-date information.
E2B
Using MCP to run code via e2b.
Neon Database
MCP server for interacting with Neon Management API and databases
Exa Search
A Model Context Protocol (MCP) server lets AI assistants like Claude use the Exa AI Search API for web searches. This setup allows AI models to get real-time web information in a safe and controlled way.
Qdrant Server
This repository is an example of how to create a MCP server for Qdrant, a vector search engine.