@codexhost/cli-linux-x64 0.2.6 → 0.3.0-test.1
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 +4 -1
- package/THIRD_PARTY_NOTICES.txt +4 -0
- package/app/codexhost-distribution.json +1 -1
- package/app/desktop-controller.mjs +55 -20
- package/app/host-runtime.mjs +6762 -1624
- package/app/renderer-extension.js +440 -141
- package/bin/codexhost +0 -0
- package/libexec/codexhost-shim +0 -0
- package/libexec/codexhost-updater +0 -0
- package/licenses/ws-LICENSE.txt +20 -0
- package/package.json +1 -1
|
@@ -36,6 +36,7 @@
|
|
|
36
36
|
#ownershipRequestGenerations = /* @__PURE__ */ new WeakMap();
|
|
37
37
|
#states = /* @__PURE__ */ new WeakMap();
|
|
38
38
|
#switching = /* @__PURE__ */ new Set();
|
|
39
|
+
#pendingSubmissions = /* @__PURE__ */ new Set();
|
|
39
40
|
#composerSequence = 0;
|
|
40
41
|
#modelRequestSequence = 0;
|
|
41
42
|
#ownershipRequestSequence = 0;
|
|
@@ -95,6 +96,7 @@
|
|
|
95
96
|
rebindConversation(composer, target) {
|
|
96
97
|
if (!isConversationTarget(target)) return null;
|
|
97
98
|
const previous = this.#state(composer);
|
|
99
|
+
this.#pendingSubmissions.delete(previous);
|
|
98
100
|
this.#modelRequestGenerations.set(previous, ++this.#modelRequestSequence);
|
|
99
101
|
this.#ownershipRequestGenerations.set(previous, ++this.#ownershipRequestSequence);
|
|
100
102
|
let state = this.#conversationState(target);
|
|
@@ -114,6 +116,7 @@
|
|
|
114
116
|
restore(composer, agent, model, thinkingOptionId, permissionModeId) {
|
|
115
117
|
if (!this.#enabledAgents.has(agent)) return null;
|
|
116
118
|
const state = this.#state(composer);
|
|
119
|
+
this.#pendingSubmissions.delete(state);
|
|
117
120
|
state.agent = agent;
|
|
118
121
|
state.phase = "locked";
|
|
119
122
|
if (agent === "pi" && model) state.piModel = model;
|
|
@@ -204,9 +207,21 @@
|
|
|
204
207
|
}
|
|
205
208
|
lock(composer) {
|
|
206
209
|
const state = this.#state(composer);
|
|
210
|
+
this.#pendingSubmissions.delete(state);
|
|
207
211
|
state.phase = "locked";
|
|
208
212
|
return state;
|
|
209
213
|
}
|
|
214
|
+
markSubmissionPending(composer) {
|
|
215
|
+
const state = this.#state(composer);
|
|
216
|
+
if (state.phase === "draft") this.#pendingSubmissions.add(state);
|
|
217
|
+
return state;
|
|
218
|
+
}
|
|
219
|
+
isSubmissionPending(composer) {
|
|
220
|
+
return this.#pendingSubmissions.has(this.#state(composer));
|
|
221
|
+
}
|
|
222
|
+
clearPendingSubmission(composer) {
|
|
223
|
+
this.#pendingSubmissions.delete(this.#state(composer));
|
|
224
|
+
}
|
|
210
225
|
recordSubmission(composer) {
|
|
211
226
|
const state = this.#state(composer);
|
|
212
227
|
this.#lastSubmittedAgent = state.agent;
|
|
@@ -224,6 +239,9 @@
|
|
|
224
239
|
if (isConversationTarget(target) && !bound) {
|
|
225
240
|
this.#conversationStates.push({ target, state });
|
|
226
241
|
}
|
|
242
|
+
if (isConversationTarget(target) && this.#pendingSubmissions.delete(state)) {
|
|
243
|
+
state.phase = "locked";
|
|
244
|
+
}
|
|
227
245
|
return true;
|
|
228
246
|
}
|
|
229
247
|
async switchAgent(composer, nextAgent, operations) {
|
|
@@ -231,6 +249,7 @@
|
|
|
231
249
|
if (!this.#enabledAgents.has(nextAgent)) return false;
|
|
232
250
|
if (state.phase !== "draft" || this.#switching.has(state)) return false;
|
|
233
251
|
if (state.agent === nextAgent) return true;
|
|
252
|
+
this.#pendingSubmissions.delete(state);
|
|
234
253
|
this.#switching.add(state);
|
|
235
254
|
try {
|
|
236
255
|
if (!operations.applyAgent(nextAgent)) return false;
|
|
@@ -15783,21 +15802,88 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
15783
15802
|
return view;
|
|
15784
15803
|
}
|
|
15785
15804
|
|
|
15805
|
+
// src/renderer-model-picker-positioning.ts
|
|
15806
|
+
var MENU_GAP = 4;
|
|
15807
|
+
var MAIN_MENU_SIDE_OFFSET = 8;
|
|
15808
|
+
var COLLISION_PADDING = 8;
|
|
15809
|
+
var RENDERER_MODEL_PICKER_MAIN_MENU_WIDTH = 260;
|
|
15810
|
+
var RENDERER_MODEL_PICKER_MODEL_MENU_WIDTH = 280;
|
|
15811
|
+
var RENDERER_MODEL_PICKER_MODEL_MENU_MAX_HEIGHT = 360;
|
|
15812
|
+
function clampPosition(value, minimum, maximum) {
|
|
15813
|
+
return Math.min(Math.max(value, minimum), Math.max(minimum, maximum));
|
|
15814
|
+
}
|
|
15815
|
+
function fitWidth(preferredWidth, viewportWidth) {
|
|
15816
|
+
return Math.max(
|
|
15817
|
+
COLLISION_PADDING,
|
|
15818
|
+
Math.min(preferredWidth, viewportWidth - COLLISION_PADDING * 2)
|
|
15819
|
+
);
|
|
15820
|
+
}
|
|
15821
|
+
function fitHeight(viewport, top = COLLISION_PADDING) {
|
|
15822
|
+
return Math.max(
|
|
15823
|
+
COLLISION_PADDING,
|
|
15824
|
+
Math.min(
|
|
15825
|
+
RENDERER_MODEL_PICKER_MODEL_MENU_MAX_HEIGHT,
|
|
15826
|
+
viewport.height * 0.6,
|
|
15827
|
+
viewport.height - top - COLLISION_PADDING
|
|
15828
|
+
)
|
|
15829
|
+
);
|
|
15830
|
+
}
|
|
15831
|
+
function rendererModelPickerMainMenuPlacement(triggerRect, viewport, width = RENDERER_MODEL_PICKER_MAIN_MENU_WIDTH) {
|
|
15832
|
+
const maxLeft = viewport.width - COLLISION_PADDING - width;
|
|
15833
|
+
return {
|
|
15834
|
+
left: clampPosition(triggerRect.right - width, COLLISION_PADDING, maxLeft),
|
|
15835
|
+
width,
|
|
15836
|
+
bottom: Math.max(COLLISION_PADDING, viewport.height - triggerRect.top + MAIN_MENU_SIDE_OFFSET)
|
|
15837
|
+
};
|
|
15838
|
+
}
|
|
15839
|
+
function rendererModelPickerStandaloneModelMenuPlacement(triggerRect, viewport) {
|
|
15840
|
+
const width = fitWidth(RENDERER_MODEL_PICKER_MODEL_MENU_WIDTH, viewport.width);
|
|
15841
|
+
const maxLeft = viewport.width - COLLISION_PADDING - width;
|
|
15842
|
+
return {
|
|
15843
|
+
left: clampPosition(triggerRect.right - width, COLLISION_PADDING, maxLeft),
|
|
15844
|
+
width,
|
|
15845
|
+
maxHeight: fitHeight(viewport),
|
|
15846
|
+
bottom: Math.max(COLLISION_PADDING, viewport.height - triggerRect.top + MAIN_MENU_SIDE_OFFSET)
|
|
15847
|
+
};
|
|
15848
|
+
}
|
|
15849
|
+
function rendererModelPickerModelMenuPlacement(mainRect, viewport) {
|
|
15850
|
+
const preferredWidth = fitWidth(RENDERER_MODEL_PICKER_MODEL_MENU_WIDTH, viewport.width);
|
|
15851
|
+
const rightLeft = mainRect.right + MENU_GAP;
|
|
15852
|
+
const leftLeft = mainRect.left - MENU_GAP - preferredWidth;
|
|
15853
|
+
const rightAvailable = viewport.width - rightLeft - COLLISION_PADDING;
|
|
15854
|
+
const leftAvailable = mainRect.left - MENU_GAP - COLLISION_PADDING;
|
|
15855
|
+
let width;
|
|
15856
|
+
let left;
|
|
15857
|
+
if (rightAvailable >= preferredWidth) {
|
|
15858
|
+
width = preferredWidth;
|
|
15859
|
+
left = rightLeft;
|
|
15860
|
+
} else if (leftAvailable >= preferredWidth) {
|
|
15861
|
+
width = preferredWidth;
|
|
15862
|
+
left = leftLeft;
|
|
15863
|
+
} else if (rightAvailable >= leftAvailable) {
|
|
15864
|
+
width = Math.max(COLLISION_PADDING, rightAvailable);
|
|
15865
|
+
left = rightLeft;
|
|
15866
|
+
} else {
|
|
15867
|
+
width = Math.max(COLLISION_PADDING, leftAvailable);
|
|
15868
|
+
left = mainRect.left - MENU_GAP - width;
|
|
15869
|
+
}
|
|
15870
|
+
const top = clampPosition(mainRect.top, COLLISION_PADDING, viewport.height - COLLISION_PADDING);
|
|
15871
|
+
const maxHeight = fitHeight(viewport, top);
|
|
15872
|
+
return {
|
|
15873
|
+
left: clampPosition(left, COLLISION_PADDING, viewport.width - COLLISION_PADDING - width),
|
|
15874
|
+
top,
|
|
15875
|
+
width,
|
|
15876
|
+
maxHeight
|
|
15877
|
+
};
|
|
15878
|
+
}
|
|
15879
|
+
|
|
15786
15880
|
// src/renderer-model-picker.ts
|
|
15787
15881
|
var RENDERER_MODEL_TRIGGER_FALLBACK_CLASSES = "border-token-border no-drag cursor-interaction items-center gap-1 border whitespace-nowrap select-none focus:outline-none disabled:cursor-not-allowed disabled:opacity-40 flex rounded-full text-token-text-tertiary enabled:hover:bg-token-list-hover-background enabled:active:bg-token-foreground/15 data-[state=open]:bg-token-list-hover-background border-transparent h-token-button-composer px-2 py-0 text-sm leading-[18px] min-w-0";
|
|
15788
15882
|
var MENU_CLASSES = "fixed z-50 overflow-hidden rounded-xl bg-token-dropdown-background/90 text-token-foreground shadow-lg backdrop-blur-xl";
|
|
15789
15883
|
var SEARCH_INPUT_CLASSES = "mb-1 w-full shrink-0 rounded-lg border border-token-border bg-token-dropdown-background/95 px-2 py-1.5 text-sm text-token-foreground outline-none placeholder:text-token-text-tertiary disabled:cursor-not-allowed disabled:opacity-40";
|
|
15790
15884
|
var OPTION_CLASSES = "flex w-full cursor-interaction items-center gap-2 rounded-lg px-2 py-2 text-left text-sm text-token-foreground outline-none enabled:hover:bg-token-list-hover-background enabled:active:bg-token-foreground/15 disabled:cursor-not-allowed disabled:opacity-40";
|
|
15791
15885
|
var HEADING_CLASSES = "px-2 pb-1 pt-1.5 text-sm text-token-text-tertiary";
|
|
15792
|
-
var MAIN_MENU_MIN_WIDTH = 160;
|
|
15793
|
-
var MAIN_MENU_MAX_WIDTH = 180;
|
|
15794
|
-
var MODEL_MENU_PREFERRED_WIDTH = 360;
|
|
15795
|
-
var MODEL_MENU_MAX_WIDTH = 420;
|
|
15796
|
-
var MODEL_MENU_MAX_HEIGHT = 360;
|
|
15797
15886
|
var MODEL_TRIGGER_MAX_WIDTH = "min(200px, 26vw)";
|
|
15798
|
-
var MAIN_MENU_LEFT_OFFSET = 96;
|
|
15799
|
-
var MENU_GAP = 4;
|
|
15800
|
-
var VIEWPORT_MARGIN = 8;
|
|
15801
15887
|
var MODEL_SCROLLBAR_STYLE_ATTRIBUTE = "data-codexhost-model-picker-scrollbar";
|
|
15802
15888
|
function popoverOpen2(menu) {
|
|
15803
15889
|
return menu.matches(":popover-open");
|
|
@@ -15877,47 +15963,38 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
15877
15963
|
}
|
|
15878
15964
|
function positionMainMenu(control) {
|
|
15879
15965
|
const triggerRect = control.trigger.getBoundingClientRect();
|
|
15880
|
-
const
|
|
15881
|
-
|
|
15882
|
-
|
|
15883
|
-
|
|
15966
|
+
const placement = rendererModelPickerMainMenuPlacement(
|
|
15967
|
+
triggerRect,
|
|
15968
|
+
{ width: window.innerWidth, height: window.innerHeight },
|
|
15969
|
+
RENDERER_MODEL_PICKER_MAIN_MENU_WIDTH
|
|
15884
15970
|
);
|
|
15885
|
-
|
|
15886
|
-
|
|
15887
|
-
|
|
15888
|
-
const left = Math.max(
|
|
15889
|
-
VIEWPORT_MARGIN,
|
|
15890
|
-
Math.min(preferredLeft, Math.max(rightReservedLeft, VIEWPORT_MARGIN), maxLeft)
|
|
15891
|
-
);
|
|
15892
|
-
control.menu.style.setProperty("width", `${width}px`, "important");
|
|
15893
|
-
control.menu.style.left = `${left}px`;
|
|
15894
|
-
control.menu.style.maxWidth = `${width}px`;
|
|
15971
|
+
control.menu.style.setProperty("width", `${placement.width}px`, "important");
|
|
15972
|
+
control.menu.style.left = `${placement.left}px`;
|
|
15973
|
+
control.menu.style.maxWidth = `${placement.width}px`;
|
|
15895
15974
|
control.menu.style.right = "auto";
|
|
15896
15975
|
control.menu.style.top = "auto";
|
|
15897
|
-
control.menu.style.bottom = `${
|
|
15898
|
-
|
|
15899
|
-
|
|
15900
|
-
)
|
|
15901
|
-
|
|
15902
|
-
|
|
15903
|
-
|
|
15904
|
-
const
|
|
15905
|
-
const
|
|
15906
|
-
|
|
15907
|
-
|
|
15908
|
-
|
|
15909
|
-
|
|
15910
|
-
|
|
15911
|
-
|
|
15912
|
-
|
|
15913
|
-
|
|
15914
|
-
control.modelMenu.style.
|
|
15976
|
+
control.menu.style.bottom = `${placement.bottom}px`;
|
|
15977
|
+
}
|
|
15978
|
+
function positionAdvancedMenus(control) {
|
|
15979
|
+
positionMainMenu(control);
|
|
15980
|
+
positionModelMenu(control);
|
|
15981
|
+
}
|
|
15982
|
+
function positionModelMenu(control, standalone = false) {
|
|
15983
|
+
const anchorRect = standalone ? control.trigger.getBoundingClientRect() : control.menu.getBoundingClientRect();
|
|
15984
|
+
const placement = standalone ? rendererModelPickerStandaloneModelMenuPlacement(anchorRect, {
|
|
15985
|
+
width: window.innerWidth,
|
|
15986
|
+
height: window.innerHeight
|
|
15987
|
+
}) : rendererModelPickerModelMenuPlacement(anchorRect, {
|
|
15988
|
+
width: window.innerWidth,
|
|
15989
|
+
height: window.innerHeight
|
|
15990
|
+
});
|
|
15991
|
+
control.modelMenu.style.setProperty("width", `${placement.width}px`, "important");
|
|
15992
|
+
control.modelMenu.style.left = `${placement.left}px`;
|
|
15993
|
+
control.modelMenu.style.maxWidth = `${placement.width}px`;
|
|
15994
|
+
control.modelMenu.style.maxHeight = `${placement.maxHeight}px`;
|
|
15915
15995
|
control.modelMenu.style.right = "auto";
|
|
15916
|
-
control.modelMenu.style.top = "auto"
|
|
15917
|
-
control.modelMenu.style.bottom = `${
|
|
15918
|
-
VIEWPORT_MARGIN,
|
|
15919
|
-
window.innerHeight - mainRect.bottom
|
|
15920
|
-
)}px`;
|
|
15996
|
+
control.modelMenu.style.top = placement.top === void 0 ? "auto" : `${placement.top}px`;
|
|
15997
|
+
control.modelMenu.style.bottom = placement.bottom === void 0 ? "auto" : `${placement.bottom}px`;
|
|
15921
15998
|
}
|
|
15922
15999
|
function syncRendererModelTriggerClass(control, nativeClassName) {
|
|
15923
16000
|
control.trigger.className = nativeClassName?.trim() || RENDERER_MODEL_TRIGGER_FALLBACK_CLASSES;
|
|
@@ -16012,7 +16089,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16012
16089
|
modelMenu.style.margin = "0";
|
|
16013
16090
|
modelMenu.style.padding = "4px";
|
|
16014
16091
|
modelMenu.style.border = "0";
|
|
16015
|
-
modelMenu.style.maxHeight =
|
|
16092
|
+
modelMenu.style.maxHeight = `min(${RENDERER_MODEL_PICKER_MODEL_MENU_MAX_HEIGHT}px, 60vh)`;
|
|
16016
16093
|
modelMenu.style.overflowY = "auto";
|
|
16017
16094
|
modelButton.setAttribute("aria-controls", modelMenu.id);
|
|
16018
16095
|
const options = /* @__PURE__ */ new Map();
|
|
@@ -16073,33 +16150,41 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16073
16150
|
applyModelSearchFilter(control);
|
|
16074
16151
|
}
|
|
16075
16152
|
};
|
|
16153
|
+
const pickerOpen = () => popoverOpen2(menu) || popoverOpen2(modelMenu);
|
|
16076
16154
|
const close = () => {
|
|
16077
16155
|
closeModelMenu();
|
|
16078
16156
|
if (popoverOpen2(menu)) menu.hidePopover();
|
|
16079
16157
|
};
|
|
16080
|
-
const openModelMenu = () => {
|
|
16081
|
-
if (!popoverOpen2(menu) || popoverOpen2(modelMenu)) return;
|
|
16158
|
+
const openModelMenu = (standalone = false) => {
|
|
16159
|
+
if (!standalone && !popoverOpen2(menu) || popoverOpen2(modelMenu)) return;
|
|
16082
16160
|
modelMenu.showPopover();
|
|
16083
|
-
positionModelMenu(control);
|
|
16161
|
+
positionModelMenu(control, standalone);
|
|
16084
16162
|
modelButton.setAttribute("aria-expanded", "true");
|
|
16085
16163
|
};
|
|
16086
16164
|
const open = () => {
|
|
16087
|
-
if (trigger.disabled ||
|
|
16165
|
+
if (trigger.disabled || pickerOpen()) return;
|
|
16166
|
+
if (control.thinkingOptions.size === 0) {
|
|
16167
|
+
openModelMenu(true);
|
|
16168
|
+
return;
|
|
16169
|
+
}
|
|
16088
16170
|
menu.showPopover();
|
|
16089
|
-
|
|
16171
|
+
positionAdvancedMenus(control);
|
|
16090
16172
|
};
|
|
16091
16173
|
const onTriggerClick = () => {
|
|
16092
|
-
if (
|
|
16174
|
+
if (pickerOpen()) close();
|
|
16093
16175
|
else open();
|
|
16094
16176
|
};
|
|
16095
16177
|
const onToggle = () => {
|
|
16096
16178
|
const openState = popoverOpen2(menu);
|
|
16097
|
-
trigger.setAttribute("aria-expanded", String(openState));
|
|
16179
|
+
trigger.setAttribute("aria-expanded", String(openState || popoverOpen2(modelMenu)));
|
|
16098
16180
|
trigger.setAttribute("data-state", openState ? "open" : "closed");
|
|
16099
16181
|
if (!openState) closeModelMenu();
|
|
16100
16182
|
};
|
|
16101
16183
|
const onModelToggle = () => {
|
|
16102
|
-
|
|
16184
|
+
const openState = popoverOpen2(modelMenu);
|
|
16185
|
+
modelButton.setAttribute("aria-expanded", String(openState));
|
|
16186
|
+
trigger.setAttribute("aria-expanded", String(openState || popoverOpen2(menu)));
|
|
16187
|
+
trigger.setAttribute("data-state", openState || popoverOpen2(menu) ? "open" : "closed");
|
|
16103
16188
|
};
|
|
16104
16189
|
const onRootClick = (event) => {
|
|
16105
16190
|
const target = event.target instanceof Element ? event.target.closest("button") : null;
|
|
@@ -16138,21 +16223,21 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16138
16223
|
trigger.focus();
|
|
16139
16224
|
};
|
|
16140
16225
|
const onViewportChange = () => {
|
|
16141
|
-
if (popoverOpen2(menu))
|
|
16142
|
-
if (popoverOpen2(modelMenu)) positionModelMenu(control);
|
|
16226
|
+
if (popoverOpen2(menu)) positionAdvancedMenus(control);
|
|
16227
|
+
else if (popoverOpen2(modelMenu)) positionModelMenu(control, true);
|
|
16143
16228
|
};
|
|
16144
16229
|
trigger.addEventListener("click", onTriggerClick);
|
|
16145
16230
|
menu.addEventListener("toggle", onToggle);
|
|
16146
16231
|
modelMenu.addEventListener("toggle", onModelToggle);
|
|
16147
16232
|
modelButton.addEventListener("mouseenter", onModelHover);
|
|
16148
|
-
|
|
16233
|
+
menu.addEventListener("click", onRootClick);
|
|
16149
16234
|
modelMenu.addEventListener("click", onModelMenuClick);
|
|
16150
16235
|
document.addEventListener("pointerdown", onDocumentPointerDown, true);
|
|
16151
16236
|
document.addEventListener("keydown", onDocumentKeyDown, true);
|
|
16152
16237
|
window.addEventListener("resize", onViewportChange);
|
|
16153
16238
|
window.addEventListener("scroll", onViewportChange, true);
|
|
16154
|
-
root.append(trigger
|
|
16155
|
-
document.body.append(modelMenu);
|
|
16239
|
+
root.append(trigger);
|
|
16240
|
+
document.body.append(menu, modelMenu);
|
|
16156
16241
|
searchHeader.append(searchInput);
|
|
16157
16242
|
modelMenu.append(searchHeader, searchEmpty);
|
|
16158
16243
|
const control = {
|
|
@@ -16175,7 +16260,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16175
16260
|
menu.removeEventListener("toggle", onToggle);
|
|
16176
16261
|
modelMenu.removeEventListener("toggle", onModelToggle);
|
|
16177
16262
|
modelButton.removeEventListener("mouseenter", onModelHover);
|
|
16178
|
-
|
|
16263
|
+
menu.removeEventListener("click", onRootClick);
|
|
16179
16264
|
modelMenu.removeEventListener("click", onModelMenuClick);
|
|
16180
16265
|
searchInput.removeEventListener("input", onSearchInput);
|
|
16181
16266
|
for (const type of silencedEventTypes) {
|
|
@@ -16186,6 +16271,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
16186
16271
|
document.removeEventListener("keydown", onDocumentKeyDown, true);
|
|
16187
16272
|
window.removeEventListener("resize", onViewportChange);
|
|
16188
16273
|
window.removeEventListener("scroll", onViewportChange, true);
|
|
16274
|
+
menu.remove();
|
|
16189
16275
|
modelMenu.remove();
|
|
16190
16276
|
root.remove();
|
|
16191
16277
|
}
|
|
@@ -17138,7 +17224,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17138
17224
|
var CONTROL_ATTRIBUTE2 = "data-codexhost-harness-command-control";
|
|
17139
17225
|
var MENU_ATTRIBUTE = "data-codexhost-harness-command-menu";
|
|
17140
17226
|
var MENU_WIDTH = 320;
|
|
17141
|
-
var
|
|
17227
|
+
var VIEWPORT_MARGIN = 8;
|
|
17142
17228
|
var MENU_GAP2 = 8;
|
|
17143
17229
|
var SVG_NS = "http://www.w3.org/2000/svg";
|
|
17144
17230
|
var COMMAND_ICON_PATHS = [
|
|
@@ -17254,7 +17340,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17254
17340
|
menu.style.inset = "auto";
|
|
17255
17341
|
menu.style.zIndex = "2147483647";
|
|
17256
17342
|
menu.style.width = `${MENU_WIDTH}px`;
|
|
17257
|
-
menu.style.maxWidth = `calc(100vw - ${
|
|
17343
|
+
menu.style.maxWidth = `calc(100vw - ${VIEWPORT_MARGIN * 2}px)`;
|
|
17258
17344
|
menu.style.maxHeight = "min(360px, calc(100vh - 16px))";
|
|
17259
17345
|
menu.style.overflowY = "auto";
|
|
17260
17346
|
menu.style.padding = "4px";
|
|
@@ -17275,14 +17361,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17275
17361
|
const positionMenu2 = () => {
|
|
17276
17362
|
const rect = trigger.getBoundingClientRect();
|
|
17277
17363
|
const menuHeight = menu.getBoundingClientRect().height;
|
|
17278
|
-
const opensAbove = rect.top >= menuHeight + MENU_GAP2 +
|
|
17364
|
+
const opensAbove = rect.top >= menuHeight + MENU_GAP2 + VIEWPORT_MARGIN;
|
|
17279
17365
|
const left = clamp(
|
|
17280
17366
|
rect.left,
|
|
17281
|
-
|
|
17282
|
-
window.innerWidth - MENU_WIDTH -
|
|
17367
|
+
VIEWPORT_MARGIN,
|
|
17368
|
+
window.innerWidth - MENU_WIDTH - VIEWPORT_MARGIN
|
|
17283
17369
|
);
|
|
17284
17370
|
menu.style.left = `${left}px`;
|
|
17285
|
-
menu.style.top = opensAbove ? `${Math.max(
|
|
17371
|
+
menu.style.top = opensAbove ? `${Math.max(VIEWPORT_MARGIN, rect.top - menuHeight - MENU_GAP2)}px` : `${Math.min(window.innerHeight - menuHeight - VIEWPORT_MARGIN, rect.bottom + MENU_GAP2)}px`;
|
|
17286
17372
|
};
|
|
17287
17373
|
const focusActive = () => {
|
|
17288
17374
|
const item = items[activeIndex];
|
|
@@ -17457,23 +17543,86 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17457
17543
|
if (target instanceof Element) return target;
|
|
17458
17544
|
return target instanceof Node ? target.parentElement : null;
|
|
17459
17545
|
}
|
|
17546
|
+
function controlDescription(element) {
|
|
17547
|
+
const typed = element;
|
|
17548
|
+
const read = (name) => typeof element.getAttribute === "function" ? element.getAttribute(name) : null;
|
|
17549
|
+
return [typed.type, read("aria-label"), read("title"), read("data-testid")].filter((value) => typeof value === "string").join(" ").toLowerCase();
|
|
17550
|
+
}
|
|
17460
17551
|
function buttonText(button) {
|
|
17461
|
-
return
|
|
17462
|
-
|
|
17463
|
-
|
|
17464
|
-
|
|
17465
|
-
button.getAttribute("data-testid")
|
|
17466
|
-
].filter((value) => typeof value === "string").join(" ").toLowerCase();
|
|
17552
|
+
return controlDescription(button);
|
|
17553
|
+
}
|
|
17554
|
+
function isOwnedRendererControl(element) {
|
|
17555
|
+
return element.hasAttribute(CONTROL_ATTRIBUTE) || element.hasAttribute("data-codexhost-model-control") || element.hasAttribute("data-codexhost-permission-mode-control") || element.hasAttribute("data-codexhost-usage-control") || element.hasAttribute("data-codexhost-credits-control") || element.hasAttribute("data-codexhost-harness-command-control");
|
|
17467
17556
|
}
|
|
17468
17557
|
function isComposerSubmitButton(button) {
|
|
17469
17558
|
if (button.type === "submit") return true;
|
|
17470
17559
|
return /(^|\s)(send|submit|发送|提交)(\s|$)/u.test(buttonText(button));
|
|
17471
17560
|
}
|
|
17561
|
+
var VOICE_CONTROL_PATTERN = /(dictat|microphone|speech(?:[-_\s]?to[-_\s]?text)?|voice[-_\s]?input|(^|\s)voice(\s|$)|composer[-_](?:speech|dictat|mic)|语音|听写|麦克风|pause|暂停|stop recording|stop dictation|停止录音|停止听写|(^|\s)stop(\s|$))/iu;
|
|
17562
|
+
var CANCEL_CONTROL_PATTERN = /(cancel|discard|close|dismiss|取消|关闭|丢弃)/iu;
|
|
17563
|
+
var ATTACH_CONTROL_PATTERN = /(add files|attach files|attach file|attachment|composer[-_]attach|添加文件|附件)/iu;
|
|
17564
|
+
var TRAILING_ACTION_WALK_DEPTH = 3;
|
|
17565
|
+
function isComposerCancelButton(element) {
|
|
17566
|
+
if (isOwnedRendererControl(element)) return false;
|
|
17567
|
+
return CANCEL_CONTROL_PATTERN.test(controlDescription(element));
|
|
17568
|
+
}
|
|
17569
|
+
function isComposerVoiceButton(element) {
|
|
17570
|
+
if (isOwnedRendererControl(element) || isComposerCancelButton(element)) return false;
|
|
17571
|
+
const description = controlDescription(element);
|
|
17572
|
+
if (/(^|\s)(send|submit|发送|提交)(\s|$)/u.test(description)) return false;
|
|
17573
|
+
return VOICE_CONTROL_PATTERN.test(description);
|
|
17574
|
+
}
|
|
17575
|
+
function isComposerAttachButton(element) {
|
|
17576
|
+
if (isOwnedRendererControl(element)) return false;
|
|
17577
|
+
return ATTACH_CONTROL_PATTERN.test(controlDescription(element));
|
|
17578
|
+
}
|
|
17579
|
+
function isComposerTrailingActionButton(element) {
|
|
17580
|
+
return isComposerVoiceButton(element) || isComposerSubmitButton(element);
|
|
17581
|
+
}
|
|
17582
|
+
function isTrailingActionNode(element) {
|
|
17583
|
+
if (isComposerCancelButton(element)) return false;
|
|
17584
|
+
if (isComposerTrailingActionButton(element)) return true;
|
|
17585
|
+
if (typeof element.querySelectorAll !== "function") return false;
|
|
17586
|
+
const buttons = [...element.querySelectorAll("button")];
|
|
17587
|
+
return buttons.length > 0 && buttons.every((button) => isComposerTrailingActionButton(button));
|
|
17588
|
+
}
|
|
17589
|
+
function attachControlWithin(root) {
|
|
17590
|
+
if (isComposerAttachButton(root)) return root;
|
|
17591
|
+
if (typeof root.querySelectorAll !== "function") return null;
|
|
17592
|
+
const matches = [
|
|
17593
|
+
...root.querySelectorAll("button, [aria-label], [title], [data-testid]")
|
|
17594
|
+
].filter(isComposerAttachButton);
|
|
17595
|
+
return matches.length === 1 ? matches[0] ?? null : null;
|
|
17596
|
+
}
|
|
17472
17597
|
function sendButtonWithin(root) {
|
|
17473
17598
|
return [...root.querySelectorAll("button")].find(
|
|
17474
17599
|
(button) => isComposerSubmitButton(button)
|
|
17475
17600
|
) ?? null;
|
|
17476
17601
|
}
|
|
17602
|
+
function leftmostTrailingSibling(container, before) {
|
|
17603
|
+
for (const child of container.children) {
|
|
17604
|
+
if (child === before) break;
|
|
17605
|
+
if (typeof child.hasAttribute !== "function") continue;
|
|
17606
|
+
const element = child;
|
|
17607
|
+
if (isOwnedRendererControl(element) || isComposerCancelButton(element)) continue;
|
|
17608
|
+
if (isTrailingActionNode(element)) return element;
|
|
17609
|
+
}
|
|
17610
|
+
return null;
|
|
17611
|
+
}
|
|
17612
|
+
function trailingActionAnchor(sendButton) {
|
|
17613
|
+
let container = sendButton.parentElement;
|
|
17614
|
+
let before = sendButton;
|
|
17615
|
+
for (let depth = 0; container && depth < TRAILING_ACTION_WALK_DEPTH; depth += 1) {
|
|
17616
|
+
if (typeof container.matches === "function" && container.matches(CODEX_COMPOSER_SELECTOR)) {
|
|
17617
|
+
break;
|
|
17618
|
+
}
|
|
17619
|
+
const candidate = leftmostTrailingSibling(container, before);
|
|
17620
|
+
if (candidate) return candidate;
|
|
17621
|
+
before = container;
|
|
17622
|
+
container = container.parentElement;
|
|
17623
|
+
}
|
|
17624
|
+
return sendButton;
|
|
17625
|
+
}
|
|
17477
17626
|
function editorForElement(element) {
|
|
17478
17627
|
return element.matches(EDITOR_SELECTOR) ? element : element.closest(EDITOR_SELECTOR);
|
|
17479
17628
|
}
|
|
@@ -17619,7 +17768,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17619
17768
|
for (const child of parent.children) {
|
|
17620
17769
|
if (typeof child.hasAttribute !== "function") continue;
|
|
17621
17770
|
const element = child;
|
|
17622
|
-
if (element.hasAttribute("data-codexhost-credits-control") || element.hasAttribute("data-codexhost-harness-command-control")) {
|
|
17771
|
+
if (element.hasAttribute("data-codexhost-credits-control") || element.hasAttribute("data-codexhost-harness-command-control") || isTrailingActionNode(element)) {
|
|
17623
17772
|
continue;
|
|
17624
17773
|
}
|
|
17625
17774
|
return element;
|
|
@@ -17632,12 +17781,28 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17632
17781
|
const parent = current.parentElement;
|
|
17633
17782
|
if (!parent) break;
|
|
17634
17783
|
const first = firstMaterialChild(parent);
|
|
17635
|
-
if (first && first !== current && !first.contains(usageRoot))
|
|
17784
|
+
if (first && first !== current && !first.contains(usageRoot)) {
|
|
17785
|
+
return attachControlWithin(first) ?? first;
|
|
17786
|
+
}
|
|
17636
17787
|
if (parent === composer) break;
|
|
17637
17788
|
current = parent;
|
|
17638
17789
|
}
|
|
17639
17790
|
return null;
|
|
17640
17791
|
}
|
|
17792
|
+
function refreshTrailingClusterPlacement(control) {
|
|
17793
|
+
const sendButton = control.sendButton;
|
|
17794
|
+
const modelRoot = control.modelPicker?.root;
|
|
17795
|
+
const agentRoot = control.root ?? control.picker?.root;
|
|
17796
|
+
if (!sendButton || !modelRoot || !agentRoot) return;
|
|
17797
|
+
const anchor = trailingActionAnchor(sendButton);
|
|
17798
|
+
const parent = anchor.parentElement;
|
|
17799
|
+
if (!parent || typeof parent.insertBefore !== "function") return;
|
|
17800
|
+
if (modelRoot.parentElement === parent && agentRoot.parentElement === parent && modelRoot.nextElementSibling === agentRoot && agentRoot.nextElementSibling === anchor) {
|
|
17801
|
+
return;
|
|
17802
|
+
}
|
|
17803
|
+
parent.insertBefore(modelRoot, anchor);
|
|
17804
|
+
parent.insertBefore(agentRoot, anchor);
|
|
17805
|
+
}
|
|
17641
17806
|
function refreshUsagePlacement(control) {
|
|
17642
17807
|
const anchor = usagePlacementAnchor(control);
|
|
17643
17808
|
if (!anchor) {
|
|
@@ -17690,6 +17855,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17690
17855
|
}
|
|
17691
17856
|
function reconcileComposerNativeControls(control, hideModel, hidePermissionMode) {
|
|
17692
17857
|
refreshNativeModelControl(control);
|
|
17858
|
+
refreshTrailingClusterPlacement(control);
|
|
17693
17859
|
refreshUsagePlacement(control);
|
|
17694
17860
|
refreshNativePermissionModeControl(control);
|
|
17695
17861
|
setNativeControlHidden(control.nativeModelControl, hideModel);
|
|
@@ -17717,7 +17883,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17717
17883
|
const toolbar = sendButton.parentElement;
|
|
17718
17884
|
const harnessCommands = mountRendererHarnessCommandControl(
|
|
17719
17885
|
toolbar ?? composer,
|
|
17720
|
-
sendButton,
|
|
17886
|
+
trailingActionAnchor(sendButton),
|
|
17721
17887
|
onSelectCommand
|
|
17722
17888
|
);
|
|
17723
17889
|
const permissionParent = nativePermissionModeControl?.element.parentElement;
|
|
@@ -17726,12 +17892,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17726
17892
|
} else {
|
|
17727
17893
|
composer.append(permissionModePicker.root);
|
|
17728
17894
|
}
|
|
17729
|
-
if (toolbar)
|
|
17730
|
-
toolbar.insertBefore(modelPicker.root, sendButton);
|
|
17731
|
-
toolbar.insertBefore(picker.root, sendButton);
|
|
17732
|
-
} else {
|
|
17733
|
-
composer.append(modelPicker.root, picker.root);
|
|
17734
|
-
}
|
|
17895
|
+
if (!toolbar) composer.append(modelPicker.root, picker.root);
|
|
17735
17896
|
const control = {
|
|
17736
17897
|
composer,
|
|
17737
17898
|
root: picker.root,
|
|
@@ -17747,6 +17908,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
17747
17908
|
sendButton,
|
|
17748
17909
|
sendDisabledBeforeSwitch: null
|
|
17749
17910
|
};
|
|
17911
|
+
refreshTrailingClusterPlacement(control);
|
|
17750
17912
|
refreshUsagePlacement(control);
|
|
17751
17913
|
return control;
|
|
17752
17914
|
}
|
|
@@ -18467,28 +18629,38 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18467
18629
|
}
|
|
18468
18630
|
return `${CLAUDE_CODE_TRANSPORT_MODEL_PREFIX}${parsedModel.id}${parsedPermissionMode ? `@${parsedPermissionMode}` : ""}`;
|
|
18469
18631
|
}
|
|
18470
|
-
function grokTransportModelId(model, thinkingOptionId) {
|
|
18632
|
+
function grokTransportModelId(model, permissionModeId, thinkingOptionId) {
|
|
18471
18633
|
if (!model) {
|
|
18472
|
-
if (thinkingOptionId)
|
|
18634
|
+
if (permissionModeId || thinkingOptionId) {
|
|
18635
|
+
throw new Error("Grok transport configuration requires a Model Ref");
|
|
18636
|
+
}
|
|
18473
18637
|
return GROK_TRANSPORT_MODEL_ID;
|
|
18474
18638
|
}
|
|
18475
18639
|
const parsedModel = harnessModelRefSchema.parse(model);
|
|
18640
|
+
const parsedPermissionMode = permissionModeId ? harnessPermissionModeIdSchema.parse(permissionModeId) : void 0;
|
|
18476
18641
|
const parsedThinking = thinkingOptionId ? harnessThinkingOptionIdSchema.parse(thinkingOptionId) : void 0;
|
|
18477
|
-
|
|
18642
|
+
if (parsedThinking) {
|
|
18643
|
+
return `${GROK_TRANSPORT_MODEL_PREFIX}${parsedModel.id}@${parsedPermissionMode ?? ""}@${parsedThinking}`;
|
|
18644
|
+
}
|
|
18645
|
+
return `${GROK_TRANSPORT_MODEL_PREFIX}${parsedModel.id}${parsedPermissionMode ? `@${parsedPermissionMode}` : ""}`;
|
|
18478
18646
|
}
|
|
18479
18647
|
function decodeGrokTransportModelId(value) {
|
|
18480
18648
|
if (value === GROK_TRANSPORT_MODEL_ID) return {};
|
|
18481
18649
|
if (typeof value !== "string" || !value.startsWith(GROK_TRANSPORT_MODEL_PREFIX)) return null;
|
|
18482
18650
|
const components = value.slice(GROK_TRANSPORT_MODEL_PREFIX.length).split("@");
|
|
18483
|
-
if (components.length
|
|
18484
|
-
const [modelId,
|
|
18485
|
-
if (components.length ===
|
|
18651
|
+
if (components.length < 1 || components.length > 3) return null;
|
|
18652
|
+
const [modelId, permissionModeId, thinkingOptionId] = components;
|
|
18653
|
+
if (components.length === 2 && !permissionModeId) return null;
|
|
18654
|
+
if (components.length === 3 && !thinkingOptionId) return null;
|
|
18486
18655
|
const model = harnessModelRefSchema.safeParse({ id: modelId });
|
|
18487
18656
|
if (!model.success) return null;
|
|
18657
|
+
const permissionMode = permissionModeId ? harnessPermissionModeIdSchema.safeParse(permissionModeId) : null;
|
|
18658
|
+
if (permissionMode && !permissionMode.success) return null;
|
|
18488
18659
|
const thinking = thinkingOptionId ? harnessThinkingOptionIdSchema.safeParse(thinkingOptionId) : null;
|
|
18489
18660
|
if (thinking && !thinking.success) return null;
|
|
18490
18661
|
return {
|
|
18491
18662
|
model: model.data,
|
|
18663
|
+
...permissionMode?.success ? { permissionModeId: permissionMode.data } : {},
|
|
18492
18664
|
...thinking?.success ? { thinkingOptionId: thinking.data } : {}
|
|
18493
18665
|
};
|
|
18494
18666
|
}
|
|
@@ -18560,7 +18732,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18560
18732
|
}
|
|
18561
18733
|
function matchesCurrentPrewarmSignature(target) {
|
|
18562
18734
|
const bridge = target.requestClient ?? target;
|
|
18563
|
-
const stableApiShape = bridge.hostId === "
|
|
18735
|
+
const stableApiShape = typeof bridge.hostId === "string" && bridge.hostId.length > 0 && typeof bridge.sendRequest === "function" && typeof bridge.prewarmThreadStart === "function" && typeof bridge.enqueueRequest === "function";
|
|
18564
18736
|
if (stableApiShape) return true;
|
|
18565
18737
|
const prewarm = target.prewarmThreadStart ?? target.requestClient?.prewarmThreadStart;
|
|
18566
18738
|
if (!prewarm) return false;
|
|
@@ -18651,10 +18823,17 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18651
18823
|
return false;
|
|
18652
18824
|
}
|
|
18653
18825
|
}
|
|
18654
|
-
function
|
|
18655
|
-
const
|
|
18656
|
-
|
|
18657
|
-
if (
|
|
18826
|
+
function findComposerDomIdentity(composer) {
|
|
18827
|
+
const children = Array.from(composer.children ?? []);
|
|
18828
|
+
const portals = children.filter((child) => child.hasAttribute("data-above-composer-portal"));
|
|
18829
|
+
if (portals.length === 0) return { kind: "unsupported" };
|
|
18830
|
+
if (portals.length !== 1) return { kind: "ambiguous" };
|
|
18831
|
+
const value = portals[0]?.getAttribute("data-above-composer-conversation-id");
|
|
18832
|
+
if (value === null) return { kind: "draft" };
|
|
18833
|
+
const candidate = hostThreadIdSchema.safeParse(value);
|
|
18834
|
+
return candidate.success ? { kind: "conversation", threadId: candidate.data } : { kind: "ambiguous" };
|
|
18835
|
+
}
|
|
18836
|
+
function findComposerDraftIds(composer) {
|
|
18658
18837
|
const draftIds = /* @__PURE__ */ new Set();
|
|
18659
18838
|
let fiber = findComposerFiber(composer);
|
|
18660
18839
|
for (let depth = 0; fiber && depth < 120; depth += 1) {
|
|
@@ -18669,6 +18848,21 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18669
18848
|
const parent = fiber.return;
|
|
18670
18849
|
fiber = (typeof parent === "object" || typeof parent === "function") && parent !== null ? parent : null;
|
|
18671
18850
|
}
|
|
18851
|
+
return draftIds;
|
|
18852
|
+
}
|
|
18853
|
+
function findComposerModelTarget(composer) {
|
|
18854
|
+
const draftIds = findComposerDraftIds(composer);
|
|
18855
|
+
const domIdentity = findComposerDomIdentity(composer);
|
|
18856
|
+
if (domIdentity.kind === "ambiguous") return null;
|
|
18857
|
+
if (domIdentity.kind === "conversation") {
|
|
18858
|
+
return ["conversation", domIdentity.threadId];
|
|
18859
|
+
}
|
|
18860
|
+
if (domIdentity.kind === "draft") {
|
|
18861
|
+
return draftIds.size === 1 ? ["default", draftIds.values().next().value] : null;
|
|
18862
|
+
}
|
|
18863
|
+
const conversationThreadId = findComposerConversationThreadId(composer);
|
|
18864
|
+
if (conversationThreadId === null) return null;
|
|
18865
|
+
if (conversationThreadId !== void 0) return ["conversation", conversationThreadId];
|
|
18672
18866
|
if (draftIds.size !== 1) return null;
|
|
18673
18867
|
return ["default", draftIds.values().next().value];
|
|
18674
18868
|
}
|
|
@@ -18676,7 +18870,34 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18676
18870
|
return isRecord5(value) && value.state === "ready";
|
|
18677
18871
|
}
|
|
18678
18872
|
function isDraftPrewarmPolicyReady(value) {
|
|
18679
|
-
return isRecord5(value) && value.state === "ready" && typeof value.select === "function" && typeof value.clear === "function";
|
|
18873
|
+
return isRecord5(value) && value.state === "ready" && typeof value.hostId === "string" && value.hostId.length > 0 && typeof value.select === "function" && typeof value.clear === "function";
|
|
18874
|
+
}
|
|
18875
|
+
function activeRendererDraftPrewarmTargets(policy, targets) {
|
|
18876
|
+
if (!isDraftPrewarmPolicyReady(policy)) return null;
|
|
18877
|
+
const activeTargets = targets.filter((target) => {
|
|
18878
|
+
const bridge = target.requestClient ?? target;
|
|
18879
|
+
return (target.getHostId?.() ?? bridge.hostId) === policy.hostId;
|
|
18880
|
+
});
|
|
18881
|
+
return activeTargets.length === 1 ? activeTargets : null;
|
|
18882
|
+
}
|
|
18883
|
+
function resolveRendererRequestRoute(policy, discoveredTargets, previous) {
|
|
18884
|
+
const activeTargets = activeRendererDraftPrewarmTargets(policy, discoveredTargets);
|
|
18885
|
+
if (isDraftPrewarmPolicyReady(policy) && activeTargets) {
|
|
18886
|
+
return { policy, targets: activeTargets };
|
|
18887
|
+
}
|
|
18888
|
+
return discoveredTargets.length === 0 && isDraftPrewarmPolicyReady(policy) && previous?.policy === policy ? previous : null;
|
|
18889
|
+
}
|
|
18890
|
+
function createRendererRequestRouteResolver(readPolicy, discoverTargets) {
|
|
18891
|
+
let route = null;
|
|
18892
|
+
return {
|
|
18893
|
+
resolve() {
|
|
18894
|
+
route = resolveRendererRequestRoute(readPolicy(), discoverTargets(), route);
|
|
18895
|
+
return route;
|
|
18896
|
+
},
|
|
18897
|
+
clear() {
|
|
18898
|
+
route = null;
|
|
18899
|
+
}
|
|
18900
|
+
};
|
|
18680
18901
|
}
|
|
18681
18902
|
async function waitForRendererDraftPrewarmPolicy(target) {
|
|
18682
18903
|
const deadline = Date.now() + DRAFT_PREWARM_POLICY_WAIT_TIMEOUT_MS;
|
|
@@ -18691,7 +18912,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18691
18912
|
}
|
|
18692
18913
|
}
|
|
18693
18914
|
function modelSelectionForAgent(officialSelection, reasoningEffort, agent, model, thinkingOptionId, permissionModeId) {
|
|
18694
|
-
const transportModelId = agent === "pi" ? piTransportModelId(model, thinkingOptionId) : agent === "claude-code" ? claudeTransportModelId(model, permissionModeId, thinkingOptionId) : agent === "deepseek-harness" ? deepSeekHarnessTransportModelId(model) : agent === "grok" ? grokTransportModelId(model, thinkingOptionId) : transportModelIdForAgent(agent);
|
|
18915
|
+
const transportModelId = agent === "pi" ? piTransportModelId(model, thinkingOptionId) : agent === "claude-code" ? claudeTransportModelId(model, permissionModeId, thinkingOptionId) : agent === "deepseek-harness" ? deepSeekHarnessTransportModelId(model) : agent === "grok" ? grokTransportModelId(model, permissionModeId, thinkingOptionId) : transportModelIdForAgent(agent);
|
|
18695
18916
|
return transportModelId ? { model: transportModelId, reasoningEffort } : officialSelection;
|
|
18696
18917
|
}
|
|
18697
18918
|
function installCurrentRendererAdapter() {
|
|
@@ -18717,8 +18938,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18717
18938
|
}
|
|
18718
18939
|
});
|
|
18719
18940
|
const usageSubscription = createThreadUsageSubscriptionRelay();
|
|
18941
|
+
const requestRouteResolver = createRendererRequestRouteResolver(
|
|
18942
|
+
() => window.__codexhostDraftPrewarmPolicyV1,
|
|
18943
|
+
() => findActivePrewarmTargets(document)
|
|
18944
|
+
);
|
|
18945
|
+
const currentRequestRoute = () => requestRouteResolver.resolve();
|
|
18720
18946
|
const currentModelClient = () => {
|
|
18721
|
-
const client = createRendererModelClient(
|
|
18947
|
+
const client = createRendererModelClient(currentRequestRoute()?.targets ?? []);
|
|
18722
18948
|
if (!client) throw new Error("Renderer Model request manager is unavailable");
|
|
18723
18949
|
usageSubscription.connect(client);
|
|
18724
18950
|
return client;
|
|
@@ -18754,10 +18980,12 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18754
18980
|
});
|
|
18755
18981
|
let routingPolicy = null;
|
|
18756
18982
|
let policyTimer = null;
|
|
18983
|
+
let desiredCarrier = null;
|
|
18757
18984
|
const captureRoutingPolicy = () => {
|
|
18758
|
-
const
|
|
18759
|
-
if (!
|
|
18760
|
-
routingPolicy =
|
|
18985
|
+
const route = currentRequestRoute();
|
|
18986
|
+
if (!route) return false;
|
|
18987
|
+
routingPolicy = route.policy;
|
|
18988
|
+
routingPolicy.select(desiredCarrier);
|
|
18761
18989
|
if (policyTimer !== null) {
|
|
18762
18990
|
window.clearInterval(policyTimer);
|
|
18763
18991
|
policyTimer = null;
|
|
@@ -18769,8 +18997,12 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18769
18997
|
updateStatus("installing", "draft-routing-policy-unavailable", null);
|
|
18770
18998
|
policyTimer = window.setInterval(captureRoutingPolicy, DRAFT_PREWARM_POLICY_POLL_INTERVAL_MS);
|
|
18771
18999
|
}
|
|
19000
|
+
const handleRoutingPolicyChange = () => {
|
|
19001
|
+
captureRoutingPolicy();
|
|
19002
|
+
};
|
|
19003
|
+
window.addEventListener("codexhost:draft-prewarm-policy-changed", handleRoutingPolicyChange);
|
|
18772
19004
|
const applyAgent = (agent, model, thinkingOptionId, permissionModeId) => {
|
|
18773
|
-
if (disposed
|
|
19005
|
+
if (disposed) return false;
|
|
18774
19006
|
const selection = modelSelectionForAgent(
|
|
18775
19007
|
null,
|
|
18776
19008
|
null,
|
|
@@ -18781,7 +19013,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18781
19013
|
);
|
|
18782
19014
|
const carrier = selection?.model;
|
|
18783
19015
|
if (carrier !== null && carrier !== void 0 && typeof carrier !== "string") return false;
|
|
18784
|
-
|
|
19016
|
+
desiredCarrier = carrier ?? null;
|
|
19017
|
+
const route = currentRequestRoute();
|
|
19018
|
+
if (!route) return false;
|
|
19019
|
+
routingPolicy = route.policy;
|
|
19020
|
+
if (route.policy.select(desiredCarrier)) {
|
|
18785
19021
|
modelUpdates += 1;
|
|
18786
19022
|
liveStatus.modelUpdates = modelUpdates;
|
|
18787
19023
|
}
|
|
@@ -18795,8 +19031,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18795
19031
|
if (disposed) return;
|
|
18796
19032
|
disposed = true;
|
|
18797
19033
|
if (policyTimer !== null) window.clearInterval(policyTimer);
|
|
19034
|
+
window.removeEventListener(
|
|
19035
|
+
"codexhost:draft-prewarm-policy-changed",
|
|
19036
|
+
handleRoutingPolicyChange
|
|
19037
|
+
);
|
|
18798
19038
|
routingPolicy?.select(null);
|
|
18799
19039
|
routingPolicy = null;
|
|
19040
|
+
requestRouteResolver.clear();
|
|
18800
19041
|
forkControl.dispose();
|
|
18801
19042
|
usageSubscription.dispose();
|
|
18802
19043
|
}
|
|
@@ -18848,9 +19089,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18848
19089
|
const model = harnessModelRefSchema.safeParse(value.model);
|
|
18849
19090
|
if (!model.success) return void 0;
|
|
18850
19091
|
const thinkingOptionId = harnessThinkingOptionIdSchema.safeParse(value.thinkingOptionId);
|
|
19092
|
+
const permissionModeId = harnessPermissionModeIdSchema.safeParse(value.permissionModeId);
|
|
18851
19093
|
return {
|
|
18852
19094
|
model: model.data,
|
|
18853
|
-
...thinkingOptionId.success ? { thinkingOptionId: thinkingOptionId.data } : {}
|
|
19095
|
+
...thinkingOptionId.success ? { thinkingOptionId: thinkingOptionId.data } : {},
|
|
19096
|
+
...permissionModeId.success ? { permissionModeId: permissionModeId.data } : {}
|
|
18854
19097
|
};
|
|
18855
19098
|
}
|
|
18856
19099
|
function readPreference(storage) {
|
|
@@ -18890,15 +19133,17 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18890
19133
|
const agent = readPreference(storage)?.lastAgent;
|
|
18891
19134
|
return agent && enabledAgents.has(agent) ? agent : void 0;
|
|
18892
19135
|
}
|
|
18893
|
-
function readNewThreadExternalConfigurationPreference(agent, catalog, storage = rendererStorage2()) {
|
|
19136
|
+
function readNewThreadExternalConfigurationPreference(agent, catalog, permissionModes, storage = rendererStorage2()) {
|
|
18894
19137
|
const preference = readPreference(storage)?.externalByAgent[agent];
|
|
18895
19138
|
if (!preference) return void 0;
|
|
18896
19139
|
const catalogModel = catalog.models.find(({ ref }) => ref.id === preference.model.id);
|
|
18897
19140
|
if (!catalogModel) return void 0;
|
|
18898
19141
|
const thinkingOptionId = preference.thinkingOptionId && catalogModel.supportedThinkingOptionIds?.includes(preference.thinkingOptionId) ? preference.thinkingOptionId : void 0;
|
|
19142
|
+
const permissionModeId = preference.permissionModeId && permissionModes?.modes.some(({ id }) => id === preference.permissionModeId) ? preference.permissionModeId : void 0;
|
|
18899
19143
|
return {
|
|
18900
19144
|
model: catalogModel.ref,
|
|
18901
|
-
...thinkingOptionId ? { thinkingOptionId } : {}
|
|
19145
|
+
...thinkingOptionId ? { thinkingOptionId } : {},
|
|
19146
|
+
...permissionModeId ? { permissionModeId } : {}
|
|
18902
19147
|
};
|
|
18903
19148
|
}
|
|
18904
19149
|
function writeNewThreadAgentPreference(agent, storage = rendererStorage2()) {
|
|
@@ -18912,7 +19157,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18912
19157
|
storage
|
|
18913
19158
|
);
|
|
18914
19159
|
}
|
|
18915
|
-
function writeNewThreadExternalConfigurationPreference(agent, model, thinkingOptionId, storage = rendererStorage2()) {
|
|
19160
|
+
function writeNewThreadExternalConfigurationPreference(agent, model, thinkingOptionId, permissionModeId, storage = rendererStorage2()) {
|
|
18916
19161
|
const current = readPreference(storage);
|
|
18917
19162
|
writePreference(
|
|
18918
19163
|
{
|
|
@@ -18922,7 +19167,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
18922
19167
|
...current?.externalByAgent,
|
|
18923
19168
|
[agent]: {
|
|
18924
19169
|
model: harnessModelRefSchema.parse(model),
|
|
18925
|
-
...thinkingOptionId ? { thinkingOptionId: harnessThinkingOptionIdSchema.parse(thinkingOptionId) } : {}
|
|
19170
|
+
...thinkingOptionId ? { thinkingOptionId: harnessThinkingOptionIdSchema.parse(thinkingOptionId) } : {},
|
|
19171
|
+
...permissionModeId ? { permissionModeId: harnessPermissionModeIdSchema.parse(permissionModeId) } : {}
|
|
18926
19172
|
}
|
|
18927
19173
|
}
|
|
18928
19174
|
},
|
|
@@ -21034,6 +21280,9 @@ ${error51.stderrTail}`] : []
|
|
|
21034
21280
|
function draftPermissionMode(catalog, requested) {
|
|
21035
21281
|
return catalog.modes.find(({ id }) => id === requested)?.id ?? catalog.modes.find(({ id }) => id === catalog.defaultModeId)?.id ?? catalog.defaultModeId;
|
|
21036
21282
|
}
|
|
21283
|
+
function shouldPersistNewThreadConfigurationSelection(phase) {
|
|
21284
|
+
return phase === "draft";
|
|
21285
|
+
}
|
|
21037
21286
|
function restoredThreadOwnership(inspection) {
|
|
21038
21287
|
if (inspection.owner === "codex") return { agent: "codex" };
|
|
21039
21288
|
if (inspection.harnessId === "pi") {
|
|
@@ -21057,10 +21306,12 @@ ${error51.stderrTail}`] : []
|
|
|
21057
21306
|
}
|
|
21058
21307
|
const model = inspection.effectiveModel ?? transportSelection.model;
|
|
21059
21308
|
const thinkingOptionId = selectableThinkingOptionId(inspection) ?? transportSelection.thinkingOptionId;
|
|
21309
|
+
const permissionModeId = inspection.effectivePermissionModeId ?? transportSelection.permissionModeId;
|
|
21060
21310
|
return {
|
|
21061
21311
|
agent: "grok",
|
|
21062
21312
|
...model ? { model } : {},
|
|
21063
|
-
...thinkingOptionId ? { thinkingOptionId } : {}
|
|
21313
|
+
...thinkingOptionId ? { thinkingOptionId } : {},
|
|
21314
|
+
...permissionModeId ? { permissionModeId } : {}
|
|
21064
21315
|
};
|
|
21065
21316
|
}
|
|
21066
21317
|
if (inspection.harnessId === "claude-code") {
|
|
@@ -21091,10 +21342,10 @@ ${error51.stderrTail}`] : []
|
|
|
21091
21342
|
function isOwnershipSubmissionBlocked(status) {
|
|
21092
21343
|
return status === "loading" || status === "error";
|
|
21093
21344
|
}
|
|
21094
|
-
function shouldTransferComposerState(sourceTarget, replacementTarget, sourcePhase) {
|
|
21345
|
+
function shouldTransferComposerState(sourceTarget, replacementTarget, sourcePhase, submissionPending = false) {
|
|
21095
21346
|
if (!sourceTarget || !replacementTarget) return false;
|
|
21096
21347
|
if (sourceTarget === replacementTarget) return true;
|
|
21097
|
-
return sourcePhase === "locked" && sourceTarget[0] === "default" && replacementTarget[0] === "conversation";
|
|
21348
|
+
return (sourcePhase === "locked" || submissionPending) && sourceTarget[0] === "default" && replacementTarget[0] === "conversation";
|
|
21098
21349
|
}
|
|
21099
21350
|
function isLateConversationTarget(mountedTarget, currentTarget) {
|
|
21100
21351
|
if (currentTarget?.[0] !== "conversation") return false;
|
|
@@ -21103,13 +21354,16 @@ ${error51.stderrTail}`] : []
|
|
|
21103
21354
|
if (mountedTarget?.[0] !== "conversation") return false;
|
|
21104
21355
|
return mountedTarget.length !== currentTarget.length || mountedTarget.some((value, index) => value !== currentTarget[index]);
|
|
21105
21356
|
}
|
|
21106
|
-
function lateConversationTargetResolution(mountedTarget, currentTarget, sourcePhase) {
|
|
21357
|
+
function lateConversationTargetResolution(mountedTarget, currentTarget, sourcePhase, submissionPending = false) {
|
|
21107
21358
|
if (!isLateConversationTarget(mountedTarget, currentTarget)) return "none";
|
|
21108
|
-
return mountedTarget?.[0] === "default" && sourcePhase === "locked" ? "transfer" : "inspect";
|
|
21359
|
+
return mountedTarget?.[0] === "default" && (sourcePhase === "locked" || submissionPending) ? "transfer" : "inspect";
|
|
21109
21360
|
}
|
|
21110
21361
|
function isComposerModelWriteAllowed(target) {
|
|
21111
21362
|
return target?.[0] === "default";
|
|
21112
21363
|
}
|
|
21364
|
+
function shouldApplyDraftAgentCarrier(agent, model) {
|
|
21365
|
+
return agent === "codex" || model !== void 0;
|
|
21366
|
+
}
|
|
21113
21367
|
function applyComposerModelWrite(target, write) {
|
|
21114
21368
|
if (target?.[0] === "conversation") return true;
|
|
21115
21369
|
if (!isComposerModelWriteAllowed(target)) return false;
|
|
@@ -21217,7 +21471,8 @@ ${error51.stderrTail}`] : []
|
|
|
21217
21471
|
writeNewThreadExternalConfigurationPreference(
|
|
21218
21472
|
state.agent,
|
|
21219
21473
|
model,
|
|
21220
|
-
controller.thinkingOptionForAgent(composer, state.agent)
|
|
21474
|
+
controller.thinkingOptionForAgent(composer, state.agent),
|
|
21475
|
+
controller.permissionModeForAgent(composer, state.agent)
|
|
21221
21476
|
);
|
|
21222
21477
|
}
|
|
21223
21478
|
}
|
|
@@ -21426,7 +21681,8 @@ ${error51.stderrTail}`] : []
|
|
|
21426
21681
|
const resolution = lateConversationTargetResolution(
|
|
21427
21682
|
mounted.modelTarget,
|
|
21428
21683
|
currentTarget,
|
|
21429
|
-
controller.get(mounted.composer).phase
|
|
21684
|
+
controller.get(mounted.composer).phase,
|
|
21685
|
+
controller.isSubmissionPending(mounted.composer)
|
|
21430
21686
|
);
|
|
21431
21687
|
if (resolution === "none") return false;
|
|
21432
21688
|
const previousTarget = mounted.modelTarget;
|
|
@@ -21493,6 +21749,16 @@ ${error51.stderrTail}`] : []
|
|
|
21493
21749
|
}
|
|
21494
21750
|
if (inspection.status !== "ready") throw new Error(inspection.error.message);
|
|
21495
21751
|
const current = controller.get(mounted.composer);
|
|
21752
|
+
const previousModel = controller.modelForAgent(mounted.composer, agent);
|
|
21753
|
+
const previousModelAvailable = previousModel !== void 0 && inspection.catalog.models.some((model) => model.ref.id === previousModel.id);
|
|
21754
|
+
if (current.phase === "locked" && previousModel && !previousModelAvailable) {
|
|
21755
|
+
throw new Error("Existing Thread Model is absent from the current Catalog");
|
|
21756
|
+
}
|
|
21757
|
+
const preferredConfiguration = current.phase === "draft" && !previousModelAvailable ? readNewThreadExternalConfigurationPreference(
|
|
21758
|
+
agent,
|
|
21759
|
+
inspection.catalog,
|
|
21760
|
+
inspection.permissionModes
|
|
21761
|
+
) : void 0;
|
|
21496
21762
|
const previousPermissionModeId = controller.permissionModeForAgent(mounted.composer, agent);
|
|
21497
21763
|
let selectedPermissionModeId;
|
|
21498
21764
|
if (inspection.capabilities.configuration.selectPermissionMode) {
|
|
@@ -21502,7 +21768,7 @@ ${error51.stderrTail}`] : []
|
|
|
21502
21768
|
}
|
|
21503
21769
|
mounted.permissionModeView = { status: "loading", catalog: permissionModes };
|
|
21504
21770
|
const effectivePermissionModeId = current.phase === "locked" ? mounted.threadConfiguration?.effectivePermissionModeId : void 0;
|
|
21505
|
-
const preferredPermissionModeId = agent === "claude-code" ? readClaudePermissionModePreference(permissionModes) : void 0;
|
|
21771
|
+
const preferredPermissionModeId = preferredConfiguration?.permissionModeId ?? (agent === "claude-code" ? readClaudePermissionModePreference(permissionModes) : void 0);
|
|
21506
21772
|
selectedPermissionModeId = draftPermissionMode(
|
|
21507
21773
|
permissionModes,
|
|
21508
21774
|
effectivePermissionModeId ?? previousPermissionModeId ?? preferredPermissionModeId
|
|
@@ -21531,12 +21797,6 @@ ${error51.stderrTail}`] : []
|
|
|
21531
21797
|
}
|
|
21532
21798
|
return;
|
|
21533
21799
|
}
|
|
21534
|
-
const previousModel = controller.modelForAgent(mounted.composer, agent);
|
|
21535
|
-
const previousModelAvailable = previousModel !== void 0 && inspection.catalog.models.some((model) => model.ref.id === previousModel.id);
|
|
21536
|
-
if (current.phase === "locked" && previousModel && !previousModelAvailable) {
|
|
21537
|
-
throw new Error("Existing Thread Model is absent from the current Catalog");
|
|
21538
|
-
}
|
|
21539
|
-
const preferredConfiguration = current.phase === "draft" && !previousModelAvailable ? readNewThreadExternalConfigurationPreference(agent, inspection.catalog) : void 0;
|
|
21540
21800
|
const selected = previousModelAvailable ? previousModel : preferredConfiguration?.model ?? inspection.catalog.defaultModel;
|
|
21541
21801
|
if (!selected) throw new Error("External Harness did not report its default Model");
|
|
21542
21802
|
const effectiveCatalog = current.phase === "locked" && mounted.threadConfiguration ? catalogWithConfigurationState(inspection.catalog, selected, mounted.threadConfiguration) : inspection.catalog;
|
|
@@ -21616,6 +21876,7 @@ ${error51.stderrTail}`] : []
|
|
|
21616
21876
|
}
|
|
21617
21877
|
};
|
|
21618
21878
|
const selectExternalModel = async (mounted, modelId) => {
|
|
21879
|
+
controller.clearPendingSubmission(mounted.composer);
|
|
21619
21880
|
const current = controller.get(mounted.composer);
|
|
21620
21881
|
if (current.agent === "codex") return;
|
|
21621
21882
|
const agent = current.agent;
|
|
@@ -21687,13 +21948,13 @@ ${error51.stderrTail}`] : []
|
|
|
21687
21948
|
effectiveThinkingOptionId = supportsThinkingSelection ? selectableThinkingOptionId(state) : void 0;
|
|
21688
21949
|
effectiveCatalog = supportsThinkingSelection ? catalogWithConfigurationState(catalog, effectiveModel, state) : catalog;
|
|
21689
21950
|
resolvedModelLabel = state.resolvedModelLabel;
|
|
21690
|
-
const
|
|
21951
|
+
const effectivePermissionModeId2 = state.effectivePermissionModeId ?? previousPermissionModeId;
|
|
21691
21952
|
if (!applyExternalConfiguration(
|
|
21692
21953
|
mounted,
|
|
21693
21954
|
agent,
|
|
21694
21955
|
effectiveModel,
|
|
21695
21956
|
effectiveThinkingOptionId,
|
|
21696
|
-
|
|
21957
|
+
effectivePermissionModeId2
|
|
21697
21958
|
)) {
|
|
21698
21959
|
throw new Error("Confirmed external Model could not be applied to the Composer");
|
|
21699
21960
|
}
|
|
@@ -21702,11 +21963,18 @@ ${error51.stderrTail}`] : []
|
|
|
21702
21963
|
if (!isCurrentModelRequest(mounted, generation)) return;
|
|
21703
21964
|
controller.setExternalModel(mounted.composer, agent, effectiveModel);
|
|
21704
21965
|
controller.setExternalThinkingOption(mounted.composer, agent, effectiveThinkingOptionId);
|
|
21705
|
-
|
|
21706
|
-
|
|
21707
|
-
|
|
21708
|
-
|
|
21709
|
-
)
|
|
21966
|
+
const effectivePermissionModeId = mounted.threadConfiguration?.effectivePermissionModeId ?? previousPermissionModeId;
|
|
21967
|
+
if (effectivePermissionModeId) {
|
|
21968
|
+
controller.setExternalPermissionMode(mounted.composer, agent, effectivePermissionModeId);
|
|
21969
|
+
}
|
|
21970
|
+
if (shouldPersistNewThreadConfigurationSelection(current.phase)) {
|
|
21971
|
+
writeNewThreadExternalConfigurationPreference(
|
|
21972
|
+
agent,
|
|
21973
|
+
effectiveModel,
|
|
21974
|
+
effectiveThinkingOptionId,
|
|
21975
|
+
effectivePermissionModeId
|
|
21976
|
+
);
|
|
21977
|
+
}
|
|
21710
21978
|
mounted.modelView = {
|
|
21711
21979
|
status: "ready",
|
|
21712
21980
|
catalog: effectiveCatalog,
|
|
@@ -21739,6 +22007,7 @@ ${error51.stderrTail}`] : []
|
|
|
21739
22007
|
}
|
|
21740
22008
|
};
|
|
21741
22009
|
const selectPermissionMode = async (mounted, permissionModeId) => {
|
|
22010
|
+
controller.clearPendingSubmission(mounted.composer);
|
|
21742
22011
|
const current = controller.get(mounted.composer);
|
|
21743
22012
|
if (current.agent === "codex") return;
|
|
21744
22013
|
const agent = current.agent;
|
|
@@ -21747,9 +22016,6 @@ ${error51.stderrTail}`] : []
|
|
|
21747
22016
|
const model = controller.modelForAgent(mounted.composer, agent);
|
|
21748
22017
|
if (!catalog || !selectedPermissionModeId || !model || !modelControl) return;
|
|
21749
22018
|
const previousPermissionModeId = controller.permissionModeForAgent(mounted.composer, agent);
|
|
21750
|
-
if (agent === "claude-code") {
|
|
21751
|
-
writeClaudePermissionModePreference(selectedPermissionModeId);
|
|
21752
|
-
}
|
|
21753
22019
|
const thinkingOptionId = controller.thinkingOptionForAgent(mounted.composer, agent);
|
|
21754
22020
|
const generation = controller.beginModelRequest(mounted.composer);
|
|
21755
22021
|
mounted.permissionModeView = {
|
|
@@ -21814,6 +22080,17 @@ ${error51.stderrTail}`] : []
|
|
|
21814
22080
|
}
|
|
21815
22081
|
if (!isCurrentModelRequest(mounted, generation)) return;
|
|
21816
22082
|
controller.setExternalPermissionMode(mounted.composer, agent, effectivePermissionModeId);
|
|
22083
|
+
if (shouldPersistNewThreadConfigurationSelection(current.phase)) {
|
|
22084
|
+
writeNewThreadExternalConfigurationPreference(
|
|
22085
|
+
agent,
|
|
22086
|
+
model,
|
|
22087
|
+
thinkingOptionId,
|
|
22088
|
+
effectivePermissionModeId
|
|
22089
|
+
);
|
|
22090
|
+
if (agent === "claude-code") {
|
|
22091
|
+
writeClaudePermissionModePreference(effectivePermissionModeId);
|
|
22092
|
+
}
|
|
22093
|
+
}
|
|
21817
22094
|
mounted.permissionModeView = {
|
|
21818
22095
|
status: "ready",
|
|
21819
22096
|
catalog,
|
|
@@ -21841,6 +22118,7 @@ ${error51.stderrTail}`] : []
|
|
|
21841
22118
|
}
|
|
21842
22119
|
};
|
|
21843
22120
|
const selectExternalThinking = async (mounted, thinkingOptionId) => {
|
|
22121
|
+
controller.clearPendingSubmission(mounted.composer);
|
|
21844
22122
|
const current = controller.get(mounted.composer);
|
|
21845
22123
|
if (current.agent === "codex") return;
|
|
21846
22124
|
const agent = current.agent;
|
|
@@ -21919,7 +22197,18 @@ ${error51.stderrTail}`] : []
|
|
|
21919
22197
|
}
|
|
21920
22198
|
if (!isCurrentModelRequest(mounted, generation)) return;
|
|
21921
22199
|
controller.setExternalThinkingOption(mounted.composer, agent, effectiveThinkingOptionId);
|
|
21922
|
-
|
|
22200
|
+
const effectivePermissionModeId = mounted.threadConfiguration?.effectivePermissionModeId ?? permissionModeId;
|
|
22201
|
+
if (effectivePermissionModeId) {
|
|
22202
|
+
controller.setExternalPermissionMode(mounted.composer, agent, effectivePermissionModeId);
|
|
22203
|
+
}
|
|
22204
|
+
if (shouldPersistNewThreadConfigurationSelection(current.phase)) {
|
|
22205
|
+
writeNewThreadExternalConfigurationPreference(
|
|
22206
|
+
agent,
|
|
22207
|
+
model,
|
|
22208
|
+
effectiveThinkingOptionId,
|
|
22209
|
+
effectivePermissionModeId
|
|
22210
|
+
);
|
|
22211
|
+
}
|
|
21923
22212
|
mounted.modelView = {
|
|
21924
22213
|
status: "ready",
|
|
21925
22214
|
catalog: effectiveCatalog,
|
|
@@ -21944,13 +22233,16 @@ ${error51.stderrTail}`] : []
|
|
|
21944
22233
|
};
|
|
21945
22234
|
const switchComposerAgent = async (mounted, agent) => {
|
|
21946
22235
|
if (agent !== "codex" && harnessAvailability[agent] !== "ready") return false;
|
|
22236
|
+
controller.clearPendingSubmission(mounted.composer);
|
|
21947
22237
|
const composerId = controller.get(mounted.composer).composerId;
|
|
21948
22238
|
controller.invalidateModelRequests(mounted.composer);
|
|
21949
22239
|
const switching = controller.switchAgent(mounted.composer, agent, {
|
|
21950
22240
|
applyAgent(nextAgent) {
|
|
22241
|
+
const model = controller.modelForAgent(mounted.composer, nextAgent);
|
|
22242
|
+
if (!shouldApplyDraftAgentCarrier(nextAgent, model)) return true;
|
|
21951
22243
|
return applyAdapterAgent?.(
|
|
21952
22244
|
nextAgent,
|
|
21953
|
-
|
|
22245
|
+
model,
|
|
21954
22246
|
nextAgent !== "codex" ? controller.thinkingOptionForAgent(mounted.composer, nextAgent) : void 0,
|
|
21955
22247
|
nextAgent !== "codex" ? controller.permissionModeForAgent(mounted.composer, nextAgent) : void 0,
|
|
21956
22248
|
mounted.composer
|
|
@@ -22169,13 +22461,16 @@ ${error51.stderrTail}`] : []
|
|
|
22169
22461
|
};
|
|
22170
22462
|
mountedByComposer.set(composer, mounted);
|
|
22171
22463
|
if (isComposerModelWriteAllowed(modelTarget)) {
|
|
22172
|
-
|
|
22173
|
-
|
|
22174
|
-
|
|
22175
|
-
|
|
22176
|
-
|
|
22177
|
-
|
|
22178
|
-
|
|
22464
|
+
const model = controller.modelForAgent(composer, state.agent);
|
|
22465
|
+
if (shouldApplyDraftAgentCarrier(state.agent, model)) {
|
|
22466
|
+
applyAdapterAgent?.(
|
|
22467
|
+
state.agent,
|
|
22468
|
+
model,
|
|
22469
|
+
state.agent !== "codex" ? controller.thinkingOptionForAgent(composer, state.agent) : void 0,
|
|
22470
|
+
state.agent !== "codex" ? controller.permissionModeForAgent(composer, state.agent) : void 0,
|
|
22471
|
+
composer
|
|
22472
|
+
);
|
|
22473
|
+
}
|
|
22179
22474
|
}
|
|
22180
22475
|
renderMounted(mounted);
|
|
22181
22476
|
sidebarAgentIcons.refresh();
|
|
@@ -22200,7 +22495,8 @@ ${error51.stderrTail}`] : []
|
|
|
22200
22495
|
if (!shouldTransferComposerState(
|
|
22201
22496
|
replacement.sourceModelTarget,
|
|
22202
22497
|
replacementTarget,
|
|
22203
|
-
sourceState.phase
|
|
22498
|
+
sourceState.phase,
|
|
22499
|
+
controller.isSubmissionPending(replacement.source.composer)
|
|
22204
22500
|
) || !controller.transfer(replacement.source.composer, target, replacementTarget)) {
|
|
22205
22501
|
pendingReplacements.delete(target);
|
|
22206
22502
|
}
|
|
@@ -22282,11 +22578,13 @@ ${error51.stderrTail}`] : []
|
|
|
22282
22578
|
return state.phase === "locked" && mounted.ownershipStatus === "ready";
|
|
22283
22579
|
}
|
|
22284
22580
|
if (!mounted || !isComposerModelWriteAllowed(mounted.modelTarget)) return false;
|
|
22581
|
+
const model = controller.modelForAgent(composer, state.agent);
|
|
22582
|
+
if (!shouldApplyDraftAgentCarrier(state.agent, model)) return false;
|
|
22285
22583
|
return applyComposerModelWrite(
|
|
22286
22584
|
mounted.modelTarget,
|
|
22287
22585
|
() => applyAdapterAgent?.(
|
|
22288
22586
|
state.agent,
|
|
22289
|
-
|
|
22587
|
+
model,
|
|
22290
22588
|
state.agent !== "codex" ? controller.thinkingOptionForAgent(composer, state.agent) : void 0,
|
|
22291
22589
|
state.agent !== "codex" ? controller.permissionModeForAgent(composer, state.agent) : void 0,
|
|
22292
22590
|
composer
|
|
@@ -22308,7 +22606,7 @@ ${error51.stderrTail}`] : []
|
|
|
22308
22606
|
if (!isExternalConfigurationReady(mounted)) return false;
|
|
22309
22607
|
if (current.phase === "locked") return true;
|
|
22310
22608
|
if (!applyComposerAgent(composer)) return false;
|
|
22311
|
-
controller.
|
|
22609
|
+
controller.markSubmissionPending(composer);
|
|
22312
22610
|
renderMounted(mounted);
|
|
22313
22611
|
return true;
|
|
22314
22612
|
};
|
|
@@ -22321,6 +22619,7 @@ ${error51.stderrTail}`] : []
|
|
|
22321
22619
|
const onBeforeInput = (event) => {
|
|
22322
22620
|
const composer = composerForTarget(event.target);
|
|
22323
22621
|
if (!composer) return;
|
|
22622
|
+
controller.clearPendingSubmission(composer);
|
|
22324
22623
|
const mounted = mountedByComposer.get(composer);
|
|
22325
22624
|
if (mounted && isOwnershipSubmissionBlocked(mounted.ownershipStatus)) return;
|
|
22326
22625
|
if (controller.isSwitching(composer) || !applyComposerAgent(composer)) blockEvent(event);
|