rbctmz/b24-mcp
If you are the rightful owner of b24-mcp and would like to certify it and/or have it hosted online, please leave a comment on the right or send an email to dayong@mcphub.com.
The Bitrix24 MCP Server is a FastAPI-based server that integrates Bitrix24 CRM data with LLM agents through the Model Context Protocol (MCP).
Bitrix24 MCP Server
FastAPI-based Model Context Protocol (MCP) server that exposes Bitrix24 CRM data and actions to LLM agents. The server translates MCP resource and tool calls into Bitrix24 REST API requests.
Features
- MCP resources for listing deals, leads, contacts, users, tasks, currencies, and Bitrix24 dictionaries (lead stages/sources, deal categories/stages, task statuses/priorities)
- MCP tools for retrieving CRM entities (deals, leads, contacts, users, tasks) and companies (list/detail via
getCompanies/getCompany) - Localized MCP prompts (Russian), including structuredContent and warnings for missing arguments
- Tool responses conform to CallToolResult (fields
content,structuredContent,isError) compatible with fastmcp - Uniform warnings and recommended date filters for all tools, allowing clients to automatically retry requests with adjustments
- Resource responses include
_metablocks with human-readable labels (responsible user, stage, source, priority, etc.) - Tool responses for
getLeadsnow reuse the cachedcrm/leadsdictionary so they ship the same_metadata (responsible, creator, modifier, status, source, currency), exposestructuredContent.aggregateswith counts, includestructuredContent.hints.copyableFilter(примеры недельного фильтра/iter) so агент может копировать фильтр для следующего запроса, а предупреждения поtoolWarnings.getLeadsбольше не приводят только к диапазону «сегодня» — теперь пример показывает последнюю неделю с>=DATE_CREATE/<=DATE_CREATE. - Date-range hints, warnings, and weekly samples respect a configurable timezone (
SERVER_TIMEZONE, defaultUTC), so the generatedYYYY-MM-DDTHH:MM:SS±HH:MMboundaries match your portal’s local day. - Configurable via environment variables (
.env) - HTTPX-based Bitrix24 client with retry/backoff
- Async FastAPI application ready for Docker or local execution
- Pytest suite with in-memory Bitrix24 client stubs
- Claude Desktop stdio proxy (
mcp_stdio_proxy.py) with configurable base URL/timeout via environment versions/releasesresource exposes structured release metadata (version, status, title, notes) derived fromCHANGELOG.mdso agents can fetch the latest release history through MCP.- Configure
GITHUB_RELEASES_REPO(and optionalGITHUB_TOKEN,GITHUB_TIMEOUT_SECONDS,GITHUB_CACHE_TTL_SECONDS) to keepversions/releasesin sync with GitHub Releases instead of the static changelog snapshot.
MCP Prompts and Cheat Sheets
- All prompt texts, tool descriptions, and ready-made payloads are stored in
mcp_server/app/docs/prompts_ru.md. When the file is changed, the server automatically picks up new instructions without code modifications. - The
initializeresponse containsstructuredInstructionsandinstructionNoteswith examples: how to get fresh leads (order = {"DATE_MODIFY": "DESC"}) and how to set date ranges via>=DATE_CREATE,<=DATE_CREATE. - MCP tools return
structuredContentwith the full Bitrix24 response and warnings. If no date range is provided, any list tool (getDeals,getLeads,getContacts,getUsers,getTasks,getCompanies) adds a message, recommended filters, andsuggestedFix, allowing fastmcp/SGR to automatically retry the request. - The
bitrix24_leads_guideresource provides a cheat sheet with typical scenarios (fresh leads, today's selection, status filter) and rules for combining filters. - The
prompts_ru.mdstructure provides for localization: for a new locale, it is enough to add aprompts_<locale>.mdfile and update the settings.
Tool Response Format (CallToolResult)
- MCP tools (
/mcp/tool/call, JSON-RPCtools/call, WebSocket/SSE) return a dictionary in the format:
{
"content": [
{"type": "text", "text": "crm/leads: 42 records received. Full response in structuredContent.result."},
{"type": "text", "text": "Warning: Add range filters ..."} // optional
],
"structuredContent": {
"metadata": {"provider": "bitrix24", "tool": "getLeads", "resource": "crm/leads"},
"request": {"order": {"DATE_MODIFY": "DESC"}, "filter": {...}},
"result": {...}, // original Bitrix24 response
"warnings": [...] // optional
},
"isError": false
}
mcp_server/
app/
main.py # FastAPI application factory and lifespan management
settings.py # Pydantic settings loaded from environment
bitrix_client.py # Async HTTP client wrapper for Bitrix24 REST API
exceptions.py # Shared exception types for MCP responses
dependencies.py # FastAPI dependencies for resource/tool registries
mcp/
schemas.py # Pydantic models for MCP requests/responses
resources.py # Resource registry (crm/deals, crm/leads, ...)
tools.py # Tool registry (getDeals, getLeads, ...)
routes.py # MCP endpoints (`/mcp/index`, `/mcp/resource/query`, `/mcp/tool/call`)
tests/
test_resources.py # Resource query tests
test_tools.py # Tool call tests
conftest.py # Shared fixtures and settings overrides
mmp@m copypaste? Wait patch wants to change line 105 from ` ``` ` to ` ```text `. Need patch near that line. We'll produce patch.
- The `structuredContent` field stores the original REST payload, so clients can continue to use `metadata` and `result`.
- Warnings about missing dates and other critical arguments are added to `structuredContent.warnings`, and specific filters and sorts to apply are available in `structuredContent.suggestedFix.filters`.
- SSE/WebSocket transmissions use the same CallToolResult, which eliminates fastmcp validator errors.
- For list tools the server additionally exposes `structuredContent.pagination` (`limit`, `start`, `next`, `total`, `fetched`), so you can immediately report the total count or use `next` to page through the full selection.
- For dictionaries like `crm/lead_statuses` and `crm/deal_stages` we now include each stage’s `group`/`groupName` derived from its semantics (`process` → «В работе», `success` → «Заключена», `failure` → «Провалена»), so agents can filter or aggregate by status groups directly.
- `getLeads` now supports `statusSemantics` (or alias `groupSemantics`) — a list of semantic groups (`process`, `success`, `failure`). The server resolves them into the corresponding `STATUS_ID` values before handing the filter to Bitrix, so you can request “лиды в работе” without managing the ID list yourself.
- Added `callBitrixMethod` so you can proxy arbitrary REST calls (for example, `crm.activity.list` to fetch calls by `OWNER_TYPE_ID`/`TYPE_ID`). This keeps MCP flexible while reusing the same logging/warnings/pagination wrappers.
- Added `getLeadCalls`, which combines `crm.activity.list` + `crm.activity.get` + `voximplant.statistic.get` to produce a detailed call log for a lead (`date`, `CALL_ID`, `duration`, and recording info).
## Release History Resource
Use the MCP resource `versions/releases` (alias `releases`) to get structured release notes directly from `CHANGELOG.md`. It returns a list of entries with `version`, `status`, `title`, and `notes`, so agents can inspect what changed without leaving the MCP context:
```bash
curl -sS http://localhost:8000/mcp/resource/query -H "Content-Type: application/json" \
-d '{"resource": "versions/releases", "params": {}}' | jq .
GitHub release synchronization
Set GITHUB_RELEASES_REPO=owner/repo to pull releases from GitHub instead of the built-in changelog. An optional GITHUB_TOKEN lets you read private repos or avoid rate limiting, GITHUB_TIMEOUT_SECONDS controls the fetch timeout, and GITHUB_CACHE_TTL_SECONDS determines how long results stay cached before another GitHub call. When GitHub is unreachable, the resource falls back to the static entries derived from CHANGELOG.md.
Resource Response Metadata (_meta)
- Every entity returned via
crm/deals,crm/leads, andcrm/tasksis enriched with a_metasection that contains human-readable descriptors resolved through cached Bitrix24 dictionaries:
{
"ID": "123",
"ASSIGNED_BY_ID": "42",
"STATUS_ID": "NEW",
"_meta": {
"responsible": {
"id": "42",
"name": "Анна Иванова",
"email": "anna@example.com"
},
"status": {
"id": "NEW",
"name": "Новый"
},
"source": {
"id": "CALL",
"name": "Звонок"
}
}
}
- Available enrichments today:
- Deals:
responsible,category,stage - Leads:
responsible,creator,modifier,status,source,currency - Tasks:
responsible,creator,status,priority
- Deals:
- Each
_meta.<key>entry exposes anid, aname, andraw(original Bitrix24 dictionary entry) so MCP clients can keep working with the underlying IDs when needed. - Cached dictionaries (
crm/currencies,crm/lead_statuses,crm/lead_sources,crm/deal_categories,crm/deal_stages,tasks/statuses,tasks/priorities) are also exposed as standalone MCP resources for direct lookups.
Project Layout
mcp_server/
app/
main.py # FastAPI application factory and lifespan management
settings.py # Pydantic settings loaded from environment
bitrix_client.py # Async HTTP client wrapper for Bitrix24 REST API
exceptions.py # Shared exception types for MCP responses
dependencies.py # FastAPI dependencies for resource/tool registries
mcp/
schemas.py # Pydantic models for MCP requests/responses
resources.py # Resource registry (crm/deals, crm/leads, ...)
tools.py # Tool registry (getDeals, getLeads, ...)
routes.py # MCP endpoints (`/mcp/index`, `/mcp/resource/query`, `/mcp/tool/call`)
tests/
test_resources.py # Resource query tests
test_tools.py # Tool call tests
conftest.py # Shared fixtures and settings overrides
Getting Started
1. Configure environment
Create .env based on .env.example:
cp .env.example .env
Update the following values:
BITRIX_BASE_URL: your Bitrix24 REST endpoint (usually<portal>/rest)BITRIX_TOKEN: webhook key or OAuth access tokenBITRIX_INSTANCE_NAME(optional): identifier used in MCP metadataSERVER_*: customize local server host/port/log level if requiredSERVER_TIMEZONE(optional): IANA timezone (defaultUTC) used when building date-range warnings/hints so agents always see consistent local boundaries.
2. Install dependencies
python -m venv .venv
source .venv/bin/activate
pip install -e '.[dev]'
3. Run the server (local)
uvicorn mcp_server.app.main:app --reload
Health check:
curl http://localhost:8000/healthz
MCP discovery:
curl http://localhost:8000/mcp/index
4. Run tests
pytest
5. Run with Docker (optional)
docker build -t b24-mcp .
docker run --rm -p 8000:8000 --env-file .env b24-mcp
Note: The provided
.envfile is mounted as environment variables inside the container. Ensure it contains valid Bitrix24 credentials before starting the container.
6. Connect Claude Desktop via stdio proxy
Use the included mcp_stdio_proxy.py script to bridge Claude Desktop (stdio-based MCP client) with the HTTP server:
-
Ensure the MCP server is running locally (defaults to
http://127.0.0.1:8000). -
Optional environment variables for the proxy:
MCP_PROXY_BASE_URL– override the target server URL (defaults tohttp://127.0.0.1:8000).MCP_PROXY_TIMEOUT– request timeout in seconds (defaults to30).
-
Update Claude Desktop settings (
~/Library/Application Support/Claude/Settings/settings.json):{ "mcpServers": { "b24-mcp": { "command": "/Users/gregkisel/Documents/GitHub/b24-mcp/.venv/bin/python", "args": [ "/Users/gregkisel/Documents/GitHub/b24-mcp/mcp_stdio_proxy.py" ], "cwd": "/Users/gregkisel/Documents/GitHub/b24-mcp", "env": { "MCP_PROXY_BASE_URL": "http://127.0.0.1:8000", "MCP_PROXY_TIMEOUT": "30" }, "autoStart": false } } }Adjust the paths if your checkout lives elsewhere or you use a different Python interpreter.
-
Restart Claude Desktop and select the
b24-mcpMCP server. The proxy skips JSON-RPC notifications (noid) to avoid spurious errors while forwarding responses untouched.
Bitrix Token Requirements
- The server authenticates requests to Bitrix24 via the
BITRIX_TOKENenvironment variable. - You can supply either:
- Inbound webhook key (recommended for service integrations) — create in Bitrix24 and ensure it has access to CRM entities (deals, leads, contacts) and tasks.
- OAuth access token — ensure the application scopes cover at least
crm,task, and user directory access.
- Token must remain secret. Store it only in
.env, CI secrets, or secure secret stores; never commit to source control. - When rotating tokens, simply update the value in
.envor provided secret source and restart the MCP server.
MCP Endpoints
| Endpoint | Method | Description |
|---|---|---|
/mcp/index | GET | Lists available resources and tools |
/mcp/resource/query | POST | Queries a resource (crm/deals, crm/leads, crm/contacts, crm/users, crm/tasks) |
/mcp/tool/call | POST | Executes a tool (getDeals, getLeads, getContacts, getUsers, getTasks, getCompanies, getCompany) |
Resource queries for crm/deals, crm/leads, crm/contacts, and crm/tasks default to returning at most five records when no filters are provided so that an empty request does not stream the entire CRM list.
Debug logging
- To inspect incoming MCP payloads and outgoing tool responses directly in the server logs, set
SERVER_LOG_LEVEL=debugbefore starting the app (FastAPI reads this from.envor the environment). WithDEBUGenabled you will see JSON-RPC requests,tool/resourceparameters, and pagination metadata in the logs, which helps when tuning filters for Open WebUI or other agents.
Example resource query
curl -X POST http://localhost:8000/mcp/resource/query \
-H "Content-Type: application/json" \
-d '{"resource": "crm/deals", "params": {"select": ["ID", "TITLE"], "filter": {">OPPORTUNITY": 10000}}}'
Example tool call
curl -X POST http://localhost:8000/mcp/tool/call \
-H "Content-Type: application/json" \
-d '{"tool": "getDeals", "params": {"select": ["ID", "TITLE"], "filter": {">OPPORTUNITY": 10000}}}'
Deployment Notes
- Use Docker or a process manager (systemd, supervisord) to host the FastAPI app.
- Ensure
.envis stored securely and not committed to source control. - For production, configure HTTPS termination and add authentication in front of the MCP server if required.
Local WebSocket / CORS testing
- During local development the MCP server accepts WebSocket connections at
ws://<host>:<port>/mcp. - By default the application is configured to accept origins from
http://localhostandhttp://127.0.0.1. - If you see
403 Forbiddenwhen attempting to open a WebSocket, try supplying an explicitOriginheader with your client (for exampleOrigin: http://localhost) or update theallow_originssetting inmcp_server/app/main.py.
Testing examples:
# quick HTTP index check
curl -sS http://127.0.0.1:8000/mcp/index | jq .
# JSON-RPC handshake over HTTP GET
curl -sS http://127.0.0.1:8000/mcp | jq .
# websocat with explicit Origin header (recommended when debugging CORS)
websocat -H 'Origin: http://localhost' ws://127.0.0.1:8000/mcp
# FastMCP CLI (if installed) to test MCP handshake
python -m fastmcp.cli connect ws://127.0.0.1:8000/mcp
Note: For production deployments, restrict allow_origins to trusted domains and enable TLS (wss://).
Server-Sent Events (SSE) streaming
This MCP server exposes a simple Server-Sent Events endpoint at /mcp/sse.
Use SSE when you want a streaming transport from server → client. The server
will send an initial handshake payload on connect and will broadcast tool and
resource results to connected SSE clients.
How it works:
- Connect a client to
GET /mcp/sseto receive events (Content-Typetext/event-stream). - Send JSON-RPC requests via
POST /mcp(the server will reply to the POST and also broadcast results to SSE subscribers). - For local testing use the following commands:
# Tail the HTTP index
curl -sS http://127.0.0.1:8000/mcp/index | jq .
# Connect to SSE (example using curl) — note: curl will not nicely render continuous SSE output
# but can be used to test the handshake
curl -v http://127.0.0.1:8000/mcp/sse
# Send initialize over HTTP JSON-RPC (you should also see this payload on the SSE connection)
curl -sS -X POST http://127.0.0.1:8000/mcp \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{}}' | jq .
# Health endpoint
curl -sS http://127.0.0.1:8000/mcp/health | jq .
For production, replace curl with a proper SSE client (browser EventSource or an SSE-capable client library) and secure the connection with TLS (https/wss).
MCP Client Setup (Claude, Codex, Cursor)
The server can be used by any MCP-capable client. Below are quick-start examples for the most common desktop clients. Adjust paths for your operating system and restart the client after editing its config.
Claude Desktop
- Ensure the MCP server is running locally (
uvicorn mcp_server.app.main:app --reload). - Edit
~/Library/Application Support/Claude/claude_desktop_config.json(macOS) or%AppData%\Claude\claude_desktop_config.json(Windows). - Add an entry under
mcpServers:
{
"mcpServers": {
"b24-mcp": {
"command": "/Users/gregkisel/Documents/GitHub/b24-mcp/.venv/bin/python",
"args": [
"/Users/gregkisel/Documents/GitHub/b24-mcp/mcp_stdio_proxy.py"
],
"cwd": "/Users/gregkisel/Documents/GitHub/b24-mcp",
"env": {
"MCP_PROXY_BASE_URL": "http://127.0.0.1:8000",
"MCP_PROXY_TIMEOUT": "30"
},
"autoStart": false
}
}
}
Restart Claude Desktop and the Bitrix24 MCP server will appear in the MCP servers menu.
Codex CLI
- Run the MCP server (
uvicorn mcp_server.app.main:app --reload). - Update
~/.codex/config.tomland add an entry beneath[mcp_servers]:
[mcp_servers.bitrix24]
url = "http://127.0.0.1:8000/mcp"
- Restart the Codex CLI; run
codex mcp listto verify the connection.
Cursor IDE
- Start the MCP server locally.
- Edit
~/.cursor/mcp.json(Cursor creates the file automatically after the first launch) and add a new server definition:
{
"mcpServers": {
"bitrix24": {
"url": "http://127.0.0.1:8000/mcp",
"timeout": 30000,
"name": "Bitrix24 MCP"
}
}
}
After saving the file, reopen Cursor. The Bitrix24 MCP server will be available in the MCP panel and can be enabled per project.
License
MIT License. See for details.