Для разработчика (или ИИ-агента), подключающего сервис экосистемы (bugtrail, gntodo, smart-home, gnexus-auth, Navi…) к хабу уведомлений. Контракт приёма — docs/05-ingestion-api.md; этот документ — порядок внедрения и паттерны. Клиентские библиотеки: gn-synapse-client-py / gn-synapse-client-php (README последних — полный справочник API).
source,subject,action), цели и правила.Админка — единственный способ конфигурировать Synapse: тип не зарегистрирован → 422 на каждое событие. Подключение сервиса начинается не с кода, а с регистрации: сначала в Synapse, потом код.
^[a-z0-9]([a-z0-9._-]*[a-z0-9])?$, 1..64, латиница строчными) — обычно имя репо/сервиса (bugtrail, gntodo, navi-rei);(subject, action) — что сервис будет сообщать (см. §4), с приоритетом по умолчанию каждой тройки;internal_log, push, telegram, s2s в Navi) и «о ком» — нужен ли payload.user_id.source_create (или §админка → источники) → key_issue → plaintext-ключ в .env сервиса и gnexus-creds, нигде больше; type_register для каждой тройки; rule_create/rule_set.SYNAPSE_URL=https://synapse.gnexus.space # или :8013 в LAN SYNAPSE_API_KEY=syn_... SYNAPSE_DEFAULT_SOURCE=<имя источника>
emit/send. Быстрая проверка после первого отправа — админка → поток (лог доставок), или send_test_event (MCP).Python:
pip install "git+https://git.gnexus.space/git/root/gn-synapse-client-py.git@v0.1.0"
from gnexus_synapse import SynapseClient sync = SynapseClient() # конфиг из SYNAPSE_* async_client = AsyncSynapseClient() # для FastAPI-контекста
PHP (composer, repositories vcs — см. README либы):
$client = new \GNexus\Synapse\SynapseClient(
\GNexus\Synapse\Config\SynapseConfig::fromGlobals(),
new \GuzzleHttp\Client(['timeout' => 10.0]),
new \GuzzleHttp\Psr7\HttpFactory(),
new \GuzzleHttp\Psr7\HttpFactory(),
);
Правило: один клиент-инстанс на процесс (переиспользует http-соединения); при ручном создании — таймаут обязательно (SYNAPSE_TIMEOUT и timeoutSeconds у Guzzle-транспорта), иначе вечный вис при лежащем Synapse.
| Паттерн | Когда | Возврат/падение | |
|---|---|---|---|
emit(source?, subject, action, …) |
событие «потери не страшно», основной путь большинства сервисов | `Event\ | None;SynapseError`/транспорт → warning в лог, не бросаются |
send(...) |
событие, чья потеря = инцидент (уведомление о падении монитора, инцидент безопасности) | бросает типизированные исключения (см. README) — у caller'а есть ретри- или эскалационная политика | |
send_batch([...]) |
прогон «сотни мелких» (импорт, массовая рассылка) | BatchResult.accepted/rejected; локально битые и серверные отклонения — по индексам, 202 и 422 парсятся одинаково |
|
status(event_id) |
отладка/приёмочный тест нового источника; в бизнес-коде обычно не нужен | EventStatus со списком доставок |
|
health() / ready() |
readiness-probe сервиса, старт-самоtest | без ключа |
Конвенции полей:
priority — low|normal|high|critical; critical — только действительно инциденты (обходит throttle правил).dedup_key — на «повторяющиеся в окне» события (ping-<день>, issue-<id>) чтобы не спамить; best-effort (24ч-окно, повтор вернёт id первого события с deduplicated=true) — не строить бизнес-логику на нём.payload.user_id — непустая строка (uuid gnexus-auth): это «о ком событие» (личный лог, личный push). Число/пустая → предупреждение, адресные доставки пойдут skipped.ttl_seconds — забыть событие старше N сек (актуальность), по умолчанию окно от настроек Synapse.scheduled_at — резерв контракта, сервер пока не обрабатывает.Тройки регистрируются админом один раз каждая — расширение списка это правка реестра, а не кода; берите предсказуемую схему:
task, issue, container, user, auth);created, completed, down, password_changed, login_failed); глаголы в прошедшем времени или существительные — не повелительное.Шаблон события держите в репо сервиса (или в описании сервиса gnexus-book), чтобы при регистрации нового типа не догадываться о смысле payload'а.
emit; критичные — send + try/catch с политикой
(лог + ручной ретри/эскалация — не автомедицина, Synapse сам ретраит доставки по каналам).
dedup_key не в ролях бизнес-идемпотентности.payload.user_id — uuid gnexus-auth (если адресные доставки нужны).`422` на проде = забыли тип — добавить `type_register`, не «обходить» в коде).
«что в payload»).
Быстрая приёмка после первого деплоя интеграции:
examples/plain/smoke.py, php: examples/plain-php/smoke.php (требуют источник libtest и тип; для реального сервиса подставьте своё имя).source_list → key_issue → type_register → send_test_event (прогон правила без кода сервиса) → deliveries_list.status).status() «до delivered» в бизнес-коде — события fire-and-forget; нужен мониторинг — это дежурные метрики Synapse и админка, не поллинг.statusCode = null) — ошибка кода, тесты; 422 сервера — вопрос регистрации, админ.