Протокол Gateway (WebSocket)
Протокол Gateway WS — це єдина control plane + node transport для OpenClaw. Усі клієнти (CLI, веб-UI, застосунок macOS, iOS/Android nodes, headless nodes) підключаються через WebSocket і оголошують свою role + scope під час рукостискання.Транспорт
- WebSocket, текстові фрейми з JSON-повідомленнями.
- Першим фреймом має бути запит
connect.
Рукостискання (connect)
Gateway → Client (виклик до підключення):hello-ok також містить:
hello-ok.auth також може містити додаткові
обмежені записи ролей у deviceTokens:
scopes: [], а будь-який переданий токен operator залишається обмеженим
списком дозволів bootstrap operator (operator.approvals, operator.read,
operator.talk.secrets, operator.write). Перевірки scope для bootstrap
залишаються прив’язаними до префікса ролі: записи operator задовольняють лише запити operator, а ролям, що не є operator,
усе одно потрібні scopes під префіксом їхньої власної ролі.
Приклад node
Форматування фреймів
- Запит:
{type:"req", id, method, params} - Відповідь:
{type:"res", id, ok, payload|error} - Подія:
{type:"event", event, payload, seq?, stateVersion?}
Roles + scopes
Roles
operator= клієнт control plane (CLI/UI/автоматизація).node= хост можливостей (camera/screen/canvas/system.run).
Scopes (operator)
Поширені scopes:operator.readoperator.writeoperator.adminoperator.approvalsoperator.pairingoperator.talk.secrets
talk.config з includeSecrets: true потрібен operator.talk.secrets
(або operator.admin).
RPC-методи gateway, зареєстровані плагінами, можуть запитувати власний scope operator, але
зарезервовані префікси core admin (config.*, exec.approvals.*, wizard.*,
update.*) завжди зіставляються з operator.admin.
Scope методу — це лише перший рівень перевірки. Деякі slash-команди, до яких звертаються через
chat.send, додатково застосовують суворіші перевірки на рівні команд. Наприклад, постійні
записи /config set і /config unset потребують operator.admin.
node.pair.approve також має додаткову перевірку scope під час схвалення поверх
базового scope методу:
- запити без команд:
operator.pairing - запити з командами node, що не є exec:
operator.pairing+operator.write - запити, що включають
system.run,system.run.prepareабоsystem.which:operator.pairing+operator.admin
Caps/commands/permissions (node)
Nodes оголошують заявлені можливості під час підключення:caps: високорівневі категорії можливостей.commands: allowlist команд для invoke.permissions: детальні перемикачі (наприклад,screen.record,camera.capture).
Presence
system-presenceповертає записи, згруповані за ідентичністю пристрою.- Записи присутності містять
deviceId,rolesіscopes, щоб UI могли показувати один рядок на пристрій навіть коли він підключається і як operator, і як node.
Поширені сімейства RPC-методів
Ця сторінка не є згенерованим повним дампом, але публічна WS-поверхня ширша за наведені вище приклади рукостискання/автентифікації. Ось основні сімейства методів, які Gateway надає сьогодні.hello-ok.features.methods — це консервативний список виявлення, зібраний із
src/gateway/server-methods-list.ts плюс експортів методів завантажених плагінів/каналів.
Розглядайте його як механізм виявлення можливостей, а не як згенерований дамп кожного викликуваного helper,
реалізованого в src/gateway/server-methods/*.ts.
Система та ідентичність
healthповертає кешований або щойно перевірений знімок стану gateway.statusповертає зведення gateway у стилі/status; чутливі поля включаються лише для operator-клієнтів з admin scope.gateway.identity.getповертає ідентичність пристрою gateway, що використовується в relay та потоках pairing.system-presenceповертає поточний знімок присутності для підключених пристроїв operator/node.system-eventдодає системну подію та може оновлювати/транслювати контекст присутності.last-heartbeatповертає останню збережену heartbeat-подію.set-heartbeatsперемикає обробку heartbeat на gateway.
Моделі та використання
models.listповертає каталог моделей, дозволених у runtime.usage.statusповертає зведення вікон використання постачальників/залишку квоти.usage.costповертає агреговані зведення витрат за діапазон дат.doctor.memory.statusповертає готовність vector-memory / embedding для активного робочого простору агента за замовчуванням.sessions.usageповертає зведення використання по сесіях.sessions.usage.timeseriesповертає часовий ряд використання для однієї сесії.sessions.usage.logsповертає записи журналу використання для однієї сесії.
Канали та helper-и входу
channels.statusповертає зведення стану вбудованих і bundled каналів/плагінів.channels.logoutвиконує вихід із конкретного каналу/акаунта, якщо канал підтримує вихід.web.login.startзапускає потік входу за QR/вебом для поточного веб-провайдера каналу з підтримкою QR.web.login.waitочікує завершення цього потоку входу за QR/вебом і запускає канал у разі успіху.push.testнадсилає тестовий APNs push до зареєстрованого iOS node.voicewake.getповертає збережені тригери wake-word.voicewake.setоновлює тригери wake-word і транслює зміну.
Повідомлення та журнали
send— це прямий RPC outbound-delivery для надсилання в канал/акаунт/гілку поза chat runner.logs.tailповертає tail налаштованого файлового журналу gateway з cursor/limit і обмеженнями max-byte.
Talk і TTS
talk.configповертає ефективний payload конфігурації Talk;includeSecretsпотребуєoperator.talk.secrets(абоoperator.admin).talk.modeвстановлює/транслює поточний стан режиму Talk для клієнтів WebChat/Control UI.talk.speakсинтезує мовлення через активного постачальника мовлення Talk.tts.statusповертає стан увімкнення TTS, активного постачальника, резервних постачальників і стан конфігурації постачальника.tts.providersповертає видимий інвентар постачальників TTS.tts.enableіtts.disableперемикають стан налаштувань TTS.tts.setProviderоновлює бажаного постачальника TTS.tts.convertвиконує одноразове перетворення text-to-speech.
Секрети, конфігурація, оновлення та wizard
secrets.reloadповторно розв’язує активні SecretRef і замінює runtime-стан секретів лише за повного успіху.secrets.resolveрозв’язує призначення секретів для конкретного набору command/target.config.getповертає поточний знімок конфігурації та хеш.config.setзаписує валідований payload конфігурації.config.patchоб’єднує часткове оновлення конфігурації.config.applyперевіряє та замінює повний payload конфігурації.config.schemaповертає payload актуальної схеми конфігурації, який використовують Control UI і інструменти CLI: schema,uiHints, версію та метадані генерації, включно з метаданими схем plugin + channel, коли runtime може їх завантажити. Схема містить метадані полівtitle/description, отримані з тих самих підписів і довідкового тексту, що використовує UI, включно з вкладеними object, wildcard, array-item та гілками композиціїanyOf/oneOf/allOf, коли є відповідна документація поля.config.schema.lookupповертає payload пошуку в межах шляху для одного шляху конфігурації: нормалізований шлях, поверхневий вузол схеми, відповідний hint +hintPathта зведення безпосередніх дочірніх елементів для деталізації в UI/CLI.- Вузли схеми lookup зберігають орієнтовану на користувача документацію та поширені поля валідації:
title,description,type,enum,const,format,pattern, числові/рядкові/масивні/об’єктні межі та булеві прапорці, як-отadditionalProperties,deprecated,readOnly,writeOnly. - Зведення дочірніх елементів містять
key, нормалізованийpath,type,required,hasChildren, а також відповідніhint/hintPath.
- Вузли схеми lookup зберігають орієнтовану на користувача документацію та поширені поля валідації:
update.runзапускає потік оновлення gateway і планує перезапуск лише тоді, коли саме оновлення було успішним.wizard.start,wizard.next,wizard.statusіwizard.cancelнадають onboarding wizard через WS RPC.
Наявні основні сімейства
Helper-и агента та робочого простору
agents.listповертає налаштовані записи агентів.agents.create,agents.updateіagents.deleteкерують записами агентів і прив’язкою робочого простору.agents.files.list,agents.files.getіagents.files.setкерують файлами робочого простору bootstrap, доступними для агента.agent.identity.getповертає ефективну ідентичність помічника для агента або сесії.agent.waitочікує завершення запуску та повертає термінальний знімок, коли він доступний.
Керування сесіями
sessions.listповертає поточний індекс сесій.sessions.subscribeіsessions.unsubscribeперемикають підписки на події змін сесій для поточного WS-клієнта.sessions.messages.subscribeіsessions.messages.unsubscribeперемикають підписки на події транскрипту/повідомлень для однієї сесії.sessions.previewповертає обмежені попередні перегляди транскриптів для вказаних ключів сесій.sessions.resolveрозв’язує або канонізує ціль сесії.sessions.createстворює новий запис сесії.sessions.sendнадсилає повідомлення в наявну сесію.sessions.steer— це варіант переривання і перенаправлення для активної сесії.sessions.abortперериває активну роботу для сесії.sessions.patchоновлює метадані/перевизначення сесії.sessions.reset,sessions.deleteіsessions.compactвиконують обслуговування сесій.sessions.getповертає повний збережений рядок сесії.- виконання chat, як і раніше, використовує
chat.history,chat.send,chat.abortіchat.inject. chat.historyнормалізується для відображення для UI-клієнтів: вбудовані теги директив прибираються з видимого тексту, plain-text XML-повідомлення викликів інструментів (включно з<tool_call>...</tool_call>,<function_call>...</function_call>,<tool_calls>...</tool_calls>,<function_calls>...</function_calls>та обрізаними блоками викликів інструментів) і витіклі ASCII/full-width control tokens моделі видаляються, чисті рядки помічника з silent-token, такі як точніNO_REPLY/no_reply, опускаються, а надто великі рядки можуть бути замінені placeholder-ами.
Pairing пристроїв і токени пристроїв
device.pair.listповертає очікувальні та схвалені paired-пристрої.device.pair.approve,device.pair.rejectіdevice.pair.removeкерують записами pairing пристроїв.device.token.rotateобертає токен paired-пристрою в межах його схваленої ролі та дозволених scopes.device.token.revokeвідкликає токен paired-пристрою.
Pairing node, invoke і відкладена робота
node.pair.request,node.pair.list,node.pair.approve,node.pair.rejectіnode.pair.verifyохоплюють pairing node і bootstrap verification.node.listіnode.describeповертають стан відомих/підключених nodes.node.renameоновлює мітку paired node.node.invokeпересилає команду до підключеного node.node.invoke.resultповертає результат для запиту invoke.node.eventпереносить події, що походять від node, назад у gateway.node.canvas.capability.refreshоновлює токени canvas-capability з обмеженою областю дії.node.pending.pullіnode.pending.ack— це API черги для підключених nodes.node.pending.enqueueіnode.pending.drainкерують довговічною відкладеною роботою для offline/disconnected nodes.
Сімейства approvals
exec.approval.requestіexec.approval.resolveохоплюють одноразові запити approval для exec.exec.approval.waitDecisionочікує на одне pending approval для exec і повертає остаточне рішення (абоnullу разі тайм-ауту).exec.approvals.getіexec.approvals.setкерують знімками політики approvals для exec у gateway.exec.approvals.node.getіexec.approvals.node.setкерують локальною політикою approvals для exec у node через команди relay node.plugin.approval.request,plugin.approval.waitDecisionіplugin.approval.resolveохоплюють потоки approval, визначені плагінами.
Інші основні сімейства
- automation:
wakeпланує негайне або на наступний heartbeat введення тексту пробудженняcron.list,cron.status,cron.add,cron.update,cron.remove,cron.run,cron.runs
- skills/tools:
skills.*,tools.catalog,tools.effective
Поширені сімейства подій
chat: оновлення UI chat, такі якchat.inject, та інші події chat лише для транскрипту.session.messageіsession.tool: оновлення транскрипту/потоку подій для підписаної сесії.sessions.changed: змінився індекс сесій або їхні метадані.presence: оновлення знімка системної присутності.tick: періодична подія keepalive / liveness.health: оновлення знімка стану gateway.heartbeat: оновлення потоку heartbeat-подій.cron: подія зміни запуску/завдання cron.shutdown: сповіщення про вимкнення gateway.node.pair.requested/node.pair.resolved: життєвий цикл pairing node.node.invoke.request: трансляція запиту invoke node.device.pair.requested/device.pair.resolved: життєвий цикл paired-пристрою.voicewake.changed: змінено конфігурацію тригерів wake-word.exec.approval.requested/exec.approval.resolved: життєвий цикл approval для exec.plugin.approval.requested/plugin.approval.resolved: життєвий цикл approval плагіна.
Helper-методи node
- Nodes можуть викликати
skills.bins, щоб отримати поточний список виконуваних файлів skill для перевірок auto-allow.
Helper-методи operator
- Operators можуть викликати
tools.catalog(operator.read), щоб отримати runtime-каталог інструментів для агента. Відповідь містить згруповані інструменти та метадані походження:source:coreабоpluginpluginId: власник plugin, колиsource="plugin"optional: чи є інструмент plugin необов’язковим
- Operators можуть викликати
tools.effective(operator.read), щоб отримати runtime-ефективний інвентар інструментів для сесії.sessionKeyє обов’язковим.- Gateway виводить trusted runtime-контекст із сесії на боці сервера замість прийняття контексту auth або доставки, наданого викликачем.
- Відповідь обмежена сесією і відображає те, що активна розмова може використовувати просто зараз, включно з core, plugin і channel tools.
- Operators можуть викликати
skills.status(operator.read), щоб отримати видимий інвентар skills для агента.agentIdнеобов’язковий; не вказуйте його, щоб читати робочий простір агента за замовчуванням.- Відповідь містить eligibility, відсутні вимоги, перевірки конфігурації та санітизовані параметри встановлення без розкриття сирих значень секретів.
- Operators можуть викликати
skills.searchіskills.detail(operator.read) для метаданих виявлення ClawHub. - Operators можуть викликати
skills.install(operator.admin) у двох режимах:- Режим ClawHub:
{ source: "clawhub", slug, version?, force? }встановлює папку skill до каталогуskills/робочого простору агента за замовчуванням. - Режим інсталятора gateway:
{ name, installId, dangerouslyForceUnsafeInstall?, timeoutMs? }запускає оголошену діюmetadata.openclaw.installна хості gateway.
- Режим ClawHub:
- Operators можуть викликати
skills.update(operator.admin) у двох режимах:- Режим ClawHub оновлює один відстежуваний slug або всі відстежувані встановлення ClawHub у робочому просторі агента за замовчуванням.
- Режим Config патчить значення
skills.entries.<skillKey>, такі якenabled,apiKeyіenv.
Approvals для exec
- Коли запит exec потребує approval, gateway транслює
exec.approval.requested. - Клієнти operator завершують це викликом
exec.approval.resolve(потребує scopeoperator.approvals). - Для
host=nodeexec.approval.requestмає міститиsystemRunPlan(канонічніargv/cwd/rawCommand/метадані сесії). Запити безsystemRunPlanвідхиляються. - Після approval переслані виклики
node.invoke system.runповторно використовують цей канонічнийsystemRunPlanяк авторитетний контекст команди/cwd/сесії. - Якщо викликач змінює
command,rawCommand,cwd,agentIdабоsessionKeyміж prepare і фінальним затвердженим пересиланнямsystem.run, gateway відхиляє запуск замість довіри до зміненого payload.
Резервна доставка агента
- Запити
agentможуть включатиdeliver=true, щоб запросити outbound delivery. bestEffortDeliver=falseзберігає сувору поведінку: нерозв’язані або лише внутрішні цілі доставки повертаютьINVALID_REQUEST.bestEffortDeliver=trueдозволяє резервний перехід до виконання лише в межах сесії, коли неможливо визначити зовнішній маршрут доставки (наприклад, internal/webchat sessions або неоднозначні багатоканальні конфігурації).
Версіонування
PROTOCOL_VERSIONрозміщено вsrc/gateway/protocol/schema.ts.- Клієнти надсилають
minProtocol+maxProtocol; сервер відхиляє невідповідності. - Схеми + моделі генеруються з визначень TypeBox:
pnpm protocol:genpnpm protocol:gen:swiftpnpm protocol:check
Автентифікація
- Автентифікація gateway за спільним секретом використовує
connect.params.auth.tokenабоconnect.params.auth.passwordзалежно від налаштованого режиму auth. - Режими з передаванням ідентичності, як-от Tailscale Serve
(
gateway.auth.allowTailscale: true) або не-loopbackgateway.auth.mode: "trusted-proxy", задовольняють перевірку auth для connect через заголовки запиту замістьconnect.params.auth.*. - Режим приватного ingress
gateway.auth.mode: "none"повністю пропускає shared-secret connect auth; не відкривайте цей режим у публічному/ненадійному ingress. - Після pairing Gateway видає токен пристрою, обмежений роллю + scopes
підключення. Він повертається в
hello-ok.auth.deviceTokenі має зберігатися клієнтом для майбутніх підключень. - Клієнти мають зберігати основний
hello-ok.auth.deviceTokenпісля будь-якого успішного connect. - Повторне підключення з цим збереженим токеном пристрою також має повторно використовувати збережений схвалений набір scope для цього токена. Це зберігає вже наданий доступ на читання/перевірку/статус і не дає повторним підключенням непомітно звузитися до вужчого неявного admin-only scope.
- Звичайний пріоритет auth для connect: спочатку явний shared token/password, потім
явний
deviceToken, потім збережений токен для пристрою, потім bootstrap token. - Додаткові записи
hello-ok.auth.deviceTokens— це токени передавання bootstrap. Зберігайте їх лише тоді, коли connect використовував bootstrap auth на trusted transport, як-отwss://або loopback/local pairing. - Якщо клієнт передає явний
deviceTokenабо явніscopes, цей набір scopes, запитаний викликачем, залишається авторитетним; кешовані scopes повторно використовуються лише тоді, коли клієнт повторно використовує збережений токен для пристрою. - Токени пристрою можна обертати/відкликати через
device.token.rotateіdevice.token.revoke(потребує scopeoperator.pairing). - Видача/ротація токенів залишається обмеженою схваленим набором ролей, записаним у записі pairing цього пристрою; ротація токена не може розширити пристрій до ролі, яку ніколи не було надано під час схвалення pairing.
- Для paired-device token sessions керування пристроями обмежується самим пристроєм, якщо
викликач також не має
operator.admin: викликачі без admin можуть видаляти/відкликати/обертати лише власний запис пристрою. device.token.rotateтакож перевіряє запитаний набір scope operator щодо поточних scopes сесії викликача. Викликачі без admin не можуть обернути токен у ширший набір scope operator, ніж той, який вони вже мають.- Збої auth містять
error.details.codeплюс підказки для відновлення:error.details.canRetryWithDeviceToken(boolean)error.details.recommendedNextStep(retry_with_device_token,update_auth_configuration,update_auth_credentials,wait_then_retry,review_auth_configuration)
- Поведінка клієнта для
AUTH_TOKEN_MISMATCH:- Trusted-клієнти можуть виконати одну обмежену повторну спробу з кешованим токеном для пристрою.
- Якщо ця повторна спроба не вдається, клієнти мають припинити автоматичні цикли перепідключення та показати оператору вказівки щодо подальших дій.
Ідентичність пристрою + pairing
- Nodes мають включати стабільну ідентичність пристрою (
device.id), похідну від відбитка keypair. - Gateways видають токени на кожен пристрій + роль.
- Для нових
device.idпотрібні схвалення pairing, якщо не ввімкнено локальне авто-схвалення. - Авто-схвалення pairing зосереджене на прямих локальних loopback-підключеннях.
- OpenClaw також має вузький шлях self-connect для trusted shared-secret helper flows у локальному backend/container.
- Підключення з tailnet або LAN на тому самому хості все одно вважаються віддаленими для pairing і потребують схвалення.
- Усі WS-клієнти мають включати ідентичність
deviceпід часconnect(operator + node). Control UI може пропускати її лише в таких режимах:gateway.controlUi.allowInsecureAuth=trueдля сумісності з небезпечним HTTP лише на localhost.- успішна auth operator Control UI з
gateway.auth.mode: "trusted-proxy". gateway.controlUi.dangerouslyDisableDeviceAuth=true(аварійний режим, критичне зниження безпеки).
- Усі підключення мають підписувати наданий сервером nonce
connect.challenge.
Діагностика міграції auth пристрою
Для застарілих клієнтів, які все ще використовують поведінку підпису до challenge,connect тепер повертає
коди деталей DEVICE_AUTH_* у error.details.code зі стабільним error.details.reason.
Поширені збої міграції:
| Повідомлення | details.code | details.reason | Значення |
|---|---|---|---|
device nonce required | DEVICE_AUTH_NONCE_REQUIRED | device-nonce-missing | Клієнт не вказав device.nonce (або надіслав порожнє значення). |
device nonce mismatch | DEVICE_AUTH_NONCE_MISMATCH | device-nonce-mismatch | Клієнт підписав застарілим/неправильним nonce. |
device signature invalid | DEVICE_AUTH_SIGNATURE_INVALID | device-signature | Payload підпису не відповідає payload версії v2. |
device signature expired | DEVICE_AUTH_SIGNATURE_EXPIRED | device-signature-stale | Підписана часова позначка виходить за допустиме зміщення. |
device identity mismatch | DEVICE_AUTH_DEVICE_ID_MISMATCH | device-id-mismatch | device.id не відповідає відбитку публічного ключа. |
device public key invalid | DEVICE_AUTH_PUBLIC_KEY_INVALID | device-public-key | Не вдалося обробити формат/канонізацію публічного ключа. |
- Завжди очікуйте
connect.challenge. - Підписуйте payload v2, який містить nonce сервера.
- Надсилайте той самий nonce у
connect.params.device.nonce. - Бажаний payload підпису —
v3, який прив’язуєplatformіdeviceFamilyдодатково до полів device/client/role/scopes/token/nonce. - Застарілі підписи
v2залишаються прийнятними для сумісності, але прив’язка метаданих paired-пристрою все одно керує політикою команд під час повторного підключення.
TLS + pinning
- Для WS-підключень підтримується TLS.
- Клієнти можуть за бажанням прив’язувати відбиток сертифіката gateway (див. конфігурацію
gateway.tlsплюсgateway.remote.tlsFingerprintабо прапорець CLI--tls-fingerprint).
Обсяг
Цей протокол надає повний API gateway (status, channels, models, chat, agent, sessions, nodes, approvals тощо). Точна поверхня визначається схемами TypeBox уsrc/gateway/protocol/schema.ts.