@openclaw/codex 2026.7.2-beta.7 → 2026.8.1-beta.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -0
- package/dist/api.js +147 -0
- package/dist/app-server-policy-bg5QPSVP.js +25 -0
- package/dist/attempt-client-cleanup-URjUlCHg.js +735 -0
- package/dist/binding-connection-DAvZwp96.js +45 -0
- package/dist/{bounded-turn-D2ZAgZVz.js → bounded-turn-4BjrZEwW.js} +63 -56
- package/dist/{capabilities-BFDTVYr4.js → capabilities-CH3K57v4.js} +8 -2
- package/dist/cli-metadata.js +1 -1
- package/dist/{command-formatters-C336eRVS.js → command-formatters-D0nZ3qtd.js} +18 -18
- package/dist/{command-handlers-DAHUSry9.js → command-handlers-DC86lgT4.js} +507 -101
- package/dist/command-rpc-xUIIonsO.js +90 -0
- package/dist/{compact-D_uvHurS.js → compact-COqgBRny.js} +234 -214
- package/dist/{session-binding-BXpo9ymA.js → config-CpNeo5AE.js} +284 -1163
- package/dist/context-compaction-activity-BOeJf7yo.js +58 -0
- package/dist/{conversation-binding-data-BHRpYbX3.js → conversation-binding-data-CW2GuupV.js} +6 -10
- package/dist/doctor-contract-api.js +48 -50
- package/dist/{dynamic-tools-D2gYkSBO.js → dynamic-tools-fJZhl4CE.js} +3442 -1433
- package/dist/{effective-mcp-catalog-Bbd98Inw.js → effective-mcp-catalog-4YKn51aG.js} +20 -15
- package/dist/elicitation-input-DMkeki8d.js +71 -0
- package/dist/{event-projector-assistant-message-DTgnPPVF.js → event-projector-assistant-message-BwxV4d6N.js} +11 -23
- package/dist/{attempt-notifications-AP-a-Q5k.js → event-projector-usage-CLwNEJqW.js} +113 -29
- package/dist/harness-DoKQcF8n.js +258 -0
- package/dist/harness.js +2 -160
- package/dist/image-payload-sanitizer-CnfoUPCE.js +65 -0
- package/dist/index.js +730 -256
- package/dist/isolated-completion-DPMtlH9r.js +75 -0
- package/dist/local-runtime-attribution-B_2mnqhb.js +19 -0
- package/dist/managed-binary-By4FZC6i.js +212 -0
- package/dist/media-understanding-provider.js +5 -5
- package/dist/model-catalog-CmGoqVKB.js +48 -0
- package/dist/{models-BBMKU4jA.js → models-CZw1wClT.js} +12 -17
- package/dist/native-subagent-monitor-GGq3RnOo.js +3225 -0
- package/dist/node-exec-server.runtime-Bsu1LdFZ.js +192 -0
- package/dist/{plugin-app-cache-key-DztPafOA.js → plugin-app-cache-key-DMNQ8Zi8.js} +18 -6
- package/dist/plugin-approval-roundtrip-C75Yiiwc.js +95 -0
- package/dist/plugin-marketplace-discovery-CSWDkMrP.js +399 -0
- package/dist/{computer-use-CYEc8U3w.js → plugin-metadata-cache-BXH5NF-4.js} +109 -6
- package/dist/protocol-validators-VAVyEnDp.js +2399 -0
- package/dist/{rate-limits-CU-gVCCS.js → rate-limits-BI1dMHDG.js} +17 -35
- package/dist/{request-qKh331yu.js → request-DSK0W6YI.js} +3 -3
- package/dist/{run-attempt-CY9WlDLc.js → run-attempt-BV3HzuCf.js} +3416 -7194
- package/dist/{runtime-artifact-CmtG_t1L.js → runtime-artifact-BvyT1uyd.js} +11 -29
- package/dist/{sandbox-guard-NuhpXmPB.js → sandbox-guard-C1qEeZ5C.js} +29 -30
- package/dist/session-binding-BTrLf9Qm.js +874 -0
- package/dist/{session-catalog-DyOgR4WH.js → session-catalog-ezP_UcRM.js} +1584 -1289
- package/dist/session-catalog-home-id-BNwAJ9D7.js +18 -0
- package/dist/{session-cli-2PZaFLRh.js → session-cli-B1hKvfkI.js} +20 -7
- package/dist/session-retirement-CE4iMiLh.js +36 -0
- package/dist/{session-upstream-marker-B6U7tLw5.js → session-upstream-marker-D_2npHlA.js} +1 -1
- package/dist/{settled-turn-finalizer-CXY2Z9dT.js → settled-turn-finalizer-Dx1onIqg.js} +40 -28
- package/dist/{shared-client-DTbvH-XV.js → shared-client-Dw-rzii0.js} +1315 -469
- package/dist/{side-question-_ulBk1AL.js → side-question-DbXkJZzg.js} +140 -69
- package/dist/{thread-lifecycle-DF53ogiA.js → thread-lifecycle-DKdrnTMX.js} +927 -768
- package/dist/thread-ownership-i2NBwDUL.js +92 -0
- package/dist/thread-resume-CdJk2Ehf.js +30 -0
- package/dist/transcript-mirror-BU0_LKAL.js +588 -0
- package/dist/{transport-stdio-DXgGZ7Ib.js → transport-stdio-DhoGy33Z.js} +13 -2
- package/dist/upstream-prompt-provenance-CFmsKwr9.js +39 -0
- package/dist/{upstream-session-fork-Dy4Xvuoj.js → upstream-session-fork-BDVJCLAD.js} +14 -8
- package/dist/{usage-CQ6GhD5-.js → usage-9dKJCgcy.js} +3 -3
- package/dist/{web-search-provider.runtime-CCFhg2z5.js → web-search-provider.runtime-DCdx4DGu.js} +8 -9
- package/openclaw.plugin.json +49 -4
- package/package.json +6 -5
- package/dist/app-server-policy-BSaO2JIT.js +0 -49
- package/dist/conversation-control-xsIeXbo4.js +0 -287
- package/dist/event-projector-usage-Xp4AlR2k.js +0 -86
- package/dist/notification-correlation-CU6_AnOb.js +0 -67
- package/dist/transcript-mirror-DzsdNCf5.js +0 -6924
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { h as readCodexPluginConfig, i as resolveCodexAppServerRuntimeOptions, s as resolveCodexSupervisionAppServerRuntimeOptions } from "./config-CpNeo5AE.js";
|
|
2
|
+
import { a as resolveCodexCatalogConnectionHome, t as buildCodexAppServerConnectionFingerprint } from "./plugin-app-cache-key-DMNQ8Zi8.js";
|
|
3
|
+
//#region extensions/codex/src/app-server/binding-connection.ts
|
|
4
|
+
/** Requires the native model pair after a supervised pending branch has materialized. */
|
|
5
|
+
function requireCodexSupervisionModelSelection(binding) {
|
|
6
|
+
const model = binding.model?.trim();
|
|
7
|
+
const modelProvider = binding.modelProvider?.trim();
|
|
8
|
+
if (binding.connectionScope !== "supervision" || !model || !modelProvider) throw new Error("Codex supervised binding is missing its native model and provider; refusing request selection");
|
|
9
|
+
return {
|
|
10
|
+
model,
|
|
11
|
+
modelProvider
|
|
12
|
+
};
|
|
13
|
+
}
|
|
14
|
+
/** Resolves connection and auth ownership exclusively from the private thread binding. */
|
|
15
|
+
function resolveCodexBindingAppServerConnection(params) {
|
|
16
|
+
const { binding, authProfileId, ...runtimeParams } = params;
|
|
17
|
+
const usesSupervisionConnection = binding?.connectionScope === "supervision";
|
|
18
|
+
if (usesSupervisionConnection && readCodexPluginConfig(runtimeParams.pluginConfig).supervision?.enabled !== true) throw new Error("Codex supervision is disabled; refusing to open a native user-home supervised session");
|
|
19
|
+
let appServer = (usesSupervisionConnection ? resolveCodexSupervisionAppServerRuntimeOptions : resolveCodexAppServerRuntimeOptions)(runtimeParams);
|
|
20
|
+
if (usesSupervisionConnection) {
|
|
21
|
+
const persistedFingerprint = binding.pendingSupervisionBranch?.connectionFingerprint ?? binding.appServerRuntimeFingerprint;
|
|
22
|
+
const catalogHome = persistedFingerprint ? resolveCodexCatalogConnectionHome(persistedFingerprint, runtimeParams.agentDir) : void 0;
|
|
23
|
+
if (catalogHome) appServer = {
|
|
24
|
+
...appServer,
|
|
25
|
+
start: {
|
|
26
|
+
...appServer.start,
|
|
27
|
+
homeScope: "user",
|
|
28
|
+
env: {
|
|
29
|
+
...appServer.start.env,
|
|
30
|
+
CODEX_HOME: catalogHome
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
};
|
|
34
|
+
const currentFingerprint = buildCodexAppServerConnectionFingerprint(appServer, runtimeParams.agentDir);
|
|
35
|
+
if (!persistedFingerprint || persistedFingerprint !== currentFingerprint) throw new Error("Codex supervision connection changed; refusing to operate on its bound native thread");
|
|
36
|
+
}
|
|
37
|
+
return {
|
|
38
|
+
appServer,
|
|
39
|
+
usesSupervisionConnection,
|
|
40
|
+
requestAuthProfileId: usesSupervisionConnection ? void 0 : authProfileId,
|
|
41
|
+
clientAuthProfileId: usesSupervisionConnection ? null : authProfileId
|
|
42
|
+
};
|
|
43
|
+
}
|
|
44
|
+
//#endregion
|
|
45
|
+
export { resolveCodexBindingAppServerConnection as n, requireCodexSupervisionModelSelection as t };
|
|
@@ -1,23 +1,22 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
1
|
+
import { i as resolveCodexAppServerRuntimeOptions } from "./config-CpNeo5AE.js";
|
|
2
|
+
import { V as createCodexElicitationResponse, s as isCodexAppServerStartSelectionChangedError, ut as isJsonObject } from "./shared-client-Dw-rzii0.js";
|
|
3
|
+
import { _ as readCodexNotificationTurnId, a as closeCodexStartupClientBestEffort, o as interruptCodexTurnAndWaitBestEffort, t as CODEX_APP_SERVER_INTERRUPT_TIMEOUT_MS } from "./attempt-client-cleanup-URjUlCHg.js";
|
|
4
|
+
import { b as isTerminalTurnStatus, n as normalizeCodexResponseTokenUsage, x as readCodexNotificationItem, y as isRetryableErrorNotification } from "./event-projector-usage-CLwNEJqW.js";
|
|
5
|
+
import { a as assertCodexThreadStartResponse, c as readCodexErrorNotification, o as assertCodexTurnStartResponse, u as readCodexTurnCompletedNotification } from "./protocol-validators-VAVyEnDp.js";
|
|
6
|
+
import { r as readModelListResult } from "./models-CZw1wClT.js";
|
|
7
|
+
import { Z as mergeCodexThreadConfigs, c as buildCodexRingZeroThreadConfigPatch, l as buildCodexRuntimeThreadConfig, o as assertCodexManagedRequirementsDoNotOverrideToolPolicy, s as attestCodexRestrictedToolSurfaceMcpServersDisabled, u as readCodexInheritedMcpServerNames } from "./thread-lifecycle-DKdrnTMX.js";
|
|
8
|
+
import { readStringField } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
8
9
|
import fs from "node:fs/promises";
|
|
9
10
|
import path from "node:path";
|
|
11
|
+
import { createDeferred } from "openclaw/plugin-sdk/extension-shared";
|
|
10
12
|
import { resolveTimerTimeoutMs } from "openclaw/plugin-sdk/number-runtime";
|
|
11
13
|
import { resolvePreferredOpenClawTmpDir, withTempWorkspace } from "openclaw/plugin-sdk/temp-path";
|
|
12
14
|
//#region extensions/codex/src/app-server/bounded-turn.ts
|
|
13
|
-
const CODEX_PRIVATE_STDIO_ARGS = [
|
|
14
|
-
"app-server",
|
|
15
|
-
"--listen",
|
|
16
|
-
"stdio://"
|
|
17
|
-
];
|
|
18
15
|
const CODEX_APP_SERVER_ARGS_ENV_KEY = "OPENCLAW_CODEX_APP_SERVER_ARGS";
|
|
19
16
|
const CODEX_BOUNDED_THREAD_CONFIG = {
|
|
17
|
+
"agents.enabled": false,
|
|
20
18
|
"features.multi_agent": false,
|
|
19
|
+
"features.multi_agent_v2": false,
|
|
21
20
|
"features.apps": false,
|
|
22
21
|
"features.plugins": false,
|
|
23
22
|
"features.image_generation": false,
|
|
@@ -66,19 +65,26 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
66
65
|
const timeoutMs = deadline - Date.now();
|
|
67
66
|
if (timeoutMs <= 0) throw timeoutError;
|
|
68
67
|
const agentDir = params.agentDir?.trim() || void 0;
|
|
69
|
-
const
|
|
68
|
+
const isolatedStartOptions = workspace.codexHome ? buildPrivateCodexAppServerStartOptions(appServer.start, workspace.codexHome) : appServer.start;
|
|
69
|
+
const startOptions = workspace.codexHome && params.preparedAuth ? {
|
|
70
|
+
...isolatedStartOptions,
|
|
71
|
+
homeScope: "agent"
|
|
72
|
+
} : isolatedStartOptions;
|
|
70
73
|
const ownsClient = !params.options.clientFactory;
|
|
74
|
+
const authSelection = params.preparedAuth ? { preparedAuth: params.preparedAuth } : { authProfileId: params.profile };
|
|
71
75
|
const client = params.options.clientFactory ? await params.options.clientFactory({
|
|
72
76
|
startOptions,
|
|
73
|
-
|
|
77
|
+
...authSelection,
|
|
78
|
+
authRequirement: params.authRequirement,
|
|
74
79
|
agentDir,
|
|
75
80
|
config: params.config,
|
|
76
81
|
timeoutMs,
|
|
77
82
|
...params.signal ? { abandonSignal: params.signal } : {}
|
|
78
|
-
}) : await import("./shared-client-
|
|
83
|
+
}) : await import("./shared-client-Dw-rzii0.js").then((n) => n.m).then(({ createIsolatedCodexAppServerClient }) => createIsolatedCodexAppServerClient({
|
|
79
84
|
startOptions,
|
|
80
85
|
timeoutMs,
|
|
81
|
-
|
|
86
|
+
...authSelection,
|
|
87
|
+
authRequirement: params.authRequirement,
|
|
82
88
|
agentDir,
|
|
83
89
|
authProfileStore: params.authProfileStore,
|
|
84
90
|
config: params.config,
|
|
@@ -109,7 +115,7 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
109
115
|
timeout.unref?.();
|
|
110
116
|
let retrySelection = false;
|
|
111
117
|
try {
|
|
112
|
-
const
|
|
118
|
+
const modelSelection = await resolveCodexBoundedTurnModel({
|
|
113
119
|
client,
|
|
114
120
|
selection: params.model,
|
|
115
121
|
requiredModalities: params.requiredModalities,
|
|
@@ -117,17 +123,18 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
117
123
|
signal: abortController.signal
|
|
118
124
|
});
|
|
119
125
|
const inheritedMcpServerNames = params.requireNoExternalCapabilities ? await readCodexInheritedMcpServerNames(client, workspace.cwd, abortController.signal) : [];
|
|
120
|
-
if (params.requireNoExternalCapabilities) await
|
|
126
|
+
if (params.requireNoExternalCapabilities) await assertCodexManagedRequirementsDoNotOverrideToolPolicy(client, { restrictedToolSurface: true }, abortController.signal);
|
|
127
|
+
const threadConfig = buildCodexRuntimeThreadConfig(resolveBoundedThreadConfig(params, workspace, inheritedMcpServerNames), { nativeCodeModeEnabled: false });
|
|
121
128
|
const thread = assertCodexThreadStartResponse(await client.request("thread/start", {
|
|
122
|
-
model,
|
|
123
|
-
modelProvider:
|
|
129
|
+
model: modelSelection.runtimeModelId,
|
|
130
|
+
...params.modelProvider ? { modelProvider: params.modelProvider } : {},
|
|
124
131
|
cwd: workspace.cwd,
|
|
125
132
|
approvalPolicy: "on-request",
|
|
126
133
|
sandbox: "read-only",
|
|
127
134
|
serviceName: "OpenClaw",
|
|
128
135
|
...params.requireNoExternalCapabilities ? { baseInstructions: "" } : {},
|
|
129
136
|
developerInstructions: params.developerInstructions,
|
|
130
|
-
config:
|
|
137
|
+
config: threadConfig,
|
|
131
138
|
environments: [],
|
|
132
139
|
dynamicTools: [],
|
|
133
140
|
experimentalRawEvents: true,
|
|
@@ -138,7 +145,7 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
138
145
|
}));
|
|
139
146
|
activeThreadId = thread.thread.id;
|
|
140
147
|
if (abortController.signal.aborted) requestInterrupt();
|
|
141
|
-
if (params.requireNoExternalCapabilities) await
|
|
148
|
+
if (params.requireNoExternalCapabilities) await attestCodexRestrictedToolSurfaceMcpServersDisabled(client, thread.thread.id, threadConfig, abortController.signal);
|
|
142
149
|
if (params.historyItems?.length) await client.request("thread/inject_items", {
|
|
143
150
|
threadId: thread.thread.id,
|
|
144
151
|
items: params.historyItems
|
|
@@ -146,16 +153,15 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
146
153
|
timeoutMs,
|
|
147
154
|
signal: abortController.signal
|
|
148
155
|
});
|
|
149
|
-
const collector = createCodexBoundedTurnCollector(thread.thread.id, params.taskLabel);
|
|
156
|
+
const collector = createCodexBoundedTurnCollector(thread.thread.id, params.taskLabel, params.allowEmptyText === true);
|
|
150
157
|
const cleanup = client.addNotificationHandler(collector.handleNotification);
|
|
151
158
|
const requestCleanup = client.addRequestHandler(createCodexBoundedApprovalHandler(params.taskLabel));
|
|
152
159
|
try {
|
|
153
160
|
const turn = assertCodexTurnStartResponse(await client.request("turn/start", {
|
|
154
161
|
threadId: thread.thread.id,
|
|
155
162
|
input: params.input,
|
|
156
|
-
cwd: workspace.cwd,
|
|
157
163
|
approvalPolicy: "on-request",
|
|
158
|
-
model,
|
|
164
|
+
model: modelSelection.runtimeModelId,
|
|
159
165
|
effort: "low"
|
|
160
166
|
}, {
|
|
161
167
|
timeoutMs,
|
|
@@ -168,9 +174,10 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
168
174
|
signal: abortController.signal,
|
|
169
175
|
timeoutError
|
|
170
176
|
}),
|
|
171
|
-
model
|
|
177
|
+
model: modelSelection.catalogId
|
|
172
178
|
};
|
|
173
179
|
} finally {
|
|
180
|
+
await interruptPromise;
|
|
174
181
|
requestCleanup();
|
|
175
182
|
cleanup();
|
|
176
183
|
}
|
|
@@ -182,7 +189,7 @@ async function runBoundedCodexAppServerTurnInWorkspace(params, appServer, worksp
|
|
|
182
189
|
clearTimeout(timeout);
|
|
183
190
|
params.signal?.removeEventListener("abort", abortFromCaller);
|
|
184
191
|
await interruptPromise;
|
|
185
|
-
if (ownsClient) client
|
|
192
|
+
if (ownsClient) await closeCodexStartupClientBestEffort(client);
|
|
186
193
|
}
|
|
187
194
|
if (retrySelection) return await runBoundedCodexAppServerTurnInWorkspace(params, appServer, workspace, selectionAttempt + 1, {
|
|
188
195
|
deadline,
|
|
@@ -197,6 +204,10 @@ function resolveBoundedThreadConfig(params, workspace, inheritedMcpServerNames)
|
|
|
197
204
|
return mergeCodexThreadConfigs(privateConfig, CODEX_SETTLED_FINALIZER_THREAD_CONFIG, buildCodexRingZeroThreadConfigPatch({ toolsAllow: ["openclaw"] }, true, inheritedMcpServerNames)) ?? privateConfig;
|
|
198
205
|
}
|
|
199
206
|
function buildPrivateCodexAppServerStartOptions(start, codexHome) {
|
|
207
|
+
const providerArgs = start.args.flatMap((arg, index) => {
|
|
208
|
+
const override = arg === "-c" || arg === "--config" ? start.args[index + 1] : arg.startsWith("--config=") ? arg.slice(9) : void 0;
|
|
209
|
+
return override && /^\s*(?:openai_base_url|model_catalog_json)\s*=/u.test(override) ? ["-c", override] : [];
|
|
210
|
+
});
|
|
200
211
|
const privateEnv = Object.fromEntries(Object.entries(start.env ?? {}).filter(([name]) => name.trim().toUpperCase() !== CODEX_APP_SERVER_ARGS_ENV_KEY));
|
|
201
212
|
const clearEnv = (start.clearEnv ?? []).filter((name) => {
|
|
202
213
|
const normalized = name.trim().toUpperCase();
|
|
@@ -204,7 +215,12 @@ function buildPrivateCodexAppServerStartOptions(start, codexHome) {
|
|
|
204
215
|
});
|
|
205
216
|
return {
|
|
206
217
|
...start,
|
|
207
|
-
args: [
|
|
218
|
+
args: [
|
|
219
|
+
"app-server",
|
|
220
|
+
...providerArgs,
|
|
221
|
+
"--listen",
|
|
222
|
+
"stdio://"
|
|
223
|
+
],
|
|
208
224
|
env: {
|
|
209
225
|
...privateEnv,
|
|
210
226
|
CODEX_HOME: codexHome
|
|
@@ -226,7 +242,7 @@ function createCodexBoundedApprovalHandler(taskLabel) {
|
|
|
226
242
|
decision: "decline",
|
|
227
243
|
reason: `OpenClaw Codex ${taskLabel} does not grant native approvals.`
|
|
228
244
|
};
|
|
229
|
-
if (request.method === "mcpServer/elicitation/request") return {
|
|
245
|
+
if (request.method === "mcpServer/elicitation/request") return createCodexElicitationResponse("decline", null, { message: `OpenClaw Codex ${taskLabel} does not support interactive input.` });
|
|
230
246
|
};
|
|
231
247
|
}
|
|
232
248
|
async function resolveCodexBoundedTurnModel(params) {
|
|
@@ -242,16 +258,22 @@ async function resolveCodexBoundedTurnModel(params) {
|
|
|
242
258
|
const supported = listed.filter((entry) => params.requiredModalities.every((modality) => entry.inputModalities.includes(modality)));
|
|
243
259
|
const selected = supported.find((entry) => entry.isDefault) ?? supported[0];
|
|
244
260
|
if (!selected) throw new Error(`Codex app-server has no model supporting ${params.requiredModalities.join(" and ")} input.`);
|
|
245
|
-
return
|
|
261
|
+
return {
|
|
262
|
+
catalogId: selected.id,
|
|
263
|
+
runtimeModelId: selected.model
|
|
264
|
+
};
|
|
246
265
|
}
|
|
247
266
|
const model = params.selection.id;
|
|
248
267
|
const match = listed.find((entry) => entry.model === model || entry.id === model);
|
|
249
268
|
if (!match) throw new Error(`Codex app-server model not found: ${model}`);
|
|
250
269
|
if (params.requiredModalities.includes("image") && !match.inputModalities.includes("image")) throw new Error(`Codex app-server model does not support images: ${model}`);
|
|
251
270
|
if (params.requiredModalities.includes("text") && !match.inputModalities.includes("text")) throw new Error(`Codex app-server model does not support text: ${model}`);
|
|
252
|
-
return
|
|
271
|
+
return {
|
|
272
|
+
catalogId: match.id,
|
|
273
|
+
runtimeModelId: match.model
|
|
274
|
+
};
|
|
253
275
|
}
|
|
254
|
-
function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
276
|
+
function createCodexBoundedTurnCollector(threadId, taskLabel, allowEmptyText) {
|
|
255
277
|
let turnId;
|
|
256
278
|
let completedTurn;
|
|
257
279
|
let promptError;
|
|
@@ -260,10 +282,7 @@ function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
|
260
282
|
const completedItems = /* @__PURE__ */ new Map();
|
|
261
283
|
const assistantTextByItem = /* @__PURE__ */ new Map();
|
|
262
284
|
const assistantItemOrder = [];
|
|
263
|
-
|
|
264
|
-
const completion = new Promise((resolve) => {
|
|
265
|
-
resolveCompletion = resolve;
|
|
266
|
-
});
|
|
285
|
+
const { promise: completion, resolve: resolveCompletion } = createDeferred();
|
|
267
286
|
const rememberAssistantText = (itemId, text) => {
|
|
268
287
|
if (!text) return;
|
|
269
288
|
if (!assistantTextByItem.has(itemId)) assistantItemOrder.push(itemId);
|
|
@@ -271,12 +290,12 @@ function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
|
271
290
|
};
|
|
272
291
|
const handleNotification = (notification) => {
|
|
273
292
|
const params = isJsonObject(notification.params) ? notification.params : void 0;
|
|
274
|
-
if (!params ||
|
|
293
|
+
if (!params || readStringField(params, "threadId") !== threadId) return;
|
|
275
294
|
if (!turnId) {
|
|
276
295
|
pending.push(notification);
|
|
277
296
|
return;
|
|
278
297
|
}
|
|
279
|
-
if (
|
|
298
|
+
if (readCodexNotificationTurnId(params) !== turnId) return;
|
|
280
299
|
if (notification.method === "item/completed") {
|
|
281
300
|
const item = readCodexNotificationItem(notification.params);
|
|
282
301
|
if (item) {
|
|
@@ -286,8 +305,8 @@ function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
|
286
305
|
return;
|
|
287
306
|
}
|
|
288
307
|
if (notification.method === "item/agentMessage/delta") {
|
|
289
|
-
const itemId =
|
|
290
|
-
const delta =
|
|
308
|
+
const itemId = readStringField(params, "itemId") ?? readStringField(params, "id") ?? "assistant";
|
|
309
|
+
const delta = readStringField(params, "delta") ?? "";
|
|
291
310
|
rememberAssistantText(itemId, `${assistantTextByItem.get(itemId) ?? ""}${delta}`);
|
|
292
311
|
return;
|
|
293
312
|
}
|
|
@@ -298,20 +317,20 @@ function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
|
298
317
|
}
|
|
299
318
|
if (notification.method === "turn/completed") {
|
|
300
319
|
completedTurn = readCodexTurnCompletedNotification(notification.params)?.turn ?? completedTurn;
|
|
301
|
-
resolveCompletion
|
|
320
|
+
resolveCompletion();
|
|
302
321
|
return;
|
|
303
322
|
}
|
|
304
323
|
if (notification.method === "error") {
|
|
305
324
|
if (isRetryableErrorNotification(notification.params)) return;
|
|
306
325
|
promptError = readCodexErrorNotification(notification.params)?.error.message ?? `codex app-server ${taskLabel} turn failed`;
|
|
307
|
-
resolveCompletion
|
|
326
|
+
resolveCompletion();
|
|
308
327
|
}
|
|
309
328
|
};
|
|
310
329
|
return {
|
|
311
330
|
handleNotification,
|
|
312
331
|
async collect(startedTurn, options) {
|
|
313
332
|
turnId = startedTurn.id;
|
|
314
|
-
if (
|
|
333
|
+
if (isTerminalTurnStatus(startedTurn.status)) completedTurn = startedTurn;
|
|
315
334
|
for (const notification of pending.splice(0)) handleNotification(notification);
|
|
316
335
|
if (!completedTurn && !promptError) await waitForTurnCompletion({
|
|
317
336
|
completion,
|
|
@@ -326,7 +345,7 @@ function createCodexBoundedTurnCollector(threadId, taskLabel) {
|
|
|
326
345
|
const itemText = collectAssistantTextFromItems(items);
|
|
327
346
|
const deltaText = assistantItemOrder.map((itemId) => assistantTextByItem.get(itemId)?.trim()).filter((text) => Boolean(text)).join("\n\n").trim();
|
|
328
347
|
const text = (itemText || deltaText).trim();
|
|
329
|
-
if (!text) throw new Error(`Codex app-server ${taskLabel} turn returned no text.`);
|
|
348
|
+
if (!text && !allowEmptyText) throw new Error(`Codex app-server ${taskLabel} turn returned no text.`);
|
|
330
349
|
return {
|
|
331
350
|
text,
|
|
332
351
|
items,
|
|
@@ -359,17 +378,5 @@ function resolveCodexBoundedTurnAbortError(signal, taskLabel, timeoutError) {
|
|
|
359
378
|
function collectAssistantTextFromItems(items) {
|
|
360
379
|
return (items ?? []).filter((item) => item.type === "agentMessage").map((item) => item.text.trim()).filter(Boolean).join("\n\n").trim();
|
|
361
380
|
}
|
|
362
|
-
function readNotificationTurnId(record) {
|
|
363
|
-
const direct = readString(record, "turnId");
|
|
364
|
-
if (direct) return direct;
|
|
365
|
-
return isJsonObject(record.turn) ? readString(record.turn, "id") : void 0;
|
|
366
|
-
}
|
|
367
|
-
function readString(record, key) {
|
|
368
|
-
const value = record[key];
|
|
369
|
-
return typeof value === "string" ? value : void 0;
|
|
370
|
-
}
|
|
371
|
-
function isTerminalTurn(turn) {
|
|
372
|
-
return turn.status === "completed" || turn.status === "interrupted" || turn.status === "failed";
|
|
373
|
-
}
|
|
374
381
|
//#endregion
|
|
375
382
|
export { runBoundedCodexAppServerTurn as t };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { B as CodexAppServerRpcError } from "./shared-client-Dw-rzii0.js";
|
|
2
2
|
//#region extensions/codex/src/app-server/capabilities.ts
|
|
3
3
|
/**
|
|
4
4
|
* Capability helpers for optional Codex app-server control-plane methods.
|
|
@@ -6,10 +6,14 @@ import { v as CodexAppServerRpcError } from "./shared-client-DTbvH-XV.js";
|
|
|
6
6
|
/** Known app-server methods used by OpenClaw control surfaces. */
|
|
7
7
|
const CODEX_CONTROL_METHODS = {
|
|
8
8
|
account: "account/read",
|
|
9
|
-
|
|
9
|
+
installedApps: "app/installed",
|
|
10
|
+
listApps: "app/list",
|
|
11
|
+
readApps: "app/read",
|
|
10
12
|
feedback: "feedback/upload",
|
|
11
13
|
forkThread: "thread/fork",
|
|
14
|
+
listHooks: "hooks/list",
|
|
12
15
|
listMcpServers: "mcpServerStatus/list",
|
|
16
|
+
listPlugins: "plugin/list",
|
|
13
17
|
listSkills: "skills/list",
|
|
14
18
|
listThreads: "thread/list",
|
|
15
19
|
listThreadTurns: "thread/turns/list",
|
|
@@ -19,6 +23,8 @@ const CODEX_CONTROL_METHODS = {
|
|
|
19
23
|
renameThread: "thread/name/set",
|
|
20
24
|
resumeThread: "thread/resume",
|
|
21
25
|
review: "review/start",
|
|
26
|
+
installPlugin: "plugin/install",
|
|
27
|
+
reloadMcpServers: "config/mcpServer/reload",
|
|
22
28
|
unarchiveThread: "thread/unarchive",
|
|
23
29
|
getThreadGoal: "thread/goal/get",
|
|
24
30
|
setThreadGoal: "thread/goal/set",
|
package/dist/cli-metadata.js
CHANGED
|
@@ -2,7 +2,7 @@ import { definePluginEntry } from "openclaw/plugin-sdk/plugin-entry";
|
|
|
2
2
|
//#region extensions/codex/cli-metadata.ts
|
|
3
3
|
function registerCodexCliMetadata(api) {
|
|
4
4
|
api.registerCli(async ({ program }) => {
|
|
5
|
-
const { registerCodexSessionCli } = await import("./session-cli-
|
|
5
|
+
const { registerCodexSessionCli } = await import("./session-cli-B1hKvfkI.js");
|
|
6
6
|
registerCodexSessionCli(program);
|
|
7
7
|
}, { descriptors: [{
|
|
8
8
|
name: "codex",
|
|
@@ -1,6 +1,11 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { c as summarizeCodexRateLimits, o as summarizeCodexAccountRateLimits, r as hasCodexRateLimitSnapshots } from "./rate-limits-
|
|
1
|
+
import { ut as isJsonObject } from "./shared-client-Dw-rzii0.js";
|
|
2
|
+
import { c as summarizeCodexRateLimits, o as summarizeCodexAccountRateLimits, r as hasCodexRateLimitSnapshots } from "./rate-limits-BI1dMHDG.js";
|
|
3
|
+
import { normalizeOptionalString } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
3
4
|
//#region extensions/codex/src/command-formatters.ts
|
|
5
|
+
/**
|
|
6
|
+
* Formats Codex command responses for safe chat display, including status,
|
|
7
|
+
* lists, account summaries, and user-facing help text.
|
|
8
|
+
*/
|
|
4
9
|
/** Formats the combined `/codex status` probe result. */
|
|
5
10
|
function formatCodexStatus(probes) {
|
|
6
11
|
const lines = [`Codex app-server: ${probes.models.ok || probes.account.ok || probes.limits.ok || probes.mcps.ok || probes.skills.ok ? "connected" : "unavailable"}`];
|
|
@@ -25,12 +30,12 @@ function formatThreads(response) {
|
|
|
25
30
|
if (threads.length === 0) return "No Codex threads returned.";
|
|
26
31
|
return ["Codex threads:", ...threads.slice(0, 10).map((thread) => {
|
|
27
32
|
const record = isJsonObject(thread) ? thread : {};
|
|
28
|
-
const id =
|
|
29
|
-
const title =
|
|
33
|
+
const id = normalizeOptionalString(record.threadId) ?? normalizeOptionalString(record.id) ?? "<unknown>";
|
|
34
|
+
const title = normalizeOptionalString(record.title) ?? normalizeOptionalString(record.name) ?? normalizeOptionalString(record.summary);
|
|
30
35
|
const details = [
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
36
|
+
normalizeOptionalString(record.model),
|
|
37
|
+
normalizeOptionalString(record.cwd),
|
|
38
|
+
normalizeOptionalString(record.updatedAt) ?? normalizeOptionalString(record.lastUpdatedAt)
|
|
34
39
|
].filter((value) => Boolean(value));
|
|
35
40
|
return `- ${formatCodexDisplayText(id)}${title ? ` - ${formatCodexDisplayText(title)}` : ""}${details.length > 0 ? ` (${details.map(formatCodexDisplayText).join(", ")})` : ""}\n Resume: ${formatCodexResumeHint(id)}`;
|
|
36
41
|
})].join("\n");
|
|
@@ -85,7 +90,7 @@ function formatList(response, label) {
|
|
|
85
90
|
if (entries.length === 0) return `${label}: none returned.`;
|
|
86
91
|
return [`${label}:`, ...entries.slice(0, 25).map((entry) => {
|
|
87
92
|
const record = isJsonObject(entry) ? entry : {};
|
|
88
|
-
return `- ${formatCodexDisplayText(
|
|
93
|
+
return `- ${formatCodexDisplayText(normalizeOptionalString(record.name) ?? normalizeOptionalString(record.id) ?? JSON.stringify(entry))}`;
|
|
89
94
|
})].join("\n");
|
|
90
95
|
}
|
|
91
96
|
/** Formats Codex skills grouped by scope, omitting disabled entries. */
|
|
@@ -113,7 +118,7 @@ function formatSkills(response) {
|
|
|
113
118
|
return lines.join("\n");
|
|
114
119
|
}
|
|
115
120
|
function formatCodexSkillEntry(entry) {
|
|
116
|
-
return `\`${formatCodexDisplayText(
|
|
121
|
+
return `\`${formatCodexDisplayText(normalizeOptionalString((isJsonObject(entry) ? entry : {}).name) ?? "<unknown>")}\``;
|
|
117
122
|
}
|
|
118
123
|
const CODEX_RESUME_SAFE_THREAD_ID_PATTERN = /^[A-Za-z0-9._:-]+$/;
|
|
119
124
|
function formatCodexResumeHint(threadId) {
|
|
@@ -200,8 +205,8 @@ function buildHelp() {
|
|
|
200
205
|
function summarizeAccount(value) {
|
|
201
206
|
if (!isJsonObject(value)) return "unavailable";
|
|
202
207
|
const account = isJsonObject(value.account) ? value.account : value;
|
|
203
|
-
if (
|
|
204
|
-
return
|
|
208
|
+
if (normalizeOptionalString(account.type) === "amazonBedrock") return "Amazon Bedrock";
|
|
209
|
+
return normalizeOptionalString(account.email) ?? normalizeOptionalString(account.accountEmail) ?? normalizeOptionalString(account.planType) ?? normalizeOptionalString(account.id) ?? "available";
|
|
205
210
|
}
|
|
206
211
|
function summarizeArrayLike(value) {
|
|
207
212
|
const entries = extractArray(value);
|
|
@@ -249,7 +254,7 @@ function summarizeRateLimits(value) {
|
|
|
249
254
|
}
|
|
250
255
|
function isMeaningfulRateLimitSnapshot(value) {
|
|
251
256
|
if (!isJsonObject(value)) return false;
|
|
252
|
-
if (
|
|
257
|
+
if (normalizeOptionalString(value.rateLimitReachedType) ?? normalizeOptionalString(value.rate_limit_reached_type)) return true;
|
|
253
258
|
return ["primary", "secondary"].some((key) => {
|
|
254
259
|
const window = value[key];
|
|
255
260
|
return isJsonObject(window) && Object.values(window).some((entry) => entry != null);
|
|
@@ -272,10 +277,5 @@ function extractArray(value) {
|
|
|
272
277
|
}
|
|
273
278
|
return [];
|
|
274
279
|
}
|
|
275
|
-
/** Reads and trims a non-empty string field from a JSON object. */
|
|
276
|
-
function readString(record, key) {
|
|
277
|
-
const value = record[key];
|
|
278
|
-
return typeof value === "string" && value.trim() ? value.trim() : void 0;
|
|
279
|
-
}
|
|
280
280
|
//#endregion
|
|
281
|
-
export { formatComputerUseStatus as a, formatSkills as c, formatCodexStatus as i, formatThreads as l, formatAccount as n, formatList as o, formatCodexDisplayText as r, formatModels as s, buildHelp as t
|
|
281
|
+
export { formatComputerUseStatus as a, formatSkills as c, formatCodexStatus as i, formatThreads as l, formatAccount as n, formatList as o, formatCodexDisplayText as r, formatModels as s, buildHelp as t };
|