@yansigit/opencodex 2.31.3 → 2.33.0
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 -2
- package/bin/ocx.mjs +99 -70
- package/gui/dist/assets/index-DKLr4LTE.js +102 -0
- package/gui/dist/assets/index-DrSQdTRd.css +1 -0
- package/gui/dist/index.html +2 -2
- package/package.json +6 -5
- package/src/adapters/anthropic.ts +25 -13
- package/src/adapters/azure.ts +20 -4
- package/src/adapters/base.ts +5 -1
- package/src/adapters/command-code.ts +42 -10
- package/src/adapters/cursor/live-models.ts +8 -0
- package/src/adapters/cursor/live-transport.ts +1 -1
- package/src/adapters/cursor/native-exec-desktop.ts +16 -0
- package/src/adapters/cursor/protobuf-events.ts +158 -7
- package/src/adapters/cursor/protobuf-request.ts +33 -15
- package/src/adapters/cursor/request-builder.ts +4 -3
- package/src/adapters/cursor/tool-definitions.ts +27 -1
- package/src/adapters/cursor/types.ts +4 -3
- package/src/adapters/cursor.ts +9 -0
- package/src/adapters/google-antigravity-replay.ts +2 -2
- package/src/adapters/google-antigravity-wire.ts +7 -0
- package/src/adapters/google-errors.ts +6 -2
- package/src/adapters/google-http.ts +30 -7
- package/src/adapters/google-truncation.ts +5 -0
- package/src/adapters/google-wire-compiler.ts +38 -6
- package/src/adapters/google.ts +154 -33
- package/src/adapters/kiro-tools.ts +20 -9
- package/src/adapters/kiro.ts +0 -3
- package/src/adapters/openai-chat.ts +9 -0
- package/src/adapters/openai-responses.ts +4 -1
- package/src/adapters/tool-catalog-nudge.ts +1 -1
- package/src/adapters/xai-web-search.ts +7 -2
- package/src/bridge.ts +133 -24
- package/src/claude/context-windows.ts +16 -9
- package/src/cli/dispatch.ts +50 -2
- package/src/cli/doctor.ts +26 -13
- package/src/cli/help.ts +4 -3
- package/src/cli/index.ts +20 -6
- package/src/cli/models.ts +13 -3
- package/src/cli/observe.ts +20 -5
- package/src/cli/provider.ts +8 -1
- package/src/cli/registry.ts +7 -5
- package/src/cli/status.ts +25 -1
- package/src/cli/system-restart-client.ts +1 -1
- package/src/cli/usage-report.ts +134 -0
- package/src/codex/app-server-processes.ts +3 -1
- package/src/codex/auth-api.ts +4 -2
- package/src/codex/autostart-health.ts +16 -0
- package/src/codex/catalog/aggregation.ts +12 -0
- package/src/codex/catalog/effort.ts +42 -12
- package/src/codex/catalog/metadata.ts +27 -1
- package/src/codex/catalog/model-metadata.ts +593 -0
- package/src/codex/catalog/parsing.ts +71 -27
- package/src/codex/catalog/provider-fetch.ts +189 -33
- package/src/codex/catalog/sync.ts +6 -5
- package/src/codex/convergence.ts +5 -0
- package/src/codex/desktop-app-restart.ts +342 -0
- package/src/codex/history-job.ts +32 -3
- package/src/codex/history-manifest.ts +112 -0
- package/src/codex/history-migration-guardian.ts +5 -5
- package/src/codex/history-provider.ts +825 -247
- package/src/codex/history-worker.ts +8 -5
- package/src/codex/inject.ts +49 -21
- package/src/codex/injected-marker.ts +1 -1
- package/src/codex/internal/history-writer.ts +4 -3
- package/src/codex/native-profile-startup.ts +157 -27
- package/src/codex/native-residue.ts +26 -33
- package/src/codex/shim.ts +56 -3
- package/src/combos/failover.ts +27 -0
- package/src/compatibility/index.ts +26 -0
- package/src/compatibility/manifest.ts +253 -0
- package/src/compatibility/openai-responses.ts +81 -0
- package/src/config/atomic-write.ts +219 -0
- package/src/config/paths.ts +40 -0
- package/src/config/process-state.ts +308 -0
- package/src/config/provider-validation.ts +214 -0
- package/src/config.ts +153 -814
- package/src/generated/compatibility-version.json +232 -148
- package/src/images/loop.ts +37 -6
- package/src/images/plan.ts +5 -4
- package/src/integrations/ownership-policy.ts +141 -0
- package/src/integrations/ownership.ts +10 -0
- package/src/integrations/state.ts +44 -5
- package/src/integrations/writer.ts +6 -0
- package/src/lib/azure-identity.ts +154 -0
- package/src/lib/bounded-body.ts +14 -2
- package/src/lib/debug.ts +42 -0
- package/src/lib/errors.ts +14 -0
- package/src/lib/process-control.ts +2 -1
- package/src/lib/provider-outbound.ts +45 -33
- package/src/lib/provider-tls-profile.ts +309 -0
- package/src/lib/proxy-env.ts +49 -0
- package/src/lib/redact.ts +10 -1
- package/src/lib/state-store-registrations.ts +2 -0
- package/src/lib/tool-argument-integers.ts +56 -5
- package/src/oauth/antigravity-routing.ts +282 -236
- package/src/oauth/callback-server.ts +22 -2
- package/src/oauth/command-code.ts +5 -16
- package/src/oauth/google-antigravity.ts +42 -5
- package/src/oauth/health.ts +1 -1
- package/src/oauth/index.ts +15 -3
- package/src/oauth/kimi.ts +9 -1
- package/src/oauth/open-browser-choice.ts +26 -0
- package/src/oauth/store.ts +6 -0
- package/src/providers/antigravity-quota.ts +3 -1
- package/src/providers/api-keys.ts +2 -1
- package/src/providers/auto-compact-budget.ts +65 -0
- package/src/providers/derive.ts +4 -0
- package/src/providers/key-failover.ts +5 -1
- package/src/providers/openai-tiers.ts +5 -0
- package/src/providers/provider-id-rewrite.ts +1 -0
- package/src/providers/quota.ts +59 -13
- package/src/providers/registry.ts +4 -2
- package/src/providers/request-pacing.ts +33 -6
- package/src/providers/xai-transport.ts +21 -0
- package/src/reasoning-effort.ts +19 -2
- package/src/responses/apply-patch-envelope.ts +63 -0
- package/src/responses/custom-tool-compat.ts +132 -38
- package/src/responses/google-provider-options.ts +36 -0
- package/src/responses/namespace-tool-compat.ts +84 -4
- package/src/responses/parser.ts +14 -2
- package/src/responses/provider-opaque-metadata.ts +3 -3
- package/src/responses/reasoning-replay-cache.ts +81 -3
- package/src/responses/schema.ts +37 -0
- package/src/responses/state.ts +94 -4
- package/src/router.ts +8 -2
- package/src/server/auth-cors.ts +37 -7
- package/src/server/images.ts +19 -35
- package/src/server/index.ts +102 -21
- package/src/server/local-management-read-client.ts +1 -1
- package/src/server/local-provider-reload-client.ts +1 -1
- package/src/server/management/agent-settings-routes.ts +206 -16
- package/src/server/management/combo-routes.ts +6 -0
- package/src/server/management/config-routes.ts +35 -6
- package/src/server/management/context.ts +1 -1
- package/src/server/management/logs-usage-routes.ts +27 -6
- package/src/server/management/model-routes.ts +8 -4
- package/src/server/management/model-rows.ts +4 -0
- package/src/server/management/native-integration-routes.ts +2 -1
- package/src/server/management/oauth-account-routes.ts +25 -4
- package/src/server/management/provider-capability-config.ts +1 -1
- package/src/server/management/provider-routes.ts +113 -15
- package/src/server/management/routing-profile-routes.ts +3 -0
- package/src/server/management/system-restart.ts +1 -1
- package/src/server/port-reclaim.ts +1 -1
- package/src/server/proxy-liveness.ts +2 -1
- package/src/server/request-log-conversation.ts +30 -0
- package/src/server/request-log.ts +21 -0
- package/src/server/responses/agent-task-recovery.ts +1 -1
- package/src/server/responses/codex-auth-error.ts +55 -0
- package/src/server/responses/combo-stream-preflight.ts +171 -0
- package/src/server/responses/compact.ts +36 -22
- package/src/server/responses/core.ts +584 -247
- package/src/server/responses/empty-completion-guard.ts +35 -6
- package/src/server/responses/fetch-helpers.ts +20 -102
- package/src/server/responses/v2-native-parent-override.ts +59 -0
- package/src/server/responses/ws-upstream.ts +75 -2
- package/src/server/responses-custom-tool-repair.ts +41 -5
- package/src/server/responses-undeclared-tool-guard.ts +241 -18
- package/src/service.ts +9 -5
- package/src/types/config.ts +16 -1
- package/src/types/provider.ts +16 -0
- package/src/types/request.ts +34 -1
- package/src/types/tools.ts +114 -11
- package/src/types.ts +7 -1
- package/src/update/index.ts +5 -4
- package/src/update/job.ts +3 -1
- package/src/update/transactional-install.mjs +8 -1
- package/src/usage/log.ts +16 -8
- package/src/usage/summary.ts +201 -8
- package/src/vision/describe.ts +18 -13
- package/src/web-search/executor.ts +10 -3
- package/src/web-search/gemini-executor.ts +6 -4
- package/src/web-search/loop.ts +42 -6
- package/gui/dist/assets/index-CGoDO3uO.css +0 -1
- package/gui/dist/assets/index-Cxt5fZMP.js +0 -102
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
import { formatErrorResponse } from "../../bridge";
|
|
2
|
+
import {
|
|
3
|
+
CodexAccountCooldownError,
|
|
4
|
+
codexMainProfileDrainingResponse,
|
|
5
|
+
cooldownErrorResponse,
|
|
6
|
+
CodexAuthContextError,
|
|
7
|
+
CodexDirectAuthenticationError,
|
|
8
|
+
CodexMainProfileDrainingError,
|
|
9
|
+
CodexMainSubstitutionUnavailableError,
|
|
10
|
+
CodexPoolAuthenticationError,
|
|
11
|
+
CodexThreadAffinityExpiredError,
|
|
12
|
+
} from "../../codex/auth-context";
|
|
13
|
+
|
|
14
|
+
export interface CodexAuthContextErrorResponseOptions {
|
|
15
|
+
accountSelector?: string;
|
|
16
|
+
now: number;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/** Shared HTTP contract for Codex auth-context failures on Responses surfaces. */
|
|
20
|
+
export function mapCodexAuthContextErrorToResponse(
|
|
21
|
+
error: unknown,
|
|
22
|
+
options: CodexAuthContextErrorResponseOptions,
|
|
23
|
+
): Response | undefined {
|
|
24
|
+
if (error instanceof CodexAccountCooldownError) {
|
|
25
|
+
return cooldownErrorResponse(error, options.now, options.accountSelector);
|
|
26
|
+
}
|
|
27
|
+
if (error instanceof CodexMainProfileDrainingError) {
|
|
28
|
+
return codexMainProfileDrainingResponse();
|
|
29
|
+
}
|
|
30
|
+
if (error instanceof CodexThreadAffinityExpiredError) {
|
|
31
|
+
return formatErrorResponse(
|
|
32
|
+
409,
|
|
33
|
+
"invalid_request_error",
|
|
34
|
+
"Codex thread account affinity expired; start a new session",
|
|
35
|
+
);
|
|
36
|
+
}
|
|
37
|
+
if (error instanceof CodexAuthContextError) {
|
|
38
|
+
return formatErrorResponse(
|
|
39
|
+
401,
|
|
40
|
+
"authentication_error",
|
|
41
|
+
"Selected Codex account needs reauthentication",
|
|
42
|
+
);
|
|
43
|
+
}
|
|
44
|
+
if (error instanceof CodexPoolAuthenticationError || error instanceof CodexDirectAuthenticationError) {
|
|
45
|
+
return formatErrorResponse(401, "authentication_error", error.message);
|
|
46
|
+
}
|
|
47
|
+
if (error instanceof CodexMainSubstitutionUnavailableError) {
|
|
48
|
+
return formatErrorResponse(
|
|
49
|
+
401,
|
|
50
|
+
"authentication_error",
|
|
51
|
+
"No usable Codex main credential to serve this request",
|
|
52
|
+
);
|
|
53
|
+
}
|
|
54
|
+
return undefined;
|
|
55
|
+
}
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import type { ResponsesTerminalStatus } from "../../bridge";
|
|
2
|
+
import type { RequestLogContext } from "../request-log";
|
|
3
|
+
import { createSseInspector } from "../relay";
|
|
4
|
+
import { MAX_CLIENT_SSE_FRAME_BYTES } from "../sse-frame-buffer";
|
|
5
|
+
|
|
6
|
+
const COMBO_STREAM_PREFLIGHT_MAX_BYTES = MAX_CLIENT_SSE_FRAME_BYTES;
|
|
7
|
+
|
|
8
|
+
const PRE_OUTPUT_CONTROL_EVENTS = new Set([
|
|
9
|
+
"response.created",
|
|
10
|
+
"response.in_progress",
|
|
11
|
+
"response.queued",
|
|
12
|
+
"response.heartbeat",
|
|
13
|
+
]);
|
|
14
|
+
|
|
15
|
+
const TERMINAL_EVENTS = new Set([
|
|
16
|
+
"response.completed",
|
|
17
|
+
"response.failed",
|
|
18
|
+
"response.incomplete",
|
|
19
|
+
]);
|
|
20
|
+
|
|
21
|
+
/**
|
|
22
|
+
* Decide when replaying the request on another combo target would risk duplicating
|
|
23
|
+
* client-visible output or a tool-side effect. Unknown event types commit the child
|
|
24
|
+
* conservatively; only the small Responses lifecycle preamble remains replayable.
|
|
25
|
+
*/
|
|
26
|
+
export function comboStreamPayloadCommitsOutput(payload: unknown): boolean {
|
|
27
|
+
if (!payload || typeof payload !== "object" || Array.isArray(payload)) return true;
|
|
28
|
+
const type = (payload as { type?: unknown }).type;
|
|
29
|
+
if (typeof type !== "string") return true;
|
|
30
|
+
return !PRE_OUTPUT_CONTROL_EVENTS.has(type) && !TERMINAL_EVENTS.has(type);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function replayBufferedResponse(
|
|
34
|
+
response: Response,
|
|
35
|
+
reader: ReadableStreamDefaultReader<Uint8Array>,
|
|
36
|
+
buffered: Uint8Array[],
|
|
37
|
+
): Response {
|
|
38
|
+
let index = 0;
|
|
39
|
+
const body = new ReadableStream<Uint8Array>({
|
|
40
|
+
async pull(controller) {
|
|
41
|
+
if (index < buffered.length) {
|
|
42
|
+
controller.enqueue(buffered[index++]!);
|
|
43
|
+
return;
|
|
44
|
+
}
|
|
45
|
+
try {
|
|
46
|
+
const next = await reader.read();
|
|
47
|
+
if (next.done) controller.close();
|
|
48
|
+
else controller.enqueue(next.value);
|
|
49
|
+
} catch (error) {
|
|
50
|
+
try { controller.error(error); } catch { /* consumer already closed */ }
|
|
51
|
+
}
|
|
52
|
+
},
|
|
53
|
+
cancel(reason) {
|
|
54
|
+
reader.cancel(reason).catch(() => undefined);
|
|
55
|
+
},
|
|
56
|
+
});
|
|
57
|
+
return new Response(body, {
|
|
58
|
+
status: response.status,
|
|
59
|
+
statusText: response.statusText,
|
|
60
|
+
headers: response.headers,
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
function failedTerminalResponse(
|
|
65
|
+
response: Response,
|
|
66
|
+
terminalPayload: Record<string, unknown>,
|
|
67
|
+
logCtx: RequestLogContext,
|
|
68
|
+
): Response {
|
|
69
|
+
const nested = terminalPayload.response;
|
|
70
|
+
const terminalResponse = nested && typeof nested === "object" && !Array.isArray(nested)
|
|
71
|
+
? nested as Record<string, unknown>
|
|
72
|
+
: {};
|
|
73
|
+
const nestedError = terminalResponse.error;
|
|
74
|
+
const error = nestedError && typeof nestedError === "object" && !Array.isArray(nestedError)
|
|
75
|
+
? nestedError as Record<string, unknown>
|
|
76
|
+
: {
|
|
77
|
+
type: "upstream_error",
|
|
78
|
+
code: "upstream_server_error",
|
|
79
|
+
message: logCtx.upstreamError ?? "Provider stream failed before producing output",
|
|
80
|
+
};
|
|
81
|
+
const headers = new Headers(response.headers);
|
|
82
|
+
headers.set("content-type", "application/json");
|
|
83
|
+
headers.delete("content-length");
|
|
84
|
+
headers.delete("content-encoding");
|
|
85
|
+
const usage = terminalResponse.usage;
|
|
86
|
+
return new Response(JSON.stringify({
|
|
87
|
+
error,
|
|
88
|
+
// The combo classifier needs only the error and optional usage. Do not carry
|
|
89
|
+
// response ids, provider metadata, or future terminal fields into the client
|
|
90
|
+
// error envelope merely because they shared the terminal snapshot.
|
|
91
|
+
response: {
|
|
92
|
+
error,
|
|
93
|
+
...(usage && typeof usage === "object" && !Array.isArray(usage) ? { usage } : {}),
|
|
94
|
+
},
|
|
95
|
+
}), {
|
|
96
|
+
status: logCtx.terminalHttpStatus ?? 502,
|
|
97
|
+
headers,
|
|
98
|
+
});
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
export type ComboStreamPreflightResult =
|
|
102
|
+
| { kind: "accepted"; response: Response }
|
|
103
|
+
| { kind: "failed"; response: Response };
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* Buffer a combo child's downstream SSE only until the request becomes unsafe to
|
|
107
|
+
* replay or reaches a terminal. This owns exactly one body reader. The aggregate
|
|
108
|
+
* buffer is capped; hitting the cap commits the current target instead of growing
|
|
109
|
+
* memory or guessing that replay is safe.
|
|
110
|
+
*/
|
|
111
|
+
export async function preflightComboStreamResponse(
|
|
112
|
+
response: Response,
|
|
113
|
+
logCtx: RequestLogContext,
|
|
114
|
+
): Promise<ComboStreamPreflightResult> {
|
|
115
|
+
const contentType = response.headers.get("content-type")?.toLowerCase() ?? "";
|
|
116
|
+
if (!response.ok || !response.body || !contentType.includes("text/event-stream")) {
|
|
117
|
+
return { kind: "accepted", response };
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
const reader = response.body.getReader();
|
|
121
|
+
const buffered: Uint8Array[] = [];
|
|
122
|
+
let bufferedBytes = 0;
|
|
123
|
+
let outputCommitted = false;
|
|
124
|
+
let terminalStatus: ResponsesTerminalStatus | undefined;
|
|
125
|
+
let failedPayload: Record<string, unknown> | undefined;
|
|
126
|
+
const inspector = createSseInspector({
|
|
127
|
+
logCtx,
|
|
128
|
+
onParsedPayload: payload => {
|
|
129
|
+
if (comboStreamPayloadCommitsOutput(payload)) outputCommitted = true;
|
|
130
|
+
if (!payload || typeof payload !== "object" || Array.isArray(payload)) return;
|
|
131
|
+
if ((payload as { type?: unknown }).type === "response.failed") {
|
|
132
|
+
failedPayload = payload as Record<string, unknown>;
|
|
133
|
+
}
|
|
134
|
+
},
|
|
135
|
+
onTerminal: status => { terminalStatus = status; },
|
|
136
|
+
});
|
|
137
|
+
|
|
138
|
+
try {
|
|
139
|
+
for (;;) {
|
|
140
|
+
const next = await reader.read();
|
|
141
|
+
if (next.done) {
|
|
142
|
+
inspector.finish();
|
|
143
|
+
} else {
|
|
144
|
+
if (bufferedBytes + next.value.byteLength > COMBO_STREAM_PREFLIGHT_MAX_BYTES) {
|
|
145
|
+
// Keep the cap about memory the preflight allocates. The upstream chunk already exists;
|
|
146
|
+
// copying it before committing would transiently exceed the boundary for no
|
|
147
|
+
// replay benefit. Preserve it unsliced behind the already-bounded prefix.
|
|
148
|
+
return {
|
|
149
|
+
kind: "accepted",
|
|
150
|
+
response: replayBufferedResponse(response, reader, [...buffered, next.value]),
|
|
151
|
+
};
|
|
152
|
+
}
|
|
153
|
+
const retained = next.value.slice();
|
|
154
|
+
buffered.push(retained);
|
|
155
|
+
bufferedBytes += retained.byteLength;
|
|
156
|
+
inspector.feed(retained);
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
if (terminalStatus === "failed" && !outputCommitted && failedPayload) {
|
|
160
|
+
await reader.cancel("retrying zero-output combo stream failure").catch(() => undefined);
|
|
161
|
+
return { kind: "failed", response: failedTerminalResponse(response, failedPayload, logCtx) };
|
|
162
|
+
}
|
|
163
|
+
if (next.done || terminalStatus !== undefined || outputCommitted
|
|
164
|
+
|| bufferedBytes >= COMBO_STREAM_PREFLIGHT_MAX_BYTES) {
|
|
165
|
+
return { kind: "accepted", response: replayBufferedResponse(response, reader, buffered) };
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
} finally {
|
|
169
|
+
inspector.dispose();
|
|
170
|
+
}
|
|
171
|
+
}
|
|
@@ -42,17 +42,9 @@ import { describeImagesInPlace, planVisionSidecar, shouldResolveOpenAiVisionSide
|
|
|
42
42
|
import { createAdapterEventQueue, preflightAdapterEvents } from "../../adapters/run-turn-queue";
|
|
43
43
|
import {
|
|
44
44
|
applyCodexAuthContextToProvider,
|
|
45
|
-
CodexAccountCooldownError,
|
|
46
|
-
codexMainProfileDrainingResponse,
|
|
47
|
-
cooldownErrorResponse,
|
|
48
|
-
CodexAuthContextError,
|
|
49
|
-
CodexDirectAuthenticationError,
|
|
50
45
|
CodexMainProfileDrainingError,
|
|
51
|
-
CodexPoolAuthenticationError,
|
|
52
|
-
CodexThreadAffinityExpiredError,
|
|
53
46
|
headersForCodexAuthContext,
|
|
54
47
|
materializeCodexUpstreamAuth,
|
|
55
|
-
CodexMainSubstitutionUnavailableError,
|
|
56
48
|
isCodexAuthContextUsable,
|
|
57
49
|
resolveCodexAuthContext,
|
|
58
50
|
codexProbeLeaseId,
|
|
@@ -134,6 +126,8 @@ import {
|
|
|
134
126
|
usesCodexForwardPoolAuth,
|
|
135
127
|
} from "./core";
|
|
136
128
|
import { fetchWithHeaderTimeout, providerFetch, safeHostLabel, safeOriginLabel } from "./fetch-helpers";
|
|
129
|
+
import { mapCodexAuthContextErrorToResponse } from "./codex-auth-error";
|
|
130
|
+
import { decideV2NativeParentOverride } from "./v2-native-parent-override";
|
|
137
131
|
|
|
138
132
|
export const COMPACT_RESPONSE_MAX_BYTES = 32 * 1024 * 1024;
|
|
139
133
|
|
|
@@ -304,6 +298,31 @@ export async function handleResponsesCompact(
|
|
|
304
298
|
}
|
|
305
299
|
return formatErrorResponse(404, "invalid_request_error", err instanceof Error ? err.message : String(err));
|
|
306
300
|
}
|
|
301
|
+
const requestedModel = raw.model;
|
|
302
|
+
// Populate source-route identity before the opt-in decision can fail closed. This keeps
|
|
303
|
+
// malformed/unavailable targets observable as the caller's route without exposing any new data.
|
|
304
|
+
logCtx.requestedModel = requestedModel;
|
|
305
|
+
logCtx.model = route.modelId;
|
|
306
|
+
logCtx.routeDecision = route.routeDecision;
|
|
307
|
+
logCtx.provider = route.codexAccountNamespace
|
|
308
|
+
? `${route.providerName}-${route.codexAccountNamespace}`
|
|
309
|
+
: route.providerName;
|
|
310
|
+
logCtx.providerAdapter = route.provider.adapter;
|
|
311
|
+
const parentOverride = decideV2NativeParentOverride({
|
|
312
|
+
kind: "compact",
|
|
313
|
+
config,
|
|
314
|
+
headers: req.headers,
|
|
315
|
+
sourceRoute: route,
|
|
316
|
+
targetEvidence: evidenceFromBody(raw),
|
|
317
|
+
});
|
|
318
|
+
if (parentOverride.kind === "reject") {
|
|
319
|
+
if (parentOverride.trace) logCtx.routeDecision = parentOverride.trace as typeof logCtx.routeDecision;
|
|
320
|
+
return formatErrorResponse(404, "invalid_request_error", parentOverride.message);
|
|
321
|
+
}
|
|
322
|
+
if (parentOverride.kind === "override") {
|
|
323
|
+
route = parentOverride.route;
|
|
324
|
+
raw.model = route.modelId;
|
|
325
|
+
}
|
|
307
326
|
const selectedModelId = route.modelId;
|
|
308
327
|
// Derive from the RESOLVED route model, not the caller's raw string. An account-qualified
|
|
309
328
|
// selector like `side/gpt-daybreak-blue-latest` does not match the gated map — `slugsEquivalent`
|
|
@@ -311,7 +330,7 @@ export async function handleResponsesCompact(
|
|
|
311
330
|
// exactly the selector form back down the native compact endpoint this guard exists to avoid.
|
|
312
331
|
// `route.modelId` is the same value `applyCodexAccountGatedWireNormalization` uses in core.ts.
|
|
313
332
|
const accountGatedCompactWireModel = codexAccountGatedCanonicalWireModel(selectedModelId);
|
|
314
|
-
logCtx.requestedModel =
|
|
333
|
+
logCtx.requestedModel = requestedModel;
|
|
315
334
|
logCtx.model = selectedModelId;
|
|
316
335
|
logCtx.routeDecision = route.routeDecision;
|
|
317
336
|
logCtx.provider = route.codexAccountNamespace
|
|
@@ -395,19 +414,11 @@ export async function handleResponsesCompact(
|
|
|
395
414
|
}
|
|
396
415
|
}
|
|
397
416
|
} catch (err) {
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
if (
|
|
403
|
-
return formatErrorResponse(409, "invalid_request_error", "Codex thread account affinity expired; start a new session");
|
|
404
|
-
}
|
|
405
|
-
if (err instanceof CodexAuthContextError) {
|
|
406
|
-
return formatErrorResponse(401, "authentication_error", "Selected Codex account needs reauthentication");
|
|
407
|
-
}
|
|
408
|
-
if (err instanceof CodexPoolAuthenticationError || err instanceof CodexDirectAuthenticationError) {
|
|
409
|
-
return formatErrorResponse(401, "authentication_error", err.message);
|
|
410
|
-
}
|
|
417
|
+
const response = mapCodexAuthContextErrorToResponse(err, {
|
|
418
|
+
accountSelector: route.codexAccountNamespace,
|
|
419
|
+
now: Date.now(),
|
|
420
|
+
});
|
|
421
|
+
if (response) return response;
|
|
411
422
|
throw err;
|
|
412
423
|
}
|
|
413
424
|
const base = isCanonicalOpenAiForwardProvider(compactProvider)
|
|
@@ -692,6 +703,9 @@ export async function handleResponsesCompact(
|
|
|
692
703
|
body: JSON.stringify(internalBody),
|
|
693
704
|
});
|
|
694
705
|
const response = await handleResponses(internalReq, config, logCtx, { abortSignal: req.signal, turnAdmissionLease, ...(admission ? { admission } : {}) });
|
|
706
|
+
// The internal summarizer is a routed Responses turn, but compact logs retain the
|
|
707
|
+
// caller's selector just like the native compact branch above.
|
|
708
|
+
logCtx.requestedModel = requestedModel;
|
|
695
709
|
if (!response.ok) return response;
|
|
696
710
|
let json: { output?: unknown[]; status?: unknown; error?: unknown };
|
|
697
711
|
if (response.headers.get("content-type")?.includes("text/event-stream")) {
|