lody 0.69.0 → 0.70.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/dist/chunks/{directory-handle-B28RRBM4.js → directory-handle-Ydn6ZTye.js} +1 -1
- package/dist/chunks/{index-DjSKImM-.js → index-DgU7G-DU.js} +691 -104
- package/dist/chunks/package-DqzNopZM.js +11 -0
- package/dist/chunks/{review-viewer-cjVseAUz.js → review-viewer-DYasOJ94.js} +2 -2
- package/dist/chunks/{schemas-BunMNnz1.js → schemas-Dq_X20sw.js} +35 -24
- package/dist/claude-acp.js +54251 -51421
- package/dist/codex-acp.js +1 -1
- package/dist/file-index-scan-worker.js +2 -2
- package/dist/index.js +4802 -1573
- package/package.json +8 -8
|
@@ -20801,6 +20801,22 @@ var LEGACY_SET_SESSION_MODEL_METHOD = "session/set_model";
|
|
|
20801
20801
|
var ACP_EXT_SESSION_USAGE_UPDATE_METHOD = "_acp_ext:session_usage_update";
|
|
20802
20802
|
var ACP_EXT_SESSION_RATE_LIMITS_METHOD = "_acp_ext:session_rate_limits";
|
|
20803
20803
|
var ACP_EXT_CODEX_PROPOSED_PLAN_METHOD = "_acp_ext:codex_proposed_plan";
|
|
20804
|
+
var CODEX_STEER_APPLIED_METHOD = "_codex/steerApplied";
|
|
20805
|
+
var CODEX_STEER_CAPABILITY = {
|
|
20806
|
+
version: 1,
|
|
20807
|
+
appliedNotification: CODEX_STEER_APPLIED_METHOD,
|
|
20808
|
+
upstreamTurn: "same",
|
|
20809
|
+
configPolicy: "active"
|
|
20810
|
+
};
|
|
20811
|
+
function getCodexSteerId(meta3) {
|
|
20812
|
+
if (typeof meta3 !== "object" || meta3 === null) return null;
|
|
20813
|
+
const codex = meta3["codex"];
|
|
20814
|
+
if (typeof codex !== "object" || codex === null) return null;
|
|
20815
|
+
const steer = codex["steer"];
|
|
20816
|
+
if (typeof steer !== "object" || steer === null) return null;
|
|
20817
|
+
const id = steer["id"];
|
|
20818
|
+
return typeof id === "string" && id.length > 0 ? id : null;
|
|
20819
|
+
}
|
|
20804
20820
|
function isExtMethodRequest(request) {
|
|
20805
20821
|
return request.method === "authentication/status" || request.method === "authentication/logout" || request.method === LEGACY_SET_SESSION_MODEL_METHOD;
|
|
20806
20822
|
}
|
|
@@ -21442,6 +21458,7 @@ function createTerminalOutputMeta(mode, terminalId, data) {
|
|
|
21442
21458
|
};
|
|
21443
21459
|
}
|
|
21444
21460
|
}
|
|
21461
|
+
var CONTEXT_COMPACTION_META = { contextCompaction: true };
|
|
21445
21462
|
function toAcpStatus(status) {
|
|
21446
21463
|
switch (status) {
|
|
21447
21464
|
case "inProgress":
|
|
@@ -21584,6 +21601,35 @@ function createImageGenerationUpdate(item, options) {
|
|
|
21584
21601
|
rawOutput: imageGenerationRawOutput(item)
|
|
21585
21602
|
};
|
|
21586
21603
|
}
|
|
21604
|
+
function createContextCompactionStartUpdate(item) {
|
|
21605
|
+
return {
|
|
21606
|
+
sessionUpdate: "tool_call",
|
|
21607
|
+
toolCallId: item.id,
|
|
21608
|
+
kind: "other",
|
|
21609
|
+
title: "Context compacting",
|
|
21610
|
+
status: "in_progress",
|
|
21611
|
+
_meta: CONTEXT_COMPACTION_META
|
|
21612
|
+
};
|
|
21613
|
+
}
|
|
21614
|
+
function createContextCompactionCompleteUpdate(item) {
|
|
21615
|
+
return {
|
|
21616
|
+
sessionUpdate: "tool_call_update",
|
|
21617
|
+
toolCallId: item.id,
|
|
21618
|
+
title: "Context compacted",
|
|
21619
|
+
status: "completed",
|
|
21620
|
+
_meta: CONTEXT_COMPACTION_META
|
|
21621
|
+
};
|
|
21622
|
+
}
|
|
21623
|
+
function createCompletedContextCompactionUpdate(item) {
|
|
21624
|
+
return {
|
|
21625
|
+
sessionUpdate: "tool_call",
|
|
21626
|
+
toolCallId: item.id,
|
|
21627
|
+
kind: "other",
|
|
21628
|
+
title: "Context compacted",
|
|
21629
|
+
status: "completed",
|
|
21630
|
+
_meta: CONTEXT_COMPACTION_META
|
|
21631
|
+
};
|
|
21632
|
+
}
|
|
21587
21633
|
async function createExecuteToolCallUpdate(item, title, rawInput, rawOutput) {
|
|
21588
21634
|
return {
|
|
21589
21635
|
sessionUpdate: "tool_call",
|
|
@@ -22063,6 +22109,69 @@ async function readFileContent(filePath) {
|
|
|
22063
22109
|
function recoverCorruptedDiff(diff) {
|
|
22064
22110
|
return diff.replace(/\n\nMoved to: .*$/, "");
|
|
22065
22111
|
}
|
|
22112
|
+
var COMPLETE_EMPTY_COMMENT = /^<!--\s*(?:\*\/\s*)?-->\s*$/u;
|
|
22113
|
+
var PARTIAL_COMMENT_BODY = /^\s*(?:\*\/?\s*)?$/u;
|
|
22114
|
+
var PARTIAL_COMMENT_CLOSE = /^\s*(?:\*\/\s*)?-{1,2}$/u;
|
|
22115
|
+
var isHorizontalWhitespace = (char) => char === " " || char === " ";
|
|
22116
|
+
var canBecomeEmptyComment = (text) => {
|
|
22117
|
+
if (text === "<" || text === "<!" || text === "<!-") {
|
|
22118
|
+
return true;
|
|
22119
|
+
}
|
|
22120
|
+
if (!text.startsWith("<!--")) {
|
|
22121
|
+
return false;
|
|
22122
|
+
}
|
|
22123
|
+
const tail = text.slice(4);
|
|
22124
|
+
return COMPLETE_EMPTY_COMMENT.test(text) || PARTIAL_COMMENT_BODY.test(tail) || PARTIAL_COMMENT_CLOSE.test(tail);
|
|
22125
|
+
};
|
|
22126
|
+
var ReasoningSummaryFilter = class {
|
|
22127
|
+
pending = "";
|
|
22128
|
+
lineHasContent = false;
|
|
22129
|
+
push(delta) {
|
|
22130
|
+
let output = "";
|
|
22131
|
+
const emit = (text) => {
|
|
22132
|
+
output += text;
|
|
22133
|
+
for (const char of text) {
|
|
22134
|
+
if (char === "\n" || char === "\r") {
|
|
22135
|
+
this.lineHasContent = false;
|
|
22136
|
+
} else if (!isHorizontalWhitespace(char)) {
|
|
22137
|
+
this.lineHasContent = true;
|
|
22138
|
+
}
|
|
22139
|
+
}
|
|
22140
|
+
};
|
|
22141
|
+
for (const char of delta) {
|
|
22142
|
+
if (this.pending) {
|
|
22143
|
+
this.pending += char;
|
|
22144
|
+
if (canBecomeEmptyComment(this.pending)) {
|
|
22145
|
+
continue;
|
|
22146
|
+
}
|
|
22147
|
+
emit(this.pending);
|
|
22148
|
+
this.pending = "";
|
|
22149
|
+
continue;
|
|
22150
|
+
}
|
|
22151
|
+
if (char === "<" && !this.lineHasContent) {
|
|
22152
|
+
this.pending = char;
|
|
22153
|
+
} else {
|
|
22154
|
+
emit(char);
|
|
22155
|
+
}
|
|
22156
|
+
}
|
|
22157
|
+
return output;
|
|
22158
|
+
}
|
|
22159
|
+
finish() {
|
|
22160
|
+
const output = COMPLETE_EMPTY_COMMENT.test(this.pending) ? "" : this.pending;
|
|
22161
|
+
this.pending = "";
|
|
22162
|
+
this.lineHasContent = false;
|
|
22163
|
+
return output;
|
|
22164
|
+
}
|
|
22165
|
+
};
|
|
22166
|
+
function stripEmptyReasoningComments(text) {
|
|
22167
|
+
const filter = new ReasoningSummaryFilter();
|
|
22168
|
+
return filter.push(text) + filter.finish();
|
|
22169
|
+
}
|
|
22170
|
+
function sanitizeReasoningParts(summary, content) {
|
|
22171
|
+
const useSummary = summary.length > 0;
|
|
22172
|
+
const parts = useSummary ? summary : content;
|
|
22173
|
+
return parts.map((part) => useSummary ? stripEmptyReasoningComments(part) : part).filter((part) => part.length > 0);
|
|
22174
|
+
}
|
|
22066
22175
|
function createCodexMessagePhaseMeta(phase) {
|
|
22067
22176
|
if (!phase) {
|
|
22068
22177
|
return void 0;
|
|
@@ -22129,6 +22238,7 @@ var CodexEventHandler = class {
|
|
|
22129
22238
|
activeImageGenerationItems = /* @__PURE__ */ new Set();
|
|
22130
22239
|
emittedImageViewItems = /* @__PURE__ */ new Set();
|
|
22131
22240
|
seenReasoningDeltaItemIds = /* @__PURE__ */ new Set();
|
|
22241
|
+
reasoningSummaryFilters = /* @__PURE__ */ new Map();
|
|
22132
22242
|
terminalCommandIds = /* @__PURE__ */ new Set();
|
|
22133
22243
|
terminalCommandOutputIds = /* @__PURE__ */ new Set();
|
|
22134
22244
|
proposedPlanMarkdown = "";
|
|
@@ -22142,6 +22252,10 @@ var CodexEventHandler = class {
|
|
|
22142
22252
|
return this.failure;
|
|
22143
22253
|
}
|
|
22144
22254
|
async handleNotification(notification) {
|
|
22255
|
+
if (notification.method === "account/rateLimits/updated") {
|
|
22256
|
+
await this.handleRateLimitsSnapshot(notification.params.rateLimits, true);
|
|
22257
|
+
return;
|
|
22258
|
+
}
|
|
22145
22259
|
const session = new ACPSessionConnection(this.connection, this.sessionState.sessionId);
|
|
22146
22260
|
const updateEvent = await this.createUpdateEvent(notification);
|
|
22147
22261
|
if (updateEvent) {
|
|
@@ -22170,6 +22284,8 @@ var CodexEventHandler = class {
|
|
|
22170
22284
|
case "thread/tokenUsage/updated":
|
|
22171
22285
|
return this.createUsageUpdate(notification.params);
|
|
22172
22286
|
case "thread/name/updated":
|
|
22287
|
+
this.sessionState.sessionTitle = notification.params.threadName ?? null;
|
|
22288
|
+
this.sessionState.sessionTitleSource = notification.params.threadName == null ? "unset" : "explicit";
|
|
22173
22289
|
return {
|
|
22174
22290
|
sessionUpdate: "session_info_update",
|
|
22175
22291
|
title: notification.params.threadName ?? null
|
|
@@ -22195,7 +22311,6 @@ var CodexEventHandler = class {
|
|
|
22195
22311
|
case "item/mcpToolCall/progress":
|
|
22196
22312
|
return this.createMcpToolProgressEvent(notification.params);
|
|
22197
22313
|
case "account/rateLimits/updated":
|
|
22198
|
-
this.handleRateLimitsUpdated(notification.params);
|
|
22199
22314
|
return null;
|
|
22200
22315
|
case "configWarning":
|
|
22201
22316
|
return await this.createConfigWarningEvent(notification.params);
|
|
@@ -22210,9 +22325,9 @@ var CodexEventHandler = class {
|
|
|
22210
22325
|
case "thread/compacted":
|
|
22211
22326
|
return this.createContextCompactedEvent();
|
|
22212
22327
|
case "item/reasoning/summaryTextDelta":
|
|
22213
|
-
return this.
|
|
22328
|
+
return this.createReasoningSummaryDeltaEvent(notification.params);
|
|
22214
22329
|
case "item/reasoning/textDelta":
|
|
22215
|
-
return this.
|
|
22330
|
+
return this.createRawReasoningDeltaEvent(notification.params);
|
|
22216
22331
|
case "item/reasoning/summaryPartAdded":
|
|
22217
22332
|
return this.createReasoningSectionBreakEvent(notification.params);
|
|
22218
22333
|
case "model/rerouted":
|
|
@@ -22277,12 +22392,6 @@ var CodexEventHandler = class {
|
|
|
22277
22392
|
this.createSessionUsageExtNotification(notification.params)
|
|
22278
22393
|
);
|
|
22279
22394
|
return;
|
|
22280
|
-
case "account/rateLimits/updated":
|
|
22281
|
-
await this.notifyExt(
|
|
22282
|
-
ACP_EXT_SESSION_RATE_LIMITS_METHOD,
|
|
22283
|
-
this.createSessionRateLimitsExtNotification(notification.params)
|
|
22284
|
-
);
|
|
22285
|
-
return;
|
|
22286
22395
|
case "item/plan/delta":
|
|
22287
22396
|
await this.emitCodexProposedPlanDelta(notification.params);
|
|
22288
22397
|
return;
|
|
@@ -22344,16 +22453,26 @@ var CodexEventHandler = class {
|
|
|
22344
22453
|
isLatest: true
|
|
22345
22454
|
};
|
|
22346
22455
|
}
|
|
22347
|
-
createSessionRateLimitsExtNotification(
|
|
22348
|
-
const
|
|
22456
|
+
createSessionRateLimitsExtNotification(rateLimits) {
|
|
22457
|
+
const windows = [rateLimits.primary, rateLimits.secondary].filter(
|
|
22458
|
+
(window) => window !== null
|
|
22459
|
+
);
|
|
22460
|
+
const fiveHour = windows.find((window) => window.windowDurationMins === 5 * 60) ?? null;
|
|
22461
|
+
const sevenDay = windows.find((window) => window.windowDurationMins === 7 * 24 * 60) ?? null;
|
|
22349
22462
|
return {
|
|
22463
|
+
schemaVersion: 2,
|
|
22350
22464
|
planName: rateLimits.planType,
|
|
22351
22465
|
limitName: rateLimits.limitName,
|
|
22352
22466
|
limitId: rateLimits.limitId,
|
|
22353
|
-
|
|
22354
|
-
|
|
22355
|
-
|
|
22356
|
-
|
|
22467
|
+
windows: windows.map((window) => ({
|
|
22468
|
+
usedPercent: window.usedPercent,
|
|
22469
|
+
windowDurationMins: window.windowDurationMins,
|
|
22470
|
+
resetsAt: window.resetsAt
|
|
22471
|
+
})),
|
|
22472
|
+
fiveHour: fiveHour?.usedPercent ?? null,
|
|
22473
|
+
sevenDay: sevenDay?.usedPercent ?? null,
|
|
22474
|
+
fiveHourResetAt: fiveHour?.resetsAt ?? null,
|
|
22475
|
+
sevenDayResetAt: sevenDay?.resetsAt ?? null
|
|
22357
22476
|
};
|
|
22358
22477
|
}
|
|
22359
22478
|
createCodexSessionInfoUpdate(codexMetadata) {
|
|
@@ -22415,13 +22534,34 @@ ${event.details}` : "";
|
|
|
22415
22534
|
sameThreadGoalSnapshot(left, right) {
|
|
22416
22535
|
return left !== null && left !== void 0 && left.objective === right.objective && left.status === right.status && left.tokenBudget === right.tokenBudget;
|
|
22417
22536
|
}
|
|
22418
|
-
|
|
22537
|
+
createReasoningSummaryDeltaEvent(event) {
|
|
22538
|
+
this.seenReasoningDeltaItemIds.add(event.itemId);
|
|
22539
|
+
let filter = this.reasoningSummaryFilters.get(event.itemId);
|
|
22540
|
+
if (!filter) {
|
|
22541
|
+
filter = new ReasoningSummaryFilter();
|
|
22542
|
+
this.reasoningSummaryFilters.set(event.itemId, filter);
|
|
22543
|
+
}
|
|
22544
|
+
const text = filter.push(event.delta);
|
|
22545
|
+
return text.length > 0 ? this.createAgentThoughtEvent(text, event.itemId) : null;
|
|
22546
|
+
}
|
|
22547
|
+
createRawReasoningDeltaEvent(event) {
|
|
22419
22548
|
this.seenReasoningDeltaItemIds.add(event.itemId);
|
|
22420
22549
|
return this.createAgentThoughtEvent(event.delta, event.itemId);
|
|
22421
22550
|
}
|
|
22422
22551
|
createReasoningSectionBreakEvent(event) {
|
|
22423
22552
|
this.seenReasoningDeltaItemIds.add(event.itemId);
|
|
22424
|
-
|
|
22553
|
+
const trailingText = this.finishReasoningSummaryFilter(event.itemId);
|
|
22554
|
+
return this.createAgentThoughtEvent(`${trailingText}
|
|
22555
|
+
|
|
22556
|
+
`, event.itemId);
|
|
22557
|
+
}
|
|
22558
|
+
finishReasoningSummaryFilter(itemId) {
|
|
22559
|
+
const filter = this.reasoningSummaryFilters.get(itemId);
|
|
22560
|
+
if (!filter) {
|
|
22561
|
+
return "";
|
|
22562
|
+
}
|
|
22563
|
+
this.reasoningSummaryFilters.delete(itemId);
|
|
22564
|
+
return filter.finish();
|
|
22425
22565
|
}
|
|
22426
22566
|
createAgentThoughtEvent(text, messageId) {
|
|
22427
22567
|
return createAgentTextThoughtChunk(text, messageId);
|
|
@@ -22456,6 +22596,8 @@ ${event.details}` : "";
|
|
|
22456
22596
|
case "agentMessage":
|
|
22457
22597
|
this.rememberAgentMessagePhase(event.item);
|
|
22458
22598
|
return null;
|
|
22599
|
+
case "contextCompaction":
|
|
22600
|
+
return createContextCompactionStartUpdate(event.item);
|
|
22459
22601
|
case "subAgentActivity":
|
|
22460
22602
|
case "sleep":
|
|
22461
22603
|
case "userMessage":
|
|
@@ -22463,7 +22605,6 @@ ${event.details}` : "";
|
|
|
22463
22605
|
case "reasoning":
|
|
22464
22606
|
case "enteredReviewMode":
|
|
22465
22607
|
case "exitedReviewMode":
|
|
22466
|
-
case "contextCompaction":
|
|
22467
22608
|
case "plan":
|
|
22468
22609
|
return null;
|
|
22469
22610
|
}
|
|
@@ -22499,7 +22640,8 @@ ${event.details}` : "";
|
|
|
22499
22640
|
return createImageGenerationUpdate(event.item, { terminalStatus: true });
|
|
22500
22641
|
case "reasoning":
|
|
22501
22642
|
if (this.seenReasoningDeltaItemIds.delete(event.item.id)) {
|
|
22502
|
-
|
|
22643
|
+
const trailingText = this.finishReasoningSummaryFilter(event.item.id);
|
|
22644
|
+
return trailingText.length > 0 ? this.createAgentThoughtEvent(trailingText, event.item.id) : null;
|
|
22503
22645
|
}
|
|
22504
22646
|
return this.createCompletedReasoningEvent(event.item);
|
|
22505
22647
|
case "webSearch":
|
|
@@ -22512,7 +22654,7 @@ ${event.details}` : "";
|
|
|
22512
22654
|
case "exitedReviewMode":
|
|
22513
22655
|
return this.createExitedReviewModeEvent(event.item);
|
|
22514
22656
|
case "contextCompaction":
|
|
22515
|
-
return
|
|
22657
|
+
return createContextCompactionCompleteUpdate(event.item);
|
|
22516
22658
|
//ignored types
|
|
22517
22659
|
case "subAgentActivity":
|
|
22518
22660
|
case "sleep":
|
|
@@ -22527,8 +22669,7 @@ ${event.details}` : "";
|
|
|
22527
22669
|
this.agentMessagePhases.set(item.id, item.phase);
|
|
22528
22670
|
}
|
|
22529
22671
|
createCompletedReasoningEvent(item) {
|
|
22530
|
-
const
|
|
22531
|
-
const text = parts.filter((part) => part.length > 0).join("\n\n");
|
|
22672
|
+
const text = sanitizeReasoningParts(item.summary, item.content).join("\n\n");
|
|
22532
22673
|
if (text.length === 0) {
|
|
22533
22674
|
return null;
|
|
22534
22675
|
}
|
|
@@ -22662,7 +22803,15 @@ ${event.stdin}
|
|
|
22662
22803
|
}
|
|
22663
22804
|
async createErrorEvent(params) {
|
|
22664
22805
|
const error48 = params.error.codexErrorInfo;
|
|
22665
|
-
if (
|
|
22806
|
+
if (params.willRetry) {
|
|
22807
|
+
return this.createCodexSessionInfoUpdate({
|
|
22808
|
+
error: {
|
|
22809
|
+
...params.error,
|
|
22810
|
+
turnId: params.turnId,
|
|
22811
|
+
willRetry: true
|
|
22812
|
+
}
|
|
22813
|
+
});
|
|
22814
|
+
} else if (error48 === "usageLimitExceeded") {
|
|
22666
22815
|
this.failure = RequestError.internalError(
|
|
22667
22816
|
this.createTurnErrorData(params.error)
|
|
22668
22817
|
);
|
|
@@ -22720,16 +22869,36 @@ ${event.stdin}
|
|
|
22720
22869
|
size
|
|
22721
22870
|
};
|
|
22722
22871
|
}
|
|
22723
|
-
|
|
22872
|
+
async handleRateLimitsSnapshot(rateLimits, sparse = false) {
|
|
22873
|
+
const merged = this.storeRateLimitsSnapshot(rateLimits, sparse);
|
|
22874
|
+
await this.notifyExt(
|
|
22875
|
+
ACP_EXT_SESSION_RATE_LIMITS_METHOD,
|
|
22876
|
+
this.createSessionRateLimitsExtNotification(merged)
|
|
22877
|
+
);
|
|
22878
|
+
}
|
|
22879
|
+
storeRateLimitsSnapshot(rateLimits, sparse) {
|
|
22724
22880
|
if (!this.sessionState.rateLimits) {
|
|
22725
22881
|
this.sessionState.rateLimits = /* @__PURE__ */ new Map();
|
|
22726
22882
|
}
|
|
22727
|
-
const
|
|
22883
|
+
const fallbackLimitId = this.sessionState.rateLimits.size === 1 ? this.sessionState.rateLimits.keys().next().value : null;
|
|
22884
|
+
const limitId = rateLimits.limitId ?? rateLimits.limitName ?? fallbackLimitId ?? "unknown";
|
|
22885
|
+
const existing = this.sessionState.rateLimits.get(limitId)?.snapshot;
|
|
22886
|
+
const snapshot = sparse && existing ? {
|
|
22887
|
+
limitId: rateLimits.limitId ?? existing.limitId,
|
|
22888
|
+
limitName: rateLimits.limitName ?? existing.limitName,
|
|
22889
|
+
primary: rateLimits.primary ?? existing.primary,
|
|
22890
|
+
secondary: rateLimits.secondary ?? existing.secondary,
|
|
22891
|
+
credits: rateLimits.credits ?? existing.credits,
|
|
22892
|
+
individualLimit: rateLimits.individualLimit ?? existing.individualLimit,
|
|
22893
|
+
planType: rateLimits.planType ?? existing.planType,
|
|
22894
|
+
rateLimitReachedType: rateLimits.rateLimitReachedType ?? existing.rateLimitReachedType
|
|
22895
|
+
} : rateLimits;
|
|
22728
22896
|
this.sessionState.rateLimits.set(limitId, {
|
|
22729
22897
|
limitId,
|
|
22730
|
-
limitName:
|
|
22731
|
-
snapshot
|
|
22898
|
+
limitName: snapshot.limitName ?? limitId,
|
|
22899
|
+
snapshot
|
|
22732
22900
|
});
|
|
22901
|
+
return snapshot;
|
|
22733
22902
|
}
|
|
22734
22903
|
handleFuzzyFileSearchSessionUpdated(params) {
|
|
22735
22904
|
const toolCallId = fuzzyFileSearchToolCallId(params.sessionId);
|
|
@@ -23084,6 +23253,7 @@ var ELICITATION_OPTIONS = [
|
|
|
23084
23253
|
{ optionId: "accept", name: "Accept", kind: "allow_once" },
|
|
23085
23254
|
{ optionId: "decline", name: "Decline", kind: "reject_once" }
|
|
23086
23255
|
];
|
|
23256
|
+
var USER_INPUT_OTHER_FIELD_SUFFIX = "__other";
|
|
23087
23257
|
function parsePersistOptions(meta3) {
|
|
23088
23258
|
const result = /* @__PURE__ */ new Set();
|
|
23089
23259
|
if (!meta3 || typeof meta3 !== "object") return result;
|
|
@@ -23219,6 +23389,27 @@ function elicitationResponseMeta(response, context, persist = void 0) {
|
|
|
23219
23389
|
}
|
|
23220
23390
|
return Object.keys(meta3).length === 0 ? null : meta3;
|
|
23221
23391
|
}
|
|
23392
|
+
function userInputOtherFieldId(questionId, questionIds) {
|
|
23393
|
+
const base = `${questionId}${USER_INPUT_OTHER_FIELD_SUFFIX}`;
|
|
23394
|
+
if (!questionIds.has(base)) {
|
|
23395
|
+
return base;
|
|
23396
|
+
}
|
|
23397
|
+
let index = 1;
|
|
23398
|
+
while (questionIds.has(`${base}${index}`)) {
|
|
23399
|
+
index += 1;
|
|
23400
|
+
}
|
|
23401
|
+
return `${base}${index}`;
|
|
23402
|
+
}
|
|
23403
|
+
function userInputResponseValue(content, fieldId) {
|
|
23404
|
+
const value = content[fieldId];
|
|
23405
|
+
if (typeof value === "string" && value.trim() === "") {
|
|
23406
|
+
return void 0;
|
|
23407
|
+
}
|
|
23408
|
+
if (Array.isArray(value) && value.length === 0) {
|
|
23409
|
+
return void 0;
|
|
23410
|
+
}
|
|
23411
|
+
return value;
|
|
23412
|
+
}
|
|
23222
23413
|
function buildToolApprovalOptions(persistOptions) {
|
|
23223
23414
|
const options = [
|
|
23224
23415
|
{ optionId: McpApprovalOptionId.AllowOnce, name: "Allow", kind: "allow_once" }
|
|
@@ -23315,8 +23506,68 @@ var CodexElicitationHandler = class {
|
|
|
23315
23506
|
return { action: "cancel", content: null, _meta: null };
|
|
23316
23507
|
}
|
|
23317
23508
|
}
|
|
23318
|
-
|
|
23319
|
-
|
|
23509
|
+
async handleUserInput(params) {
|
|
23510
|
+
if (!clientSupportsFormElicitation(this.clientCapabilities)) {
|
|
23511
|
+
return { answers: {} };
|
|
23512
|
+
}
|
|
23513
|
+
try {
|
|
23514
|
+
const response = await this.requestUserInputElicitation(params);
|
|
23515
|
+
if (response === null) {
|
|
23516
|
+
return { answers: {} };
|
|
23517
|
+
}
|
|
23518
|
+
return this.convertUserInputResponse(response, params);
|
|
23519
|
+
} catch (error48) {
|
|
23520
|
+
logger.error("Error handling Codex user input request", error48);
|
|
23521
|
+
return { answers: {} };
|
|
23522
|
+
}
|
|
23523
|
+
}
|
|
23524
|
+
requestOptions(cancellationSignal = this.cancellationSignal) {
|
|
23525
|
+
return cancellationSignal ? { cancellationSignal } : void 0;
|
|
23526
|
+
}
|
|
23527
|
+
async requestUserInputElicitation(params) {
|
|
23528
|
+
const request = this.buildUserInputRequest(params);
|
|
23529
|
+
if (params.autoResolutionMs === null) {
|
|
23530
|
+
return await this.connection.request(
|
|
23531
|
+
methods.client.elicitation.create,
|
|
23532
|
+
request,
|
|
23533
|
+
this.requestOptions()
|
|
23534
|
+
);
|
|
23535
|
+
}
|
|
23536
|
+
const abortController = new AbortController();
|
|
23537
|
+
let timeout;
|
|
23538
|
+
let removeAbortListener;
|
|
23539
|
+
const timeoutPromise = new Promise((resolve) => {
|
|
23540
|
+
const resolveWithoutInput = () => {
|
|
23541
|
+
abortController.abort();
|
|
23542
|
+
resolve(null);
|
|
23543
|
+
};
|
|
23544
|
+
timeout = setTimeout(resolveWithoutInput, Math.max(0, params.autoResolutionMs ?? 0));
|
|
23545
|
+
if (this.cancellationSignal?.aborted) {
|
|
23546
|
+
resolveWithoutInput();
|
|
23547
|
+
return;
|
|
23548
|
+
}
|
|
23549
|
+
if (this.cancellationSignal) {
|
|
23550
|
+
this.cancellationSignal.addEventListener("abort", resolveWithoutInput, { once: true });
|
|
23551
|
+
removeAbortListener = () => {
|
|
23552
|
+
this.cancellationSignal?.removeEventListener("abort", resolveWithoutInput);
|
|
23553
|
+
};
|
|
23554
|
+
}
|
|
23555
|
+
});
|
|
23556
|
+
const requestPromise = Promise.resolve(this.connection.request(
|
|
23557
|
+
methods.client.elicitation.create,
|
|
23558
|
+
request,
|
|
23559
|
+
this.requestOptions(abortController.signal)
|
|
23560
|
+
));
|
|
23561
|
+
void requestPromise.catch(() => {
|
|
23562
|
+
});
|
|
23563
|
+
try {
|
|
23564
|
+
return await Promise.race([requestPromise, timeoutPromise]);
|
|
23565
|
+
} finally {
|
|
23566
|
+
if (timeout) {
|
|
23567
|
+
clearTimeout(timeout);
|
|
23568
|
+
}
|
|
23569
|
+
removeAbortListener?.();
|
|
23570
|
+
}
|
|
23320
23571
|
}
|
|
23321
23572
|
createMcpElicitationContext(params) {
|
|
23322
23573
|
const isToolApproval = isMcpToolCallApproval(params._meta);
|
|
@@ -23362,6 +23613,72 @@ var CodexElicitationHandler = class {
|
|
|
23362
23613
|
};
|
|
23363
23614
|
}
|
|
23364
23615
|
}
|
|
23616
|
+
buildUserInputRequest(params) {
|
|
23617
|
+
const properties = {};
|
|
23618
|
+
const required2 = [];
|
|
23619
|
+
const questionIds = new Set(params.questions.map((question) => question.id));
|
|
23620
|
+
for (const question of params.questions) {
|
|
23621
|
+
const options = question.options ?? [];
|
|
23622
|
+
const hasOptions = options.length > 0;
|
|
23623
|
+
const hasOtherAnswer = question.isOther && hasOptions;
|
|
23624
|
+
const base = {
|
|
23625
|
+
title: question.header || question.id,
|
|
23626
|
+
description: question.question,
|
|
23627
|
+
_meta: {
|
|
23628
|
+
codex: {
|
|
23629
|
+
isOther: question.isOther,
|
|
23630
|
+
isSecret: question.isSecret
|
|
23631
|
+
}
|
|
23632
|
+
}
|
|
23633
|
+
};
|
|
23634
|
+
if (!hasOtherAnswer) {
|
|
23635
|
+
required2.push(question.id);
|
|
23636
|
+
}
|
|
23637
|
+
properties[question.id] = hasOptions ? {
|
|
23638
|
+
...base,
|
|
23639
|
+
type: "string",
|
|
23640
|
+
oneOf: options.map((option) => ({
|
|
23641
|
+
const: option.label,
|
|
23642
|
+
title: option.label,
|
|
23643
|
+
description: option.description
|
|
23644
|
+
}))
|
|
23645
|
+
} : {
|
|
23646
|
+
...base,
|
|
23647
|
+
type: "string"
|
|
23648
|
+
};
|
|
23649
|
+
if (hasOtherAnswer) {
|
|
23650
|
+
properties[userInputOtherFieldId(question.id, questionIds)] = {
|
|
23651
|
+
type: "string",
|
|
23652
|
+
title: "Other",
|
|
23653
|
+
description: "Type your own answer instead of choosing an option above.",
|
|
23654
|
+
_meta: {
|
|
23655
|
+
codex: {
|
|
23656
|
+
questionId: question.id,
|
|
23657
|
+
isOtherAnswer: true,
|
|
23658
|
+
isSecret: question.isSecret
|
|
23659
|
+
}
|
|
23660
|
+
}
|
|
23661
|
+
};
|
|
23662
|
+
}
|
|
23663
|
+
}
|
|
23664
|
+
const firstQuestion = params.questions[0];
|
|
23665
|
+
return {
|
|
23666
|
+
sessionId: this.sessionState.sessionId,
|
|
23667
|
+
toolCallId: params.itemId,
|
|
23668
|
+
mode: "form",
|
|
23669
|
+
message: params.questions.length === 1 && firstQuestion ? firstQuestion.question : "Input requested",
|
|
23670
|
+
requestedSchema: {
|
|
23671
|
+
type: "object",
|
|
23672
|
+
properties,
|
|
23673
|
+
required: required2
|
|
23674
|
+
},
|
|
23675
|
+
_meta: {
|
|
23676
|
+
codex: {
|
|
23677
|
+
autoResolutionMs: params.autoResolutionMs
|
|
23678
|
+
}
|
|
23679
|
+
}
|
|
23680
|
+
};
|
|
23681
|
+
}
|
|
23365
23682
|
buildPermissionRequest(params, context) {
|
|
23366
23683
|
const sessionId = this.sessionState.sessionId;
|
|
23367
23684
|
const messageContent = {
|
|
@@ -23459,6 +23776,24 @@ var CodexElicitationHandler = class {
|
|
|
23459
23776
|
}
|
|
23460
23777
|
return { action: "cancel", content: null, _meta: null };
|
|
23461
23778
|
}
|
|
23779
|
+
convertUserInputResponse(response, params) {
|
|
23780
|
+
if (!CreateElicitationResponse.isAccept(response)) {
|
|
23781
|
+
return { answers: {} };
|
|
23782
|
+
}
|
|
23783
|
+
const answers = {};
|
|
23784
|
+
const content = contentRecord(response.content);
|
|
23785
|
+
const questionIds = new Set(params.questions.map((question) => question.id));
|
|
23786
|
+
for (const question of params.questions) {
|
|
23787
|
+
const value = question.isOther && question.options != null && question.options.length > 0 ? userInputResponseValue(content, userInputOtherFieldId(question.id, questionIds)) ?? userInputResponseValue(content, question.id) : userInputResponseValue(content, question.id);
|
|
23788
|
+
if (value === void 0) {
|
|
23789
|
+
continue;
|
|
23790
|
+
}
|
|
23791
|
+
answers[question.id] = {
|
|
23792
|
+
answers: Array.isArray(value) ? value.map(String) : [String(value)]
|
|
23793
|
+
};
|
|
23794
|
+
}
|
|
23795
|
+
return { answers };
|
|
23796
|
+
}
|
|
23462
23797
|
async publishAcceptedMcpToolApproval(context, accepted) {
|
|
23463
23798
|
if (!accepted || context.correlatedCallId === void 0) {
|
|
23464
23799
|
return;
|
|
@@ -24245,7 +24580,7 @@ var package_default = {
|
|
|
24245
24580
|
publishConfig: {
|
|
24246
24581
|
access: "public"
|
|
24247
24582
|
},
|
|
24248
|
-
version: "1.1
|
|
24583
|
+
version: "1.2.1",
|
|
24249
24584
|
description: "An ACP-compatible coding agent powered by Codex",
|
|
24250
24585
|
main: "dist/index.js",
|
|
24251
24586
|
bin: {
|
|
@@ -24311,13 +24646,17 @@ var package_default = {
|
|
|
24311
24646
|
},
|
|
24312
24647
|
dependencies: {
|
|
24313
24648
|
"@agentclientprotocol/sdk": "^1.2.1",
|
|
24314
|
-
"@openai/codex": "^0.144.
|
|
24649
|
+
"@openai/codex": "^0.144.4",
|
|
24315
24650
|
diff: "^9.0.0",
|
|
24316
24651
|
open: "^11.0.0",
|
|
24317
24652
|
"vscode-jsonrpc": "^9.0.1",
|
|
24318
24653
|
zod: "^4.0.0"
|
|
24319
24654
|
}
|
|
24320
24655
|
};
|
|
24656
|
+
var CUSTOM_GATEWAY_PROVIDER_ID = "custom-gateway";
|
|
24657
|
+
var SUPPORTED_GATEWAY_PROTOCOLS = {
|
|
24658
|
+
openai: "responses"
|
|
24659
|
+
};
|
|
24321
24660
|
var CodexAcpClient = class {
|
|
24322
24661
|
codexClient;
|
|
24323
24662
|
config;
|
|
@@ -24355,6 +24694,7 @@ var CodexAcpClient = class {
|
|
|
24355
24694
|
if (!isCodexAuthRequest(authRequest)) {
|
|
24356
24695
|
throw RequestError.invalidRequest();
|
|
24357
24696
|
}
|
|
24697
|
+
this.gatewayConfig = null;
|
|
24358
24698
|
switch (authRequest.methodId) {
|
|
24359
24699
|
case "api-key": {
|
|
24360
24700
|
const apiKey = authRequest._meta?.["api-key"]?.apiKey ?? this.readApiKeyFromEnv();
|
|
@@ -24363,7 +24703,6 @@ var CodexAcpClient = class {
|
|
|
24363
24703
|
case "chat-gpt": {
|
|
24364
24704
|
const accountResponse = await this.codexClient.accountRead({ refreshToken: true });
|
|
24365
24705
|
if (accountResponse.account?.type === "chatgpt") {
|
|
24366
|
-
this.gatewayConfig = null;
|
|
24367
24706
|
return true;
|
|
24368
24707
|
}
|
|
24369
24708
|
const loginCompletedPromise = this.awaitNextLoginCompleted();
|
|
@@ -24371,7 +24710,6 @@ var CodexAcpClient = class {
|
|
|
24371
24710
|
if (loginResponse.type == "chatgpt") {
|
|
24372
24711
|
await open_default(loginResponse.authUrl);
|
|
24373
24712
|
}
|
|
24374
|
-
this.gatewayConfig = null;
|
|
24375
24713
|
const result = await loginCompletedPromise;
|
|
24376
24714
|
return result.success;
|
|
24377
24715
|
}
|
|
@@ -24379,25 +24717,14 @@ var CodexAcpClient = class {
|
|
|
24379
24717
|
if (!authRequest._meta) throw RequestError.invalidRequest();
|
|
24380
24718
|
const gatewaySettings = authRequest._meta["gateway"];
|
|
24381
24719
|
if (!gatewaySettings) throw RequestError.invalidRequest();
|
|
24382
|
-
|
|
24383
|
-
|
|
24384
|
-
|
|
24385
|
-
|
|
24386
|
-
|
|
24387
|
-
};
|
|
24388
|
-
this.gatewayConfig = {
|
|
24389
|
-
modelProvider: "custom-gateway",
|
|
24390
|
-
config: {
|
|
24391
|
-
name: providerName,
|
|
24392
|
-
base_url: baseUrl,
|
|
24393
|
-
http_headers: headers,
|
|
24394
|
-
wire_api: "responses"
|
|
24395
|
-
}
|
|
24396
|
-
};
|
|
24720
|
+
this.applyGatewayConfig({
|
|
24721
|
+
baseUrl: gatewaySettings.baseUrl,
|
|
24722
|
+
apiType: GatewayAuthMethod._meta.gateway.protocol,
|
|
24723
|
+
headers: gatewaySettings.headers,
|
|
24724
|
+
providerName: gatewaySettings.providerName
|
|
24725
|
+
});
|
|
24397
24726
|
return true;
|
|
24398
24727
|
}
|
|
24399
|
-
this.gatewayConfig = null;
|
|
24400
|
-
return false;
|
|
24401
24728
|
}
|
|
24402
24729
|
async authenticateWithApiKey(apiKey) {
|
|
24403
24730
|
const loginCompletedPromise = this.awaitNextLoginCompleted();
|
|
@@ -24405,7 +24732,6 @@ var CodexAcpClient = class {
|
|
|
24405
24732
|
type: "apiKey",
|
|
24406
24733
|
apiKey
|
|
24407
24734
|
});
|
|
24408
|
-
this.gatewayConfig = null;
|
|
24409
24735
|
const result = await loginCompletedPromise;
|
|
24410
24736
|
return result.success;
|
|
24411
24737
|
}
|
|
@@ -24472,12 +24798,90 @@ var CodexAcpClient = class {
|
|
|
24472
24798
|
const response = await this.codexClient.accountRead({ refreshToken: false });
|
|
24473
24799
|
return response.requiresOpenaiAuth && !response.account;
|
|
24474
24800
|
}
|
|
24475
|
-
|
|
24476
|
-
|
|
24801
|
+
/**
|
|
24802
|
+
* Validates and stores custom gateway routing. Shared by the `gateway` auth
|
|
24803
|
+
* method and the ACP `providers/set` method. Throws `invalid_params` for an
|
|
24804
|
+
* unsupported protocol or a malformed base URL.
|
|
24805
|
+
*/
|
|
24806
|
+
applyGatewayConfig(params) {
|
|
24807
|
+
const apiType = params.apiType;
|
|
24808
|
+
const wireApi = SUPPORTED_GATEWAY_PROTOCOLS[apiType];
|
|
24809
|
+
if (!wireApi) {
|
|
24810
|
+
throw RequestError.invalidParams(
|
|
24811
|
+
{ apiType },
|
|
24812
|
+
`Unsupported provider apiType "${apiType}"; supported: ${Object.keys(SUPPORTED_GATEWAY_PROTOCOLS).join(", ")}`
|
|
24813
|
+
);
|
|
24814
|
+
}
|
|
24815
|
+
if (typeof params.baseUrl !== "string" || params.baseUrl.trim().length === 0) {
|
|
24816
|
+
throw RequestError.invalidParams(void 0, "baseUrl must be a non-empty string");
|
|
24817
|
+
}
|
|
24818
|
+
const providerName = typeof params.providerName === "string" && params.providerName.trim().length > 0 ? params.providerName : "User-provided gateway";
|
|
24819
|
+
const headers = {
|
|
24820
|
+
"X-Client-Feature-ID": "codex",
|
|
24821
|
+
...params.headers
|
|
24822
|
+
};
|
|
24823
|
+
this.gatewayConfig = {
|
|
24824
|
+
modelProvider: CUSTOM_GATEWAY_PROVIDER_ID,
|
|
24825
|
+
config: {
|
|
24826
|
+
name: providerName,
|
|
24827
|
+
base_url: params.baseUrl,
|
|
24828
|
+
http_headers: headers,
|
|
24829
|
+
wire_api: wireApi
|
|
24830
|
+
}
|
|
24831
|
+
};
|
|
24832
|
+
}
|
|
24833
|
+
/**
|
|
24834
|
+
* `providers/list`: returns the single client-configurable custom gateway
|
|
24835
|
+
* provider. `current` carries only non-secret routing (never headers), and is
|
|
24836
|
+
* `null` when the provider is not configured/disabled.
|
|
24837
|
+
*/
|
|
24838
|
+
listProviders() {
|
|
24839
|
+
const gatewayConfig = this.gatewayConfig;
|
|
24840
|
+
const current = gatewayConfig ? {
|
|
24841
|
+
apiType: gatewayApiTypeFromConfig(gatewayConfig),
|
|
24842
|
+
baseUrl: gatewayConfig.config.base_url
|
|
24843
|
+
} : null;
|
|
24844
|
+
return [
|
|
24845
|
+
{
|
|
24846
|
+
providerId: CUSTOM_GATEWAY_PROVIDER_ID,
|
|
24847
|
+
supported: Object.keys(SUPPORTED_GATEWAY_PROTOCOLS),
|
|
24848
|
+
required: false,
|
|
24849
|
+
current
|
|
24850
|
+
}
|
|
24851
|
+
];
|
|
24852
|
+
}
|
|
24853
|
+
/**
|
|
24854
|
+
* `providers/set`: replaces the full configuration for the custom gateway
|
|
24855
|
+
* provider. Rejects unknown provider ids with `invalid_params`.
|
|
24856
|
+
*/
|
|
24857
|
+
setProvider(request) {
|
|
24858
|
+
if (request.providerId !== CUSTOM_GATEWAY_PROVIDER_ID) {
|
|
24859
|
+
throw RequestError.invalidParams(
|
|
24860
|
+
{ providerId: request.providerId },
|
|
24861
|
+
`Unknown providerId "${request.providerId}"; only "${CUSTOM_GATEWAY_PROVIDER_ID}" is configurable`
|
|
24862
|
+
);
|
|
24863
|
+
}
|
|
24864
|
+
this.applyGatewayConfig({
|
|
24865
|
+
apiType: request.apiType,
|
|
24866
|
+
baseUrl: request.baseUrl,
|
|
24867
|
+
headers: request.headers
|
|
24868
|
+
});
|
|
24869
|
+
}
|
|
24870
|
+
/**
|
|
24871
|
+
* `providers/disable`: disables the custom gateway provider. Disabling an
|
|
24872
|
+
* unknown provider id is idempotent success (RFD behavior §7).
|
|
24873
|
+
*/
|
|
24874
|
+
disableProvider(request) {
|
|
24875
|
+
if (request.providerId === CUSTOM_GATEWAY_PROVIDER_ID) {
|
|
24876
|
+
this.gatewayConfig = null;
|
|
24877
|
+
}
|
|
24477
24878
|
}
|
|
24478
24879
|
async getAccount() {
|
|
24479
24880
|
return this.codexClient.accountRead({ refreshToken: false });
|
|
24480
24881
|
}
|
|
24882
|
+
async getRateLimits() {
|
|
24883
|
+
return this.codexClient.accountRateLimitsRead();
|
|
24884
|
+
}
|
|
24481
24885
|
async resumeSession(request, onSubscribed) {
|
|
24482
24886
|
const additionalDirectories = readAdditionalDirectories(request.cwd, request.additionalDirectories, request._meta);
|
|
24483
24887
|
await this.refreshSkills(request.cwd, additionalDirectories);
|
|
@@ -24715,6 +25119,10 @@ var CodexAcpClient = class {
|
|
|
24715
25119
|
handleElicitation: async (params) => {
|
|
24716
25120
|
await this.waitForSessionNotifications(sessionId);
|
|
24717
25121
|
return await elicitationHandler.handleElicitation(params);
|
|
25122
|
+
},
|
|
25123
|
+
handleUserInput: async (params) => {
|
|
25124
|
+
await this.waitForSessionNotifications(sessionId);
|
|
25125
|
+
return await elicitationHandler.handleUserInput(params);
|
|
24718
25126
|
}
|
|
24719
25127
|
});
|
|
24720
25128
|
}
|
|
@@ -24764,6 +25172,15 @@ var CodexAcpClient = class {
|
|
|
24764
25172
|
}
|
|
24765
25173
|
return await this.codexClient.runTurn(params, onTurnStarted);
|
|
24766
25174
|
}
|
|
25175
|
+
async sendSteer(request, expectedTurnId, steerId) {
|
|
25176
|
+
const response = await this.codexClient.turnSteer({
|
|
25177
|
+
threadId: request.sessionId,
|
|
25178
|
+
input: buildPromptItems(request.prompt),
|
|
25179
|
+
expectedTurnId,
|
|
25180
|
+
clientUserMessageId: steerId
|
|
25181
|
+
});
|
|
25182
|
+
return response.turnId;
|
|
25183
|
+
}
|
|
24767
25184
|
resolveTurnInterrupted(params) {
|
|
24768
25185
|
this.codexClient.resolveTurnInterrupted(params.threadId, params.turnId);
|
|
24769
25186
|
}
|
|
@@ -24881,7 +25298,7 @@ var CodexAcpClient = class {
|
|
|
24881
25298
|
const [allProviders, archivedAllProviders, customGateway] = await Promise.all([
|
|
24882
25299
|
this.codexClient.threadList({}),
|
|
24883
25300
|
this.codexClient.threadList({ archived: true }),
|
|
24884
|
-
this.codexClient.threadList({ modelProviders: [
|
|
25301
|
+
this.codexClient.threadList({ modelProviders: [CUSTOM_GATEWAY_PROVIDER_ID] })
|
|
24885
25302
|
]);
|
|
24886
25303
|
return {
|
|
24887
25304
|
allProviders: {
|
|
@@ -25034,6 +25451,11 @@ function arraysEqual(left, right) {
|
|
|
25034
25451
|
function isJsonObject(value) {
|
|
25035
25452
|
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
25036
25453
|
}
|
|
25454
|
+
function gatewayApiTypeFromConfig(gatewayConfig) {
|
|
25455
|
+
const wireApi = gatewayConfig.config.wire_api;
|
|
25456
|
+
const match = Object.entries(SUPPORTED_GATEWAY_PROTOCOLS).find(([, wire]) => wire === wireApi);
|
|
25457
|
+
return match?.[0] ?? "openai";
|
|
25458
|
+
}
|
|
25037
25459
|
function mergeGatewayConfig(config2, gatewayConfig) {
|
|
25038
25460
|
if (gatewayConfig !== null) {
|
|
25039
25461
|
const newConfig = { ...config2 };
|
|
@@ -25050,6 +25472,9 @@ function mergeGatewayConfig(config2, gatewayConfig) {
|
|
|
25050
25472
|
}
|
|
25051
25473
|
var MODEL_CONFIG_ID = "model";
|
|
25052
25474
|
var REASONING_EFFORT_CONFIG_ID = "reasoning_effort";
|
|
25475
|
+
function capitalize(value) {
|
|
25476
|
+
return value.charAt(0).toUpperCase() + value.slice(1);
|
|
25477
|
+
}
|
|
25053
25478
|
function findSupportedEffort(options, effort) {
|
|
25054
25479
|
if (!effort) return void 0;
|
|
25055
25480
|
return options.find((o) => o.reasoningEffort === effort)?.reasoningEffort;
|
|
@@ -25087,7 +25512,7 @@ function createReasoningEffortConfigOption(supportedReasoningEfforts, currentEff
|
|
|
25087
25512
|
currentValue: currentEffort,
|
|
25088
25513
|
options: supportedReasoningEfforts.map((option) => ({
|
|
25089
25514
|
value: option.reasoningEffort,
|
|
25090
|
-
name: option.reasoningEffort,
|
|
25515
|
+
name: capitalize(option.reasoningEffort),
|
|
25091
25516
|
description: option.description
|
|
25092
25517
|
}))
|
|
25093
25518
|
};
|
|
@@ -25288,8 +25713,7 @@ var CodexCommands = class {
|
|
|
25288
25713
|
return { handled: true };
|
|
25289
25714
|
}
|
|
25290
25715
|
default:
|
|
25291
|
-
|
|
25292
|
-
return { handled: true };
|
|
25716
|
+
return { handled: false };
|
|
25293
25717
|
}
|
|
25294
25718
|
}
|
|
25295
25719
|
async runReviewCommand(sessionState, target, options) {
|
|
@@ -25371,17 +25795,6 @@ var CodexCommands = class {
|
|
|
25371
25795
|
const session = new ACPSessionConnection(this.connection, sessionId);
|
|
25372
25796
|
await session.update(createAgentTextMessageChunk(text));
|
|
25373
25797
|
}
|
|
25374
|
-
async sendUnknownCommandMessage(name, sessionId) {
|
|
25375
|
-
const lines = this.getBuiltinCommands().map((command) => `- /${command.name}: ${command.description}`);
|
|
25376
|
-
const text = [
|
|
25377
|
-
`Unknown command "/${name}".`,
|
|
25378
|
-
"Available commands:"
|
|
25379
|
-
];
|
|
25380
|
-
if (lines.length > 0) {
|
|
25381
|
-
text.push(...lines);
|
|
25382
|
-
}
|
|
25383
|
-
await this.sendCommandMessage(text.join("\n"), sessionId);
|
|
25384
|
-
}
|
|
25385
25798
|
buildStatusMessage(sessionState) {
|
|
25386
25799
|
const agentMode = sessionState.agentMode;
|
|
25387
25800
|
const accountText = this.formatAccountInfo(sessionState.account);
|
|
@@ -25645,6 +26058,7 @@ function toolCallIdFromThreadItem(item) {
|
|
|
25645
26058
|
case "webSearch":
|
|
25646
26059
|
case "imageView":
|
|
25647
26060
|
case "imageGeneration":
|
|
26061
|
+
case "contextCompaction":
|
|
25648
26062
|
return item.id;
|
|
25649
26063
|
case "userMessage":
|
|
25650
26064
|
case "hookPrompt":
|
|
@@ -25654,7 +26068,6 @@ function toolCallIdFromThreadItem(item) {
|
|
|
25654
26068
|
case "subAgentActivity":
|
|
25655
26069
|
case "enteredReviewMode":
|
|
25656
26070
|
case "exitedReviewMode":
|
|
25657
|
-
case "contextCompaction":
|
|
25658
26071
|
case "sleep":
|
|
25659
26072
|
return null;
|
|
25660
26073
|
}
|
|
@@ -25737,9 +26150,13 @@ function createAgentReasoningEventUpdates(payload) {
|
|
|
25737
26150
|
if (text === null || text.length === 0) {
|
|
25738
26151
|
return [];
|
|
25739
26152
|
}
|
|
26153
|
+
const sanitizedText = stripEmptyReasoningComments(text);
|
|
26154
|
+
if (sanitizedText.length === 0) {
|
|
26155
|
+
return [];
|
|
26156
|
+
}
|
|
25740
26157
|
return [{
|
|
25741
26158
|
sessionUpdate: "agent_thought_chunk",
|
|
25742
|
-
content: { type: "text", text }
|
|
26159
|
+
content: { type: "text", text: sanitizedText }
|
|
25743
26160
|
}];
|
|
25744
26161
|
}
|
|
25745
26162
|
function imageBlocks(images) {
|
|
@@ -25776,11 +26193,7 @@ function contentBlocksFromResponseContent(content) {
|
|
|
25776
26193
|
});
|
|
25777
26194
|
}
|
|
25778
26195
|
function createReasoningUpdates(item) {
|
|
25779
|
-
|
|
25780
|
-
if (parts.length === 0) {
|
|
25781
|
-
parts.push(...textParts(item["content"]));
|
|
25782
|
-
}
|
|
25783
|
-
return parts.map((text) => ({
|
|
26196
|
+
return sanitizeReasoningParts(textParts(item["summary"]), textParts(item["content"])).map((text) => ({
|
|
25784
26197
|
sessionUpdate: "agent_thought_chunk",
|
|
25785
26198
|
content: { type: "text", text }
|
|
25786
26199
|
}));
|
|
@@ -26571,6 +26984,7 @@ var CodexAcpServer = class _CodexAcpServer {
|
|
|
26571
26984
|
pendingMcpStartupSessions;
|
|
26572
26985
|
pendingTurnStarts;
|
|
26573
26986
|
activePrompts;
|
|
26987
|
+
pendingSteers;
|
|
26574
26988
|
closingSessions;
|
|
26575
26989
|
sessionGenerations;
|
|
26576
26990
|
sessionOpenGenerations;
|
|
@@ -26579,6 +26993,7 @@ var CodexAcpServer = class _CodexAcpServer {
|
|
|
26579
26993
|
this.pendingMcpStartupSessions = /* @__PURE__ */ new Map();
|
|
26580
26994
|
this.pendingTurnStarts = /* @__PURE__ */ new Map();
|
|
26581
26995
|
this.activePrompts = /* @__PURE__ */ new Map();
|
|
26996
|
+
this.pendingSteers = /* @__PURE__ */ new Map();
|
|
26582
26997
|
this.closingSessions = /* @__PURE__ */ new Map();
|
|
26583
26998
|
this.sessionGenerations = /* @__PURE__ */ new Map();
|
|
26584
26999
|
this.sessionOpenGenerations = /* @__PURE__ */ new Map();
|
|
@@ -26616,6 +27031,7 @@ var CodexAcpServer = class _CodexAcpServer {
|
|
|
26616
27031
|
auth: {
|
|
26617
27032
|
logout: {}
|
|
26618
27033
|
},
|
|
27034
|
+
providers: {},
|
|
26619
27035
|
loadSession: true,
|
|
26620
27036
|
promptCapabilities: {
|
|
26621
27037
|
embeddedContext: true,
|
|
@@ -26632,6 +27048,11 @@ var CodexAcpServer = class _CodexAcpServer {
|
|
|
26632
27048
|
acp: false,
|
|
26633
27049
|
http: true,
|
|
26634
27050
|
sse: false
|
|
27051
|
+
},
|
|
27052
|
+
_meta: {
|
|
27053
|
+
codex: {
|
|
27054
|
+
steer: CODEX_STEER_CAPABILITY
|
|
27055
|
+
}
|
|
26635
27056
|
}
|
|
26636
27057
|
},
|
|
26637
27058
|
authMethods: getCodexAuthMethods(_params.clientCapabilities)
|
|
@@ -26807,9 +27228,12 @@ You have been logged out. Please try again.`);
|
|
|
26807
27228
|
planModeEnabled: false,
|
|
26808
27229
|
planModeExplicitlySet: false,
|
|
26809
27230
|
sessionMcpServers,
|
|
26810
|
-
terminalOutputMode: this.terminalOutputMode
|
|
27231
|
+
terminalOutputMode: this.terminalOutputMode,
|
|
27232
|
+
sessionTitle: null,
|
|
27233
|
+
sessionTitleSource: "sessionId" in request ? "unknown" : "unset"
|
|
26811
27234
|
};
|
|
26812
27235
|
this.sessions.set(sessionId, sessionState);
|
|
27236
|
+
this.publishRateLimitsAsync(sessionState);
|
|
26813
27237
|
resumeSubscribed = false;
|
|
26814
27238
|
if (requestedMcpServers.length > 0 && mcpServerStartupVersion !== null) {
|
|
26815
27239
|
this.pendingMcpStartupSessions.set(sessionId, {
|
|
@@ -26845,6 +27269,27 @@ You have been logged out. Please try again.`);
|
|
|
26845
27269
|
}
|
|
26846
27270
|
return a === b;
|
|
26847
27271
|
}
|
|
27272
|
+
publishRateLimitsAsync(sessionState) {
|
|
27273
|
+
if (!sessionState.authConfigured || !this.authProviderUsesOpenAiAccount(sessionState.authProvider)) {
|
|
27274
|
+
return;
|
|
27275
|
+
}
|
|
27276
|
+
void this.codexAcpClient.getRateLimits().then(async (response) => {
|
|
27277
|
+
if (this.sessions.get(sessionState.sessionId) !== sessionState) {
|
|
27278
|
+
return;
|
|
27279
|
+
}
|
|
27280
|
+
if (!response?.rateLimits) {
|
|
27281
|
+
return;
|
|
27282
|
+
}
|
|
27283
|
+
const rateLimitsById = Object.values(response.rateLimitsByLimitId ?? {}).filter((snapshot) => snapshot !== void 0);
|
|
27284
|
+
const snapshots = rateLimitsById.length > 0 ? rateLimitsById : [response.rateLimits];
|
|
27285
|
+
const handler = new CodexEventHandler(this.connection, sessionState);
|
|
27286
|
+
for (const snapshot of snapshots) {
|
|
27287
|
+
await handler.handleRateLimitsSnapshot(snapshot);
|
|
27288
|
+
}
|
|
27289
|
+
}).catch((err) => {
|
|
27290
|
+
logger.error(`Failed to read rate limits for session ${sessionState.sessionId}`, err);
|
|
27291
|
+
});
|
|
27292
|
+
}
|
|
26848
27293
|
getAuthProviderForAuthenticateRequest(request) {
|
|
26849
27294
|
if (isCodexAuthRequest(request) && request.methodId === "gateway") {
|
|
26850
27295
|
return "custom-gateway";
|
|
@@ -26988,6 +27433,17 @@ You have been logged out. Please try again.`);
|
|
|
26988
27433
|
await this.refreshSessionsAuthState(null);
|
|
26989
27434
|
logger.log("Logout request completed");
|
|
26990
27435
|
}
|
|
27436
|
+
listProviders(_params) {
|
|
27437
|
+
return { providers: this.codexAcpClient.listProviders() };
|
|
27438
|
+
}
|
|
27439
|
+
setProvider(params) {
|
|
27440
|
+
this.codexAcpClient.setProvider(params);
|
|
27441
|
+
return {};
|
|
27442
|
+
}
|
|
27443
|
+
disableProvider(params) {
|
|
27444
|
+
this.codexAcpClient.disableProvider(params);
|
|
27445
|
+
return {};
|
|
27446
|
+
}
|
|
26991
27447
|
async refreshSessionsAuthState(authProvider) {
|
|
26992
27448
|
if (this.sessions.size === 0) return;
|
|
26993
27449
|
const sessionsToRefresh = [...this.sessions.values()].filter((sessionState) => this.authProvidersMatch(sessionState.authProvider, authProvider));
|
|
@@ -26996,6 +27452,7 @@ You have been logged out. Please try again.`);
|
|
|
26996
27452
|
for (const sessionState of sessionsToRefresh) {
|
|
26997
27453
|
sessionState.account = authState.account;
|
|
26998
27454
|
sessionState.authConfigured = authState.authConfigured;
|
|
27455
|
+
this.publishRateLimitsAsync(sessionState);
|
|
26999
27456
|
}
|
|
27000
27457
|
}
|
|
27001
27458
|
async setSessionMode(_params) {
|
|
@@ -27259,9 +27716,12 @@ You have been logged out. Please try again.`);
|
|
|
27259
27716
|
planModeEnabled: false,
|
|
27260
27717
|
planModeExplicitlySet: false,
|
|
27261
27718
|
sessionMcpServers,
|
|
27262
|
-
terminalOutputMode: this.terminalOutputMode
|
|
27719
|
+
terminalOutputMode: this.terminalOutputMode,
|
|
27720
|
+
sessionTitle: null,
|
|
27721
|
+
sessionTitleSource: "unset"
|
|
27263
27722
|
};
|
|
27264
27723
|
this.sessions.set(sessionId, sessionState);
|
|
27724
|
+
this.publishRateLimitsAsync(sessionState);
|
|
27265
27725
|
subscribed = false;
|
|
27266
27726
|
if (requestedMcpServers.length > 0 && mcpServerStartupVersion !== null) {
|
|
27267
27727
|
this.pendingMcpStartupSessions.set(sessionId, {
|
|
@@ -27283,6 +27743,7 @@ You have been logged out. Please try again.`);
|
|
|
27283
27743
|
async streamThreadHistory(sessionId, thread) {
|
|
27284
27744
|
const session = new ACPSessionConnection(this.connection, sessionId);
|
|
27285
27745
|
const sessionState = this.getSessionState(sessionId);
|
|
27746
|
+
await this.publishThreadHistoryTitle(session, sessionState, thread);
|
|
27286
27747
|
const responseItemFallbackUpdates = await createResponseItemHistoryFallbackUpdates(
|
|
27287
27748
|
thread,
|
|
27288
27749
|
sessionState.terminalOutputMode
|
|
@@ -27299,6 +27760,47 @@ You have been logged out. Please try again.`);
|
|
|
27299
27760
|
await session.update(update);
|
|
27300
27761
|
}
|
|
27301
27762
|
}
|
|
27763
|
+
async publishThreadHistoryTitle(session, sessionState, thread) {
|
|
27764
|
+
const explicitTitle = this.normalizeSessionTitle(thread.name);
|
|
27765
|
+
if (explicitTitle) {
|
|
27766
|
+
sessionState.sessionTitle = explicitTitle;
|
|
27767
|
+
sessionState.sessionTitleSource = "explicit";
|
|
27768
|
+
await session.update({
|
|
27769
|
+
sessionUpdate: "session_info_update",
|
|
27770
|
+
title: explicitTitle
|
|
27771
|
+
});
|
|
27772
|
+
return;
|
|
27773
|
+
}
|
|
27774
|
+
const historyTitle = this.findFirstUserMessageTitle(thread) ?? this.normalizeSessionTitle(thread.preview);
|
|
27775
|
+
await this.publishFallbackSessionTitle(sessionState, historyTitle);
|
|
27776
|
+
}
|
|
27777
|
+
findFirstUserMessageTitle(thread) {
|
|
27778
|
+
for (const turn of thread.turns) {
|
|
27779
|
+
for (const item of turn.items) {
|
|
27780
|
+
if (item.type !== "userMessage") continue;
|
|
27781
|
+
const title = this.normalizeSessionTitle(item.content.filter((input) => input.type === "text").map((input) => input.text).join(" "));
|
|
27782
|
+
if (title) return title;
|
|
27783
|
+
}
|
|
27784
|
+
}
|
|
27785
|
+
return null;
|
|
27786
|
+
}
|
|
27787
|
+
async publishFallbackSessionTitle(sessionState, title) {
|
|
27788
|
+
if (sessionState.sessionTitleSource !== "unset" || !title) return;
|
|
27789
|
+
sessionState.sessionTitle = title;
|
|
27790
|
+
sessionState.sessionTitleSource = "fallback";
|
|
27791
|
+
const session = new ACPSessionConnection(this.connection, sessionState.sessionId);
|
|
27792
|
+
await session.update({
|
|
27793
|
+
sessionUpdate: "session_info_update",
|
|
27794
|
+
title
|
|
27795
|
+
});
|
|
27796
|
+
}
|
|
27797
|
+
createPromptFallbackTitle(prompt) {
|
|
27798
|
+
return this.normalizeSessionTitle(prompt.filter((block) => block.type === "text").map((block) => block.text).join(" "));
|
|
27799
|
+
}
|
|
27800
|
+
normalizeSessionTitle(title) {
|
|
27801
|
+
const normalized = title?.replace(/\s+/g, " ").trim() ?? "";
|
|
27802
|
+
return normalized.length > 0 ? normalized : null;
|
|
27803
|
+
}
|
|
27302
27804
|
async createHistoryUpdates(item, sessionState) {
|
|
27303
27805
|
switch (item.type) {
|
|
27304
27806
|
case "userMessage":
|
|
@@ -27345,7 +27847,7 @@ You have been logged out. Please try again.`);
|
|
|
27345
27847
|
case "exitedReviewMode":
|
|
27346
27848
|
return [this.createReviewModeUpdate(item, false)];
|
|
27347
27849
|
case "contextCompaction":
|
|
27348
|
-
return [
|
|
27850
|
+
return [createCompletedContextCompactionUpdate(item)];
|
|
27349
27851
|
case "plan":
|
|
27350
27852
|
return [this.createPlanUpdate(item)];
|
|
27351
27853
|
}
|
|
@@ -27362,9 +27864,8 @@ You have been logged out. Please try again.`);
|
|
|
27362
27864
|
return updates;
|
|
27363
27865
|
}
|
|
27364
27866
|
createReasoningUpdates(item) {
|
|
27365
|
-
const parts = item.summary.length > 0 ? item.summary : item.content;
|
|
27366
27867
|
const messageId = item.id;
|
|
27367
|
-
return
|
|
27868
|
+
return sanitizeReasoningParts(item.summary, item.content).map((text) => createAgentTextThoughtChunk(text, messageId));
|
|
27368
27869
|
}
|
|
27369
27870
|
createWebSearchUpdate(item) {
|
|
27370
27871
|
return {
|
|
@@ -27388,15 +27889,6 @@ You have been logged out. Please try again.`);
|
|
|
27388
27889
|
}
|
|
27389
27890
|
};
|
|
27390
27891
|
}
|
|
27391
|
-
createContextCompactionUpdate() {
|
|
27392
|
-
return {
|
|
27393
|
-
sessionUpdate: "agent_message_chunk",
|
|
27394
|
-
content: {
|
|
27395
|
-
type: "text",
|
|
27396
|
-
text: "Context compacted."
|
|
27397
|
-
}
|
|
27398
|
-
};
|
|
27399
|
-
}
|
|
27400
27892
|
createPlanUpdate(item) {
|
|
27401
27893
|
return {
|
|
27402
27894
|
sessionUpdate: "agent_message_chunk",
|
|
@@ -27516,6 +28008,7 @@ ${item.text}`
|
|
|
27516
28008
|
cancelSignal,
|
|
27517
28009
|
signal: abortController.signal,
|
|
27518
28010
|
currentTurn: null,
|
|
28011
|
+
outcome: null,
|
|
27519
28012
|
requestCancel: () => {
|
|
27520
28013
|
if (abortController.signal.aborted) {
|
|
27521
28014
|
return;
|
|
@@ -27539,12 +28032,78 @@ ${item.text}`
|
|
|
27539
28032
|
if (this.activePrompts.get(sessionId) === activePrompt) {
|
|
27540
28033
|
this.activePrompts.delete(sessionId);
|
|
27541
28034
|
}
|
|
28035
|
+
this.clearPendingSteers(sessionId, activePrompt);
|
|
27542
28036
|
resolveCompletion();
|
|
27543
28037
|
}
|
|
27544
28038
|
};
|
|
27545
28039
|
this.activePrompts.set(sessionId, activePrompt);
|
|
27546
28040
|
return activePrompt;
|
|
27547
28041
|
}
|
|
28042
|
+
clearPendingSteers(sessionId, activePrompt) {
|
|
28043
|
+
const pending = this.pendingSteers.get(sessionId);
|
|
28044
|
+
if (!pending) return;
|
|
28045
|
+
for (const [steerId, steer] of pending) {
|
|
28046
|
+
if (steer.activePrompt === activePrompt) pending.delete(steerId);
|
|
28047
|
+
}
|
|
28048
|
+
if (pending.size === 0) this.pendingSteers.delete(sessionId);
|
|
28049
|
+
}
|
|
28050
|
+
async handleSteerAppliedNotification(sessionId, event, activePrompt) {
|
|
28051
|
+
if (event.method !== "item/completed" || event.params.item.type !== "userMessage") return;
|
|
28052
|
+
const steerId = event.params.item.clientId;
|
|
28053
|
+
if (!steerId) return;
|
|
28054
|
+
const pending = this.pendingSteers.get(sessionId);
|
|
28055
|
+
if (!pending) return;
|
|
28056
|
+
const steer = pending.get(steerId);
|
|
28057
|
+
if (!steer || steer.activePrompt !== activePrompt || steer.turnId !== event.params.turnId) return;
|
|
28058
|
+
pending.delete(steerId);
|
|
28059
|
+
if (pending.size === 0) this.pendingSteers.delete(sessionId);
|
|
28060
|
+
await this.connection.notify(CODEX_STEER_APPLIED_METHOD, { sessionId, steerId });
|
|
28061
|
+
}
|
|
28062
|
+
async steerPrompt(params) {
|
|
28063
|
+
const steerId = getCodexSteerId(params._meta);
|
|
28064
|
+
if (!steerId) throw RequestError.invalidRequest("Missing Codex steer id");
|
|
28065
|
+
const firstText = params.prompt[0]?.type === "text" ? params.prompt[0].text : "";
|
|
28066
|
+
if (firstText.startsWith("/")) {
|
|
28067
|
+
throw RequestError.invalidRequest("Slash commands cannot steer an active Codex turn");
|
|
28068
|
+
}
|
|
28069
|
+
let activePrompt = this.activePrompts.get(params.sessionId);
|
|
28070
|
+
if (!activePrompt) throw RequestError.invalidRequest("No active Codex turn to steer");
|
|
28071
|
+
if (!activePrompt.currentTurn) {
|
|
28072
|
+
await this.pendingTurnStarts.get(params.sessionId)?.promise;
|
|
28073
|
+
activePrompt = this.activePrompts.get(params.sessionId);
|
|
28074
|
+
}
|
|
28075
|
+
const turn = activePrompt?.currentTurn;
|
|
28076
|
+
if (!activePrompt || !turn || activePrompt.signal.aborted) {
|
|
28077
|
+
throw RequestError.invalidRequest("No active Codex turn to steer");
|
|
28078
|
+
}
|
|
28079
|
+
const pending = this.pendingSteers.get(params.sessionId) ?? /* @__PURE__ */ new Map();
|
|
28080
|
+
if (pending.has(steerId)) {
|
|
28081
|
+
throw RequestError.invalidRequest(`Duplicate Codex steer id: ${steerId}`);
|
|
28082
|
+
}
|
|
28083
|
+
pending.set(steerId, { activePrompt, turnId: turn.turnId });
|
|
28084
|
+
this.pendingSteers.set(params.sessionId, pending);
|
|
28085
|
+
try {
|
|
28086
|
+
const steeredTurnId = await this.runWithProcessCheck(
|
|
28087
|
+
() => this.codexAcpClient.sendSteer(params, turn.turnId, steerId)
|
|
28088
|
+
);
|
|
28089
|
+
if (steeredTurnId !== turn.turnId) {
|
|
28090
|
+
throw RequestError.internalError(
|
|
28091
|
+
void 0,
|
|
28092
|
+
`Codex steered unexpected turn ${steeredTurnId}; expected ${turn.turnId}`
|
|
28093
|
+
);
|
|
28094
|
+
}
|
|
28095
|
+
} catch (error48) {
|
|
28096
|
+
if (pending.get(steerId)?.activePrompt === activePrompt) {
|
|
28097
|
+
pending.delete(steerId);
|
|
28098
|
+
if (pending.size === 0) this.pendingSteers.delete(params.sessionId);
|
|
28099
|
+
}
|
|
28100
|
+
throw error48;
|
|
28101
|
+
}
|
|
28102
|
+
if (!activePrompt.outcome) {
|
|
28103
|
+
throw RequestError.internalError(void 0, "Active Codex prompt has no tracked outcome");
|
|
28104
|
+
}
|
|
28105
|
+
return await activePrompt.outcome;
|
|
28106
|
+
}
|
|
27548
28107
|
cancelBeforeTurnStarted(activePrompt) {
|
|
27549
28108
|
return activePrompt.cancelSignal.then(() => {
|
|
27550
28109
|
if (activePrompt.currentTurn === null) {
|
|
@@ -27676,6 +28235,22 @@ ${item.text}`
|
|
|
27676
28235
|
return turnId;
|
|
27677
28236
|
}
|
|
27678
28237
|
async prompt(params, signal) {
|
|
28238
|
+
if (getCodexSteerId(params._meta)) {
|
|
28239
|
+
return await this.steerPrompt(params);
|
|
28240
|
+
}
|
|
28241
|
+
if (this.activePrompts.has(params.sessionId)) {
|
|
28242
|
+
throw RequestError.invalidRequest(
|
|
28243
|
+
"A Codex prompt is already active; use the advertised steer extension"
|
|
28244
|
+
);
|
|
28245
|
+
}
|
|
28246
|
+
const outcome = this.runPrompt(params, signal);
|
|
28247
|
+
const activePrompt = this.activePrompts.get(params.sessionId);
|
|
28248
|
+
if (activePrompt) {
|
|
28249
|
+
activePrompt.outcome = outcome;
|
|
28250
|
+
}
|
|
28251
|
+
return await outcome;
|
|
28252
|
+
}
|
|
28253
|
+
async runPrompt(params, signal) {
|
|
27679
28254
|
logger.log("Prompt received", {
|
|
27680
28255
|
sessionId: params.sessionId,
|
|
27681
28256
|
prompt: params.prompt
|
|
@@ -27684,14 +28259,8 @@ ${item.text}`
|
|
|
27684
28259
|
sessionState.currentTurnId = null;
|
|
27685
28260
|
sessionState.lastTokenUsage = null;
|
|
27686
28261
|
const activePrompt = this.trackActivePrompt(params.sessionId);
|
|
27687
|
-
|
|
27688
|
-
|
|
27689
|
-
if (pendingTurnStart === null) {
|
|
27690
|
-
pendingTurnStart = this.createPendingTurnStart();
|
|
27691
|
-
this.pendingTurnStarts.set(params.sessionId, pendingTurnStart);
|
|
27692
|
-
}
|
|
27693
|
-
return pendingTurnStart;
|
|
27694
|
-
};
|
|
28262
|
+
const pendingTurnStart = this.createPendingTurnStart();
|
|
28263
|
+
this.pendingTurnStarts.set(params.sessionId, pendingTurnStart);
|
|
27695
28264
|
const disposePromptRequestCancellation = this.observePromptRequestCancellation(signal, sessionState, activePrompt);
|
|
27696
28265
|
try {
|
|
27697
28266
|
const eventHandler = new CodexEventHandler(this.connection, sessionState);
|
|
@@ -27705,6 +28274,7 @@ ${item.text}`
|
|
|
27705
28274
|
await this.codexAcpClient.subscribeToSessionEvents(
|
|
27706
28275
|
params.sessionId,
|
|
27707
28276
|
async (event) => {
|
|
28277
|
+
await this.handleSteerAppliedNotification(params.sessionId, event, activePrompt);
|
|
27708
28278
|
await elicitationHandler.handleNotification(event);
|
|
27709
28279
|
return eventHandler.handleNotification(event);
|
|
27710
28280
|
},
|
|
@@ -27715,9 +28285,6 @@ ${item.text}`
|
|
|
27715
28285
|
return this.cancelledPromptResponse(sessionState);
|
|
27716
28286
|
}
|
|
27717
28287
|
const commandPromise = this.availableCommands.tryHandleCommand(params.prompt, sessionState, {
|
|
27718
|
-
onTurnStartPending: () => {
|
|
27719
|
-
ensurePendingTurnStart();
|
|
27720
|
-
},
|
|
27721
28288
|
onTurnStarted: (turnId, threadId) => {
|
|
27722
28289
|
const turn = { threadId, turnId };
|
|
27723
28290
|
activePrompt.currentTurn = turn;
|
|
@@ -27726,7 +28293,7 @@ ${item.text}`
|
|
|
27726
28293
|
return;
|
|
27727
28294
|
}
|
|
27728
28295
|
sessionState.currentTurnId = turnId;
|
|
27729
|
-
pendingTurnStart
|
|
28296
|
+
pendingTurnStart.resolve(turnId);
|
|
27730
28297
|
}
|
|
27731
28298
|
});
|
|
27732
28299
|
void commandPromise.catch((err) => {
|
|
@@ -27780,7 +28347,6 @@ ${item.text}`
|
|
|
27780
28347
|
sessionState.currentModelSupportsFast
|
|
27781
28348
|
);
|
|
27782
28349
|
const collaborationMode = this.createPlanModeCollaborationMode(sessionState, modelId);
|
|
27783
|
-
ensurePendingTurnStart();
|
|
27784
28350
|
const sendPromptPromise = this.runWithProcessCheck(
|
|
27785
28351
|
() => this.codexAcpClient.sendPrompt(
|
|
27786
28352
|
params,
|
|
@@ -27799,7 +28365,7 @@ ${item.text}`
|
|
|
27799
28365
|
return;
|
|
27800
28366
|
}
|
|
27801
28367
|
sessionState.currentTurnId = turnId;
|
|
27802
|
-
pendingTurnStart
|
|
28368
|
+
pendingTurnStart.resolve(turnId);
|
|
27803
28369
|
},
|
|
27804
28370
|
() => this.promptShouldStop(params.sessionId, activePrompt)
|
|
27805
28371
|
)
|
|
@@ -27826,6 +28392,10 @@ ${item.text}`
|
|
|
27826
28392
|
if (error48) {
|
|
27827
28393
|
throw error48;
|
|
27828
28394
|
}
|
|
28395
|
+
await this.publishFallbackSessionTitle(
|
|
28396
|
+
sessionState,
|
|
28397
|
+
this.createPromptFallbackTitle(params.prompt)
|
|
28398
|
+
);
|
|
27829
28399
|
return {
|
|
27830
28400
|
stopReason: "end_turn",
|
|
27831
28401
|
usage: this.buildPromptUsage(sessionState.lastTokenUsage),
|
|
@@ -27978,6 +28548,7 @@ var CommandExecutionApprovalRequest = new import_node2.RequestType("item/command
|
|
|
27978
28548
|
var FileChangeApprovalRequest = new import_node2.RequestType("item/fileChange/requestApproval");
|
|
27979
28549
|
var PermissionsApprovalRequest = new import_node2.RequestType("item/permissions/requestApproval");
|
|
27980
28550
|
var McpServerElicitationRequest = new import_node2.RequestType("mcpServer/elicitation/request");
|
|
28551
|
+
var ToolRequestUserInputRequest = new import_node2.RequestType("item/tool/requestUserInput");
|
|
27981
28552
|
var GOAL_RUNTIME_EFFECTS_GRACE_MS = 1e3;
|
|
27982
28553
|
var CodexAppServerClient = class {
|
|
27983
28554
|
connection;
|
|
@@ -28075,6 +28646,16 @@ var CodexAppServerClient = class {
|
|
|
28075
28646
|
}
|
|
28076
28647
|
return await handler.handleElicitation(params);
|
|
28077
28648
|
});
|
|
28649
|
+
this.connection.onRequest(ToolRequestUserInputRequest, async (params) => {
|
|
28650
|
+
if (this.isStaleTurn(params.threadId, params.turnId)) {
|
|
28651
|
+
return { answers: {} };
|
|
28652
|
+
}
|
|
28653
|
+
const handler = this.elicitationHandlers.get(params.threadId);
|
|
28654
|
+
if (!handler) {
|
|
28655
|
+
return { answers: {} };
|
|
28656
|
+
}
|
|
28657
|
+
return await handler.handleUserInput(params);
|
|
28658
|
+
});
|
|
28078
28659
|
}
|
|
28079
28660
|
onApprovalRequest(threadId, handler) {
|
|
28080
28661
|
this.approvalHandlers.set(threadId, handler);
|
|
@@ -28093,6 +28674,9 @@ var CodexAppServerClient = class {
|
|
|
28093
28674
|
async turnStart(params) {
|
|
28094
28675
|
return await this.sendRequest({ method: "turn/start", params });
|
|
28095
28676
|
}
|
|
28677
|
+
async turnSteer(params) {
|
|
28678
|
+
return await this.sendRequest({ method: "turn/steer", params });
|
|
28679
|
+
}
|
|
28096
28680
|
async runTurn(params, onTurnStarted) {
|
|
28097
28681
|
const capturedCompletions = [];
|
|
28098
28682
|
const releaseCapture = this.captureTurnCompletions(params.threadId, (event) => {
|
|
@@ -28378,6 +28962,9 @@ var CodexAppServerClient = class {
|
|
|
28378
28962
|
async accountRead(params) {
|
|
28379
28963
|
return await this.sendRequest({ method: "account/read", params });
|
|
28380
28964
|
}
|
|
28965
|
+
async accountRateLimitsRead() {
|
|
28966
|
+
return await this.sendRequest({ method: "account/rateLimits/read", params: void 0 });
|
|
28967
|
+
}
|
|
28381
28968
|
//TODO create type-safe helper
|
|
28382
28969
|
async awaitTurnCompleted(threadId, turnId) {
|
|
28383
28970
|
return await new Promise((resolve) => {
|
|
@@ -28932,5 +29519,5 @@ function startAcpServer() {
|
|
|
28932
29519
|
codexAcpServer = null;
|
|
28933
29520
|
}
|
|
28934
29521
|
});
|
|
28935
|
-
}).onRequest(methods.agent.initialize, (ctx) => getAgent().initialize(ctx.params)).onRequest(methods.agent.session.new, (ctx) => getAgent().newSession(ctx.params)).onRequest(methods.agent.session.load, (ctx) => getAgent().loadSession(ctx.params)).onRequest(methods.agent.session.list, (ctx) => getAgent().listSessions(ctx.params)).onRequest(methods.agent.session.delete, (ctx) => getAgent().deleteSession(ctx.params)).onRequest(methods.agent.session.resume, (ctx) => getAgent().resumeSession(ctx.params)).onRequest(methods.agent.session.close, (ctx) => getAgent().closeSession(ctx.params)).onRequest(methods.agent.session.setMode, (ctx) => getAgent().setSessionMode(ctx.params)).onRequest(methods.agent.session.setConfigOption, (ctx) => getAgent().setSessionConfigOption(ctx.params)).onRequest(methods.agent.authenticate, (ctx) => getAgent().authenticate(ctx.params)).onRequest(methods.agent.logout, (ctx) => getAgent().logout(ctx.params)).onRequest(methods.agent.session.prompt, (ctx) => getAgent().prompt(ctx.params, ctx.signal)).onNotification(methods.agent.session.cancel, (ctx) => getAgent().cancel(ctx.params)).onRequest("authentication/status", emptyExtensionParamsParser, (ctx) => getAgent().extMethod("authentication/status", ctx.params)).onRequest("authentication/logout", emptyExtensionParamsParser, (ctx) => getAgent().extMethod("authentication/logout", ctx.params)).onRequest(LEGACY_SET_SESSION_MODEL_METHOD, legacySetSessionModelParamsParser, (ctx) => getAgent().extMethod(LEGACY_SET_SESSION_MODEL_METHOD, ctx.params)).connect(acpJsonStream);
|
|
29522
|
+
}).onRequest(methods.agent.initialize, (ctx) => getAgent().initialize(ctx.params)).onRequest(methods.agent.session.new, (ctx) => getAgent().newSession(ctx.params)).onRequest(methods.agent.session.load, (ctx) => getAgent().loadSession(ctx.params)).onRequest(methods.agent.session.list, (ctx) => getAgent().listSessions(ctx.params)).onRequest(methods.agent.session.delete, (ctx) => getAgent().deleteSession(ctx.params)).onRequest(methods.agent.session.resume, (ctx) => getAgent().resumeSession(ctx.params)).onRequest(methods.agent.session.close, (ctx) => getAgent().closeSession(ctx.params)).onRequest(methods.agent.session.setMode, (ctx) => getAgent().setSessionMode(ctx.params)).onRequest(methods.agent.session.setConfigOption, (ctx) => getAgent().setSessionConfigOption(ctx.params)).onRequest(methods.agent.authenticate, (ctx) => getAgent().authenticate(ctx.params)).onRequest(methods.agent.logout, (ctx) => getAgent().logout(ctx.params)).onRequest(methods.agent.providers.list, (ctx) => getAgent().listProviders(ctx.params)).onRequest(methods.agent.providers.set, (ctx) => getAgent().setProvider(ctx.params)).onRequest(methods.agent.providers.disable, (ctx) => getAgent().disableProvider(ctx.params)).onRequest(methods.agent.session.prompt, (ctx) => getAgent().prompt(ctx.params, ctx.signal)).onNotification(methods.agent.session.cancel, (ctx) => getAgent().cancel(ctx.params)).onRequest("authentication/status", emptyExtensionParamsParser, (ctx) => getAgent().extMethod("authentication/status", ctx.params)).onRequest("authentication/logout", emptyExtensionParamsParser, (ctx) => getAgent().extMethod("authentication/logout", ctx.params)).onRequest(LEGACY_SET_SESSION_MODEL_METHOD, legacySetSessionModelParamsParser, (ctx) => getAgent().extMethod(LEGACY_SET_SESSION_MODEL_METHOD, ctx.params)).connect(acpJsonStream);
|
|
28936
29523
|
}
|