Synapse встраивает FastMCP (пакет mcp) — тот же контейнер API, тот же процесс uvicorn. Эндпоинт /mcp, транспорт streamable-http (stateless), доступ — статический Bearer-токен MCP_TOKEN из .env.
Зачем: ИИ-агент (Claude Code и совместимые) управляет Synapse целиком — выдаёт API-ключи клиентам (сервисам-источникам), регистрирует типы, ведёт правила маршрутизации, смотрит поток событий и доставок, меняет настройки — без ручной работы в админке. Правка 2026-10-03.
MCP_TOKEN=<hex> в .env (и gnexus-creds). Пусто/не задано — /mcp не существует: GET уходит в SPA, POST отвечает 405.claude mcp add --transport http synapse http://localhost:8013/mcp \ --header "Authorization: Bearer <MCP_TOKEN>"
Генерация токена: openssl rand -hex 32. Токен — как ключ прод-сервера (внутри API полномочия MCD = superadmin), хранить в .env + gnexus-creds, никогда не в репозитории.
app/api/admin_routes.py) напрямую — та же pydantic-валидация, те же коды ошибок и тексты. Автор запросов — синтетический superadmin (токен и есть доверие).{"error": 409, "detail": "…"} — агент читает причину и может её исправить (например restore архивной записи).McpTokenGuard, app/mcp/server.py): проверяет Authorization: Bearer на каждом запросе, 401 (www-authenticate: Bearer) при несовпадении; не BaseHTTPMiddleware — SSE-стримы не ломает.MCP_TOKEN → сервер не монтируется.| Группа | Тулы |
|---|---|
| Состояние | system_status (БД + Celery ping + SSO) · stats_get (счётчики по статусам, живые справочники) |
| Источники | sources_list (query, include_archived) · source_create · source_archive · source_restore |
| Ключи | keys_list · key_issue (plaintext один раз в token) · key_revoke |
| Типы | types_list (source_id, query, include_archived) · type_register · type_archive · type_restore |
| Цели | targets_list (channel, enabled, include_archived) · target_create · target_patch · target_archive · target_restore |
| Правила | rules_list (enabled, include_archived) · rule_create · rule_patch · rule_archive · rule_restore |
| Поток | events_list (status, source_name) · event_get · deliveries_list (status, channel) |
| Push | push_subscriptions_list (user_id) · push_subscription_delete (жёстко — устройства пользователей) |
| Настройки | settings_get (секреты write-only: value=null, факт в set) · settings_put (правила docs/06: "" — не менять, null — сброс; настройка push-канала — рецепт VAPID в docs/06 «Как задать VAPID», выполняется shell'ом в контейнере) |
| Контроль | send_test_event (source_name, subject, action, payload, priority) — полный маршрут в воркере |
DELETE не удаляет — ставит deleted_at (архив). Действует на sources, notification_types, channel_targets, routing_rules. Пуш-подписки — исключение: устройства пользователей удаляются физически (push-нотификации не переживают несуществующую подписку).
Что это значит:
include_archived=true покажет архив (deleted_at в объектах; в UI-списках поле всегда null).skipped с причиной «цель в архиве» (аудит, видно в deliveries).POST /api/v1/admin/{sources|types|targets|rules}/{id}/restore → 200 с объектом; конфликт имени с живой записью → 409. Restore типа требует живого источника (409).REST-эквивалент доступен и из админ-API (те же эндпоинты), UI-клиент SPA ничего не заметил (204-ответы прежние).
Выдать ключ клиенту:
1. source_create(name="bugtrail", description="Трекер ошибок…") 2. key_issue(source_id=<id>, name="основной") → token: "syn_…" — передать клиенту один раз 3. type_register(source_id, subject="issue", action="created") 4. Третьесторонний сервис шлёт POST /api/v1/events с Bearer syn_…
Проверить правило:
1. rule_create(name="critical → Navi rei", actions=[{"channel":"s2s","target_id":3}],
conditions={"priority_min":"critical"})
2. send_test_event(source_name="monitoring", subject="container", action="down",
payload={"container":"api"}, priority="critical")
3. events_list(source_name="monitoring") → доставed в цель
settings_get их не отдаёт).send_test_event и просмотр потока требуют живого воркера (Celery) — system_status покажет./mcp не публикуем.