exec i wait.
Ta strona dokumentuje tryb kodu OpenClaw. Nie jest to tryb kodu Codex. Te dwie
funkcje mają wspólną nazwę, ale są implementowane przez różne środowiska uruchomieniowe i udostępniają
różne kontrakty exec:
- Tryb kodu Codex jest włączony dla wątków serwera aplikacji Codex, chyba że ograniczająca
polityka narzędzi wyłącza natywny tryb kodu. Działa w uprzęży kodowania Codex,
gdzie model zapisuje polecenia powłoki przez kontrakt
exec.command. - Tryb kodu OpenClaw jest wyłączony, chyba że skonfigurowano
tools.codeMode.enabled: true. Działa w ogólnym środowisku uruchomieniowym agentów OpenClaw, gdzie model zapisuje programy JavaScript lub TypeScript przez kontraktexec.code.
quickjs-wasi,
ukrytego katalogu narzędzi OpenClaw oraz standardowego wykonawcy narzędzi OpenClaw.
Co to jest?
Tryb kodu OpenClaw pozwala modelowi napisać mały program JavaScript lub TypeScript zamiast wybierać bezpośrednio z długiej listy narzędzi. Gdy tryb kodu jest aktywny:- Lista narzędzi widoczna dla modelu to dokładnie
execiwait. execocenia wygenerowany przez model kod JavaScript lub TypeScript w ograniczonym workerze QuickJS-WASI.- Standardowe narzędzia OpenClaw są ukryte przed promptem modelu i udostępnione wewnątrz
programu gościa przez
ALL_TOOLSitools. - Kod gościa może przeszukiwać ukryty katalog, opisywać narzędzie i wywoływać narzędzie przez tę samą ścieżkę wykonania OpenClaw, której używają standardowe tury agenta.
- Narzędzia MCP są grupowane w przestrzeni nazw
MCP. W trybie kodu ta przestrzeń nazw jest jedynym obsługiwanym sposobem wywoływania narzędzi MCP. waitwznawia zawieszone uruchomienie w trybie kodu, gdy zagnieżdżone wywołania narzędzi nadal oczekują.
Dlaczego to jest dobre?
Tryb kodu ułatwia modelom korzystanie z dużych katalogów narzędzi.- Mniejsza powierzchnia promptu: dostawcy otrzymują dwa narzędzia sterujące zamiast dziesiątek lub setek pełnych schematów narzędzi.
- Lepsza orkiestracja: model może używać pętli, złączeń, małych transformacji, logiki warunkowej i równoległych zagnieżdżonych wywołań narzędzi w jednej komórce kodu.
- Neutralność względem dostawcy: działa dla narzędzi OpenClaw, Plugin, MCP i klienta bez zależności od natywnego dla dostawcy wykonywania kodu.
- Istniejąca polityka pozostaje w mocy: zagnieżdżone wywołania narzędzi nadal przechodzą przez politykę OpenClaw, zatwierdzenia, hooki, kontekst sesji i ścieżki audytu.
- Jasny tryb awarii: gdy tryb kodu jest jawnie włączony, a środowisko uruchomieniowe jest niedostępne, OpenClaw kończy niepowodzeniem w sposób zamknięty zamiast wracać do szerokiej bezpośredniej ekspozycji narzędzi.
Jak go włączyć
Dodajtools.codeMode.enabled: true do konfiguracji agenta lub środowiska uruchomieniowego:
tools.codeMode jest pominięte, ma wartość false albo jest obiektem
bez enabled: true.
Gdy używasz agentów w piaskownicy ze skonfigurowanymi serwerami MCP, upewnij się też, że
polityka narzędzi piaskownicy pozwala na dołączony Plugin MCP, na przykład przez
tools.sandbox.tools.alsoAllow: ["bundle-mcp"]. Zobacz
Konfiguracja - narzędzia i dostawcy niestandardowi.
Użyj jawnych limitów, gdy chcesz ściślejszych ograniczeń:
exec i
wait. Jeśli potrzebujesz zredagowanego payloadu dostawcy, dodaj
OPENCLAW_DEBUG_MODEL_PAYLOAD=full-redacted na krótką sesję debugowania.
Przegląd techniczny
Pozostała część tej strony opisuje kontrakt środowiska uruchomieniowego i szczegóły implementacji. Jest przeznaczona dla maintainerów, autorów Plugin debugujących ekspozycję narzędzi oraz operatorów walidujących wdrożenia wysokiego ryzyka.Stan środowiska uruchomieniowego
- Środowisko uruchomieniowe:
quickjs-wasi. - Stan domyślny: wyłączone.
- Stabilność: eksperymentalna powierzchnia OpenClaw; tryb kodu Codex to osobna stabilna powierzchnia uprzęży Codex.
- Powierzchnia docelowa: ogólne uruchomienia agentów OpenClaw.
- Postawa bezpieczeństwa: kod modelu jest wrogi.
- Obietnica dla użytkownika: włączenie trybu kodu nigdy po cichu nie wraca do szerokiej bezpośredniej ekspozycji narzędzi.
Zakres
Tryb kodu odpowiada za widoczny dla modelu kształt orkiestracji przygotowanego uruchomienia. Nie odpowiada za wybór modelu, zachowanie kanałów, uwierzytelnianie, politykę narzędzi ani implementacje narzędzi. W zakresie:- definicje narzędzi
execiwaitwidoczne dla modelu - budowanie ukrytego katalogu narzędzi
- wykonywanie kodu gościa JavaScript i TypeScript
- środowisko uruchomieniowe workera QuickJS-WASI
- callbacki hosta do wyszukiwania w katalogu, opisu schematu i wywołania narzędzia
- wznawialny stan dla zawieszonych programów gościa
- limity wyjścia, czasu, pamięci, oczekujących wywołań i snapshotów
- telemetria i projekcja trajektorii dla zagnieżdżonych wywołań narzędzi
- natywne dla dostawcy zdalne wykonywanie kodu
- semantyka wykonywania powłoki
- zmiana istniejącej autoryzacji narzędzi
- trwałe skrypty tworzone przez użytkownika
- dostęp do menedżera pakietów, plików, sieci lub modułów w kodzie gościa
- bezpośrednie ponowne użycie wewnętrznych mechanizmów trybu kodu Codex
Terminy
Tryb kodu to tryb środowiska uruchomieniowego OpenClaw, który ukrywa standardowe narzędzia modelu i udostępnia tylkoexec oraz wait.
Środowisko uruchomieniowe gościa to maszyna wirtualna JavaScript QuickJS-WASI, która ocenia kod modelu.
Most hosta to wąska, zgodna z JSON powierzchnia callbacków z kodu gościa
z powrotem do OpenClaw.
Katalog to lista skutecznych narzędzi ograniczona do uruchomienia, po standardowej polityce narzędzi,
rozwiązaniu Plugin, MCP i narzędzi klienta.
Zagnieżdżone wywołanie narzędzia to wywołanie narzędzia wykonane z kodu gościa przez most hosta.
Snapshot to zserializowany stan maszyny wirtualnej QuickJS-WASI zapisany tak, aby wait mogło kontynuować
zawieszone uruchomienie w trybie kodu.
Konfiguracja
tools.codeMode.enabled jest bramką aktywacji. Ustawienie innych pól trybu kodu
nie włącza funkcji.
Obsługiwane pola:
enabled: boolean. Domyślniefalse. Włącza tryb kodu tylko przy wartościtrue.runtime:"quickjs-wasi". Jedyne obsługiwane środowisko uruchomieniowe.mode:"only". Udostępniaexeciwait, ukrywa standardowe narzędzia modelu.languages: tablica"javascript"i"typescript". Domyślnie zawiera oba.timeoutMs: limit czasu zegarowego dla jednegoexeclubwait. Domyślnie10000. Ograniczenie środowiska uruchomieniowego: od100do60000.memoryLimitBytes: limit sterty QuickJS. Domyślnie67108864. Ograniczenie środowiska uruchomieniowego: od1048576do1073741824.maxOutputBytes: limit dla zwracanego tekstu, JSON i logów. Domyślnie65536. Ograniczenie środowiska uruchomieniowego: od1024do10485760.maxSnapshotBytes: limit dla zserializowanych snapshotów VM. Domyślnie10485760. Ograniczenie środowiska uruchomieniowego: od1024do268435456.maxPendingToolCalls: limit równoległych zagnieżdżonych wywołań narzędzi. Domyślnie16. Ograniczenie środowiska uruchomieniowego: od1do128.snapshotTtlSeconds: czas, przez jaki można wznowić zawieszoną VM. Domyślnie900. Ograniczenie środowiska uruchomieniowego: od1do86400.searchDefaultLimit: domyślna liczba wyników wyszukiwania w ukrytym katalogu. Domyślnie8. Środowisko uruchomieniowe ogranicza ją domaxSearchLimit.maxSearchLimit: maksymalna liczba wyników wyszukiwania w ukrytym katalogu. Domyślnie50. Ograniczenie środowiska uruchomieniowego: od1do50.
Aktywacja
Tryb kodu jest oceniany po ustaleniu skutecznej polityki narzędzi i przed złożeniem ostatecznego żądania modelu. Kolejność aktywacji:- Rozwiąż agenta, model, dostawcę, piaskownicę, kanał, nadawcę i politykę uruchomienia.
- Zbuduj skuteczną listę narzędzi OpenClaw.
- Dodaj kwalifikujące się narzędzia Plugin, MCP i klienta.
- Zastosuj politykę allow i deny.
- Jeśli
tools.codeMode.enabledma wartość false, kontynuuj ze standardową ekspozycją narzędzi. - Jeśli jest włączone, a narzędzia są aktywne dla uruchomienia, zarejestruj skuteczne narzędzia w katalogu trybu kodu.
- Usuń wszystkie standardowe narzędzia z listy narzędzi widocznej dla modelu.
- Dodaj
execiwaittrybu kodu.
disableTools
lub pusta lista allow, nie aktywują powierzchni trybu kodu nawet wtedy, gdy konfiguracja
zawiera tools.codeMode.enabled: true.
Katalog trybu kodu jest ograniczony do uruchomienia. Nie może wyciekać narzędzi z innego agenta,
sesji, nadawcy ani uruchomienia.
Narzędzia widoczne dla modelu
Gdy tryb kodu jest aktywny, model widzi dokładnie te narzędzia najwyższego poziomu:execwait
exec do orkiestracji narzędzi, łączenia danych, pętli,
równoległych zagnieżdżonych wywołań i strukturalnych transformacji. Model powinien używać
wait tylko wtedy, gdy exec zwraca wznawialny wynik waiting.
exec
exec uruchamia komórkę trybu kodu i zwraca jeden wynik. Kod wejściowy jest generowany przez model
i musi być traktowany jako wrogi.
Wejście:
- Jedno z pól
codelubcommandmusi być niepuste. codejest udokumentowanym polem widocznym dla modelu.commandjest akceptowane jako alias zgodny z exec dla polityk hooków i zaufanych przekształceń; gdy oba pola są obecne, wartości muszą się zgadzać.- Zewnętrzne zdarzenia hooków
exectrybu kodu zawierajątoolKind: "code_mode_exec"i zawierajątoolInputKind: "javascript" | "typescript", gdy język wejściowy jest znany, aby polityki mogły odróżniać komórki trybu kodu od wywołańexecw stylu powłoki, które mają tę samą nazwę narzędzia. languagedomyślnie ma wartość"javascript".- Jeśli
languagema wartość"typescript", OpenClaw transpiluje kod przed oceną. execodrzucaimport,require, dynamiczny import i wzorce loaderów modułów w v1.execnie udostępnia rekurencyjnie standardowej implementacji powłokowegoexec.
exec zwraca waiting, gdy VM QuickJS zawiesza się ze wznawialnym stanem, który
nadal wymaga kontynuacji widocznej dla modelu. Wynik zawiera runId dla
wait. Wywołania mostu przestrzeni nazw, w tym wywołania przestrzeni nazw MCP, są automatycznie opróżniane
w ramach tego samego wywołania exec/wait, gdy są gotowe, dzięki czemu zwarty blok kodu
może sprawdzić $api() i wywołać narzędzie MCP bez wymuszania jednego wywołania narzędzia modelu na każde
oczekiwanie przestrzeni nazw.
exec zwraca completed tylko wtedy, gdy maszyna wirtualna gościa nie ma oczekującej pracy, a
wartość końcowa jest zgodna z JSON po uruchomieniu adaptera wyjścia OpenClaw.
wait
wait wznawia zawieszoną maszynę wirtualną trybu kodu.
Wejście:
CodeModeResult, którą zwraca exec.
wait istnieje, ponieważ zagnieżdżone narzędzia OpenClaw mogą być wolne, interaktywne, bramkowane
zatwierdzeniami albo strumieniować częściowe aktualizacje. Model nie powinien musieć trzymać jednego długiego
wywołania exec otwartego, gdy host czeka na pracę zewnętrzną.
Migawka i przywracanie QuickJS-WASI to mechanizm wznawiania w wersji v1:
execwykonuje kod do ukończenia, niepowodzenia albo zawieszenia.- Przy zawieszeniu OpenClaw zapisuje migawkę maszyny wirtualnej QuickJS i rejestruje oczekującą pracę hosta.
- Gdy oczekująca praca się zakończy,
waitprzywraca migawkę maszyny wirtualnej. - OpenClaw ponownie rejestruje wywołania zwrotne hosta według stabilnych nazw.
- OpenClaw dostarcza wyniki zagnieżdżonych narzędzi do przywróconej maszyny wirtualnej.
- OpenClaw opróżnia oczekujące zadania QuickJS.
waitzwracacompleted,failedalbo kolejny wynikwaiting.
wait kończy się niepowodzeniem, gdy:
runIdjest nieznany.- migawka wygasła.
- nadrzędne uruchomienie lub sesja zostały przerwane.
- wywołujący nie jest w tym samym zakresie uruchomienia/sesji.
- przywracanie QuickJS-WASI kończy się niepowodzeniem.
- przywrócenie przekroczyłoby skonfigurowane limity.
API środowiska uruchomieniowego gościa
Środowisko uruchomieniowe gościa udostępnia małe globalne API:ALL_TOOLS to zwięzłe metadane katalogu ograniczonego do uruchomienia. Domyślnie nie zawiera
pełnych schematów.
tools.call(...) ani wygodne
funkcje w trybie kodu. Są udostępniane tylko przez wygenerowaną przestrzeń nazw MCP.
Pliki deklaracji w stylu TypeScript są dostępne przez wirtualną powierzchnię plików API tylko do odczytu,
więc agenci mogą sprawdzać sygnatury MCP bez dodawania schematów MCP do promptu:
API.read("mcp/<server>.d.ts") zwraca zwięzłe deklaracje wywnioskowane z metadanych
narzędzi MCP:
exec w trybie kodu OpenClaw buduje ograniczony do uruchomienia
katalog narzędzi, zachowuje widoczne wpisy MCP, renderuje mcp/index.d.ts oraz jedną
deklarację mcp/<server>.d.ts dla każdego widocznego serwera i wstrzykuje tę małą
tabelę tylko do odczytu do workera QuickJS. Kod gościa widzi tylko obiekt API:
API.list(prefix?) zwraca metadane plików, a API.read(path) zwraca
wybraną treść deklaracji. Nieznane ścieżki oraz segmenty . / .. są odrzucane.
Dzięki temu duże schematy MCP nie trafiają do promptu modelu. Agent dowiaduje się, że
wirtualne API istnieje, z opisu narzędzia exec, odczytuje tylko potrzebny
plik deklaracji, a następnie wywołuje MCP.<server>.<tool>() z jednym argumentem obiektowym.
MCP.<server>.$api() pozostaje dostępne jako awaryjna opcja inline, gdy agent
potrzebuje odpowiedzi ze schematem pojedynczego narzędzia wewnątrz programu.
Środowisko uruchomieniowe gościa nie może bezpośrednio udostępniać obiektów hosta. Wejścia i wyjścia przechodzą
przez most jako wartości zgodne z JSON, z jawnymi limitami rozmiaru.
Wewnętrzne przestrzenie nazw
Wewnętrzne przestrzenie nazw dają trybowi kodu zwięzłe API domenowe bez dodawania kolejnych narzędzi widocznych dla modelu. Integracja będąca własnością loadera może zarejestrować przestrzeń nazw taką jakIssues, Fictions albo Calendar; kod gościa wywołuje wtedy tę przestrzeń nazw
wewnątrz programu QuickJS, podczas gdy OpenClaw nadal pokazuje modelowi tylko exec i wait.
Przestrzenie nazw są na razie wewnętrzne. Nie ma publicznego API przestrzeni nazw w SDK pluginów:
zewnętrzne przestrzenie nazw pluginów wymagają kontraktu będącego własnością loadera, aby tożsamość pluginu,
zainstalowane manifesty, stan uwierzytelniania i zbuforowane deskryptory katalogu nie mogły odbiec
od narzędzi pluginu, które obsługują przestrzeń nazw. Główny tryb kodu posiada tylko
piaskownicę, serializację, bramkowanie katalogu i wysyłkę przez most.
Kod gościa może wtedy używać bezpośredniego obiektu globalnego albo mapy namespaces:
Cykl życia rejestru
Rejestr przestrzeni nazw jest lokalny dla procesu i kluczowany identyfikatorem przestrzeni nazw. Typowe uruchomienie przechodzi taką ścieżką:- Zaufany loader wywołuje
registerCodeModeNamespaceForPlugin(pluginId, registration). - Tryb kodu tworzy ukryte
ToolSearchRuntimedla uruchomienia i odczytuje jego katalog ograniczony do uruchomienia. createCodeModeNamespaceRuntime(ctx, catalog)zachowuje tylko rejestracje, którychrequiredToolNamessą wszystkie widoczne i należą do tego samegopluginId.- Każda widoczna przestrzeń nazw wywołuje
createScope(ctx)dla bieżącego uruchomienia. Zakres otrzymuje kontekst uruchomienia, taki jakagentId,sessionKey,sessionId,runId, konfigurację i stan przerwania. - Dane zakresu są serializowane do prostego deskryptora i wstrzykiwane do QuickJS jako
bezpośrednie obiekty globalne oraz
namespaces.<globalName>. - Wywołania gościa zawieszają się przez most workera, rozwiązują ścieżkę przestrzeni nazw na
hoście, mapują wywołanie na zadeklarowane narzędzie katalogu należące do pluginu i wykonują
to narzędzie przez
ToolSearchRuntime.call. - OpenClaw automatycznie opróżnia gotowe wywołania mostu przestrzeni nazw wewnątrz aktywnego
wywołania narzędzia
exec/wait. Jeśli praca przestrzeni nazw nadal oczekuje po limicie czasu albo gość jawnie odda sterowanie,waitwznawia później to samo środowisko uruchomieniowe przestrzeni nazw. - Wycofanie lub odinstalowanie pluginu wywołuje
clearCodeModeNamespacesForPlugin(pluginId), aby przestarzałe obiekty globalne nie przetrwały nieudanego ładowania pluginu.
tools.call(...).
Kształt rejestracji
Rejestruj przestrzenie nazw z integracji, która jest właścicielem narzędzi bazowych. Utrzymuj mały zakres i udostępniaj tylko czasowniki domenowe, które mapują się na zadeklarowane narzędzia katalogu.createCodeModeNamespaceTool(toolName, inputMapper) oznacza element zakresu jako
wywoływalną funkcję przestrzeni nazw. Opcjonalny inputMapper otrzymuje argumenty gościa
i zwraca obiekt wejściowy dla bazowego narzędzia katalogu. Bez
mapera wejścia używany jest pierwszy argument gościa albo {} w razie pominięcia.
Surowe funkcje hosta są odrzucane przed uruchomieniem kodu gościa:
Własność i widoczność
Własność przestrzeni nazw jest powiązana zpluginId wywołującego rejestrację.
requiredToolNames jest jednocześnie bramką widoczności i kontrolą własności:
- każde wymagane narzędzie musi istnieć w katalogu uruchomienia
- każde wymagane narzędzie musi mieć
sourceName === pluginId - przestrzeń nazw jest ukryta, gdy któregokolwiek wymaganego narzędzia brakuje albo należy do innego pluginu
- każda wywoływalna ścieżka może kierować tylko do narzędzia nazwanego w
requiredToolNames
Reguły serializacji zakresu
createScope(ctx) może zwrócić prosty obiekt zawierający wartości zgodne z JSON,
tablice, obiekty zagnieżdżone i znaczniki wywołań createCodeModeNamespaceTool(...).
Obiekty hosta nigdy nie trafiają bezpośrednio do QuickJS.
Serializer odrzuca:
- surowe funkcje
- cykliczne grafy obiektów
- niebezpieczne segmenty ścieżki:
__proto__,constructor,prototype, puste klucze albo klucze zawierające wewnętrzny separator ścieżki - wartości
globalName, które nie są identyfikatorami JavaScript - kolizje
globalNamez wbudowanymi obiektami globalnymi trybu kodu, takimi jaktools,namespaces,text,json,yield_controlalbo__openclaw*
Prompty
description przestrzeni nazw i opcjonalny prompt są dołączane do widocznego dla modelu
schematu exec tylko wtedy, gdy przestrzeń nazw jest widoczna dla danego uruchomienia. Używaj ich,
aby nauczyć najmniejszej użytecznej powierzchni:
Czyszczenie
Namespaces są rejestracjami lokalnymi dla procesu. Usuń je, gdy właścicielski plugin zostanie wyłączony, odinstalowany lub wycofany:clearCodeModeNamespacesForTest(),
aby uniknąć wycieku rejestracji między przypadkami.
Lista kontrolna testów
Zmiany przestrzeni nazw powinny obejmować granicę bezpieczeństwa i zachowanie gościa:- tekst promptu przestrzeni nazw pojawia się tylko wtedy, gdy narzędzia bazowe są widoczne
- narzędzia o tej samej nazwie z innego
sourceNamenie ujawniają przestrzeni nazw - surowe funkcje zakresu są odrzucane
- podrobione identyfikatory przestrzeni nazw i podrobione ścieżki są odrzucane
- wywoływalne ścieżki nie mogą wskazywać niezadeklarowanych narzędzi
- zagnieżdżone obiekty i współdzielone referencje serializują się poprawnie
- wywołania przestrzeni nazw wykonują się przez narzędzia katalogu i zwracają szczegóły bezpieczne dla JSON
- błędy mogą być przechwytywane przez kod gościa
- zawieszone wywołania przestrzeni nazw wznawiają się przez
wait - wycofanie pluginu czyści rejestracje właścicielskich przestrzeni nazw
tools.search / tools.call. Używaj
katalogu dla dowolnych włączonych narzędzi OpenClaw, pluginów i klientów; używaj MCP
dla narzędzi MCP; używaj innych przestrzeni nazw dla właścicielskich dla pluginu,
udokumentowanych domenowych API, gdzie zwięzły kod jest bardziej niezawodny niż
powtarzane wyszukiwania schematów.
API wyjściowe
text(value) dopisuje wyjście czytelne dla człowieka do tablicy output.
json(value) dopisuje element wyjścia strukturalnego po serializacji zgodnej z JSON.
Ostateczna wartość zwrócona przez kod gościa staje się value w wyniku completed.
Element wyjścia:
- kolejność wyjścia odpowiada wywołaniom gościa
- wyjście jest ograniczone przez
maxOutputBytes - wartości nienadające się do serializacji są konwertowane na zwykłe ciągi znaków lub błędy
- wartości binarne nie są obsługiwane w v1
- obrazy i pliki przechodzą przez zwykłe narzędzia OpenClaw, a nie przez most trybu kodu
Katalog narzędzi
Ukryty katalog obejmuje narzędzia po skutecznym filtrowaniu zasad:- Narzędzia rdzenia OpenClaw.
- Narzędzia bundled pluginów.
- Narzędzia external pluginów.
- Narzędzia MCP.
- Narzędzia dostarczone przez klienta dla bieżącego uruchomienia.
execwaittool_search_codetool_searchtool_describetool_call
ALL_TOOLS, tools.search(...),
tools.describe(...) i tools.call(...) pomijają wpisy MCP. Wygenerowana przestrzeń nazw
MCP.<server>.<tool>({ ...input }) rozwiązuje się z powrotem do dokładnego identyfikatora
katalogu, a następnie wysyła wywołanie przez tę samą ścieżkę wykonawcy.
Interakcja z wyszukiwaniem narzędzi
Tryb kodu zastępuje powierzchnię modelu Wyszukiwania narzędzi OpenClaw dla uruchomień, w których jest aktywny. Gdytools.codeMode.enabled ma wartość true i tryb kodu się aktywuje:
- OpenClaw nie udostępnia
tool_search_code,tool_search,tool_describeanitool_calljako narzędzi widocznych dla modelu. - Ta sama idea katalogowania przenosi się do środowiska uruchomieniowego gościa.
- Środowisko uruchomieniowe gościa otrzymuje kompaktowe metadane
ALL_TOOLSoraz pomocniki wyszukiwania, opisu i wywołania dla narzędzi innych niż MCP. - Wywołania MCP używają wygenerowanej przestrzeni nazw
MCPi jej nagłówków$api()zamiasttools.call(...). - Zagnieżdżone wywołania są wysyłane przez tę samą ścieżkę wykonawcy OpenClaw, której używa Wyszukiwanie narzędzi.
exec i wait.
Nazwy narzędzi i kolizje
Widoczne dla modelu narzędzieexec jest narzędziem trybu kodu. Jeśli normalne
narzędzie powłoki OpenClaw exec jest włączone, jest ukryte przed modelem i
katalogowane jak każde inne narzędzie.
W środowisku uruchomieniowym gościa:
tools.call("openclaw:core:exec", input)może wywołać narzędzie powłoki exec, jeśli zasady na to pozwalają.tools.exec(...)jest instalowane tylko wtedy, gdy wpis katalogu powłoki exec ma jednoznaczną bezpieczną nazwę.- narzędzie
exectrybu kodu nigdy nie jest rekursywnie dostępne przeztools.
tools.call(id, input).
Zagnieżdżone wykonywanie narzędzi
Każde zagnieżdżone wywołanie narzędzia przechodzi przez most hosta i ponownie wchodzi do OpenClaw. Zagnieżdżone wykonywanie zachowuje:- aktywny identyfikator agenta
- identyfikator sesji i klucz sesji
- kontekst nadawcy i kanału
- zasady sandboxa
- zasady zatwierdzania
- hooki pluginu
before_tool_call - sygnał przerwania
- aktualizacje strumieniowe tam, gdzie są dostępne
- zdarzenia trajektorii i audytu
maxPendingToolCalls.
Stan środowiska uruchomieniowego
Każde uruchomienie trybu kodu ma maszynę stanów:running: VM wykonuje kod lub zagnieżdżone wywołania są w toku.waiting: migawka VM istnieje i może zostać wznowiona przezwait.completed: zwrócono wartość końcową; migawka usunięta.failed: zwrócono błąd; migawka usunięta.expired: migawka lub stan oczekujący przekroczył retencję; nie można wznowić.aborted: nadrzędne uruchomienie/sesja anulowane; migawka usunięta.
wait z innego uruchomienia lub sesji kończy się niepowodzeniem.
Przechowywanie migawek jest ograniczone:
- maksymalna liczba bajtów migawki na uruchomienie
- maksymalna liczba aktywnych migawek na proces
- TTL migawki
- czyszczenie po zakończeniu uruchomienia
- czyszczenie przy zamknięciu Gateway, gdy trwałość nie jest obsługiwana
Środowisko uruchomieniowe QuickJS-WASI
OpenClaw ładujequickjs-wasi jako bezpośrednią zależność w pakiecie właścicielskim.
Środowisko uruchomieniowe nie polega na kopii tranzytywnej zainstalowanej dla proxy,
PAC lub innych niepowiązanych zależności.
Obowiązki środowiska uruchomieniowego:
- skompilować lub załadować moduł WebAssembly QuickJS-WASI
- utworzyć jedną izolowaną VM na uruchomienie lub wznowienie trybu kodu
- zarejestrować callbacki hosta pod stabilnymi nazwami
- ustawić limity pamięci i przerwań
- ewaluować JavaScript
- opróżnić oczekujące zadania
- zapisać migawkę zawieszonego stanu VM
- przywrócić migawki dla
wait - zwolnić uchwyty VM i migawki po stanach terminalnych
TypeScript
Obsługa TypeScript jest wyłącznie transformacją źródła:- akceptowane wejście: jeden ciąg kodu TypeScript
- wyjście: ciąg JavaScript ewaluowany przez QuickJS-WASI
- brak sprawdzania typów
- brak rozwiązywania modułów
- brak
importanirequirew v1 - diagnostyka jest zwracana jako wyniki
failed
Granica bezpieczeństwa
Kod modelu jest wrogi. Środowisko uruchomieniowe używa obrony warstwowej:- uruchamiaj QuickJS-WASI poza główną pętlą zdarzeń
- ładuj
quickjs-wasijako bezpośrednią zależność, a nie przez Codex lub pakiet tranzytywny - brak systemu plików, sieci, podprocesów, importu modułów, zmiennych środowiskowych lub globalnych obiektów hosta u gościa
- używaj limitów pamięci i przerwań QuickJS
- egzekwuj limit czasu zegara ściennego procesu nadrzędnego
- egzekwuj limity wyjścia, migawek, logów i oczekujących wywołań
- serializuj wartości mostu hosta przez wąski adapter JSON
- konwertuj błędy hosta na zwykłe błędy gościa, nigdy na obiekty realm hosta
- porzucaj migawki przy przekroczeniu limitu czasu, przerwaniu, zakończeniu sesji lub wygaśnięciu
- odrzucaj rekursywny dostęp do
exec,waiti narzędzi sterujących Wyszukiwaniem narzędzi - zapobiegaj przesłanianiu pomocników katalogu przez kolizje nazw skróconych
Kody błędów
Error hosta, obiekty stosu,
prototypy i funkcje hosta nie przechodzą do QuickJS.
Telemetria
Tryb kodu raportuje:- widoczne nazwy narzędzi wysłane do modelu
- ukryty rozmiar katalogu i podział według źródeł
- liczby
execiwait - liczby zagnieżdżonych wyszukiwań, opisów i wywołań
- identyfikatory wywołanych zagnieżdżonych narzędzi
- niepowodzenia limitów czasu, pamięci, migawek i wyjścia
- zdarzenia cyklu życia migawek
Debugowanie
Używaj ukierunkowanego logowania transportu modelu, gdy tryb kodu zachowuje się inaczej niż normalne uruchomienie narzędzia:OPENCLAW_DEBUG_MODEL_PAYLOAD=full-redacted.
Loguje to ograniczoną, zredagowaną migawkę JSON żądania modelu; powinno być używane
tylko podczas debugowania, ponieważ prompty i tekst wiadomości nadal mogą się pojawić.
Do debugowania strumienia użyj OPENCLAW_DEBUG_SSE=peek, aby zalogować pierwszych pięć
zredagowanych zdarzeń SSE. Tryb kodu również zamyka się bezpiecznie, jeśli końcowy payload
providera nie zawiera dokładnie exec i wait po aktywacji powierzchni trybu kodu.
Układ implementacji
Jednostki implementacji:- kontrakt konfiguracji:
tools.codeMode - budowniczy katalogu: skuteczne narzędzia do kompaktowych wpisów i mapy identyfikatorów
- adapter powierzchni modelu: zastępuje widoczne narzędzia przez
execiwait - adapter środowiska uruchomieniowego QuickJS-WASI: ładowanie, ewaluacja, migawka, przywracanie, zwalnianie
- nadzorca workera: limit czasu, przerwanie, izolacja awarii
- adapter mostu: bezpieczne dla JSON callbacki hosta i dostarczanie wyników
- adapter transformacji TypeScript
- magazyn migawek: TTL, limity rozmiaru, zakres uruchomienia/sesji
- projekcja trajektorii dla zagnieżdżonych wywołań narzędzi
- liczniki telemetrii i diagnostyka
node:vm jako sandboxa.
Lista kontrolna walidacji
Pokrycie trybu kodu powinno wykazać:- wyłączona konfiguracja pozostawia istniejącą ekspozycję narzędzi bez zmian
- konfiguracja obiektowa bez
enabled: truepozostawia tryb kodu wyłączony - włączona konfiguracja udostępnia modelowi tylko
execiwait, gdy narzędzia są aktywne dla uruchomienia - surowe uruchomienia bez narzędzi,
disableToolsi puste listy dozwolonych narzędzi nie uruchamiają wymuszania ładunku trybu kodu - wszystkie efektywne narzędzia inne niż MCP pojawiają się w
ALL_TOOLS - odrzucone narzędzia nie pojawiają się w
ALL_TOOLS tools.search,tools.describeitools.calldziałają dla narzędzi OpenClawAPI.list("mcp")iAPI.read("mcp/<server>.d.ts")udostępniają deklaracje MCP w stylu TypeScript bez mostka ani wywołania narzędzia- przestrzeń nazw MCP
$api()pozostaje dostępna jako wbudowana rezerwa dla schematów - wywołania przestrzeni nazw MCP działają dla widocznych narzędzi MCP z jednym wejściem obiektowym, podczas gdy
bezpośrednie wpisy katalogu MCP są nieobecne w
tools.* - narzędzia sterujące Wyszukiwania narzędzi są ukryte zarówno przed powierzchnią modelu, jak i ukrytym katalogiem
- zagnieżdżone wywołania zachowują zachowanie zatwierdzania i hooków
- powłoka
execjest ukryta przed modelem, ale można ją wywołać według identyfikatora katalogu, gdy jest dozwolona - rekurencyjne
execiwaitw trybie kodu nie mogą być wywoływane z kodu gościa - wejście TypeScript jest przekształcane i oceniane bez ładowania TypeScript na ścieżkach wyłączonych lub tylko JavaScript
- dostęp przez
import,require, do systemu plików, sieci i środowiska kończy się niepowodzeniem - nieskończone pętle przekraczają limit czasu i nie mogą zablokować Gateway
- przekroczenia limitu pamięci kończą działanie maszyny wirtualnej gościa
- limity wyjścia i migawek są wymuszane dla ukończonych i zawieszonych wywołań
waitwznawia zawieszoną migawkę i zwraca wartość końcową- wygasłe, przerwane, z niewłaściwą sesją i nieznane wartości
runIdkończą się niepowodzeniem - odtwarzanie i utrwalanie transkrypcji zachowują wywołania sterujące trybu kodu
- transkrypcja i telemetria wyraźnie pokazują zagnieżdżone wywołania narzędzi
Plan testów E2E
Uruchom je jako testy integracyjne lub end-to-end podczas zmiany środowiska uruchomieniowego:- Uruchom Gateway z
tools.codeMode.enabled: false. - Wyślij turę agenta z małym bezpośrednim zestawem narzędzi.
- Potwierdź, że narzędzia widoczne dla modelu pozostają bez zmian.
- Uruchom ponownie z
tools.codeMode.enabled: true. - Wyślij turę agenta z narzędziami testowymi OpenClaw, pluginu, MCP i klienta.
- Potwierdź, że lista narzędzi widoczna dla modelu to dokładnie
exec,wait. - W
execodczytajALL_TOOLSi potwierdź, że efektywne narzędzia testowe są obecne. - W
execwywołaj narzędzia OpenClaw/pluginu/klienta przeztools.search,tools.describeitools.call. - W
execwywołajAPI.list("mcp")iAPI.read("mcp/<server>.d.ts"), a następnie potwierdź, że pliki deklaracji opisują widoczne narzędzia MCP. - W
execwywołaj narzędzia MCP przezMCP.<server>.<tool>({ ...input })i potwierdź, że bezpośrednie wpisy katalogu MCP są nieobecne wALL_TOOLSitools.*. - Potwierdź, że odrzucone narzędzia są nieobecne i nie można ich wywołać po odgadniętym identyfikatorze.
- Uruchom zagnieżdżone wywołanie narzędzia, które kończy się po zwróceniu przez
execwartościwaiting. - Wywołaj
waiti potwierdź, że przywrócona maszyna wirtualna otrzymuje wynik narzędzia. - Potwierdź, że odpowiedź końcowa zawiera wyjście utworzone po przywróceniu.
- Potwierdź, że limit czasu, przerwanie i wygaśnięcie migawki czyszczą stan środowiska uruchomieniowego.
- Wyeksportuj trajektorię i potwierdź, że zagnieżdżone wywołania są widoczne pod nadrzędnym wywołaniem trybu kodu.
pnpm check:docs.