Gateway
Gateway-Protokoll
Das Gateway-WS-Protokoll ist die einzige Steuerungsebene + Node-Transport für OpenClaw. Alle Clients (CLI, Web-UI, macOS-App, iOS/Android-Nodes, headless Nodes) verbinden sich per WebSocket und deklarieren ihre Rolle + ihren Geltungsbereich beim Handshake.
Transport
- WebSocket, Text-Frames mit JSON-Payloads.
- Der erste Frame muss eine
connect-Anfrage sein. - Pre-Connect-Frames sind auf 64 KiB begrenzt. Nach einem erfolgreichen Handshake sollten Clients
die Limits
hello-ok.policy.maxPayloadundhello-ok.policy.maxBufferedByteseinhalten. Bei aktivierter Diagnose erzeugen zu große eingehende Frames und langsame ausgehende Pufferpayload.large-Ereignisse, bevor der Gateway den betroffenen Frame schließt oder verwirft. Diese Ereignisse speichern Größen, Limits, Oberflächen und sichere Reason-Codes. Sie speichern nicht den Nachrichteninhalt, Attachment-Inhalte, den rohen Frame-Body, Tokens, Cookies oder Secret-Werte.
Handshake (connect)
Gateway → Client (Pre-Connect-Challenge):
{ "type": "event", "event": "connect.challenge", "payload": { "nonce": "…", "ts": 1737264000000 }}Client → Gateway:
{ "type": "req", "id": "…", "method": "connect", "params": { "minProtocol": 3, "maxProtocol": 4, "client": { "id": "cli", "version": "1.2.3", "platform": "macos", "mode": "operator" }, "role": "operator", "scopes": ["operator.read", "operator.write"], "caps": [], "commands": [], "permissions": {}, "auth": { "token": "…" }, "locale": "en-US", "userAgent": "openclaw-cli/1.2.3", "device": { "id": "device_fingerprint", "publicKey": "…", "signature": "…", "signedAt": 1737264000000, "nonce": "…" } }}Gateway → Client:
{ "type": "res", "id": "…", "ok": true, "payload": { "type": "hello-ok", "protocol": 4, "server": { "version": "…", "connId": "…" }, "features": { "methods": ["…"], "events": ["…"] }, "snapshot": { "…": "…" }, "auth": { "role": "operator", "scopes": ["operator.read", "operator.write"] }, "policy": { "maxPayload": 26214400, "maxBufferedBytes": 52428800, "tickIntervalMs": 15000 } }}Während der Gateway noch Start-Sidecars abschließt, kann die connect-Anfrage
einen erneut versuchbaren UNAVAILABLE-Fehler mit details.reason auf
"startup-sidecars" und retryAfterMs zurückgeben. Clients sollten diese Antwort
innerhalb ihres gesamten Verbindungsbudgets erneut versuchen, statt sie als terminalen
Handshake-Fehler anzuzeigen.
server, features, snapshot und policy sind alle vom Schema
(packages/gateway-protocol/src/schema/frames.ts) vorgeschrieben. auth ist ebenfalls erforderlich und meldet
die ausgehandelte Rolle bzw. die ausgehandelten Geltungsbereiche. pluginSurfaceUrls ist optional und ordnet Plugin-
Oberflächennamen wie canvas bereichsgebundenen gehosteten URLs zu.
Bereichsgebundene Plugin-Oberflächen-URLs können ablaufen. Nodes können
node.pluginSurface.refresh mit { "surface": "canvas" } aufrufen, um einen frischen
Eintrag in pluginSurfaceUrls zu erhalten. Das experimentelle Canvas-Plugin-Refactoring
unterstützt nicht den veralteten Kompatibilitätspfad canvasHostUrl, canvasCapability oder
node.canvas.capability.refresh; aktuelle native Clients und
Gateways müssen Plugin-Oberflächen verwenden.
Wenn kein Device-Token ausgestellt wird, meldet hello-ok.auth die ausgehandelten
Berechtigungen ohne Token-Felder:
{ "auth": { "role": "operator", "scopes": ["operator.read", "operator.write"] }}Vertrauenswürdige Same-Process-Backend-Clients (client.id: "gateway-client",
client.mode: "backend") dürfen device bei direkten Loopback-Verbindungen weglassen, wenn
sie sich mit dem gemeinsamen Gateway-Token/Passwort authentifizieren. Dieser Pfad ist
für interne Steuerungsebenen-RPCs reserviert und verhindert, dass veraltete CLI-/Device-Pairing-Baselines
lokale Backend-Arbeit wie Subagent-Sitzungsaktualisierungen blockieren. Remote-Clients,
Browser-Origin-Clients, Node-Clients und explizite Device-Token-/Device-Identity-
Clients verwenden weiterhin die normalen Pairing- und Scope-Upgrade-Prüfungen.
Wenn ein Device-Token ausgestellt wird, enthält hello-ok außerdem:
{ "auth": { "deviceToken": "…", "role": "operator", "scopes": ["operator.read", "operator.write"] }}Der integrierte QR-/Setup-Code-Bootstrap ist ein frischer mobiler Übergabepfad. Eine erfolgreiche Baseline-Setup-Code-Verbindung gibt ein primäres Node-Token plus ein begrenztes Operator-Token zurück:
{ "auth": { "deviceToken": "…", "role": "node", "scopes": [], "deviceTokens": [ { "deviceToken": "…", "role": "operator", "scopes": ["operator.approvals", "operator.read", "operator.talk.secrets", "operator.write"] } ] }}Die Operator-Übergabe ist bewusst begrenzt, damit das QR-Onboarding die
mobile Operator-Schleife starten und die native Einrichtung abschließen kann, ohne Pairing-
Mutations-Scopes oder operator.admin zu gewähren. Sie enthält operator.talk.secrets, damit der
native Client die nach dem Bootstrap benötigte Talk-Konfiguration lesen kann. Umfassenderer
Pairing- und Admin-Zugriff erfordert einen separaten genehmigten Operator-Pairing- oder Token-
Flow. Clients sollten
hello-ok.auth.deviceTokens nur dann persistieren,
wenn die Verbindung Bootstrap-Authentifizierung über vertrauenswürdigen Transport wie wss:// oder
Loopback-/lokales Pairing verwendet hat.
Node-Beispiel
{ "type": "req", "id": "…", "method": "connect", "params": { "minProtocol": 3, "maxProtocol": 4, "client": { "id": "ios-node", "version": "1.2.3", "platform": "ios", "mode": "node" }, "role": "node", "scopes": [], "caps": ["camera", "canvas", "screen", "location", "voice"], "commands": ["camera.snap", "canvas.navigate", "screen.record", "location.get"], "permissions": { "camera.capture": true, "screen.record": false }, "auth": { "token": "…" }, "locale": "en-US", "userAgent": "openclaw-ios/1.2.3", "device": { "id": "device_fingerprint", "publicKey": "…", "signature": "…", "signedAt": 1737264000000, "nonce": "…" } }}Framing
- Anfrage:
{type:"req", id, method, params} - Antwort:
{type:"res", id, ok, payload|error} - Ereignis:
{type:"event", event, payload, seq?, stateVersion?}
Methoden mit Seiteneffekten erfordern Idempotenzschlüssel (siehe Schema).
Rollen + Geltungsbereiche
Das vollständige Operator-Scope-Modell, Prüfungen zum Genehmigungszeitpunkt und die Semantik gemeinsamer Secrets finden Sie unter Operator-Scopes.
Rollen
operator= Client der Steuerungsebene (CLI/UI/Automatisierung).node= Capability-Host (Kamera/Bildschirm/Canvas/system.run).
Geltungsbereiche (Operator)
Gängige Geltungsbereiche:
operator.readoperator.writeoperator.adminoperator.approvalsoperator.pairingoperator.talk.secrets
talk.config mit includeSecrets: true erfordert operator.talk.secrets
(oder operator.admin).
Wenn Secrets enthalten sind, sollten Clients die aktive Zugangsdatenkonfiguration des Talk-Providers
aus talk.resolved.config.apiKey lesen; talk.providers.<id>.apiKey
bleibt quellförmig und kann ein SecretRef-Objekt oder ein redigierter String sein.
Von Plugins registrierte Gateway-RPC-Methoden können ihren eigenen Operator-Scope anfordern, aber
reservierte Core-Admin-Präfixe (config.*, exec.approvals.*, wizard.*,
update.*) werden immer zu operator.admin aufgelöst.
Der Methoden-Scope ist nur die erste Schranke. Einige über
chat.send erreichte Slash-Befehle wenden zusätzlich strengere Prüfungen auf Befehlsebene an. Beispielsweise erfordern persistente
/config set- und /config unset-Schreibvorgänge operator.admin.
node.pair.approve hat zusätzlich zum
Basis-Methoden-Scope eine weitere Scope-Prüfung zum Genehmigungszeitpunkt:
- Anfragen ohne Befehl:
operator.pairing - Anfragen mit Nicht-Exec-Node-Befehlen:
operator.pairing+operator.write - Anfragen, die
system.run,system.run.prepareodersystem.whichenthalten:operator.pairing+operator.admin
Caps/Befehle/Berechtigungen (Node)
Nodes deklarieren Capability-Ansprüche zum Verbindungszeitpunkt:
caps: übergeordnete Capability-Kategorien wiecamera,canvas,screen,location,voiceundtalk.commands: Befehls-Allowlist für Invoke.permissions: granulare Umschalter (z. B.screen.record,camera.capture).
Der Gateway behandelt diese als Ansprüche und erzwingt serverseitige Allowlists.
Präsenz
system-presencegibt Einträge zurück, die nach Device-Identität geschlüsselt sind.- Präsenzeinträge enthalten
deviceId,rolesundscopes, damit UIs eine einzelne Zeile pro Device anzeigen können, auch wenn es sowohl als operator als auch als node verbunden ist. node.listenthält optionale FelderlastSeenAtMsundlastSeenReason. Verbundene Nodes melden ihre aktuelle Verbindungszeit alslastSeenAtMsmit Reasonconnect; gekoppelte Nodes können außerdem dauerhafte Hintergrundpräsenz melden, wenn ein vertrauenswürdiges Node-Ereignis ihre Pairing-Metadaten aktualisiert.
Hintergrund-Alive-Ereignis für Nodes
Nodes können node.event mit event: "node.presence.alive" aufrufen, um aufzuzeichnen, dass ein gekoppelte Node
während eines Hintergrund-Weckvorgangs aktiv war, ohne ihn als verbunden zu markieren.
{ "event": "node.presence.alive", "payloadJSON": "{\"trigger\":\"silent_push\",\"sentAtMs\":1737264000000,\"displayName\":\"Peter's iPhone\",\"version\":\"2026.4.28\",\"platform\":\"iOS 18.4.0\",\"deviceFamily\":\"iPhone\",\"modelIdentifier\":\"iPhone17,1\",\"pushTransport\":\"relay\"}"}trigger ist ein geschlossenes Enum: background, silent_push, bg_app_refresh,
significant_location, manual oder connect. Unbekannte Trigger-Strings werden vom Gateway vor der Persistierung zu
background normalisiert. Das Ereignis ist nur für authentifizierte Node-
Device-Sitzungen dauerhaft; Device-lose oder nicht gekoppelte Sitzungen geben handled: false zurück.
Erfolgreiche Gateways geben ein strukturiertes Ergebnis zurück:
{ "ok": true, "event": "node.presence.alive", "handled": true, "reason": "persisted"}Ältere Gateways können für node.event weiterhin { "ok": true } zurückgeben; Clients sollten dies als
bestätigten RPC behandeln, nicht als dauerhafte Präsenzpersistierung.
Geltungsbereich für Broadcast-Ereignisse
Vom Server gepushte WebSocket-Broadcast-Ereignisse sind scope-gesteuert, damit Pairing-begrenzte oder Node-only-Sitzungen keine Sitzungsinhalte passiv empfangen.
- Chat-, Agent- und Tool-Ergebnis-Frames (einschließlich gestreamter
agent-Ereignisse und Tool-Aufrufergebnisse) erfordern mindestensoperator.read. Sitzungen ohneoperator.readüberspringen diese Frames vollständig. - Plugin-definierte
plugin.*-Broadcasts sind je nach Registrierung durch das Plugin aufoperator.writeoderoperator.adminbeschränkt. - Status- und Transportereignisse (
heartbeat,presence,tick, Connect-/Disconnect-Lebenszyklus usw.) bleiben uneingeschränkt, damit die Transportgesundheit für jede authentifizierte Sitzung beobachtbar bleibt. - Unbekannte Broadcast-Ereignisfamilien sind standardmäßig scope-gesteuert (fail-closed), sofern ein registrierter Handler sie nicht ausdrücklich lockert.
Jede Client-Verbindung behält ihre eigene Sequenznummer pro Client, sodass Broadcasts auf diesem Socket eine monotone Reihenfolge bewahren, auch wenn verschiedene Clients unterschiedliche scope-gefilterte Teilmengen des Ereignisstreams sehen.
Häufige RPC-Methodenfamilien
Die öffentliche WS-Oberfläche ist breiter als die obigen Handshake-/Auth-Beispiele. Dies
ist kein generierter Dump — hello-ok.features.methods ist eine konservative
Discovery-Liste, die aus src/gateway/server-methods-list.ts plus geladenen
Plugin-/Channel-Methodenexporten erstellt wird. Behandeln Sie sie als Feature Discovery, nicht als vollständige
Aufzählung von src/gateway/server-methods/*.ts.
System und Identität
healthgibt den zwischengespeicherten oder frisch geprüften Gateway-Health-Snapshot zurück.diagnostics.stabilitygibt den aktuellen, begrenzten Diagnosestabilitäts-Recorder zurück. Er speichert Betriebsmetadaten wie Ereignisnamen, Zählwerte, Bytegrößen, Speicherwerte, Warteschlangen-/Sitzungsstatus, Kanal-/Plugin-Namen und Sitzungs-IDs. Er speichert keine Chattexte, Webhook-Bodys, Tool-Ausgaben, rohen Anfrage- oder Antwort-Bodys, Tokens, Cookies oder geheimen Werte. Operator-Leseumfang ist erforderlich.statusgibt die Gateway-Zusammenfassung im Stil von/statuszurück; sensible Felder werden nur für Operator-Clients mit Admin-Umfang einbezogen.gateway.identity.getgibt die Gateway-Geräteidentität zurück, die von Relay- und Kopplungsabläufen verwendet wird.system-presencegibt den aktuellen Presence-Snapshot für verbundene Operator-/Node-Geräte zurück.system-eventhängt ein Systemereignis an und kann den Presence-Kontext aktualisieren/übertragen.last-heartbeatgibt das zuletzt persistierte Heartbeat-Ereignis zurück.set-heartbeatsschaltet die Heartbeat-Verarbeitung auf dem Gateway um.
Modelle und Nutzung
models.listgibt den zur Laufzeit erlaubten Modellkatalog zurück. Übergeben Sie{ "view": "configured" }für auswahlgeeignete konfigurierte Modelle (agents.defaults.modelszuerst, dannmodels.providers.*.models) oder{ "view": "all" }für den vollständigen Katalog.usage.statusgibt Nutzungsfenster und Zusammenfassungen des verbleibenden Kontingents pro Provider zurück.usage.costgibt aggregierte Kostennutzungs-Zusammenfassungen für einen Datumsbereich zurück. Übergeben SieagentIdfür einen Agenten oderagentScope: "all", um konfigurierte Agenten zu aggregieren.doctor.memory.statusgibt die Bereitschaft von Vektorspeicher / zwischengespeicherten Einbettungen für den aktiven Standard-Agenten-Arbeitsbereich zurück. Übergeben Sie{ "probe": true }oder{ "deep": true }nur, wenn der Aufrufer ausdrücklich einen Live-Ping an den Einbettungs-Provider möchte. Dreaming-fähige Clients können außerdem{ "agentId": "agent-id" }übergeben, um Statistiken des Dreaming-Speichers auf einen ausgewählten Agenten-Arbeitsbereich zu beschränken; wennagentIdweggelassen wird, bleibt der Fallback auf den Standard-Agenten erhalten und konfigurierte Dreaming-Arbeitsbereiche werden aggregiert.doctor.memory.dreamDiary,doctor.memory.backfillDreamDiary,doctor.memory.resetDreamDiary,doctor.memory.resetGroundedShortTerm,doctor.memory.repairDreamingArtifactsunddoctor.memory.dedupeDreamDiaryakzeptieren optionale Parameter{ "agentId": "agent-id" }für Dreaming-Ansichten/-Aktionen ausgewählter Agenten. WennagentIdweggelassen wird, arbeiten sie im konfigurierten Standard-Agenten-Arbeitsbereich.doctor.memory.remHarnessgibt eine begrenzte, schreibgeschützte REM-Harness-Vorschau für Remote-Control-Plane-Clients zurück. Sie kann Arbeitsbereichspfade, Speicherausschnitte, gerendertes Grounded-Markdown und Kandidaten für Deep Promotion enthalten, daher benötigen Aufruferoperator.read.sessions.usagegibt Nutzungszusammenfassungen pro Sitzung zurück. Übergeben SieagentIdfür einen Agenten oderagentScope: "all", um konfigurierte Agenten zusammen aufzulisten.sessions.usage.timeseriesgibt Zeitreihen-Nutzung für eine Sitzung zurück.sessions.usage.logsgibt Nutzungsprotokolleinträge für eine Sitzung zurück.
Kanäle und Login-Hilfen
channels.statusgibt Statuszusammenfassungen für integrierte + gebündelte Kanäle/Plugins zurück.channels.logoutmeldet einen bestimmten Kanal/ein bestimmtes Konto ab, sofern der Kanal Logout unterstützt.web.login.startstartet einen QR-/Web-Login-Flow für den aktuellen QR-fähigen Webkanal-Provider.web.login.waitwartet, bis dieser QR-/Web-Login-Flow abgeschlossen ist, und startet bei Erfolg den Kanal.push.testsendet einen Test-APNs-Push an einen registrierten iOS-Node.voicewake.getgibt die gespeicherten Aktivierungswort-Auslöser zurück.voicewake.setaktualisiert Aktivierungswort-Auslöser und sendet die Änderung.
Nachrichten und Protokolle
sendist der direkte RPC für ausgehende Zustellungen für kanal-, konto- und threadbezogene Sendungen außerhalb des Chat-Runners.logs.tailgibt den konfigurierten Gateway-Dateiprotokollauszug mit Cursor-/Limit- und Maximalbyte-Steuerung zurück.
Talk und TTS
talk.cataloggibt den schreibgeschützten Talk-Provider-Katalog für Sprache, Streaming-Transkription und Echtzeitstimme zurück. Er enthält kanonische Provider-IDs, Registry-Aliase, Beschriftungen, konfigurierten Zustand, ein optionalesready-Ergebnis auf Gruppenebene, offengelegte Modell-/Stimmen-IDs, kanonische Modi, Transporte, Brain-Strategien sowie Echtzeit-Audio-/Capability-Flags, ohne Provider-Geheimnisse zurückzugeben oder die globale Konfiguration zu ändern. Aktuelle Gateways setzenready, nachdem die Laufzeit-Provider-Auswahl angewendet wurde; Clients sollten das Fehlen dieses Werts zur Kompatibilität mit älteren Gateways als nicht verifiziert behandeln.talk.configgibt die effektive Talk-Konfigurationsnutzlast zurück;includeSecretserfordertoperator.talk.secrets(oderoperator.admin).talk.session.createerstellt eine vom Gateway verwaltete Talk-Sitzung fürrealtime/gateway-relay,transcription/gateway-relayoderstt-tts/managed-room. Fürstt-tts/managed-roommüssen Aufrufer mitoperator.write, diesessionKeyübergeben, auchspawnedByfür die bereichsgebundene Sichtbarkeit des Sitzungsschlüssels übergeben; die ungebundene Erstellung vonsessionKeyundbrain: "direct-tools"erfordernoperator.admin.talk.session.joinvalidiert ein Sitzungstoken für einen verwalteten Raum, gibt bei Bedarfsession.ready- odersession.replaced-Ereignisse aus und gibt Raum-/Sitzungsmetadaten sowie aktuelle Talk-Ereignisse ohne Klartexttoken oder gespeicherten Token-Hash zurück.talk.session.appendAudiohängt base64-codiertes PCM-Eingabeaudio an vom Gateway verwaltete Echtzeit-Relay- und Transkriptionssitzungen an.talk.session.startTurn,talk.session.endTurnundtalk.session.cancelTurnsteuern den Turn-Lebenszyklus eines verwalteten Raums mit Ablehnung veralteter Turns, bevor der Zustand gelöscht wird.talk.session.cancelOutputstoppt die Audioausgabe des Assistenten, hauptsächlich für VAD-gesteuertes Dazwischenreden in Gateway-Relay-Sitzungen.talk.session.submitToolResultschließt einen Provider-Tool-Aufruf ab, der von einer vom Gateway verwalteten Echtzeit-Relay-Sitzung ausgegeben wurde. Übergeben Sieoptions: { willContinue: true }für vorläufige Tool-Ausgabe, wenn ein finales Ergebnis folgt, oderoptions: { suppressResponse: true }, wenn das Tool-Ergebnis den Provider-Aufruf erfüllen soll, ohne eine weitere Echtzeit-Assistentenantwort zu starten.talk.session.steersendet Sprachsteuerung für einen aktiven Lauf an eine vom Gateway verwaltete, agentengestützte Talk-Sitzung. Akzeptiert wird{ sessionId, text, mode? }, wobeimodestatus,steer,canceloderfollowupist; ein ausgelassener Modus wird aus dem gesprochenen Text klassifiziert.talk.session.closeschließt eine vom Gateway verwaltete Relay-, Transkriptions- oder verwaltete-Raum-Sitzung und gibt terminale Talk-Ereignisse aus.talk.modesetzt/überträgt den aktuellen Talk-Moduszustand für WebChat-/Control-UI-Clients.talk.client.createerstellt eine clientverwaltete Echtzeit-Provider-Sitzung mitwebrtcoderprovider-websocket, während das Gateway Konfiguration, Zugangsdaten, Anweisungen und Tool-Richtlinie verwaltet.talk.client.toolCallermöglicht clientverwalteten Echtzeit-Transporten, Provider-Tool-Aufrufe an die Gateway-Richtlinie weiterzuleiten. Das erste unterstützte Tool istopenclaw_agent_consult; Clients erhalten eine Lauf-ID und warten auf normale Chat-Lebenszyklusereignisse, bevor sie das providerspezifische Tool-Ergebnis übermitteln.talk.client.steersendet Sprachsteuerung für einen aktiven Lauf bei clientverwalteten Echtzeit-Transporten. Das Gateway löst den aktiven eingebetteten Lauf aussessionKeyauf und gibt statt stillschweigendem Verwerfen der Steuerung ein strukturiertes akzeptiert/abgelehnt-Ergebnis zurück.talk.eventist der einzelne Talk-Ereigniskanal für Echtzeit-, Transkriptions-, STT/TTS-, verwaltete-Raum-, Telefonie- und Meeting-Adapter.talk.speaksynthetisiert Sprache über den aktiven Talk-Sprach-Provider.tts.statusgibt den aktivierten TTS-Zustand, den aktiven Provider, Fallback-Provider und den Zustand der Provider-Konfiguration zurück.tts.providersgibt den sichtbaren TTS-Provider-Bestand zurück.tts.enableundtts.disableschalten den TTS-Einstellungszustand um.tts.setProvideraktualisiert den bevorzugten TTS-Provider.tts.convertführt eine einmalige Text-zu-Sprache-Konvertierung aus.
Geheimnisse, Konfiguration, Aktualisierung und Assistent
secrets.reloadlöst aktive SecretRefs erneut auf und tauscht den Laufzeit-Geheimniszustand nur bei vollständigem Erfolg aus.secrets.resolvelöst befehlszielbezogene Geheimniszuweisungen für einen bestimmten Befehls-/Zielsatz auf.config.getgibt den aktuellen Konfigurations-Snapshot und Hash zurück.config.setschreibt eine validierte Konfigurationsnutzlast.config.patchführt eine teilweise Konfigurationsaktualisierung zusammen. Destruktive Array- Ersetzung erfordert den betroffenen Pfad inreplacePaths; verschachtelte Arrays unter Array-Einträgen verwenden[]-Pfade wieagents.list[].skills.config.applyvalidiert + ersetzt die vollständige Konfigurationsnutzlast.config.schemagibt die Live-Konfigurationsschemanutzlast zurück, die von Control UI und CLI-Werkzeugen verwendet wird: Schema,uiHints, Version und Generierungsmetadaten, einschließlich Plugin- und Kanalschemametadaten, wenn die Laufzeit sie laden kann. Das Schema enthält Feldmetadatentitle/description, die aus denselben Beschriftungen und Hilfetexten abgeleitet sind, die von der UI verwendet werden, einschließlich verschachtelter Objekt-, Platzhalter-, Array-Element- undanyOf- /oneOf- /allOf-Kompositionszweige, wenn passende Felddokumentation vorhanden ist.config.schema.lookupgibt eine pfadbezogene Lookup-Nutzlast für einen Konfigurationspfad zurück: normalisierter Pfad, ein flacher Schemaknoten, passender Hinweis +hintPath, optionalesreloadKindund unmittelbare Kindzusammenfassungen für UI-/CLI-Drill-down.reloadKindist eines vonrestart,hotodernoneund spiegelt den Gateway-Konfigurations-Neuladeplaner für den angeforderten Pfad wider. Lookup-Schemaknoten behalten die nutzerseitige Dokumentation und gängige Validierungsfelder (title,description,type,enum,const,format,pattern, numerische/String-/Array-/Objektgrenzen und Flags wieadditionalProperties,deprecated,readOnly,writeOnly). Kindzusammenfassungen stellenkey, den normalisiertenpath,type,required,hasChildren, optionalesreloadKindsowie den passendenhint/hintPathbereit.update.runführt den Gateway-Aktualisierungsablauf aus und plant einen Neustart nur, wenn die Aktualisierung selbst erfolgreich war; Aufrufer mit einer Sitzung könnencontinuationMessageeinschließen, damit der Start einen Folge-Agenten-Turn über die Neustart-Fortsetzungswarteschlange fortsetzt. Paketmanager-Aktualisierungen und überwachte Git-Checkout-Aktualisierungen aus der Steuerungsebene verwenden eine getrennte Übergabe an einen verwalteten Dienst, statt den Paketbaum zu ersetzen oder Checkout-/Build-Ausgaben innerhalb des laufenden Gateways zu verändern. Eine gestartete Übergabe gibtok: truemitresult.reason: "managed-service-handoff-started"undhandoff.status: "started"zurück; nicht verfügbare oder fehlgeschlagene Übergaben gebenok: falsemitmanaged-service-handoff-unavailableodermanaged-service-handoff-failedsowiehandoff.commandzurück, wenn eine manuelle Shell-Aktualisierung erforderlich ist. Eine nicht verfügbare Übergabe bedeutet, dass OpenClaw keine sichere Supervisor-Grenze oder dauerhafte Dienstidentität hat, etwaOPENCLAW_SYSTEMD_UNITfür systemd. Während einer gestarteten Übergabe kann der Neustart-Sentinel kurzstats.reason: "restart-health-pending"melden; die Fortsetzung wird verzögert, bis die CLI das neu gestartete Gateway verifiziert und den finalenok-Sentinel schreibt.update.statusaktualisiert den neuesten Neustart-Sentinel der Aktualisierung und gibt ihn zurück, einschließlich der nach dem Neustart laufenden Version, sofern verfügbar.wizard.start,wizard.next,wizard.statusundwizard.cancelstellen den Onboarding-Assistenten über WS RPC bereit.
Agenten- und Arbeitsbereichshelfer
agents.listgibt konfigurierte Agenteneinträge zurück, einschließlich effektivem Modell und Laufzeitmetadaten.agents.create,agents.updateundagents.deleteverwalten Agentendatensätze und Arbeitsbereichsverdrahtung.agents.files.list,agents.files.getundagents.files.setverwalten die Bootstrap-Arbeitsbereichsdateien, die für einen Agenten offengelegt werden.tasks.list,tasks.getundtasks.cancelstellen das Gateway-Aufgabenbuch für SDK- und Operator-Clients bereit.artifacts.list,artifacts.getundartifacts.downloadstellen aus Transkripten abgeleitete Artefaktzusammenfassungen und Downloads für einen expliziten ScopesessionKey,runIdodertaskIdbereit. Run- und Aufgabenabfragen lösen die besitzende Sitzung serverseitig auf und geben nur Transkriptmedien mit passender Herkunft zurück; unsichere oder lokale URL-Quellen geben nicht unterstützte Downloads zurück, statt serverseitig abgerufen zu werden.environments.listundenvironments.statusstellen schreibgeschützte Gateway-lokale und Node-Umgebungserkennung für SDK-Clients bereit.agent.identity.getgibt die effektive Assistentenidentität für einen Agenten oder eine Sitzung zurück.agent.waitwartet, bis ein Run beendet ist, und gibt den terminalen Snapshot zurück, sofern verfügbar.
Sitzungssteuerung
sessions.listgibt den aktuellen Sitzungsindex zurück, einschließlichagentRuntime-Metadaten pro Zeile, wenn ein Agentenlaufzeit-Backend konfiguriert ist.sessions.subscribeundsessions.unsubscribeschalten Sitzungsänderungs-Ereignisabonnements für den aktuellen WS-Client um.sessions.messages.subscribeundsessions.messages.unsubscribeschalten Transkript-/Nachrichten-Ereignisabonnements für eine Sitzung um.sessions.previewgibt begrenzte Transkriptvorschauen für bestimmte Sitzungsschlüssel zurück.sessions.describegibt eine Gateway-Sitzungszeile für einen exakten Sitzungsschlüssel zurück.sessions.resolvelöst ein Sitzungsziel auf oder kanonisiert es.sessions.createerstellt einen neuen Sitzungseintrag.sessions.sendsendet eine Nachricht in eine vorhandene Sitzung.sessions.steerist die Unterbrechen-und-Steuern-Variante für eine aktive Sitzung.sessions.abortbricht aktive Arbeit für eine Sitzung ab. Ein Aufrufer kannkeyplus optionalrunIdübergeben oder nurrunIdfür aktive Runs übergeben, die das Gateway zu einer Sitzung auflösen kann.sessions.patchaktualisiert Sitzungsmetadaten/-Overrides und meldet das aufgelöste kanonische Modell plus effektiveagentRuntime.sessions.reset,sessions.deleteundsessions.compactführen Sitzungswartung aus.sessions.getgibt die vollständige gespeicherte Sitzungszeile zurück.- Die Chat-Ausführung verwendet weiterhin
chat.history,chat.send,chat.abortundchat.inject.chat.historyist für UI-Clients anzeige-normalisiert: Inline-Direktiv-Tags werden aus sichtbarem Text entfernt, Nur-Text-XML-Nutzdaten für Tool-Aufrufe (einschließlich<tool_call>...</tool_call>,<function_call>...</function_call>,<tool_calls>...</tool_calls>,<function_calls>...</function_calls>und gekürzter Tool-Aufrufblöcke) sowie durchgesickerte ASCII-/Vollbreiten-Modellsteuerungstoken werden entfernt, reine Assistant-Zeilen mit stillen Token wie exaktNO_REPLY/no_replywerden ausgelassen, und übergroße Zeilen können durch Platzhalter ersetzt werden. chat.message.getist der additive begrenzte Vollnachrichten-Reader für einen einzelnen sichtbaren Transkripteintrag. Clients übergebensessionKey, optionalagentId, wenn die Sitzungsauswahl agentenbezogen ist, plus eine Transkript-messageId, die zuvor überchat.historybereitgestellt wurde, und das Gateway gibt dieselbe anzeige-normalisierte Projektion ohne die leichte Kürzungsgrenze der Historie zurück, wenn der gespeicherte Eintrag noch verfügbar und nicht übergroß ist.chat.sendakzeptiert für einen einzelnen TurnfastMode: "auto", um den Schnellmodus für Modellaufrufe zu verwenden, die vor dem automatischen Grenzwert gestartet wurden, und danach spätere Wiederholungs-, Fallback-, Tool-Ergebnis- oder Fortsetzungsaufrufe ohne Schnellmodus zu starten. Der Grenzwert ist standardmäßig 60 Sekunden und kann pro Modell mitagents.defaults.models["<provider>/<model>"].params.fastAutoOnSecondskonfiguriert werden. Einchat.send-Aufrufer kann für einen einzelnen TurnfastAutoOnSecondsübergeben, um den Grenzwert für diese Anfrage zu überschreiben.
Gerätekopplung und Gerätetoken
device.pair.listgibt ausstehende und genehmigte gekoppelte Geräte zurück.device.pair.setupCodeerstellt einen mobilen Einrichtungscode und standardmäßig eine PNG-QR-Daten-URL. Es erfordertoperator.adminund wird absichtlich aus der angekündigten Erkennung ausgelassen. Das Ergebnis enthältsetupCode, optionalqrDataUrl,gatewayUrl, das nicht geheimeauth-Label undurlSource.device.pair.approve,device.pair.rejectunddevice.pair.removeverwalten Gerätekopplungsdatensätze.device.token.rotaterotiert ein gekoppeltes Gerätetoken innerhalb der Grenzen seiner genehmigten Rolle und des Aufrufer-Scopes.device.token.revokewiderruft ein gekoppeltes Gerätetoken innerhalb der Grenzen seiner genehmigten Rolle und des Aufrufer-Scopes.
Der Einrichtungscode bettet eine kurzlebige Bootstrap-Anmeldeinformation ein. Clients dürfen sie nicht über den Kopplungsablauf hinaus protokollieren oder dauerhaft speichern.
Node-Kopplung, Aufruf und ausstehende Arbeit
node.pair.request,node.pair.list,node.pair.approve,node.pair.reject,node.pair.removeundnode.pair.verifydecken Node-Kopplung und Bootstrap-Verifizierung ab.node.listundnode.describegeben den bekannten/verbundenen Node-Zustand zurück.node.renameaktualisiert ein gekoppeltes Node-Label.node.invokeleitet einen Befehl an einen verbundenen Node weiter.node.invoke.resultgibt das Ergebnis für eine Aufrufanfrage zurück.node.eventträgt von Nodes ausgehende Ereignisse zurück in das Gateway.node.pending.pullundnode.pending.acksind die Warteschlangen-APIs für verbundene Nodes.node.pending.enqueueundnode.pending.drainverwalten dauerhafte ausstehende Arbeit für Offline-/getrennte Nodes.
Genehmigungsfamilien
exec.approval.request,exec.approval.get,exec.approval.listundexec.approval.resolvedecken einmalige Exec-Genehmigungsanfragen plus Suche/Wiedergabe ausstehender Genehmigungen ab.exec.approval.waitDecisionwartet auf eine ausstehende Exec-Genehmigung und gibt die endgültige Entscheidung zurück (odernullbei Timeout).exec.approvals.getundexec.approvals.setverwalten Snapshots der Gateway-Exec-Genehmigungsrichtlinie.exec.approvals.node.getundexec.approvals.node.setverwalten die Node-lokale Exec-Genehmigungsrichtlinie über Node-Relay-Befehle.plugin.approval.request,plugin.approval.list,plugin.approval.waitDecisionundplugin.approval.resolvedecken Plugin-definierte Genehmigungsabläufe ab.
Automatisierung, Skills und Tools
- Automatisierung:
wakeplant eine sofortige oder beim nächsten Heartbeat erfolgende Wake-Texteinfügung;cron.get,cron.list,cron.status,cron.add,cron.update,cron.remove,cron.run,cron.runsverwalten geplante Arbeit. cron.runbleibt ein RPC im Enqueue-Stil für manuelle Runs. Clients, die Abschlusssemantik benötigen, sollten die zurückgegebenerunIdlesen undcron.runsabfragen.cron.runsakzeptiert einen optionalen nicht leerenrunId-Filter, damit Clients einem in die Warteschlange gestellten manuellen Run folgen können, ohne mit anderen Historieneinträgen für denselben Job zu konkurrieren.- Skills und Tools:
commands.list,skills.*,tools.catalog,tools.effective,tools.invoke.
Häufige Ereignisfamilien
chat: UI-Chat-Updates wiechat.injectund andere reine Transkript-Chat- Ereignisse. In Protokoll v4 tragen Delta-NutzdatendeltaText;messagebleibt der kumulative Assistant-Snapshot. Nicht-Präfix-Ersetzungen setzenreplace=trueund verwendendeltaTextals Ersetzungstext.session.message,session.operationundsession.tool: Transkript-, laufende Sitzungsoperation- und Ereignisstrom-Updates für eine abonnierte Sitzung.sessions.changed: Sitzungsindex oder Metadaten wurden geändert.presence: Aktualisierungen des System-Präsenz-Snapshots.tick: periodisches Keepalive-/Liveness-Ereignis.health: Aktualisierung des Gateway-Health-Snapshots.heartbeat: Aktualisierung des Heartbeat-Ereignisstroms.cron: Cron-Run-/Job-Änderungsereignis.shutdown: Gateway-Herunterfahrbenachrichtigung.node.pair.requested/node.pair.resolved: Node-Kopplungslebenszyklus.node.invoke.request: Broadcast einer Node-Aufrufanfrage.device.pair.requested/device.pair.resolved: Lebenszyklus gekoppelter Geräte.voicewake.changed: Wake-Word-Trigger-Konfiguration geändert.exec.approval.requested/exec.approval.resolved: Exec-Genehmigungs- lebenszyklus.plugin.approval.requested/plugin.approval.resolved: Plugin-Genehmigungs- lebenszyklus.
Node-Hilfsmethoden
- Nodes können
skills.binsaufrufen, um die aktuelle Liste der Skill-Executables für Auto-Allow-Prüfungen abzurufen.
Aufgabenbuch-RPCs
Operator-Clients können Gateway-Hintergrundaufgabendatensätze über die Aufgabenbuch-RPCs prüfen und abbrechen. Diese Methoden geben bereinigte Aufgabenzusammenfassungen zurück, keinen rohen Laufzeitzustand.
tasks.listerfordertoperator.read.- Parameter: optional
status("queued","running","completed","failed","cancelled"oder"timed_out") oder ein Array dieser Statuswerte, optionalagentId, optionalsessionKey, optionallimitvon1bis500und optionaler Stringcursor. - Ergebnis:
{ "tasks": TaskSummary[], "nextCursor"?: string }.
- Parameter: optional
tasks.geterfordertoperator.read.- Parameter:
{ "taskId": string }. - Ergebnis:
{ "task": TaskSummary }. - Fehlende Aufgaben-IDs geben die Gateway-Not-found-Fehlerform zurück.
- Parameter:
tasks.cancelerfordertoperator.write.- Parameter:
{ "taskId": string, "reason"?: string }. - Ergebnis:
{ "found": boolean, "cancelled": boolean, "reason"?: string, "task"?: TaskSummary }. foundmeldet, ob das Aufgabenbuch eine passende Aufgabe enthielt.cancelledmeldet, ob die Laufzeit den Abbruch akzeptiert oder aufgezeichnet hat.
- Parameter:
TaskSummary enthält id, status und optionale Metadaten wie kind,
runtime, title, agentId, sessionKey, childSessionKey, ownerKey,
runId, taskId, flowId, parentTaskId, sourceId, Zeitstempel, Fortschritt,
terminale Zusammenfassung und bereinigten Fehlertext. agentId identifiziert den Agenten,
der die Aufgabe ausführt; sessionKey und ownerKey bewahren Anfragesteller- und Steuerungs-
kontext.
Operator-Hilfsmethoden
- Operatoren können
commands.list(operator.read) aufrufen, um das Laufzeit- Befehlsinventar für einen Agenten abzurufen.agentIdist optional; lassen Sie es weg, um den Standard-Agent-Arbeitsbereich zu lesen.scopesteuert, welche Oberfläche das primärenameadressiert:textgibt das primäre Textbefehlstoken ohne führendes/zurücknativeund der Standardpfadbothgeben Provider-bewusste native Namen zurück, wenn verfügbar
textAliasesenthält exakte Slash-Aliasse wie/modelund/m.nativeNameenthält den Provider-bewussten nativen Befehlsnamen, wenn einer existiert.providerist optional und wirkt sich nur auf native Benennung sowie native Plugin- Befehlsverfügbarkeit aus.includeArgs=falselässt serialisierte Argumentmetadaten in der Antwort weg.
- Operatoren können
tools.catalog(operator.read) aufrufen, um den Laufzeit-Tool-Katalog für einen Agenten abzurufen. Die Antwort enthält gruppierte Tools und Herkunftsmetadaten:source:coreoderpluginpluginId: Plugin-Eigentümer, wennsource="plugin"optional: ob ein Plugin-Tool optional ist
- Operatoren können
tools.effective(operator.read) aufrufen, um das zur Laufzeit wirksame Tool- Inventar für eine Sitzung abzurufen.sessionKeyist erforderlich.- Das Gateway leitet vertrauenswürdigen Laufzeitkontext serverseitig aus der Sitzung ab, statt vom Aufrufer bereitgestellten Authentifizierungs- oder Zustellungskontext zu akzeptieren.
- Die Antwort ist eine sitzungsbezogene, serverseitig abgeleitete Projektion des aktiven Inventars, einschließlich Core-, Plugin-, Channel- und bereits entdeckter MCP-Server-Tools.
tools.effectiveist für MCP schreibgeschützt: Es kann einen warmen Sitzungs-MCP-Katalog durch die finale Tool-Richtlinie projizieren, erstellt aber keine MCP-Laufzeiten, verbindet keine Transports und gibt keintools/listaus. Wenn kein passender warmer Katalog existiert, kann die Antwort einen Hinweis wiemcp-not-yet-connected,mcp-not-yet-listedodermcp-stale-catalogenthalten.- Wirksame Tool-Einträge verwenden
source="core",source="plugin",source="channel"odersource="mcp".
- Operatoren können
tools.invoke(operator.write) aufrufen, um ein verfügbares Tool über denselben Gateway-Richtlinienpfad wie/tools/invokeaufzurufen.nameist erforderlich.args,sessionKey,agentId,confirmundidempotencyKeysind optional.- Wenn sowohl
sessionKeyals auchagentIdvorhanden sind, muss der aufgelöste Sitzungsagent mitagentIdübereinstimmen. - Nur Eigentümern vorbehaltene Core-Wrapper wie
cron,gatewayundnodeserfordern Eigentümer-/Admin-Identität (operator.admin), obwohl die Methodetools.invokeselbstoperator.writeist. - Die Antwort ist ein SDK-seitiger Umschlag mit
ok,toolName, optionalemoutputund typisiertenerror-Feldern. Genehmigungs- oder Richtlinienablehnungen gebenok:falsein der Nutzlast zurück, statt die Gateway-Tool-Richtlinienpipeline zu umgehen.
- Operatoren können
skills.status(operator.read) aufrufen, um das sichtbare Skill-Inventar für einen Agenten abzurufen.agentIdist optional; lassen Sie es weg, um den Standard-Agent-Arbeitsbereich zu lesen.- Die Antwort enthält Berechtigung, fehlende Anforderungen, Konfigurationsprüfungen und bereinigte Installationsoptionen, ohne rohe Secret-Werte offenzulegen.
- Operatoren können
skills.searchundskills.detail(operator.read) für ClawHub-Entdeckungsmetadaten aufrufen. - Operatoren können
skills.upload.begin,skills.upload.chunkundskills.upload.commit(operator.admin) aufrufen, um ein privates Skill-Archiv vor der Installation bereitzustellen. Dies ist ein separater Admin-Uploadpfad für vertrauenswürdige Clients, nicht der normale ClawHub-Skill-Installationsfluss, und standardmäßig deaktiviert, sofernskills.install.allowUploadedArchivesnicht aktiviert ist.skills.upload.begin({ kind: "skill-archive", slug, sizeBytes, sha256?, force?, idempotencyKey? })erstellt einen Upload, der an diesen Slug und Force-Wert gebunden ist.skills.upload.chunk({ uploadId, offset, dataBase64 })hängt Bytes am exakt dekodierten Offset an.skills.upload.commit({ uploadId, sha256? })verifiziert die endgültige Größe und SHA-256. Commit finalisiert nur den Upload; es installiert den Skill nicht.- Hochgeladene Skill-Archive sind Zip-Archive, die ein
SKILL.md-Root enthalten. Der interne Verzeichnisname des Archivs wählt niemals das Installationsziel aus.
- Operatoren können
skills.install(operator.admin) in drei Modi aufrufen:- ClawHub-Modus:
{ source: "clawhub", slug, version?, force? }installiert einen Skill-Ordner in dasskills/-Verzeichnis des Standard-Agent-Arbeitsbereichs. - Upload-Modus:
{ source: "upload", uploadId, slug, force?, sha256?, timeoutMs? }installiert einen committeten Upload in das Verzeichnisskills/<slug>des Standard-Agent-Arbeitsbereichs. Der Slug und der Force-Wert müssen mit der ursprünglichenskills.upload.begin-Anfrage übereinstimmen. Dieser Modus wird abgelehnt, sofernskills.install.allowUploadedArchivesnicht aktiviert ist. Die Einstellung wirkt sich nicht auf ClawHub-Installationen aus. - Gateway-Installationsmodus:
{ name, installId, timeoutMs? }führt eine deklariertemetadata.openclaw.install-Aktion auf dem Gateway-Host aus. Ältere Clients können weiterhindangerouslyForceUnsafeInstallsenden; dieses Feld ist veraltet, wird nur aus Protokollkompatibilität akzeptiert und ignoriert. Verwenden Siesecurity.installPolicyfür operatorgesteuerte Installationsentscheidungen.
- ClawHub-Modus:
- Operatoren können
skills.update(operator.admin) in zwei Modi aufrufen:- Der ClawHub-Modus aktualisiert einen verfolgten Slug oder alle verfolgten ClawHub-Installationen im Standard-Agent-Arbeitsbereich.
- Der Konfigurationsmodus patcht
skills.entries.<skillKey>-Werte wieenabled,apiKeyundenv.
models.list-Ansichten
models.list akzeptiert einen optionalen Parameter view:
- Weggelassen oder
"default": aktuelles Laufzeitverhalten. Wennagents.defaults.modelskonfiguriert ist, ist die Antwort der erlaubte Katalog, einschließlich dynamisch entdeckter Modelle fürprovider/*-Einträge. Andernfalls ist die Antwort der vollständige Gateway-Katalog. "configured": Verhalten in Picker-Größe. Wennagents.defaults.modelskonfiguriert ist, hat es weiterhin Vorrang, einschließlich providerbezogener Entdeckung fürprovider/*-Einträge. Ohne Allowlist verwendet die Antwort explizitemodels.providers.*.models-Einträge und fällt nur dann auf den vollständigen Katalog zurück, wenn keine konfigurierten Modellzeilen existieren."all": vollständiger Gateway-Katalog, unter Umgehung vonagents.defaults.models. Verwenden Sie dies für Diagnose- und Entdeckungs-UIs, nicht für normale Modell-Picker.
Exec-Genehmigungen
- Wenn eine Exec-Anfrage Genehmigung benötigt, broadcastet das Gateway
exec.approval.requested. - Operator-Clients lösen dies durch Aufruf von
exec.approval.resolveauf (erfordert den Scopeoperator.approvals). - Für
host=nodemussexec.approval.requestsystemRunPlanenthalten (kanonischeargv/cwd/rawCommand/Sitzungsmetadaten). Anfragen ohnesystemRunPlanwerden abgelehnt. - Nach der Genehmigung verwenden weitergeleitete
node.invoke system.run-Aufrufe diesen kanonischensystemRunPlanals autoritativen Befehls-/cwd-/Sitzungskontext wieder. - Wenn ein Aufrufer
command,rawCommand,cwd,agentIdodersessionKeyzwischen Vorbereitung und der final genehmigtensystem.run-Weiterleitung mutiert, lehnt das Gateway den Lauf ab, statt der mutierten Nutzlast zu vertrauen.
Fallback für Agent-Zustellung
agent-Anfragen könnendeliver=trueenthalten, um ausgehende Zustellung anzufordern.bestEffortDeliver=falsebehält striktes Verhalten bei: nicht auflösbare oder nur interne Zustellungsziele gebenINVALID_REQUESTzurück.bestEffortDeliver=trueerlaubt Fallback auf reine Sitzungsausführung, wenn keine extern zustellbare Route aufgelöst werden kann (zum Beispiel interne/Webchat-Sitzungen oder mehrdeutige Mehrkanal-Konfigurationen).- Finale
agent-Ergebnisse könnenresult.deliveryStatusenthalten, wenn Zustellung angefordert wurde, mit denselben Statuswertensent,suppressed,partial_failedundfailed, die füropenclaw agent --json --deliverdokumentiert sind.
Versionierung
PROTOCOL_VERSIONbefindet sich inpackages/gateway-protocol/src/version.ts.- Clients senden
minProtocol+maxProtocol; der Server lehnt Bereiche ab, die sein aktuelles Protokoll nicht enthalten. Aktuelle Clients und Server erfordern Protokoll v4. - Schemas + Modelle werden aus TypeBox-Definitionen generiert:
pnpm protocol:genpnpm protocol:gen:swiftpnpm protocol:check
Client-Konstanten
Der Referenzclient in src/gateway/client.ts verwendet diese Standardwerte. Werte sind
über Protokoll v4 hinweg stabil und bilden die erwartete Baseline für Drittanbieter-Clients.
| Konstante | Standardwert | Quelle |
|---|---|---|
PROTOCOL_VERSION |
4 |
packages/gateway-protocol/src/version.ts |
MIN_CLIENT_PROTOCOL_VERSION |
4 |
packages/gateway-protocol/src/version.ts |
| Anfrage-Timeout (pro RPC) | 30_000 ms |
src/gateway/client.ts (requestTimeoutMs) |
| Preauth-/Connect-Challenge-Timeout | 15_000 ms |
src/gateway/handshake-timeouts.ts (Konfig./Env kann das gekoppelte Server-/Client-Budget erhöhen) |
| Initialer Reconnect-Backoff | 1_000 ms |
src/gateway/client.ts (backoffMs) |
| Maximaler Reconnect-Backoff | 30_000 ms |
src/gateway/client.ts (scheduleReconnect) |
| Fast-Retry-Begrenzung nach Device-Token-Schließen | 250 ms |
src/gateway/client.ts |
Force-Stop-Nachfrist vor terminate() |
250 ms |
FORCE_STOP_TERMINATE_GRACE_MS |
Standard-Timeout von stopAndWait() |
1_000 ms |
STOP_AND_WAIT_TIMEOUT_MS |
Standard-Tick-Intervall (vor hello-ok) |
30_000 ms |
src/gateway/client.ts |
| Schließen bei Tick-Timeout | Code 4000, wenn Stille tickIntervalMs * 2 überschreitet |
src/gateway/client.ts |
MAX_PAYLOAD_BYTES |
25 * 1024 * 1024 (25 MB) |
src/gateway/server-constants.ts |
Der Server kündigt das effektive policy.tickIntervalMs, policy.maxPayload
und policy.maxBufferedBytes in hello-ok an; Clients sollten diese Werte
statt der Standardwerte vor dem Handshake beachten.
Auth
- Die Shared-Secret-Gateway-Authentifizierung verwendet je nach konfiguriertem Authentifizierungsmodus
connect.params.auth.tokenoderconnect.params.auth.password. - Modi mit Identitätsinformationen wie Tailscale Serve
(
gateway.auth.allowTailscale: true) oder nicht-loopbackgateway.auth.mode: "trusted-proxy"erfüllen die Authentifizierungsprüfung beim Verbindungsaufbau anhand von Request-Headern stattconnect.params.auth.*. - Private-Ingress
gateway.auth.mode: "none"überspringt die Shared-Secret-Authentifizierung beim Verbindungsaufbau vollständig; setzen Sie diesen Modus nicht auf öffentlichem/nicht vertrauenswürdigem Ingress ein. - Nach dem Pairing stellt der Gateway ein Geräte-Token aus, das auf die Verbindungsrolle
- Scopes beschränkt ist. Es wird in
hello-ok.auth.deviceTokenzurückgegeben und sollte vom Client für zukünftige Verbindungen dauerhaft gespeichert werden.
- Scopes beschränkt ist. Es wird in
- Clients sollten das primäre
hello-ok.auth.deviceTokennach jeder erfolgreichen Verbindung dauerhaft speichern. - Eine erneute Verbindung mit diesem gespeicherten Geräte-Token sollte auch den gespeicherten genehmigten Scope-Satz für dieses Token wiederverwenden. Dadurch bleiben bereits gewährte Lese-/Probe-/Statuszugriffe erhalten, und erneute Verbindungen werden nicht stillschweigend auf einen engeren impliziten Nur-Admin-Scope reduziert.
- Clientseitige Zusammensetzung der Verbindungs-Authentifizierung (
selectConnectAuthinsrc/gateway/client.ts):auth.passwordist orthogonal und wird immer weitergeleitet, wenn gesetzt.auth.tokenwird in Prioritätsreihenfolge befüllt: zuerst explizites Shared Token, dann ein explizitesdeviceToken, dann ein gespeichertes Token pro Gerät (geschlüsselt nachdeviceId+role).auth.bootstrapTokenwird nur gesendet, wenn keines der oben genannten einauth.tokenaufgelöst hat. Ein Shared Token oder ein beliebiges aufgelöstes Geräte-Token unterdrückt es.- Die automatische Hochstufung eines gespeicherten Geräte-Tokens beim einmaligen
AUTH_TOKEN_MISMATCH-Retry ist auf vertrauenswürdige Endpunkte beschränkt — loopback oderwss://mit angepinntemtlsFingerprint. Öffentlicheswss://ohne Pinning qualifiziert sich nicht.
- Der integrierte Setup-Code-Bootstrap gibt das primäre Node-
hello-ok.auth.deviceTokensowie ein begrenztes Operator-Token inhello-ok.auth.deviceTokensfür die vertrauenswürdige mobile Übergabe zurück. Das Operator-Token enthältoperator.talk.secretsfür native Talk-Konfigurationslesevorgänge, schließt aber Pairing-Mutations-Scopes undoperator.adminaus. - Während ein nicht-baseline Setup-Code-Bootstrap auf Genehmigung wartet, enthalten
PAIRING_REQUIRED- DetailsrecommendedNextStep: "wait_then_retry",retryable: trueundpauseReconnect: false. Clients sollten weiterhin mit demselben Bootstrap-Token neu verbinden, bis die Anfrage genehmigt wurde oder das Token ungültig wird. - Speichern Sie
hello-ok.auth.deviceTokensnur dauerhaft, wenn die Verbindung Bootstrap-Authentifizierung über einen vertrauenswürdigen Transport wiewss://oder loopback/lokales Pairing verwendet hat. - Wenn ein Client ein explizites
deviceTokenoder explizitescopesbereitstellt, bleibt dieser vom Aufrufer angeforderte Scope-Satz maßgeblich; gecachte Scopes werden nur wiederverwendet, wenn der Client das gespeicherte Token pro Gerät wiederverwendet. - Geräte-Token können über
device.token.rotateunddevice.token.revokerotiert/widerrufen werden (erfordert Scopeoperator.pairing). Das Rotieren oder Widerrufen eines Node- oder anderen Nicht-Operator-Rollen-Tokens erfordert zusätzlichoperator.admin. device.token.rotategibt Rotationsmetadaten zurück. Es gibt das Ersatz- Bearer-Token nur bei Aufrufen desselben Geräts zurück, die bereits mit diesem Geräte-Token authentifiziert sind, sodass reine Token-Clients ihren Ersatz vor dem erneuten Verbinden dauerhaft speichern können. Shared-/Admin-Rotationen geben das Bearer-Token nicht zurück.- Token-Ausstellung, -Rotation und -Widerruf bleiben auf den genehmigten Rollensatz beschränkt, der im Pairing-Eintrag dieses Geräts aufgezeichnet ist; Token-Mutation kann keine Geräterolle erweitern oder anvisieren, die die Pairing-Genehmigung nie gewährt hat.
- Bei gekoppelten Geräte-Token-Sitzungen ist die Geräteverwaltung selbstbezogen, es sei denn, der
Aufrufer hat zusätzlich
operator.admin: Nicht-Admin-Aufrufer können nur das Operator-Token für ihren eigenen Geräteeintrag verwalten. Node- und andere Nicht-Operator- Token-Verwaltung ist nur Admins vorbehalten, auch für das eigene Gerät des Aufrufers. device.token.rotateunddevice.token.revokeprüfen außerdem den Scope-Satz des Ziel-Operator- Tokens gegen die aktuellen Sitzungs-Scopes des Aufrufers. Nicht-Admin-Aufrufer können kein breiteres Operator-Token rotieren oder widerrufen, als sie bereits besitzen.- Authentifizierungsfehler enthalten
error.details.codeplus Wiederherstellungshinweise:error.details.canRetryWithDeviceToken(boolesch)error.details.recommendedNextStep(retry_with_device_token,update_auth_configuration,update_auth_credentials,wait_then_retry,review_auth_configuration)
- Client-Verhalten bei
AUTH_TOKEN_MISMATCH:- Vertrauenswürdige Clients dürfen einen begrenzten Retry mit einem gecachten Token pro Gerät versuchen.
- Wenn dieser Retry fehlschlägt, sollten Clients automatische Wiederverbindungs-Schleifen stoppen und Hinweise für Operator-Aktionen anzeigen.
AUTH_SCOPE_MISMATCHbedeutet, dass das Geräte-Token erkannt wurde, aber die angeforderten Rollen/Scopes nicht abdeckt. Clients sollten dies nicht als fehlerhaftes Token darstellen; fordern Sie den Operator auf, erneut zu pairen oder den engeren/breiteren Scope-Vertrag zu genehmigen.
Geräteidentität + Pairing
- Nodes sollten eine stabile Geräteidentität (
device.id) enthalten, die aus einem Schlüsselpaar-Fingerprint abgeleitet ist. - Gateways stellen Tokens pro Gerät + Rolle aus.
- Pairing-Genehmigungen sind für neue Geräte-IDs erforderlich, sofern lokale automatische Genehmigung nicht aktiviert ist.
- Die automatische Pairing-Genehmigung konzentriert sich auf direkte lokale loopback-Verbindungen.
- OpenClaw hat außerdem einen schmalen backend-/container-lokalen Selbstverbindungspfad für vertrauenswürdige Shared-Secret-Hilfsabläufe.
- Same-Host-tailnet- oder LAN-Verbindungen werden für Pairing weiterhin als remote behandelt und erfordern eine Genehmigung.
- WS-Clients enthalten normalerweise während
connecteinedevice-Identität (Operator + Node). Die einzigen gerätelosen Operator-Ausnahmen sind explizite Vertrauenspfade:gateway.controlUi.allowInsecureAuth=truefür localhost-only unsichere HTTP-Kompatibilität.- erfolgreiche Operator-Control-UI-Authentifizierung mit
gateway.auth.mode: "trusted-proxy". gateway.controlUi.dangerouslyDisableDeviceAuth=true(Break-Glass, erhebliche Sicherheitsherabstufung).- direkte-loopback
gateway-clientBackend-RPCs auf dem reservierten internen Hilfspfad.
- Das Weglassen der Geräteidentität hat Auswirkungen auf Scopes. Wenn eine gerätelose Operator-
Verbindung über einen expliziten Vertrauenspfad zugelassen wird, löscht OpenClaw dennoch
selbst deklarierte Scopes auf eine leere Menge, sofern dieser Pfad keine benannte
Ausnahme zur Scope-Beibehaltung hat. Scope-gesteuerte Methoden schlagen dann mit
missing scopefehl. gateway.controlUi.dangerouslyDisableDeviceAuth=trueist ein Control-UI- Break-Glass-Pfad zur Scope-Beibehaltung. Er gewährt keinen beliebigen benutzerdefinierten Backend- oder CLI-förmigen WebSocket-Clients Scopes.- Der reservierte direkte-loopback
gateway-clientBackend-Hilfspfad behält Scopes nur für interne lokale Control-Plane-RPCs bei; benutzerdefinierte Backend-IDs erhalten diese Ausnahme nicht. - Alle Verbindungen müssen die vom Server bereitgestellte
connect.challenge-Nonce signieren.
Diagnose der Geräteauthentifizierungs-Migration
Für Legacy-Clients, die noch das Signaturverhalten vor Challenge verwenden, gibt connect nun
DEVICE_AUTH_*-Detailcodes unter error.details.code mit einem stabilen error.details.reason zurück.
Häufige Migrationsfehler:
| Meldung | details.code | details.reason | Bedeutung |
|---|---|---|---|
device nonce required |
DEVICE_AUTH_NONCE_REQUIRED |
device-nonce-missing |
Client hat device.nonce ausgelassen (oder leer gesendet). |
device nonce mismatch |
DEVICE_AUTH_NONCE_MISMATCH |
device-nonce-mismatch |
Client hat mit einer veralteten/falschen Nonce signiert. |
device signature invalid |
DEVICE_AUTH_SIGNATURE_INVALID |
device-signature |
Signatur-Payload passt nicht zum v2-Payload. |
device signature expired |
DEVICE_AUTH_SIGNATURE_EXPIRED |
device-signature-stale |
Signierter Zeitstempel liegt außerhalb der erlaubten Abweichung. |
device identity mismatch |
DEVICE_AUTH_DEVICE_ID_MISMATCH |
device-id-mismatch |
device.id stimmt nicht mit dem Public-Key-Fingerprint überein. |
device public key invalid |
DEVICE_AUTH_PUBLIC_KEY_INVALID |
device-public-key |
Public-Key-Format/Kanonisierung fehlgeschlagen. |
Migrationsziel:
- Warten Sie immer auf
connect.challenge. - Signieren Sie den v2-Payload, der die Server-Nonce enthält.
- Senden Sie dieselbe Nonce in
connect.params.device.nonce. - Bevorzugter Signatur-Payload ist
v3, der zusätzlich zu Geräte-/Client-/Rollen-/Scope-/Token-/Nonce-FeldernplatformunddeviceFamilybindet. - Legacy-
v2-Signaturen bleiben aus Kompatibilitätsgründen akzeptiert, aber Metadaten-Pinning für gekoppelte Geräte steuert weiterhin die Befehlsrichtlinie bei erneuter Verbindung.
TLS + Pinning
- TLS wird für WS-Verbindungen unterstützt.
- Clients können optional den Gateway-Zertifikats-Fingerprint anpinnen (siehe
gateway.tls- Konfiguration plusgateway.remote.tlsFingerprintoder CLI--tls-fingerprint).
Scope
Dieses Protokoll stellt die vollständige Gateway-API bereit (Status, Kanäle, Modelle, Chat,
Agent, Sitzungen, Nodes, Genehmigungen usw.). Die genaue Oberfläche wird durch die
TypeBox-Schemas in packages/gateway-protocol/src/schema.ts definiert.