orion-super-agent-dev 0.1.23 → 0.1.24
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/out/brains/darwin-arm64/orion-brain +0 -0
- package/out/brains/darwin-x64/orion-brain +0 -0
- package/out/brains/linux-arm64/orion-brain +0 -0
- package/out/brains/linux-x64/orion-brain +0 -0
- package/out/brains/win32-x64/orion-brain.exe +0 -0
- package/out/main.js +1522 -891
- package/package.json +1 -1
package/out/main.js
CHANGED
|
@@ -29178,6 +29178,8 @@ var require_duetEntry = __commonJS({
|
|
|
29178
29178
|
}();
|
|
29179
29179
|
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
29180
29180
|
exports2.DUET_HANDOFF_BRIEF_MAX_CHARS = exports2.DUET_HANDOFF_CAPABILITY = exports2.DUET_HANDOFF_TOOL = exports2.DUET_ENTRY_OPTIONS = exports2.DUET_ENTRY_INFO = exports2.DUET_ENTRY_KEY = exports2.DUET_ENTRY_DEFAULT = exports2.DUET_ENTRIES = void 0;
|
|
29181
|
+
exports2.isModelRoutedEntry = isModelRoutedEntry;
|
|
29182
|
+
exports2.effectiveDuetEntry = effectiveDuetEntry;
|
|
29181
29183
|
exports2.duetEntryLabel = duetEntryLabel2;
|
|
29182
29184
|
exports2.normalizeDuetEntry = normalizeDuetEntry2;
|
|
29183
29185
|
exports2.duetHandoffBrief = duetHandoffBrief2;
|
|
@@ -29193,7 +29195,10 @@ var require_duetEntry = __commonJS({
|
|
|
29193
29195
|
var path14 = __importStar(__require("node:path"));
|
|
29194
29196
|
var atomicWrite_js_1 = require_atomicWrite();
|
|
29195
29197
|
var settingsPaths_js_1 = require_settingsPaths();
|
|
29196
|
-
exports2.DUET_ENTRIES = ["planner", "router"];
|
|
29198
|
+
exports2.DUET_ENTRIES = ["planner", "router", "executor"];
|
|
29199
|
+
function isModelRoutedEntry(entry) {
|
|
29200
|
+
return entry === "router" || entry === "executor";
|
|
29201
|
+
}
|
|
29197
29202
|
exports2.DUET_ENTRY_DEFAULT = "planner";
|
|
29198
29203
|
exports2.DUET_ENTRY_KEY = "duetEntry";
|
|
29199
29204
|
exports2.DUET_ENTRY_INFO = {
|
|
@@ -29213,8 +29218,20 @@ var require_duetEntry = __commonJS({
|
|
|
29213
29218
|
value: "router",
|
|
29214
29219
|
label: "Router decides",
|
|
29215
29220
|
description: "Local model routes. No planner call."
|
|
29221
|
+
},
|
|
29222
|
+
{
|
|
29223
|
+
value: "executor",
|
|
29224
|
+
label: "Executor decides",
|
|
29225
|
+
description: "Your local executor routes. No planner call, no download."
|
|
29216
29226
|
}
|
|
29217
29227
|
];
|
|
29228
|
+
function effectiveDuetEntry(setting, routerState, executorState) {
|
|
29229
|
+
if (setting === "router" && routerState !== "ready")
|
|
29230
|
+
return { entry: "planner", downgraded: true };
|
|
29231
|
+
if (setting === "executor" && executorState !== "ready")
|
|
29232
|
+
return { entry: "planner", downgraded: true };
|
|
29233
|
+
return { entry: setting, downgraded: false };
|
|
29234
|
+
}
|
|
29218
29235
|
function duetEntryLabel2(entry) {
|
|
29219
29236
|
return exports2.DUET_ENTRY_OPTIONS.find((option) => option.value === entry)?.label ?? entry;
|
|
29220
29237
|
}
|
|
@@ -29222,7 +29239,7 @@ var require_duetEntry = __commonJS({
|
|
|
29222
29239
|
if (typeof raw !== "string")
|
|
29223
29240
|
return null;
|
|
29224
29241
|
const value = raw.trim();
|
|
29225
|
-
return value === "planner" || value === "router" ? value : null;
|
|
29242
|
+
return value === "planner" || value === "router" || value === "executor" ? value : null;
|
|
29226
29243
|
}
|
|
29227
29244
|
exports2.DUET_HANDOFF_TOOL = "hand_off";
|
|
29228
29245
|
exports2.DUET_HANDOFF_CAPABILITY = "duet_handoff";
|
|
@@ -29345,6 +29362,69 @@ var require_duetEntry = __commonJS({
|
|
|
29345
29362
|
}
|
|
29346
29363
|
});
|
|
29347
29364
|
|
|
29365
|
+
// ../packages/orion-client-core/dist/duetExecutorGateStatus.js
|
|
29366
|
+
var require_duetExecutorGateStatus = __commonJS({
|
|
29367
|
+
"../packages/orion-client-core/dist/duetExecutorGateStatus.js"(exports2) {
|
|
29368
|
+
"use strict";
|
|
29369
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
29370
|
+
exports2.executorGateStatusLine = executorGateStatusLine2;
|
|
29371
|
+
exports2.executorGateDowngradeNote = executorGateDowngradeNote;
|
|
29372
|
+
exports2.executorGateOptionAvailability = executorGateOptionAvailability;
|
|
29373
|
+
function unavailableWhy(reason, problem) {
|
|
29374
|
+
switch (reason) {
|
|
29375
|
+
case "not_resolved":
|
|
29376
|
+
return "its endpoint is not configured";
|
|
29377
|
+
case "not_loopback":
|
|
29378
|
+
return "it is not on this machine";
|
|
29379
|
+
case "unreachable":
|
|
29380
|
+
return "it is not answering";
|
|
29381
|
+
case "no_completions":
|
|
29382
|
+
return "it has no /v1/completions route";
|
|
29383
|
+
case "thinking":
|
|
29384
|
+
return "it answers with thinking on (load it with thinking off)";
|
|
29385
|
+
case "unparseable":
|
|
29386
|
+
return "it did not answer E or P";
|
|
29387
|
+
case "error":
|
|
29388
|
+
return `the gate call failed (${problem})`;
|
|
29389
|
+
}
|
|
29390
|
+
}
|
|
29391
|
+
function executorGateStatusLine2(status) {
|
|
29392
|
+
switch (status.state) {
|
|
29393
|
+
case "ready":
|
|
29394
|
+
return `Executor gate: ${status.target.model} on '${status.target.name}' \xB7 ${status.mode} \xB7 threshold ${status.threshold} \xB7 ${status.calibration.passed}/${status.calibration.total} scenarios \xB7 ready`;
|
|
29395
|
+
case "miscalibrated":
|
|
29396
|
+
return `Executor gate: ${status.target.model} on '${status.target.name}' misrouted ${status.calibration.failed.length} of ${status.calibration.total} probe scenarios (${status.mode}, threshold ${status.threshold}) \u2014 tune executorGate.threshold on that endpoint.`;
|
|
29397
|
+
case "platform":
|
|
29398
|
+
return "Executor gate: needs a local executor \u2014 the Duet executor is a platform model.";
|
|
29399
|
+
case "unavailable":
|
|
29400
|
+
return `Executor gate: not available \u2014 ${unavailableWhy(status.reason, status.problem)}.`;
|
|
29401
|
+
}
|
|
29402
|
+
}
|
|
29403
|
+
function executorGateDowngradeNote(status) {
|
|
29404
|
+
const why = status.state === "platform" ? "the Duet executor is a platform model" : status.state === "unavailable" ? unavailableWhy(status.reason, status.problem) : "it could not run";
|
|
29405
|
+
return `Executor decides needs a local executor that answers a one-token routing question and ${why} \u2014 this turn ran through the planner instead.`;
|
|
29406
|
+
}
|
|
29407
|
+
function executorGateOptionAvailability(status) {
|
|
29408
|
+
if (status === null || status.state === "ready")
|
|
29409
|
+
return { disabled: false, note: null };
|
|
29410
|
+
switch (status.state) {
|
|
29411
|
+
case "platform":
|
|
29412
|
+
return { disabled: true, note: "Needs a local executor (the Duet executor is a platform model)." };
|
|
29413
|
+
case "miscalibrated":
|
|
29414
|
+
return {
|
|
29415
|
+
disabled: true,
|
|
29416
|
+
note: `The executor's routing gate failed calibration (${status.calibration.passed}/${status.calibration.total}) \u2014 see the Duet card.`
|
|
29417
|
+
};
|
|
29418
|
+
case "unavailable":
|
|
29419
|
+
return {
|
|
29420
|
+
disabled: true,
|
|
29421
|
+
note: `Needs a local executor that answers /v1/completions (${unavailableWhy(status.reason, status.problem)}).`
|
|
29422
|
+
};
|
|
29423
|
+
}
|
|
29424
|
+
}
|
|
29425
|
+
}
|
|
29426
|
+
});
|
|
29427
|
+
|
|
29348
29428
|
// ../packages/orion-client-core/dist/duetRouterModel.js
|
|
29349
29429
|
var require_duetRouterModel = __commonJS({
|
|
29350
29430
|
"../packages/orion-client-core/dist/duetRouterModel.js"(exports2) {
|
|
@@ -29400,7 +29480,6 @@ var require_duetRouterModel = __commonJS({
|
|
|
29400
29480
|
exports2.classifyWithHeads = classifyWithHeads;
|
|
29401
29481
|
exports2.createDuetRouter = createDuetRouter;
|
|
29402
29482
|
exports2.createTransformersDuetRouterEncoder = createTransformersDuetRouterEncoder;
|
|
29403
|
-
exports2.effectiveDuetEntry = effectiveDuetEntry;
|
|
29404
29483
|
exports2.duetRouterDisplayName = duetRouterDisplayName2;
|
|
29405
29484
|
exports2.duetRouterStatusLine = duetRouterStatusLine2;
|
|
29406
29485
|
exports2.duetRouterDowngradeNote = duetRouterDowngradeNote;
|
|
@@ -29412,6 +29491,8 @@ var require_duetRouterModel = __commonJS({
|
|
|
29412
29491
|
var fs15 = __importStar(__require("node:fs/promises"));
|
|
29413
29492
|
var os9 = __importStar(__require("node:os"));
|
|
29414
29493
|
var path14 = __importStar(__require("node:path"));
|
|
29494
|
+
var duetEntry_js_1 = require_duetEntry();
|
|
29495
|
+
var duetExecutorGateStatus_js_1 = require_duetExecutorGateStatus();
|
|
29415
29496
|
exports2.DUET_ROUTER_WIRE_KEY = "duet_router";
|
|
29416
29497
|
exports2.DUET_ROUTER_BUNDLE_FORMAT = "orion-router-bundle.v1";
|
|
29417
29498
|
exports2.DUET_ROUTER_MODEL_ID = "orion/orion-pe-router-1.0";
|
|
@@ -29425,13 +29506,16 @@ var require_duetRouterModel = __commonJS({
|
|
|
29425
29506
|
];
|
|
29426
29507
|
function duetRouterWireForSegment(verdict) {
|
|
29427
29508
|
return {
|
|
29509
|
+
source: verdict.source,
|
|
29428
29510
|
model: verdict.model,
|
|
29429
29511
|
version: verdict.version,
|
|
29430
29512
|
verdict: verdict.verdict,
|
|
29431
29513
|
p_plan: round6(verdict.pPlan),
|
|
29432
29514
|
asks_for_plan: verdict.asksForPlan,
|
|
29433
29515
|
high_risk: verdict.highRisk,
|
|
29434
|
-
reason: verdict.reason
|
|
29516
|
+
reason: verdict.reason,
|
|
29517
|
+
...verdict.margin !== void 0 ? { margin: round6(verdict.margin) } : {},
|
|
29518
|
+
...verdict.mode !== void 0 ? { mode: verdict.mode } : {}
|
|
29435
29519
|
};
|
|
29436
29520
|
}
|
|
29437
29521
|
function orionModelsDir(homeDir = os9.homedir()) {
|
|
@@ -29662,6 +29746,7 @@ var require_duetRouterModel = __commonJS({
|
|
|
29662
29746
|
if (!vector)
|
|
29663
29747
|
throw new Error("router encoder returned no vector");
|
|
29664
29748
|
return {
|
|
29749
|
+
source: "orion_router",
|
|
29665
29750
|
...classifyWithHeads(vector, bundle),
|
|
29666
29751
|
model: bundle.name,
|
|
29667
29752
|
version: bundle.version,
|
|
@@ -29731,11 +29816,6 @@ var require_duetRouterModel = __commonJS({
|
|
|
29731
29816
|
}
|
|
29732
29817
|
};
|
|
29733
29818
|
}
|
|
29734
|
-
function effectiveDuetEntry(setting, routerState) {
|
|
29735
|
-
if (setting === "router" && routerState !== "ready")
|
|
29736
|
-
return { entry: "planner", downgraded: true };
|
|
29737
|
-
return { entry: setting, downgraded: false };
|
|
29738
|
-
}
|
|
29739
29819
|
function duetRouterDisplayName2(name2, version) {
|
|
29740
29820
|
const trimmed = name2.trim();
|
|
29741
29821
|
const v2 = version.trim();
|
|
@@ -29757,7 +29837,9 @@ var require_duetRouterModel = __commonJS({
|
|
|
29757
29837
|
const why = status.state === "missing" ? "it is not installed" : status.state === "invalid" ? `it is unusable (${status.problem})` : `it failed to load${"problem" in status && status.problem ? ` (${status.problem})` : ""}`;
|
|
29758
29838
|
return `Router decides needs the Orion router model and ${why} \u2014 this turn ran through the planner instead.`;
|
|
29759
29839
|
}
|
|
29760
|
-
function duetEntryOptionAvailability2(entry, status) {
|
|
29840
|
+
function duetEntryOptionAvailability2(entry, status, executorStatus = null) {
|
|
29841
|
+
if (entry === "executor")
|
|
29842
|
+
return (0, duetExecutorGateStatus_js_1.executorGateOptionAvailability)(executorStatus);
|
|
29761
29843
|
if (entry !== "router" || status === null || status.state === "ready")
|
|
29762
29844
|
return { disabled: false, note: null };
|
|
29763
29845
|
return {
|
|
@@ -29797,6 +29879,7 @@ var require_duetRouterModel = __commonJS({
|
|
|
29797
29879
|
let router = null;
|
|
29798
29880
|
let building = null;
|
|
29799
29881
|
let noted = false;
|
|
29882
|
+
let executorNoted = false;
|
|
29800
29883
|
const status = async (o = {}) => {
|
|
29801
29884
|
const now2 = Date.now();
|
|
29802
29885
|
if (!o.refresh && cached !== null && now2 - cached.at < exports2.DUET_ROUTER_STATUS_TTL_MS)
|
|
@@ -29808,11 +29891,18 @@ var require_duetRouterModel = __commonJS({
|
|
|
29808
29891
|
const downgrade = (why) => {
|
|
29809
29892
|
const note = noted ? null : duetRouterDowngradeNote(why);
|
|
29810
29893
|
noted = true;
|
|
29811
|
-
return { ...effectiveDuetEntry("router", why.state), verdict: null, note };
|
|
29894
|
+
return { ...(0, duetEntry_js_1.effectiveDuetEntry)("router", why.state), verdict: null, note };
|
|
29812
29895
|
};
|
|
29813
29896
|
return {
|
|
29814
29897
|
status,
|
|
29815
|
-
async prepareTurn(setting, text) {
|
|
29898
|
+
async prepareTurn(setting, text, ctx = {}) {
|
|
29899
|
+
if (setting === "executor") {
|
|
29900
|
+
if (opts.executorGate !== void 0)
|
|
29901
|
+
return opts.executorGate.prepareTurn(text, ctx);
|
|
29902
|
+
const note = executorNoted ? null : (0, duetExecutorGateStatus_js_1.executorGateDowngradeNote)({ state: "unavailable", reason: "error", problem: "this host has no executor gate" });
|
|
29903
|
+
executorNoted = true;
|
|
29904
|
+
return { ...(0, duetEntry_js_1.effectiveDuetEntry)("executor", void 0, "unavailable"), verdict: null, note };
|
|
29905
|
+
}
|
|
29816
29906
|
if (setting !== "router")
|
|
29817
29907
|
return { entry: setting, verdict: null, note: null };
|
|
29818
29908
|
if (text.trim() === "")
|
|
@@ -29846,6 +29936,8 @@ var require_duetRouterModel = __commonJS({
|
|
|
29846
29936
|
invalidate() {
|
|
29847
29937
|
cached = null;
|
|
29848
29938
|
noted = false;
|
|
29939
|
+
executorNoted = false;
|
|
29940
|
+
opts.executorGate?.invalidate();
|
|
29849
29941
|
const live = router;
|
|
29850
29942
|
router = null;
|
|
29851
29943
|
building = null;
|
|
@@ -30164,6 +30256,7 @@ var require_duetPlan = __commonJS({
|
|
|
30164
30256
|
exports2.duetReplanFollowupPrompt = duetReplanFollowupPrompt2;
|
|
30165
30257
|
exports2.recordDuetTurnOutcome = recordDuetTurnOutcome;
|
|
30166
30258
|
exports2.foldDuetTurnEnd = foldDuetTurnEnd2;
|
|
30259
|
+
var duetEntry_js_1 = require_duetEntry();
|
|
30167
30260
|
exports2.DUET_PLAN_MAX_LEN = 65536;
|
|
30168
30261
|
exports2.DUET_PLAN_MAX_VERSION = 1e4;
|
|
30169
30262
|
exports2.DUET_PLAN_GRANTS = ["default", "workspace_write"];
|
|
@@ -30306,7 +30399,7 @@ var require_duetPlan = __commonJS({
|
|
|
30306
30399
|
return false;
|
|
30307
30400
|
const noPlan = duetPlanWireForSegment(record) === void 0;
|
|
30308
30401
|
if (noPlan) {
|
|
30309
|
-
if (
|
|
30402
|
+
if (!(0, duetEntry_js_1.isModelRoutedEntry)(entry))
|
|
30310
30403
|
return false;
|
|
30311
30404
|
if (highRiskRequest(text))
|
|
30312
30405
|
return false;
|
|
@@ -30320,7 +30413,7 @@ var require_duetPlan = __commonJS({
|
|
|
30320
30413
|
return false;
|
|
30321
30414
|
if (record.userNegativeFeedback)
|
|
30322
30415
|
return false;
|
|
30323
|
-
if (
|
|
30416
|
+
if (!(0, duetEntry_js_1.isModelRoutedEntry)(entry))
|
|
30324
30417
|
return continuationRequest(text);
|
|
30325
30418
|
return verdict ? verdict.verdict === "execute" : true;
|
|
30326
30419
|
}
|
|
@@ -35269,11 +35362,12 @@ var require_customProviders = __commonJS({
|
|
|
35269
35362
|
};
|
|
35270
35363
|
}();
|
|
35271
35364
|
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
35272
|
-
exports2.EXECUTOR_LIVENESS_TIMEOUT_MS = exports2.EXECUTOR_LIVENESS_TTL_MS = exports2.PROBE_TIMEOUT_MS = exports2.ROUTING_MODELS_KEY = exports2.MAX_CONTEXT_WINDOW = exports2.MIN_CONTEXT_WINDOW = void 0;
|
|
35365
|
+
exports2.EXECUTOR_LIVENESS_TIMEOUT_MS = exports2.EXECUTOR_LIVENESS_TTL_MS = exports2.PROBE_TIMEOUT_MS = exports2.EXECUTOR_GATE_THRESHOLD_BOUND = exports2.EXECUTOR_GATE_DEFAULT_THRESHOLD = exports2.EXECUTOR_GATE_KEY = exports2.ROUTING_MODELS_KEY = exports2.MAX_CONTEXT_WINDOW = exports2.MIN_CONTEXT_WINDOW = void 0;
|
|
35273
35366
|
exports2.customProviderSettingsPath = customProviderSettingsPath;
|
|
35274
35367
|
exports2.clampContextWindow = clampContextWindow;
|
|
35275
35368
|
exports2.normalizeModelConfig = normalizeModelConfig;
|
|
35276
35369
|
exports2.normalizeRoutingModels = normalizeRoutingModels;
|
|
35370
|
+
exports2.normalizeExecutorGate = normalizeExecutorGate;
|
|
35277
35371
|
exports2.loadCustomProviders = loadCustomProviders3;
|
|
35278
35372
|
exports2.getCustomProvider = getCustomProvider2;
|
|
35279
35373
|
exports2.saveCustomProvider = saveCustomProvider3;
|
|
@@ -35303,6 +35397,9 @@ var require_customProviders = __commonJS({
|
|
|
35303
35397
|
exports2.MIN_CONTEXT_WINDOW = 1024;
|
|
35304
35398
|
exports2.MAX_CONTEXT_WINDOW = 2e6;
|
|
35305
35399
|
exports2.ROUTING_MODELS_KEY = "routingModels";
|
|
35400
|
+
exports2.EXECUTOR_GATE_KEY = "executorGate";
|
|
35401
|
+
exports2.EXECUTOR_GATE_DEFAULT_THRESHOLD = 0;
|
|
35402
|
+
exports2.EXECUTOR_GATE_THRESHOLD_BOUND = 20;
|
|
35306
35403
|
var CUSTOM_REF_PREFIX = "custom:";
|
|
35307
35404
|
var FILE_TIERS = ["user", "project", "local"];
|
|
35308
35405
|
function customProviderSettingsPath(tier, opts = {}) {
|
|
@@ -35372,6 +35469,16 @@ var require_customProviders = __commonJS({
|
|
|
35372
35469
|
}
|
|
35373
35470
|
return Object.keys(out2).length > 0 ? out2 : void 0;
|
|
35374
35471
|
}
|
|
35472
|
+
function normalizeExecutorGate(raw) {
|
|
35473
|
+
if (typeof raw !== "object" || raw === null || Array.isArray(raw))
|
|
35474
|
+
return void 0;
|
|
35475
|
+
const threshold = raw.threshold;
|
|
35476
|
+
if (typeof threshold !== "number" || !Number.isFinite(threshold))
|
|
35477
|
+
return void 0;
|
|
35478
|
+
return {
|
|
35479
|
+
threshold: Math.max(-exports2.EXECUTOR_GATE_THRESHOLD_BOUND, Math.min(exports2.EXECUTOR_GATE_THRESHOLD_BOUND, threshold))
|
|
35480
|
+
};
|
|
35481
|
+
}
|
|
35375
35482
|
function toEntry(name2, raw) {
|
|
35376
35483
|
if (typeof raw !== "object" || raw === null || Array.isArray(raw))
|
|
35377
35484
|
return null;
|
|
@@ -35397,6 +35504,9 @@ var require_customProviders = __commonJS({
|
|
|
35397
35504
|
const routingModels = normalizeRoutingModels(value[exports2.ROUTING_MODELS_KEY]);
|
|
35398
35505
|
if (routingModels !== void 0)
|
|
35399
35506
|
entry.routingModels = routingModels;
|
|
35507
|
+
const executorGate = normalizeExecutorGate(value[exports2.EXECUTOR_GATE_KEY]);
|
|
35508
|
+
if (executorGate !== void 0)
|
|
35509
|
+
entry.executorGate = executorGate;
|
|
35400
35510
|
return entry;
|
|
35401
35511
|
}
|
|
35402
35512
|
async function readTier(tier, opts) {
|
|
@@ -35667,7 +35777,8 @@ var require_customProviders = __commonJS({
|
|
|
35667
35777
|
// keyless is valid — local servers ignore auth
|
|
35668
35778
|
wire: entry.wire,
|
|
35669
35779
|
...entry.modelConfig ? { modelConfig: entry.modelConfig } : {},
|
|
35670
|
-
...entry.routingModels ? { routingModels: entry.routingModels } : {}
|
|
35780
|
+
...entry.routingModels ? { routingModels: entry.routingModels } : {},
|
|
35781
|
+
...entry.executorGate ? { executorGate: entry.executorGate } : {}
|
|
35671
35782
|
};
|
|
35672
35783
|
routingByRef.set(provider, routing);
|
|
35673
35784
|
while (routingByRef.size > ROUTING_CACHE_MAX) {
|
|
@@ -35783,6 +35894,7 @@ var require_customProviders = __commonJS({
|
|
|
35783
35894
|
const wire = { ...routing };
|
|
35784
35895
|
delete wire.modelConfig;
|
|
35785
35896
|
delete wire.routingModels;
|
|
35897
|
+
delete wire.executorGate;
|
|
35786
35898
|
const declared = routing.modelConfig?.[modelId];
|
|
35787
35899
|
if (declared === void 0)
|
|
35788
35900
|
return wire;
|
|
@@ -36018,75 +36130,9 @@ var require_duetRouterInstall = __commonJS({
|
|
|
36018
36130
|
}
|
|
36019
36131
|
});
|
|
36020
36132
|
|
|
36021
|
-
// ../packages/orion-client-core/dist/
|
|
36022
|
-
var
|
|
36023
|
-
"../packages/orion-client-core/dist/
|
|
36024
|
-
"use strict";
|
|
36025
|
-
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
36026
|
-
exports2.mintRunId = mintRunId;
|
|
36027
|
-
exports2.runsRootFor = runsRootFor2;
|
|
36028
|
-
exports2.readJsonFile = readJsonFile;
|
|
36029
|
-
exports2.writeJsonFile = writeJsonFile;
|
|
36030
|
-
exports2.ensureDirFor = ensureDirFor;
|
|
36031
|
-
exports2.listDirNames = listDirNames;
|
|
36032
|
-
exports2.dayKey = dayKey;
|
|
36033
|
-
exports2.clipTail = clipTail;
|
|
36034
|
-
var fs_1 = __require("fs");
|
|
36035
|
-
var os_1 = __require("os");
|
|
36036
|
-
var path_1 = __require("path");
|
|
36037
|
-
var atomicWrite_js_1 = require_atomicWrite();
|
|
36038
|
-
var experienceStore_js_1 = require_experienceStore();
|
|
36039
|
-
var ID_ALPHABET = "abcdefghijklmnopqrstuvwxyz0123456789";
|
|
36040
|
-
var ID_SUFFIX_LEN = 6;
|
|
36041
|
-
function mintRunId(prefix, nowMs = Date.now(), rand = Math.random) {
|
|
36042
|
-
let suffix = "";
|
|
36043
|
-
for (let i2 = 0; i2 < ID_SUFFIX_LEN; i2 += 1) {
|
|
36044
|
-
suffix += ID_ALPHABET[Math.floor(rand() * ID_ALPHABET.length) % ID_ALPHABET.length];
|
|
36045
|
-
}
|
|
36046
|
-
return `${prefix}_${String(nowMs).padStart(13, "0")}_${suffix}`;
|
|
36047
|
-
}
|
|
36048
|
-
function runsRootFor2(kind, workspaceRoot, home = (0, os_1.homedir)()) {
|
|
36049
|
-
return (0, path_1.join)((0, experienceStore_js_1.projectDirFor)(workspaceRoot, home), "runs", kind);
|
|
36050
|
-
}
|
|
36051
|
-
async function readJsonFile(path14) {
|
|
36052
|
-
try {
|
|
36053
|
-
const raw = await fs_1.promises.readFile(path14, "utf8");
|
|
36054
|
-
return JSON.parse(raw);
|
|
36055
|
-
} catch {
|
|
36056
|
-
return null;
|
|
36057
|
-
}
|
|
36058
|
-
}
|
|
36059
|
-
async function writeJsonFile(path14, value) {
|
|
36060
|
-
await ensureDirFor(path14);
|
|
36061
|
-
await (0, atomicWrite_js_1.atomicWriteFile)(path14, JSON.stringify(value, null, 2));
|
|
36062
|
-
}
|
|
36063
|
-
async function ensureDirFor(path14) {
|
|
36064
|
-
await fs_1.promises.mkdir((0, path_1.dirname)(path14), { recursive: true });
|
|
36065
|
-
}
|
|
36066
|
-
async function listDirNames(path14) {
|
|
36067
|
-
try {
|
|
36068
|
-
return await fs_1.promises.readdir(path14);
|
|
36069
|
-
} catch {
|
|
36070
|
-
return [];
|
|
36071
|
-
}
|
|
36072
|
-
}
|
|
36073
|
-
function dayKey(nowMs = Date.now()) {
|
|
36074
|
-
const d2 = new Date(nowMs);
|
|
36075
|
-
const month = `${d2.getMonth() + 1}`.padStart(2, "0");
|
|
36076
|
-
const day = `${d2.getDate()}`.padStart(2, "0");
|
|
36077
|
-
return `${d2.getFullYear()}-${month}-${day}`;
|
|
36078
|
-
}
|
|
36079
|
-
function clipTail(text, max) {
|
|
36080
|
-
if (text.length <= max)
|
|
36081
|
-
return text;
|
|
36082
|
-
return `\u2026${text.slice(text.length - (max - 1))}`;
|
|
36083
|
-
}
|
|
36084
|
-
}
|
|
36085
|
-
});
|
|
36086
|
-
|
|
36087
|
-
// ../packages/orion-client-core/dist/customProviderModels.js
|
|
36088
|
-
var require_customProviderModels = __commonJS({
|
|
36089
|
-
"../packages/orion-client-core/dist/customProviderModels.js"(exports2) {
|
|
36133
|
+
// ../packages/orion-client-core/dist/duetRoutingLog.js
|
|
36134
|
+
var require_duetRoutingLog = __commonJS({
|
|
36135
|
+
"../packages/orion-client-core/dist/duetRoutingLog.js"(exports2) {
|
|
36090
36136
|
"use strict";
|
|
36091
36137
|
var __createBinding = exports2 && exports2.__createBinding || (Object.create ? function(o, m2, k, k2) {
|
|
36092
36138
|
if (k2 === void 0) k2 = k;
|
|
@@ -36126,291 +36172,240 @@ var require_customProviderModels = __commonJS({
|
|
|
36126
36172
|
};
|
|
36127
36173
|
}();
|
|
36128
36174
|
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
36129
|
-
exports2.
|
|
36130
|
-
exports2.
|
|
36131
|
-
exports2.
|
|
36132
|
-
exports2.
|
|
36133
|
-
exports2.
|
|
36134
|
-
exports2.
|
|
36135
|
-
exports2.
|
|
36136
|
-
exports2.
|
|
36137
|
-
exports2.
|
|
36175
|
+
exports2.DUET_ROUTING_LOG_DEFAULT_MODE = exports2.DUET_ROUTING_LOG_KEY = exports2.DUET_ROUTING_LOG_HEAD_CHARS = exports2.DUET_ROUTING_LOG_MAX_BYTES = exports2.DUET_ROUTING_LOG_SCHEMA = void 0;
|
|
36176
|
+
exports2.duetRoutingLogPath = duetRoutingLogPath2;
|
|
36177
|
+
exports2.newDecisionId = newDecisionId;
|
|
36178
|
+
exports2.sessionKey = sessionKey;
|
|
36179
|
+
exports2.lexicalSimilarity = lexicalSimilarity;
|
|
36180
|
+
exports2.planDiffRatio = planDiffRatio;
|
|
36181
|
+
exports2.clearDuetRoutingLogCache = clearDuetRoutingLogCache;
|
|
36182
|
+
exports2.duetRoutingLogMode = duetRoutingLogMode2;
|
|
36183
|
+
exports2.redactRowForMode = redactRowForMode;
|
|
36184
|
+
exports2.appendDuetRoutingRow = appendDuetRoutingRow;
|
|
36185
|
+
exports2.readDuetRoutingLog = readDuetRoutingLog2;
|
|
36186
|
+
exports2.summarizeDuetRoutingLog = summarizeDuetRoutingLog2;
|
|
36187
|
+
exports2.formatDuetRoutingLogSummary = formatDuetRoutingLogSummary2;
|
|
36138
36188
|
var node_crypto_1 = __require("node:crypto");
|
|
36189
|
+
var fs15 = __importStar(__require("node:fs/promises"));
|
|
36139
36190
|
var os9 = __importStar(__require("node:os"));
|
|
36140
36191
|
var path14 = __importStar(__require("node:path"));
|
|
36141
|
-
var
|
|
36142
|
-
|
|
36143
|
-
exports2.
|
|
36144
|
-
exports2.
|
|
36145
|
-
exports2.
|
|
36146
|
-
|
|
36147
|
-
|
|
36148
|
-
return path14.join(homeDir, ".orion", "
|
|
36192
|
+
var settingsPaths_js_1 = require_settingsPaths();
|
|
36193
|
+
exports2.DUET_ROUTING_LOG_SCHEMA = 3;
|
|
36194
|
+
exports2.DUET_ROUTING_LOG_MAX_BYTES = 5 * 1024 * 1024;
|
|
36195
|
+
exports2.DUET_ROUTING_LOG_HEAD_CHARS = 200;
|
|
36196
|
+
exports2.DUET_ROUTING_LOG_KEY = "duetRoutingLog";
|
|
36197
|
+
exports2.DUET_ROUTING_LOG_DEFAULT_MODE = "full";
|
|
36198
|
+
function duetRoutingLogPath2(opts = {}) {
|
|
36199
|
+
return path14.join(opts.homeDir ?? os9.homedir(), ".orion", "duet-routing-decisions.jsonl");
|
|
36149
36200
|
}
|
|
36150
|
-
function
|
|
36151
|
-
return
|
|
36201
|
+
function newDecisionId() {
|
|
36202
|
+
return (0, node_crypto_1.randomUUID)();
|
|
36152
36203
|
}
|
|
36153
|
-
|
|
36154
|
-
|
|
36155
|
-
|
|
36156
|
-
|
|
36157
|
-
if (record.version !== exports2.CATALOG_SCHEMA_VERSION)
|
|
36158
|
-
return null;
|
|
36159
|
-
if (normalizeBaseUrl(record.baseUrl ?? "") !== normalizeBaseUrl(baseUrl))
|
|
36160
|
-
return null;
|
|
36161
|
-
if (!Array.isArray(record.models))
|
|
36162
|
-
return null;
|
|
36163
|
-
return record;
|
|
36204
|
+
function sessionKey(sessionId) {
|
|
36205
|
+
if (sessionId === void 0 || sessionId === "")
|
|
36206
|
+
return void 0;
|
|
36207
|
+
return (0, node_crypto_1.createHash)("sha256").update(sessionId).digest("hex").slice(0, 12);
|
|
36164
36208
|
}
|
|
36165
|
-
|
|
36166
|
-
|
|
36167
|
-
if (sweptThisProcess)
|
|
36168
|
-
return;
|
|
36169
|
-
sweptThisProcess = true;
|
|
36170
|
-
try {
|
|
36171
|
-
const dir = path14.dirname(catalogPathFor("x", homeDir));
|
|
36172
|
-
const fs15 = await Promise.resolve().then(() => __importStar(__require("node:fs/promises")));
|
|
36173
|
-
for (const name2 of await fs15.readdir(dir)) {
|
|
36174
|
-
if (!name2.endsWith(".json"))
|
|
36175
|
-
continue;
|
|
36176
|
-
const file = path14.join(dir, name2);
|
|
36177
|
-
try {
|
|
36178
|
-
const record = await (0, common_1.readJsonFile)(file);
|
|
36179
|
-
const age = typeof record?.fetchedAt === "number" ? now2 - record.fetchedAt : now2 - (await fs15.stat(file)).mtimeMs;
|
|
36180
|
-
if (age > exports2.CATALOG_GC_MS)
|
|
36181
|
-
await fs15.rm(file, { force: true });
|
|
36182
|
-
} catch {
|
|
36183
|
-
}
|
|
36184
|
-
}
|
|
36185
|
-
} catch {
|
|
36186
|
-
}
|
|
36209
|
+
function tokens(text) {
|
|
36210
|
+
return new Set(text.toLowerCase().split(/[^a-z0-9]+/).filter((t) => t.length > 1));
|
|
36187
36211
|
}
|
|
36188
|
-
|
|
36189
|
-
|
|
36190
|
-
|
|
36191
|
-
|
|
36192
|
-
|
|
36193
|
-
|
|
36212
|
+
function jaccard(a, b2) {
|
|
36213
|
+
if (a.size === 0 && b2.size === 0)
|
|
36214
|
+
return 1;
|
|
36215
|
+
let inter = 0;
|
|
36216
|
+
for (const t of a)
|
|
36217
|
+
if (b2.has(t))
|
|
36218
|
+
inter += 1;
|
|
36219
|
+
const union = a.size + b2.size - inter;
|
|
36220
|
+
return union === 0 ? 0 : inter / union;
|
|
36194
36221
|
}
|
|
36195
|
-
|
|
36196
|
-
|
|
36197
|
-
function depsWith(deps2) {
|
|
36198
|
-
return {
|
|
36199
|
-
now: deps2.now ?? (() => Date.now()),
|
|
36200
|
-
probe: deps2.probe ?? customProviders_1.probeModels,
|
|
36201
|
-
readRecord: deps2.readRecord ?? readRecordFromDisk,
|
|
36202
|
-
writeRecord: deps2.writeRecord ?? writeRecordToDisk
|
|
36203
|
-
};
|
|
36222
|
+
function lexicalSimilarity(a, b2) {
|
|
36223
|
+
return Math.round(jaccard(tokens(a), tokens(b2)) * 1e3) / 1e3;
|
|
36204
36224
|
}
|
|
36205
|
-
|
|
36206
|
-
const
|
|
36207
|
-
|
|
36208
|
-
if (existing !== void 0)
|
|
36209
|
-
return existing;
|
|
36210
|
-
const run3 = (async () => {
|
|
36211
|
-
const models = await d2.probe(entry.baseUrl, await (0, customProviders_1.resolveApiKey)(entry));
|
|
36212
|
-
if (models === null || models.length === 0)
|
|
36213
|
-
return models;
|
|
36214
|
-
const record = {
|
|
36215
|
-
version: exports2.CATALOG_SCHEMA_VERSION,
|
|
36216
|
-
baseUrl: entry.baseUrl,
|
|
36217
|
-
fetchedAt: d2.now(),
|
|
36218
|
-
models
|
|
36219
|
-
};
|
|
36220
|
-
memory.set(key, record);
|
|
36221
|
-
await d2.writeRecord(record);
|
|
36222
|
-
return models;
|
|
36223
|
-
})().finally(() => inFlight2.delete(key));
|
|
36224
|
-
inFlight2.set(key, run3);
|
|
36225
|
-
return run3;
|
|
36225
|
+
function planDiffRatio(before, after) {
|
|
36226
|
+
const lines = (plan) => new Set(plan.split(/\r?\n/).map((l3) => l3.trim()).filter((l3) => l3 !== ""));
|
|
36227
|
+
return Math.round((1 - jaccard(lines(before), lines(after))) * 1e3) / 1e3;
|
|
36226
36228
|
}
|
|
36227
|
-
|
|
36228
|
-
|
|
36229
|
-
|
|
36230
|
-
|
|
36231
|
-
if (record === null) {
|
|
36232
|
-
record = await d2.readRecord(entry.baseUrl);
|
|
36233
|
-
if (record !== null)
|
|
36234
|
-
memory.set(key, record);
|
|
36235
|
-
}
|
|
36236
|
-
if (options.cachedOnly === true)
|
|
36237
|
-
return record?.models ?? [];
|
|
36238
|
-
const fresh = record !== null && d2.now() - record.fetchedAt < exports2.CATALOG_TTL_MS;
|
|
36239
|
-
if (record !== null && fresh && options.force !== true)
|
|
36240
|
-
return record.models;
|
|
36241
|
-
if (record !== null) {
|
|
36242
|
-
void probeAndStore(entry, d2).catch(() => void 0);
|
|
36243
|
-
return record.models;
|
|
36244
|
-
}
|
|
36245
|
-
return await probeAndStore(entry, d2) ?? [];
|
|
36229
|
+
var MODE_CACHE_TTL_MS = 5e3;
|
|
36230
|
+
var modeCache = /* @__PURE__ */ new Map();
|
|
36231
|
+
function clearDuetRoutingLogCache() {
|
|
36232
|
+
modeCache.clear();
|
|
36246
36233
|
}
|
|
36247
|
-
function
|
|
36248
|
-
return
|
|
36234
|
+
function coerceMode(raw) {
|
|
36235
|
+
return raw === "full" || raw === "head" || raw === "off" ? raw : null;
|
|
36249
36236
|
}
|
|
36250
|
-
function
|
|
36251
|
-
|
|
36252
|
-
|
|
36253
|
-
|
|
36254
|
-
|
|
36255
|
-
|
|
36256
|
-
|
|
36257
|
-
|
|
36258
|
-
if (maxOutputTokens !== void 0)
|
|
36259
|
-
resolved.maxOutputTokens = maxOutputTokens;
|
|
36260
|
-
if (probed?.reasoning !== void 0)
|
|
36261
|
-
resolved.reasoning = probed.reasoning;
|
|
36262
|
-
for (const knob of ["temperature", "topP", "topK", "repetitionPenalty"]) {
|
|
36263
|
-
const value = declared?.[knob];
|
|
36264
|
-
if (typeof value === "number")
|
|
36265
|
-
resolved[knob] = value;
|
|
36237
|
+
async function readTierMode(file) {
|
|
36238
|
+
if (file === null)
|
|
36239
|
+
return null;
|
|
36240
|
+
try {
|
|
36241
|
+
const parsed = JSON.parse(await fs15.readFile(file, "utf8"));
|
|
36242
|
+
return coerceMode(parsed?.[exports2.DUET_ROUTING_LOG_KEY]?.mode);
|
|
36243
|
+
} catch {
|
|
36244
|
+
return null;
|
|
36266
36245
|
}
|
|
36267
|
-
return resolved;
|
|
36268
|
-
}
|
|
36269
|
-
function catalogModelIds2(entry, catalog) {
|
|
36270
|
-
return entry.models?.length ? entry.models : catalog.map((model) => model.id);
|
|
36271
36246
|
}
|
|
36272
|
-
function
|
|
36273
|
-
|
|
36274
|
-
|
|
36275
|
-
|
|
36276
|
-
|
|
36277
|
-
|
|
36247
|
+
async function duetRoutingLogMode2(opts = {}) {
|
|
36248
|
+
const home = opts.homeDir ?? os9.homedir();
|
|
36249
|
+
const ws = opts.workspaceRoot ?? null;
|
|
36250
|
+
const key = `${home}\0${ws ?? ""}`;
|
|
36251
|
+
const hit = modeCache.get(key);
|
|
36252
|
+
if (hit !== void 0 && Date.now() - hit.at < MODE_CACHE_TTL_MS)
|
|
36253
|
+
return hit.mode;
|
|
36254
|
+
let mode = exports2.DUET_ROUTING_LOG_DEFAULT_MODE;
|
|
36255
|
+
const tiers = ["user", "project", "local"];
|
|
36256
|
+
for (const tier of tiers) {
|
|
36257
|
+
const found = await readTierMode((0, settingsPaths_js_1.settingsFilePath)(tier, { homeDir: home, workspaceRoot: ws }));
|
|
36258
|
+
if (found !== null)
|
|
36259
|
+
mode = found;
|
|
36278
36260
|
}
|
|
36279
|
-
|
|
36280
|
-
|
|
36281
|
-
inFlight2.delete(key);
|
|
36261
|
+
modeCache.set(key, { at: Date.now(), mode });
|
|
36262
|
+
return mode;
|
|
36282
36263
|
}
|
|
36283
|
-
|
|
36284
|
-
|
|
36285
|
-
const pinned = new Set(entry.models ?? []);
|
|
36286
|
-
const ids = [...pinned, ...catalog.map((model) => model.id).filter((id) => !pinned.has(id))];
|
|
36287
|
-
return ids.map((id) => {
|
|
36288
|
-
const resolved = resolveModelSettings2(entry, id, catalog);
|
|
36289
|
-
const declared = entry.modelConfig?.[id];
|
|
36290
|
-
const view = { id, pinned: pinned.has(id) };
|
|
36291
|
-
if (resolved.contextWindow !== void 0)
|
|
36292
|
-
view.contextWindow = resolved.contextWindow;
|
|
36293
|
-
if (resolved.maxOutputTokens !== void 0)
|
|
36294
|
-
view.maxOutputTokens = resolved.maxOutputTokens;
|
|
36295
|
-
if (resolved.reasoning !== void 0)
|
|
36296
|
-
view.reasoning = resolved.reasoning;
|
|
36297
|
-
if (declared?.contextWindow !== void 0 || declared?.maxOutputTokens !== void 0) {
|
|
36298
|
-
view.source = "user";
|
|
36299
|
-
} else if (view.contextWindow !== void 0 || view.maxOutputTokens !== void 0) {
|
|
36300
|
-
view.source = "endpoint";
|
|
36301
|
-
}
|
|
36302
|
-
return view;
|
|
36303
|
-
});
|
|
36264
|
+
function head(text, max) {
|
|
36265
|
+
return text.length > max ? `${text.slice(0, max - 1)}\u2026` : text;
|
|
36304
36266
|
}
|
|
36305
|
-
|
|
36306
|
-
|
|
36307
|
-
|
|
36308
|
-
|
|
36309
|
-
|
|
36310
|
-
if (
|
|
36311
|
-
|
|
36312
|
-
next.models = update.models;
|
|
36313
|
-
else
|
|
36314
|
-
delete next.models;
|
|
36267
|
+
function redactRowForMode(row, mode) {
|
|
36268
|
+
if (mode === "off")
|
|
36269
|
+
return null;
|
|
36270
|
+
if (mode === "full")
|
|
36271
|
+
return row;
|
|
36272
|
+
if (row.kind === "planner") {
|
|
36273
|
+
return row.brief === void 0 ? row : { ...row, brief: head(row.brief, exports2.DUET_ROUTING_LOG_HEAD_CHARS) };
|
|
36315
36274
|
}
|
|
36316
|
-
if (
|
|
36317
|
-
|
|
36318
|
-
|
|
36319
|
-
|
|
36320
|
-
|
|
36321
|
-
|
|
36275
|
+
if (row.kind !== "decision")
|
|
36276
|
+
return row;
|
|
36277
|
+
return {
|
|
36278
|
+
...row,
|
|
36279
|
+
prompt: head(row.prompt, exports2.DUET_ROUTING_LOG_HEAD_CHARS),
|
|
36280
|
+
assumptions: row.assumptions.map((a) => ({ id: a.id, text: head(a.text, 100) }))
|
|
36281
|
+
};
|
|
36282
|
+
}
|
|
36283
|
+
var writeQueues = /* @__PURE__ */ new Map();
|
|
36284
|
+
async function writeRow(row, file, opts) {
|
|
36285
|
+
const redacted = redactRowForMode(row, await duetRoutingLogMode2(opts));
|
|
36286
|
+
if (redacted === null)
|
|
36287
|
+
return;
|
|
36288
|
+
await fs15.mkdir(path14.dirname(file), { recursive: true });
|
|
36289
|
+
try {
|
|
36290
|
+
const stat = await fs15.stat(file);
|
|
36291
|
+
if (stat.size >= exports2.DUET_ROUTING_LOG_MAX_BYTES)
|
|
36292
|
+
await fs15.rename(file, `${file}.1`);
|
|
36293
|
+
} catch {
|
|
36322
36294
|
}
|
|
36323
|
-
await (
|
|
36324
|
-
|
|
36325
|
-
return true;
|
|
36295
|
+
await fs15.appendFile(file, `${JSON.stringify(redacted)}
|
|
36296
|
+
`, "utf8");
|
|
36326
36297
|
}
|
|
36327
|
-
|
|
36328
|
-
|
|
36329
|
-
|
|
36330
|
-
|
|
36331
|
-
|
|
36332
|
-
|
|
36333
|
-
|
|
36334
|
-
|
|
36335
|
-
|
|
36336
|
-
|
|
36337
|
-
|
|
36338
|
-
exports2.isLocalExecutorChoice = isLocalExecutorChoice;
|
|
36339
|
-
exports2.resolveDuetExecutorChoice = resolveDuetExecutorChoice2;
|
|
36340
|
-
var customProviders_js_1 = require_customProviders();
|
|
36341
|
-
var customProviderModels_js_1 = require_customProviderModels();
|
|
36342
|
-
exports2.LOCAL_EXECUTOR_READ_BUDGET_MS = 3e3;
|
|
36343
|
-
async function localExecutorOptions2(input = {}) {
|
|
36344
|
-
const { catalog, timeoutMs, ...opts } = input;
|
|
36345
|
-
let entries;
|
|
36298
|
+
async function appendDuetRoutingRow(row, opts = {}) {
|
|
36299
|
+
const file = duetRoutingLogPath2(opts);
|
|
36300
|
+
const previous = writeQueues.get(file) ?? Promise.resolve();
|
|
36301
|
+
const next = previous.then(() => writeRow(row, file, opts)).catch(() => void 0);
|
|
36302
|
+
writeQueues.set(file, next);
|
|
36303
|
+
await next;
|
|
36304
|
+
if (writeQueues.get(file) === next)
|
|
36305
|
+
writeQueues.delete(file);
|
|
36306
|
+
}
|
|
36307
|
+
async function readDuetRoutingLog2(opts = {}) {
|
|
36308
|
+
let text;
|
|
36346
36309
|
try {
|
|
36347
|
-
|
|
36310
|
+
text = await fs15.readFile(duetRoutingLogPath2(opts), "utf8");
|
|
36348
36311
|
} catch {
|
|
36349
36312
|
return [];
|
|
36350
36313
|
}
|
|
36351
|
-
|
|
36352
|
-
|
|
36353
|
-
|
|
36314
|
+
const rows = [];
|
|
36315
|
+
for (const line of text.split("\n")) {
|
|
36316
|
+
if (line.trim() === "")
|
|
36317
|
+
continue;
|
|
36354
36318
|
try {
|
|
36355
|
-
const
|
|
36356
|
-
|
|
36357
|
-
|
|
36358
|
-
|
|
36359
|
-
endpoint: entry.name,
|
|
36360
|
-
model: view.id,
|
|
36361
|
-
pinned: view.pinned
|
|
36362
|
-
};
|
|
36363
|
-
if (view.contextWindow !== void 0)
|
|
36364
|
-
option.contextWindow = view.contextWindow;
|
|
36365
|
-
if (view.maxOutputTokens !== void 0)
|
|
36366
|
-
option.maxOutputTokens = view.maxOutputTokens;
|
|
36367
|
-
return option;
|
|
36368
|
-
});
|
|
36319
|
+
const parsed = JSON.parse(line);
|
|
36320
|
+
if (parsed.kind === "decision" || parsed.kind === "turn_end" || parsed.kind === "followup" || parsed.kind === "planner") {
|
|
36321
|
+
rows.push(parsed);
|
|
36322
|
+
}
|
|
36369
36323
|
} catch {
|
|
36370
|
-
return [];
|
|
36371
36324
|
}
|
|
36372
|
-
})).then((perEndpoint) => perEndpoint.flat());
|
|
36373
|
-
const full = read(catalog ?? {});
|
|
36374
|
-
const budget = timeoutMs ?? exports2.LOCAL_EXECUTOR_READ_BUDGET_MS;
|
|
36375
|
-
if (catalog?.cachedOnly === true || budget <= 0)
|
|
36376
|
-
return full;
|
|
36377
|
-
let timer;
|
|
36378
|
-
const fallback = new Promise((resolve5) => {
|
|
36379
|
-
timer = setTimeout(() => resolve5(read({ ...catalog, cachedOnly: true })), budget);
|
|
36380
|
-
});
|
|
36381
|
-
try {
|
|
36382
|
-
return await Promise.race([full, fallback]);
|
|
36383
|
-
} finally {
|
|
36384
|
-
if (timer !== void 0)
|
|
36385
|
-
clearTimeout(timer);
|
|
36386
|
-
void full.catch(() => void 0);
|
|
36387
36325
|
}
|
|
36326
|
+
return rows;
|
|
36388
36327
|
}
|
|
36389
|
-
function
|
|
36390
|
-
|
|
36391
|
-
|
|
36392
|
-
|
|
36393
|
-
|
|
36328
|
+
function summarizeDuetRoutingLog2(rows) {
|
|
36329
|
+
const summary = {
|
|
36330
|
+
decisions: 0,
|
|
36331
|
+
routes: { plan: 0, execute: 0 },
|
|
36332
|
+
stage1PlanReasons: {},
|
|
36333
|
+
advisorEvaluated: 0,
|
|
36334
|
+
advisorFlagged: {},
|
|
36335
|
+
turnEnds: { completed: 0, error: 0, cancelled: 0 },
|
|
36336
|
+
followups: 0,
|
|
36337
|
+
missedEscalations: 0,
|
|
36338
|
+
flaggedWithoutNewPlan: 0,
|
|
36339
|
+
flaggedBarelyChanged: 0,
|
|
36340
|
+
repeats: 0,
|
|
36341
|
+
entries: { planner: 0, router: 0, executor: 0 },
|
|
36342
|
+
plannerVerdicts: { hand_off: 0, plan: 0 }
|
|
36394
36343
|
};
|
|
36395
|
-
|
|
36396
|
-
|
|
36397
|
-
|
|
36398
|
-
|
|
36399
|
-
|
|
36400
|
-
|
|
36401
|
-
|
|
36402
|
-
|
|
36403
|
-
|
|
36404
|
-
|
|
36405
|
-
|
|
36406
|
-
|
|
36407
|
-
|
|
36408
|
-
|
|
36409
|
-
|
|
36410
|
-
|
|
36411
|
-
|
|
36412
|
-
|
|
36413
|
-
|
|
36344
|
+
const decisions = /* @__PURE__ */ new Map();
|
|
36345
|
+
for (const row of rows) {
|
|
36346
|
+
if (row.kind !== "decision")
|
|
36347
|
+
continue;
|
|
36348
|
+
decisions.set(row.id, row);
|
|
36349
|
+
summary.decisions += 1;
|
|
36350
|
+
summary.routes[row.route] += 1;
|
|
36351
|
+
summary.entries[row.entry ?? "router"] += 1;
|
|
36352
|
+
if (row.stage1.verdict === "plan") {
|
|
36353
|
+
summary.stage1PlanReasons[row.stage1.reason] = (summary.stage1PlanReasons[row.stage1.reason] ?? 0) + 1;
|
|
36354
|
+
}
|
|
36355
|
+
if (row.advisor !== null) {
|
|
36356
|
+
summary.advisorEvaluated += 1;
|
|
36357
|
+
if (row.advisor.reason !== null) {
|
|
36358
|
+
summary.advisorFlagged[row.advisor.reason] = (summary.advisorFlagged[row.advisor.reason] ?? 0) + 1;
|
|
36359
|
+
}
|
|
36360
|
+
}
|
|
36361
|
+
}
|
|
36362
|
+
for (const row of rows) {
|
|
36363
|
+
if (row.kind === "turn_end") {
|
|
36364
|
+
summary.turnEnds[row.outcome] += 1;
|
|
36365
|
+
} else if (row.kind === "planner") {
|
|
36366
|
+
summary.plannerVerdicts[row.verdict] += 1;
|
|
36367
|
+
} else if (row.kind === "followup") {
|
|
36368
|
+
summary.followups += 1;
|
|
36369
|
+
const decided = decisions.get(row.decisionId);
|
|
36370
|
+
if (row.nextPromptSimilarity !== null && row.nextPromptSimilarity >= 0.8)
|
|
36371
|
+
summary.repeats += 1;
|
|
36372
|
+
if (decided === void 0)
|
|
36373
|
+
continue;
|
|
36374
|
+
if (decided.route === "execute" && (row.replanActor || row.nextExplicitPlanRequest)) {
|
|
36375
|
+
summary.missedEscalations += 1;
|
|
36376
|
+
}
|
|
36377
|
+
if (decided.advisor?.flagged) {
|
|
36378
|
+
if (!row.planVersionChanged)
|
|
36379
|
+
summary.flaggedWithoutNewPlan += 1;
|
|
36380
|
+
else if (row.planDiffRatio !== null && row.planDiffRatio < 0.1)
|
|
36381
|
+
summary.flaggedBarelyChanged += 1;
|
|
36382
|
+
}
|
|
36383
|
+
}
|
|
36384
|
+
}
|
|
36385
|
+
return summary;
|
|
36386
|
+
}
|
|
36387
|
+
function formatDuetRoutingLogSummary2(summary, file, mode) {
|
|
36388
|
+
const byKey = (m2) => Object.entries(m2).sort((a, b2) => b2[1] - a[1]).map(([k, n]) => `${k} ${n}`).join(", ") || "none";
|
|
36389
|
+
return [
|
|
36390
|
+
`Duet routing journal: ${file} (mode: ${mode})`,
|
|
36391
|
+
`decisions ${summary.decisions} \u2014 plan ${summary.routes.plan}, execute ${summary.routes.execute}`,
|
|
36392
|
+
`entry: planner ${summary.entries.planner}, router ${summary.entries.router}, executor ${summary.entries.executor}`,
|
|
36393
|
+
`planner verdicts: handed off ${summary.plannerVerdicts.hand_off}, planned ${summary.plannerVerdicts.plan}`,
|
|
36394
|
+
`stage-1 plan rules: ${byKey(summary.stage1PlanReasons)}`,
|
|
36395
|
+
`advisor evaluated ${summary.advisorEvaluated}; flagged: ${byKey(summary.advisorFlagged)}`,
|
|
36396
|
+
`turn ends \u2014 completed ${summary.turnEnds.completed}, error ${summary.turnEnds.error}, cancelled ${summary.turnEnds.cancelled}`,
|
|
36397
|
+
`follow-ups ${summary.followups} \u2014 missed escalations ${summary.missedEscalations}, flagged without a new plan ${summary.flaggedWithoutNewPlan}, flagged but barely changed ${summary.flaggedBarelyChanged}, repeats ${summary.repeats}`
|
|
36398
|
+
];
|
|
36399
|
+
}
|
|
36400
|
+
}
|
|
36401
|
+
});
|
|
36402
|
+
|
|
36403
|
+
// ../packages/orion-client-core/dist/duetRoutingSignals.js
|
|
36404
|
+
var require_duetRoutingSignals = __commonJS({
|
|
36405
|
+
"../packages/orion-client-core/dist/duetRoutingSignals.js"(exports2) {
|
|
36406
|
+
"use strict";
|
|
36407
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
36408
|
+
exports2.ROUTING_JUDGE_MAX_TOKENS = exports2.ROUTING_JUDGE_TIMEOUT_MS = exports2.ROUTING_SIGNAL_TIMEOUT_MS = void 0;
|
|
36414
36409
|
exports2.cosineSimilarity = cosineSimilarity;
|
|
36415
36410
|
exports2.normalizeRerankScores = normalizeRerankScores;
|
|
36416
36411
|
exports2.buildJudgeMessages = buildJudgeMessages;
|
|
@@ -36584,276 +36579,6 @@ Does this message invalidate any plan assumption or require architectural re-pla
|
|
|
36584
36579
|
}
|
|
36585
36580
|
});
|
|
36586
36581
|
|
|
36587
|
-
// ../packages/orion-client-core/dist/duetRoutingLog.js
|
|
36588
|
-
var require_duetRoutingLog = __commonJS({
|
|
36589
|
-
"../packages/orion-client-core/dist/duetRoutingLog.js"(exports2) {
|
|
36590
|
-
"use strict";
|
|
36591
|
-
var __createBinding = exports2 && exports2.__createBinding || (Object.create ? function(o, m2, k, k2) {
|
|
36592
|
-
if (k2 === void 0) k2 = k;
|
|
36593
|
-
var desc = Object.getOwnPropertyDescriptor(m2, k);
|
|
36594
|
-
if (!desc || ("get" in desc ? !m2.__esModule : desc.writable || desc.configurable)) {
|
|
36595
|
-
desc = { enumerable: true, get: function() {
|
|
36596
|
-
return m2[k];
|
|
36597
|
-
} };
|
|
36598
|
-
}
|
|
36599
|
-
Object.defineProperty(o, k2, desc);
|
|
36600
|
-
} : function(o, m2, k, k2) {
|
|
36601
|
-
if (k2 === void 0) k2 = k;
|
|
36602
|
-
o[k2] = m2[k];
|
|
36603
|
-
});
|
|
36604
|
-
var __setModuleDefault = exports2 && exports2.__setModuleDefault || (Object.create ? function(o, v2) {
|
|
36605
|
-
Object.defineProperty(o, "default", { enumerable: true, value: v2 });
|
|
36606
|
-
} : function(o, v2) {
|
|
36607
|
-
o["default"] = v2;
|
|
36608
|
-
});
|
|
36609
|
-
var __importStar = exports2 && exports2.__importStar || /* @__PURE__ */ function() {
|
|
36610
|
-
var ownKeys = function(o) {
|
|
36611
|
-
ownKeys = Object.getOwnPropertyNames || function(o2) {
|
|
36612
|
-
var ar = [];
|
|
36613
|
-
for (var k in o2) if (Object.prototype.hasOwnProperty.call(o2, k)) ar[ar.length] = k;
|
|
36614
|
-
return ar;
|
|
36615
|
-
};
|
|
36616
|
-
return ownKeys(o);
|
|
36617
|
-
};
|
|
36618
|
-
return function(mod2) {
|
|
36619
|
-
if (mod2 && mod2.__esModule) return mod2;
|
|
36620
|
-
var result = {};
|
|
36621
|
-
if (mod2 != null) {
|
|
36622
|
-
for (var k = ownKeys(mod2), i2 = 0; i2 < k.length; i2++) if (k[i2] !== "default") __createBinding(result, mod2, k[i2]);
|
|
36623
|
-
}
|
|
36624
|
-
__setModuleDefault(result, mod2);
|
|
36625
|
-
return result;
|
|
36626
|
-
};
|
|
36627
|
-
}();
|
|
36628
|
-
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
36629
|
-
exports2.DUET_ROUTING_LOG_DEFAULT_MODE = exports2.DUET_ROUTING_LOG_KEY = exports2.DUET_ROUTING_LOG_HEAD_CHARS = exports2.DUET_ROUTING_LOG_MAX_BYTES = exports2.DUET_ROUTING_LOG_SCHEMA = void 0;
|
|
36630
|
-
exports2.duetRoutingLogPath = duetRoutingLogPath2;
|
|
36631
|
-
exports2.newDecisionId = newDecisionId;
|
|
36632
|
-
exports2.sessionKey = sessionKey;
|
|
36633
|
-
exports2.lexicalSimilarity = lexicalSimilarity;
|
|
36634
|
-
exports2.planDiffRatio = planDiffRatio;
|
|
36635
|
-
exports2.clearDuetRoutingLogCache = clearDuetRoutingLogCache;
|
|
36636
|
-
exports2.duetRoutingLogMode = duetRoutingLogMode2;
|
|
36637
|
-
exports2.redactRowForMode = redactRowForMode;
|
|
36638
|
-
exports2.appendDuetRoutingRow = appendDuetRoutingRow;
|
|
36639
|
-
exports2.readDuetRoutingLog = readDuetRoutingLog2;
|
|
36640
|
-
exports2.summarizeDuetRoutingLog = summarizeDuetRoutingLog2;
|
|
36641
|
-
exports2.formatDuetRoutingLogSummary = formatDuetRoutingLogSummary2;
|
|
36642
|
-
var node_crypto_1 = __require("node:crypto");
|
|
36643
|
-
var fs15 = __importStar(__require("node:fs/promises"));
|
|
36644
|
-
var os9 = __importStar(__require("node:os"));
|
|
36645
|
-
var path14 = __importStar(__require("node:path"));
|
|
36646
|
-
var settingsPaths_js_1 = require_settingsPaths();
|
|
36647
|
-
exports2.DUET_ROUTING_LOG_SCHEMA = 3;
|
|
36648
|
-
exports2.DUET_ROUTING_LOG_MAX_BYTES = 5 * 1024 * 1024;
|
|
36649
|
-
exports2.DUET_ROUTING_LOG_HEAD_CHARS = 200;
|
|
36650
|
-
exports2.DUET_ROUTING_LOG_KEY = "duetRoutingLog";
|
|
36651
|
-
exports2.DUET_ROUTING_LOG_DEFAULT_MODE = "full";
|
|
36652
|
-
function duetRoutingLogPath2(opts = {}) {
|
|
36653
|
-
return path14.join(opts.homeDir ?? os9.homedir(), ".orion", "duet-routing-decisions.jsonl");
|
|
36654
|
-
}
|
|
36655
|
-
function newDecisionId() {
|
|
36656
|
-
return (0, node_crypto_1.randomUUID)();
|
|
36657
|
-
}
|
|
36658
|
-
function sessionKey(sessionId) {
|
|
36659
|
-
if (sessionId === void 0 || sessionId === "")
|
|
36660
|
-
return void 0;
|
|
36661
|
-
return (0, node_crypto_1.createHash)("sha256").update(sessionId).digest("hex").slice(0, 12);
|
|
36662
|
-
}
|
|
36663
|
-
function tokens(text) {
|
|
36664
|
-
return new Set(text.toLowerCase().split(/[^a-z0-9]+/).filter((t) => t.length > 1));
|
|
36665
|
-
}
|
|
36666
|
-
function jaccard(a, b2) {
|
|
36667
|
-
if (a.size === 0 && b2.size === 0)
|
|
36668
|
-
return 1;
|
|
36669
|
-
let inter = 0;
|
|
36670
|
-
for (const t of a)
|
|
36671
|
-
if (b2.has(t))
|
|
36672
|
-
inter += 1;
|
|
36673
|
-
const union = a.size + b2.size - inter;
|
|
36674
|
-
return union === 0 ? 0 : inter / union;
|
|
36675
|
-
}
|
|
36676
|
-
function lexicalSimilarity(a, b2) {
|
|
36677
|
-
return Math.round(jaccard(tokens(a), tokens(b2)) * 1e3) / 1e3;
|
|
36678
|
-
}
|
|
36679
|
-
function planDiffRatio(before, after) {
|
|
36680
|
-
const lines = (plan) => new Set(plan.split(/\r?\n/).map((l3) => l3.trim()).filter((l3) => l3 !== ""));
|
|
36681
|
-
return Math.round((1 - jaccard(lines(before), lines(after))) * 1e3) / 1e3;
|
|
36682
|
-
}
|
|
36683
|
-
var MODE_CACHE_TTL_MS = 5e3;
|
|
36684
|
-
var modeCache = /* @__PURE__ */ new Map();
|
|
36685
|
-
function clearDuetRoutingLogCache() {
|
|
36686
|
-
modeCache.clear();
|
|
36687
|
-
}
|
|
36688
|
-
function coerceMode(raw) {
|
|
36689
|
-
return raw === "full" || raw === "head" || raw === "off" ? raw : null;
|
|
36690
|
-
}
|
|
36691
|
-
async function readTierMode(file) {
|
|
36692
|
-
if (file === null)
|
|
36693
|
-
return null;
|
|
36694
|
-
try {
|
|
36695
|
-
const parsed = JSON.parse(await fs15.readFile(file, "utf8"));
|
|
36696
|
-
return coerceMode(parsed?.[exports2.DUET_ROUTING_LOG_KEY]?.mode);
|
|
36697
|
-
} catch {
|
|
36698
|
-
return null;
|
|
36699
|
-
}
|
|
36700
|
-
}
|
|
36701
|
-
async function duetRoutingLogMode2(opts = {}) {
|
|
36702
|
-
const home = opts.homeDir ?? os9.homedir();
|
|
36703
|
-
const ws = opts.workspaceRoot ?? null;
|
|
36704
|
-
const key = `${home}\0${ws ?? ""}`;
|
|
36705
|
-
const hit = modeCache.get(key);
|
|
36706
|
-
if (hit !== void 0 && Date.now() - hit.at < MODE_CACHE_TTL_MS)
|
|
36707
|
-
return hit.mode;
|
|
36708
|
-
let mode = exports2.DUET_ROUTING_LOG_DEFAULT_MODE;
|
|
36709
|
-
const tiers = ["user", "project", "local"];
|
|
36710
|
-
for (const tier of tiers) {
|
|
36711
|
-
const found = await readTierMode((0, settingsPaths_js_1.settingsFilePath)(tier, { homeDir: home, workspaceRoot: ws }));
|
|
36712
|
-
if (found !== null)
|
|
36713
|
-
mode = found;
|
|
36714
|
-
}
|
|
36715
|
-
modeCache.set(key, { at: Date.now(), mode });
|
|
36716
|
-
return mode;
|
|
36717
|
-
}
|
|
36718
|
-
function head(text, max) {
|
|
36719
|
-
return text.length > max ? `${text.slice(0, max - 1)}\u2026` : text;
|
|
36720
|
-
}
|
|
36721
|
-
function redactRowForMode(row, mode) {
|
|
36722
|
-
if (mode === "off")
|
|
36723
|
-
return null;
|
|
36724
|
-
if (mode === "full")
|
|
36725
|
-
return row;
|
|
36726
|
-
if (row.kind === "planner") {
|
|
36727
|
-
return row.brief === void 0 ? row : { ...row, brief: head(row.brief, exports2.DUET_ROUTING_LOG_HEAD_CHARS) };
|
|
36728
|
-
}
|
|
36729
|
-
if (row.kind !== "decision")
|
|
36730
|
-
return row;
|
|
36731
|
-
return {
|
|
36732
|
-
...row,
|
|
36733
|
-
prompt: head(row.prompt, exports2.DUET_ROUTING_LOG_HEAD_CHARS),
|
|
36734
|
-
assumptions: row.assumptions.map((a) => ({ id: a.id, text: head(a.text, 100) }))
|
|
36735
|
-
};
|
|
36736
|
-
}
|
|
36737
|
-
var writeQueues = /* @__PURE__ */ new Map();
|
|
36738
|
-
async function writeRow(row, file, opts) {
|
|
36739
|
-
const redacted = redactRowForMode(row, await duetRoutingLogMode2(opts));
|
|
36740
|
-
if (redacted === null)
|
|
36741
|
-
return;
|
|
36742
|
-
await fs15.mkdir(path14.dirname(file), { recursive: true });
|
|
36743
|
-
try {
|
|
36744
|
-
const stat = await fs15.stat(file);
|
|
36745
|
-
if (stat.size >= exports2.DUET_ROUTING_LOG_MAX_BYTES)
|
|
36746
|
-
await fs15.rename(file, `${file}.1`);
|
|
36747
|
-
} catch {
|
|
36748
|
-
}
|
|
36749
|
-
await fs15.appendFile(file, `${JSON.stringify(redacted)}
|
|
36750
|
-
`, "utf8");
|
|
36751
|
-
}
|
|
36752
|
-
async function appendDuetRoutingRow(row, opts = {}) {
|
|
36753
|
-
const file = duetRoutingLogPath2(opts);
|
|
36754
|
-
const previous = writeQueues.get(file) ?? Promise.resolve();
|
|
36755
|
-
const next = previous.then(() => writeRow(row, file, opts)).catch(() => void 0);
|
|
36756
|
-
writeQueues.set(file, next);
|
|
36757
|
-
await next;
|
|
36758
|
-
if (writeQueues.get(file) === next)
|
|
36759
|
-
writeQueues.delete(file);
|
|
36760
|
-
}
|
|
36761
|
-
async function readDuetRoutingLog2(opts = {}) {
|
|
36762
|
-
let text;
|
|
36763
|
-
try {
|
|
36764
|
-
text = await fs15.readFile(duetRoutingLogPath2(opts), "utf8");
|
|
36765
|
-
} catch {
|
|
36766
|
-
return [];
|
|
36767
|
-
}
|
|
36768
|
-
const rows = [];
|
|
36769
|
-
for (const line of text.split("\n")) {
|
|
36770
|
-
if (line.trim() === "")
|
|
36771
|
-
continue;
|
|
36772
|
-
try {
|
|
36773
|
-
const parsed = JSON.parse(line);
|
|
36774
|
-
if (parsed.kind === "decision" || parsed.kind === "turn_end" || parsed.kind === "followup" || parsed.kind === "planner") {
|
|
36775
|
-
rows.push(parsed);
|
|
36776
|
-
}
|
|
36777
|
-
} catch {
|
|
36778
|
-
}
|
|
36779
|
-
}
|
|
36780
|
-
return rows;
|
|
36781
|
-
}
|
|
36782
|
-
function summarizeDuetRoutingLog2(rows) {
|
|
36783
|
-
const summary = {
|
|
36784
|
-
decisions: 0,
|
|
36785
|
-
routes: { plan: 0, execute: 0 },
|
|
36786
|
-
stage1PlanReasons: {},
|
|
36787
|
-
advisorEvaluated: 0,
|
|
36788
|
-
advisorFlagged: {},
|
|
36789
|
-
turnEnds: { completed: 0, error: 0, cancelled: 0 },
|
|
36790
|
-
followups: 0,
|
|
36791
|
-
missedEscalations: 0,
|
|
36792
|
-
flaggedWithoutNewPlan: 0,
|
|
36793
|
-
flaggedBarelyChanged: 0,
|
|
36794
|
-
repeats: 0,
|
|
36795
|
-
entries: { planner: 0, router: 0 },
|
|
36796
|
-
plannerVerdicts: { hand_off: 0, plan: 0 }
|
|
36797
|
-
};
|
|
36798
|
-
const decisions = /* @__PURE__ */ new Map();
|
|
36799
|
-
for (const row of rows) {
|
|
36800
|
-
if (row.kind !== "decision")
|
|
36801
|
-
continue;
|
|
36802
|
-
decisions.set(row.id, row);
|
|
36803
|
-
summary.decisions += 1;
|
|
36804
|
-
summary.routes[row.route] += 1;
|
|
36805
|
-
summary.entries[row.entry ?? "router"] += 1;
|
|
36806
|
-
if (row.stage1.verdict === "plan") {
|
|
36807
|
-
summary.stage1PlanReasons[row.stage1.reason] = (summary.stage1PlanReasons[row.stage1.reason] ?? 0) + 1;
|
|
36808
|
-
}
|
|
36809
|
-
if (row.advisor !== null) {
|
|
36810
|
-
summary.advisorEvaluated += 1;
|
|
36811
|
-
if (row.advisor.reason !== null) {
|
|
36812
|
-
summary.advisorFlagged[row.advisor.reason] = (summary.advisorFlagged[row.advisor.reason] ?? 0) + 1;
|
|
36813
|
-
}
|
|
36814
|
-
}
|
|
36815
|
-
}
|
|
36816
|
-
for (const row of rows) {
|
|
36817
|
-
if (row.kind === "turn_end") {
|
|
36818
|
-
summary.turnEnds[row.outcome] += 1;
|
|
36819
|
-
} else if (row.kind === "planner") {
|
|
36820
|
-
summary.plannerVerdicts[row.verdict] += 1;
|
|
36821
|
-
} else if (row.kind === "followup") {
|
|
36822
|
-
summary.followups += 1;
|
|
36823
|
-
const decided = decisions.get(row.decisionId);
|
|
36824
|
-
if (row.nextPromptSimilarity !== null && row.nextPromptSimilarity >= 0.8)
|
|
36825
|
-
summary.repeats += 1;
|
|
36826
|
-
if (decided === void 0)
|
|
36827
|
-
continue;
|
|
36828
|
-
if (decided.route === "execute" && (row.replanActor || row.nextExplicitPlanRequest)) {
|
|
36829
|
-
summary.missedEscalations += 1;
|
|
36830
|
-
}
|
|
36831
|
-
if (decided.advisor?.flagged) {
|
|
36832
|
-
if (!row.planVersionChanged)
|
|
36833
|
-
summary.flaggedWithoutNewPlan += 1;
|
|
36834
|
-
else if (row.planDiffRatio !== null && row.planDiffRatio < 0.1)
|
|
36835
|
-
summary.flaggedBarelyChanged += 1;
|
|
36836
|
-
}
|
|
36837
|
-
}
|
|
36838
|
-
}
|
|
36839
|
-
return summary;
|
|
36840
|
-
}
|
|
36841
|
-
function formatDuetRoutingLogSummary2(summary, file, mode) {
|
|
36842
|
-
const byKey = (m2) => Object.entries(m2).sort((a, b2) => b2[1] - a[1]).map(([k, n]) => `${k} ${n}`).join(", ") || "none";
|
|
36843
|
-
return [
|
|
36844
|
-
`Duet routing journal: ${file} (mode: ${mode})`,
|
|
36845
|
-
`decisions ${summary.decisions} \u2014 plan ${summary.routes.plan}, execute ${summary.routes.execute}`,
|
|
36846
|
-
`entry: planner ${summary.entries.planner}, router ${summary.entries.router}`,
|
|
36847
|
-
`planner verdicts: handed off ${summary.plannerVerdicts.hand_off}, planned ${summary.plannerVerdicts.plan}`,
|
|
36848
|
-
`stage-1 plan rules: ${byKey(summary.stage1PlanReasons)}`,
|
|
36849
|
-
`advisor evaluated ${summary.advisorEvaluated}; flagged: ${byKey(summary.advisorFlagged)}`,
|
|
36850
|
-
`turn ends \u2014 completed ${summary.turnEnds.completed}, error ${summary.turnEnds.error}, cancelled ${summary.turnEnds.cancelled}`,
|
|
36851
|
-
`follow-ups ${summary.followups} \u2014 missed escalations ${summary.missedEscalations}, flagged without a new plan ${summary.flaggedWithoutNewPlan}, flagged but barely changed ${summary.flaggedBarelyChanged}, repeats ${summary.repeats}`
|
|
36852
|
-
];
|
|
36853
|
-
}
|
|
36854
|
-
}
|
|
36855
|
-
});
|
|
36856
|
-
|
|
36857
36582
|
// ../packages/orion-client-core/dist/duetRoutingAdvisor.js
|
|
36858
36583
|
var require_duetRoutingAdvisor = __commonJS({
|
|
36859
36584
|
"../packages/orion-client-core/dist/duetRoutingAdvisor.js"(exports2) {
|
|
@@ -37165,303 +36890,1196 @@ var require_duetRoutingAdvisor = __commonJS({
|
|
|
37165
36890
|
state.backoffUntil = now2() + exports2.DUET_ADVISOR_FAILURE_BACKOFF_MS;
|
|
37166
36891
|
return candidate;
|
|
37167
36892
|
}
|
|
37168
|
-
function sinkFor(log, homeDir, workspaceRoot) {
|
|
37169
|
-
if (log === null)
|
|
36893
|
+
function sinkFor(log, homeDir, workspaceRoot) {
|
|
36894
|
+
if (log === null)
|
|
36895
|
+
return null;
|
|
36896
|
+
if (log !== void 0)
|
|
36897
|
+
return log;
|
|
36898
|
+
return (row) => (0, duetRoutingLog_js_1.appendDuetRoutingRow)(row, { homeDir, workspaceRoot: workspaceRoot ?? null });
|
|
36899
|
+
}
|
|
36900
|
+
function emit(sink, row) {
|
|
36901
|
+
if (sink === null)
|
|
36902
|
+
return;
|
|
36903
|
+
try {
|
|
36904
|
+
void Promise.resolve(sink(row)).catch(() => void 0);
|
|
36905
|
+
} catch {
|
|
36906
|
+
}
|
|
36907
|
+
}
|
|
36908
|
+
function scorerReason(verdict, highRisk) {
|
|
36909
|
+
const base = verdict.source === "executor_gate" ? "executor_gate" : "router_model";
|
|
36910
|
+
return highRisk ? `${base}_high_risk` : base;
|
|
36911
|
+
}
|
|
36912
|
+
function stage1Verdict(record, text, entry, verdict = null) {
|
|
36913
|
+
if ((0, duetPlan_js_1.explicitPlanRequest)(text))
|
|
36914
|
+
return { verdict: "plan", reason: "explicit_plan_request" };
|
|
36915
|
+
if (record === null) {
|
|
36916
|
+
if ((0, duetPlan_js_1.highRiskRequest)(text))
|
|
36917
|
+
return { verdict: "plan", reason: "plan_invalid" };
|
|
36918
|
+
if (entry === "planner")
|
|
36919
|
+
return { verdict: "plan", reason: "planner_entry" };
|
|
36920
|
+
if (verdict?.verdict === "plan")
|
|
36921
|
+
return { verdict: "plan", reason: scorerReason(verdict, false) };
|
|
36922
|
+
if (verdict?.highRisk)
|
|
36923
|
+
return { verdict: "plan", reason: scorerReason(verdict, true) };
|
|
36924
|
+
return { verdict: "execute", reason: "no_plan" };
|
|
36925
|
+
}
|
|
36926
|
+
if (record.scopeChanged)
|
|
36927
|
+
return { verdict: "plan", reason: "scope_changed" };
|
|
36928
|
+
if (record.architectureDecisionRequired) {
|
|
36929
|
+
return { verdict: "plan", reason: "architecture_decision_required" };
|
|
36930
|
+
}
|
|
36931
|
+
if (record.planningFailures >= 2)
|
|
36932
|
+
return { verdict: "plan", reason: "failed_attempts" };
|
|
36933
|
+
if (record.userNegativeFeedback)
|
|
36934
|
+
return { verdict: "plan", reason: "negative_feedback" };
|
|
36935
|
+
if (entry === "planner") {
|
|
36936
|
+
return (0, duetPlan_js_1.continuationRequest)(text) ? { verdict: "execute", reason: "continuation" } : { verdict: "plan", reason: "planner_entry" };
|
|
36937
|
+
}
|
|
36938
|
+
if (verdict?.verdict === "plan")
|
|
36939
|
+
return { verdict: "plan", reason: scorerReason(verdict, false) };
|
|
36940
|
+
return { verdict: "execute", reason: "plan_valid" };
|
|
36941
|
+
}
|
|
36942
|
+
function executorContext(workspaceRoot) {
|
|
36943
|
+
const choice = (0, duetMode_js_1.duetExecutorWireForSegment)(workspaceRoot);
|
|
36944
|
+
const local = choice !== void 0 && (0, customProviders_js_1.isCustomProviderRef)(choice.provider);
|
|
36945
|
+
const models = local ? (0, customProviders_js_1.endpointRoutingFor)(choice.provider)?.routingModels : void 0;
|
|
36946
|
+
return {
|
|
36947
|
+
executor: local ? "local" : "platform",
|
|
36948
|
+
routingModels: {
|
|
36949
|
+
embeddings: models?.embeddings !== void 0,
|
|
36950
|
+
rerank: models?.rerank !== void 0,
|
|
36951
|
+
judge: models?.judge !== void 0
|
|
36952
|
+
}
|
|
36953
|
+
};
|
|
36954
|
+
}
|
|
36955
|
+
function followupRow(last, standing, text, at) {
|
|
36956
|
+
const versionChanged = standing !== null && standing.version !== last.planVersion;
|
|
36957
|
+
return {
|
|
36958
|
+
kind: "followup",
|
|
36959
|
+
v: duetRoutingLog_js_1.DUET_ROUTING_LOG_SCHEMA,
|
|
36960
|
+
decisionId: last.decisionId,
|
|
36961
|
+
at,
|
|
36962
|
+
planVersionChanged: versionChanged,
|
|
36963
|
+
newPlanVersion: versionChanged ? standing.version : null,
|
|
36964
|
+
planDiffRatio: versionChanged && last.planText !== null ? (0, duetRoutingLog_js_1.planDiffRatio)(last.planText, standing.plan) : null,
|
|
36965
|
+
replanActor: standing !== null && standing.scopeChanged && !last.scopeChanged,
|
|
36966
|
+
nextPromptSimilarity: text === "" ? null : (0, duetRoutingLog_js_1.lexicalSimilarity)(last.prompt, text),
|
|
36967
|
+
nextExplicitPlanRequest: text !== "" && (0, duetPlan_js_1.explicitPlanRequest)(text),
|
|
36968
|
+
planningFailuresDelta: standing === null ? 0 : standing.planningFailures - last.planningFailures,
|
|
36969
|
+
executorFailuresDelta: standing === null ? 0 : standing.executorFailures - last.executorFailures,
|
|
36970
|
+
planGone: last.planVersion > 0 && standing === null
|
|
36971
|
+
};
|
|
36972
|
+
}
|
|
36973
|
+
function journalDuetTurnEnd2(state, end, opts = {}) {
|
|
36974
|
+
const last = state.last;
|
|
36975
|
+
if (last === null)
|
|
36976
|
+
return;
|
|
36977
|
+
emit(sinkFor(opts.log, opts.homeDir, opts.workspaceRoot), {
|
|
36978
|
+
kind: "turn_end",
|
|
36979
|
+
v: duetRoutingLog_js_1.DUET_ROUTING_LOG_SCHEMA,
|
|
36980
|
+
decisionId: last.decisionId,
|
|
36981
|
+
at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
36982
|
+
outcome: end.outcome,
|
|
36983
|
+
executionLeg: end.executionLeg
|
|
36984
|
+
});
|
|
36985
|
+
}
|
|
36986
|
+
function journalDuetPlannerVerdict2(state, verdict, opts = {}) {
|
|
36987
|
+
const last = state.last;
|
|
36988
|
+
if (last === null)
|
|
36989
|
+
return;
|
|
36990
|
+
emit(sinkFor(opts.log, opts.homeDir, opts.workspaceRoot), {
|
|
36991
|
+
kind: "planner",
|
|
36992
|
+
v: duetRoutingLog_js_1.DUET_ROUTING_LOG_SCHEMA,
|
|
36993
|
+
decisionId: last.decisionId,
|
|
36994
|
+
at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
36995
|
+
verdict: verdict.verdict,
|
|
36996
|
+
...verdict.verdict === "hand_off" ? { brief: verdict.brief } : {}
|
|
36997
|
+
});
|
|
36998
|
+
}
|
|
36999
|
+
async function adviseDuetRoute2(input) {
|
|
37000
|
+
const { state } = input;
|
|
37001
|
+
const now2 = input.now ?? Date.now;
|
|
37002
|
+
const started = now2();
|
|
37003
|
+
const at = new Date(started).toISOString();
|
|
37004
|
+
const record = input.record ?? null;
|
|
37005
|
+
const entry = input.entry ?? "router";
|
|
37006
|
+
const routerVerdict = input.routerVerdict ? {
|
|
37007
|
+
model: input.routerVerdict.model,
|
|
37008
|
+
version: input.routerVerdict.version,
|
|
37009
|
+
verdict: input.routerVerdict.verdict,
|
|
37010
|
+
pPlan: Math.round(input.routerVerdict.pPlan * 1e6) / 1e6,
|
|
37011
|
+
asksForPlan: input.routerVerdict.asksForPlan,
|
|
37012
|
+
highRisk: input.routerVerdict.highRisk,
|
|
37013
|
+
reason: input.routerVerdict.reason,
|
|
37014
|
+
latencyMs: input.routerVerdict.latencyMs,
|
|
37015
|
+
source: input.routerVerdict.source,
|
|
37016
|
+
...input.routerVerdict.margin !== void 0 ? { margin: Math.round(input.routerVerdict.margin * 1e6) / 1e6 } : {},
|
|
37017
|
+
...input.routerVerdict.mode !== void 0 ? { mode: input.routerVerdict.mode } : {}
|
|
37018
|
+
} : null;
|
|
37019
|
+
const sink = sinkFor(input.log, input.homeDir, input.workspaceRoot);
|
|
37020
|
+
try {
|
|
37021
|
+
const text = input.text.trim();
|
|
37022
|
+
const standing = (0, duetPlan_js_1.duetPlanWireForSegment)(record) !== void 0 ? record : null;
|
|
37023
|
+
if (state.last !== null) {
|
|
37024
|
+
emit(sink, followupRow(state.last, standing, text, at));
|
|
37025
|
+
state.last = null;
|
|
37026
|
+
}
|
|
37027
|
+
const journal = (stage12, advisor, route, assumptions2) => {
|
|
37028
|
+
const id = (0, duetRoutingLog_js_1.newDecisionId)();
|
|
37029
|
+
const session = (0, duetRoutingLog_js_1.sessionKey)(input.sessionId);
|
|
37030
|
+
emit(sink, {
|
|
37031
|
+
kind: "decision",
|
|
37032
|
+
v: duetRoutingLog_js_1.DUET_ROUTING_LOG_SCHEMA,
|
|
37033
|
+
id,
|
|
37034
|
+
at,
|
|
37035
|
+
...session !== void 0 ? { session } : {},
|
|
37036
|
+
entry,
|
|
37037
|
+
planVersion: standing?.version ?? 0,
|
|
37038
|
+
turnUnderVersion: state.turnsUnderVersion,
|
|
37039
|
+
prompt: text,
|
|
37040
|
+
assumptions: assumptions2,
|
|
37041
|
+
...executorContext(input.workspaceRoot),
|
|
37042
|
+
stage1: stage12,
|
|
37043
|
+
router: routerVerdict,
|
|
37044
|
+
advisor: advisor === null ? null : {
|
|
37045
|
+
stage: advisor.stage,
|
|
37046
|
+
signals: advisor.signals,
|
|
37047
|
+
guards: advisor.guards,
|
|
37048
|
+
flagged: advisor.flagged,
|
|
37049
|
+
reason: advisor.reason
|
|
37050
|
+
},
|
|
37051
|
+
route,
|
|
37052
|
+
latencyMs: Math.max(0, now2() - started)
|
|
37053
|
+
});
|
|
37054
|
+
state.last = {
|
|
37055
|
+
decisionId: id,
|
|
37056
|
+
prompt: text,
|
|
37057
|
+
route,
|
|
37058
|
+
planVersion: standing?.version ?? 0,
|
|
37059
|
+
planText: standing?.plan ?? null,
|
|
37060
|
+
scopeChanged: standing?.scopeChanged ?? false,
|
|
37061
|
+
planningFailures: standing?.planningFailures ?? 0,
|
|
37062
|
+
executorFailures: standing?.executorFailures ?? 0
|
|
37063
|
+
};
|
|
37064
|
+
};
|
|
37065
|
+
if (standing === null) {
|
|
37066
|
+
resetForVersion(state, null);
|
|
37067
|
+
if (text !== "") {
|
|
37068
|
+
const stage12 = stage1Verdict(null, text, entry, input.routerVerdict ?? null);
|
|
37069
|
+
journal(stage12, null, stage12.verdict, []);
|
|
37070
|
+
}
|
|
37071
|
+
return untouched(record);
|
|
37072
|
+
}
|
|
37073
|
+
const plan = standing;
|
|
37074
|
+
if (state.planVersion !== plan.version)
|
|
37075
|
+
resetForVersion(state, plan.version);
|
|
37076
|
+
state.turnsUnderVersion += 1;
|
|
37077
|
+
if (text === "")
|
|
37078
|
+
return untouched(record);
|
|
37079
|
+
const assumptions = parsePlanAssumptions(plan.plan);
|
|
37080
|
+
const stage1 = stage1Verdict(plan, text, entry, input.routerVerdict ?? null);
|
|
37081
|
+
if (stage1.verdict === "plan") {
|
|
37082
|
+
journal(stage1, null, "plan", assumptions);
|
|
37083
|
+
return untouched(record);
|
|
37084
|
+
}
|
|
37085
|
+
if (entry === "planner") {
|
|
37086
|
+
journal(stage1, null, "execute", assumptions);
|
|
37087
|
+
return untouched(record);
|
|
37088
|
+
}
|
|
37089
|
+
const decision = {
|
|
37090
|
+
at,
|
|
37091
|
+
planVersion: plan.version,
|
|
37092
|
+
turnUnderVersion: state.turnsUnderVersion,
|
|
37093
|
+
text: text.length > DECISION_TEXT_HEAD ? `${text.slice(0, DECISION_TEXT_HEAD - 1)}\u2026` : text,
|
|
37094
|
+
stage: "cues",
|
|
37095
|
+
signals: {},
|
|
37096
|
+
guards: {},
|
|
37097
|
+
flagged: null,
|
|
37098
|
+
reason: null,
|
|
37099
|
+
latencyMs: 0
|
|
37100
|
+
};
|
|
37101
|
+
let candidate = null;
|
|
37102
|
+
const feedbackCue = negativeFeedbackCueIn(text);
|
|
37103
|
+
const negationCue = negationCueIn(text);
|
|
37104
|
+
if (feedbackCue !== null)
|
|
37105
|
+
decision.signals.feedbackCue = feedbackCue;
|
|
37106
|
+
if (negationCue !== null)
|
|
37107
|
+
decision.signals.negationCue = negationCue;
|
|
37108
|
+
if (feedbackCue !== null) {
|
|
37109
|
+
candidate = { flag: "user_negative_feedback", reason: "negative_feedback_cue", ids: [] };
|
|
37110
|
+
}
|
|
37111
|
+
if (candidate === null) {
|
|
37112
|
+
const endpoint = await advisorEndpoint(input.workspaceRoot);
|
|
37113
|
+
const models = endpoint?.routing.routingModels;
|
|
37114
|
+
if (endpoint !== null && models !== void 0) {
|
|
37115
|
+
candidate = await semanticStages({
|
|
37116
|
+
plan,
|
|
37117
|
+
assumptions,
|
|
37118
|
+
text,
|
|
37119
|
+
negationCue,
|
|
37120
|
+
dial: { baseUrl: endpoint.routing.baseUrl, apiKey: endpoint.routing.apiKey },
|
|
37121
|
+
models,
|
|
37122
|
+
executorModel: endpoint.executorModel,
|
|
37123
|
+
state,
|
|
37124
|
+
decision,
|
|
37125
|
+
fetchImpl: input.fetchImpl
|
|
37126
|
+
}, now2);
|
|
37127
|
+
}
|
|
37128
|
+
}
|
|
37129
|
+
if (candidate !== null && state.turnsUnderVersion < exports2.DUET_ADVISOR_THRESHOLDS.cooldownTurns) {
|
|
37130
|
+
decision.guards.cooldown = true;
|
|
37131
|
+
candidate = null;
|
|
37132
|
+
}
|
|
37133
|
+
let advised = plan;
|
|
37134
|
+
if (candidate !== null) {
|
|
37135
|
+
advised = candidate.flag === "user_negative_feedback" ? { ...plan, userNegativeFeedback: true } : { ...plan, architectureDecisionRequired: true };
|
|
37136
|
+
decision.flagged = candidate.flag;
|
|
37137
|
+
decision.reason = candidate.reason;
|
|
37138
|
+
}
|
|
37139
|
+
decision.latencyMs = Math.max(0, now2() - started);
|
|
37140
|
+
journal(stage1, decision, decision.flagged !== null ? "plan" : "execute", assumptions);
|
|
37141
|
+
return {
|
|
37142
|
+
record: advised,
|
|
37143
|
+
flagged: decision.flagged,
|
|
37144
|
+
reason: decision.reason,
|
|
37145
|
+
assumptionIds: candidate?.ids ?? [],
|
|
37146
|
+
decision,
|
|
37147
|
+
note: duetRoutingAdviceNote(decision.reason, candidate?.ids ?? [])
|
|
37148
|
+
};
|
|
37149
|
+
} catch {
|
|
37150
|
+
return untouched(record);
|
|
37151
|
+
}
|
|
37152
|
+
}
|
|
37153
|
+
function round3(value) {
|
|
37154
|
+
return Math.round(value * 1e3) / 1e3;
|
|
37155
|
+
}
|
|
37156
|
+
async function describeDuetRouting2(workspaceRoot) {
|
|
37157
|
+
try {
|
|
37158
|
+
const choice = await (0, duetMode_js_1.loadDuetExecutor)({ workspaceRoot: workspaceRoot ?? null });
|
|
37159
|
+
if (choice === null || !(0, customProviders_js_1.isCustomProviderRef)(choice.provider))
|
|
37160
|
+
return { kind: "platform" };
|
|
37161
|
+
const name2 = (0, customProviders_js_1.parseCustomProviderRef)(choice.provider) ?? "";
|
|
37162
|
+
const entry = await (0, customProviders_js_1.getCustomProvider)(name2, { workspaceRoot: workspaceRoot ?? null });
|
|
37163
|
+
if (entry === null)
|
|
37164
|
+
return { kind: "missing", name: name2 };
|
|
37165
|
+
return {
|
|
37166
|
+
kind: "local",
|
|
37167
|
+
name: name2,
|
|
37168
|
+
loopback: (0, customProviders_js_1.isLoopbackEndpoint)(entry.baseUrl),
|
|
37169
|
+
embeddings: entry.routingModels?.embeddings !== void 0,
|
|
37170
|
+
rerank: entry.routingModels?.rerank !== void 0,
|
|
37171
|
+
judge: entry.routingModels?.judge ?? null
|
|
37172
|
+
};
|
|
37173
|
+
} catch {
|
|
37174
|
+
return { kind: "platform" };
|
|
37175
|
+
}
|
|
37176
|
+
}
|
|
37177
|
+
function duetRoutingSummaryLine2(summary) {
|
|
37178
|
+
switch (summary.kind) {
|
|
37179
|
+
case "platform":
|
|
37180
|
+
return "Duet routing: rules only \u2014 a local executor with routing models unlocks re-ask detection and plan-assumption checks.";
|
|
37181
|
+
case "missing":
|
|
37182
|
+
return "Duet routing: rules only.";
|
|
37183
|
+
case "local": {
|
|
37184
|
+
const { name: name2, loopback, embeddings, rerank } = summary;
|
|
37185
|
+
if (!embeddings && !rerank) {
|
|
37186
|
+
return `Duet routing: rules only \u2014 add routingModels to '${name2}' to unlock re-ask detection and plan-assumption checks (the /local-ai skill can set this up).`;
|
|
37187
|
+
}
|
|
37188
|
+
if (!loopback) {
|
|
37189
|
+
return `Duet routing: rules only \u2014 semantic checks run only against a loopback endpoint, and '${name2}' is not one.`;
|
|
37190
|
+
}
|
|
37191
|
+
const parts2 = [];
|
|
37192
|
+
const via = [];
|
|
37193
|
+
if (embeddings) {
|
|
37194
|
+
parts2.push("re-ask detection");
|
|
37195
|
+
via.push("embeddings");
|
|
37196
|
+
}
|
|
37197
|
+
if (rerank) {
|
|
37198
|
+
parts2.push("plan-assumption checks");
|
|
37199
|
+
via.push("rerank");
|
|
37200
|
+
}
|
|
37201
|
+
return `Duet routing: rules + ${parts2.join(" + ")} (${via.join(" + ")} on '${name2}').`;
|
|
37202
|
+
}
|
|
37203
|
+
}
|
|
37204
|
+
}
|
|
37205
|
+
}
|
|
37206
|
+
});
|
|
37207
|
+
|
|
37208
|
+
// ../packages/orion-client-core/dist/duetExecutorGate.js
|
|
37209
|
+
var require_duetExecutorGate = __commonJS({
|
|
37210
|
+
"../packages/orion-client-core/dist/duetExecutorGate.js"(exports2) {
|
|
37211
|
+
"use strict";
|
|
37212
|
+
var __createBinding = exports2 && exports2.__createBinding || (Object.create ? function(o, m2, k, k2) {
|
|
37213
|
+
if (k2 === void 0) k2 = k;
|
|
37214
|
+
var desc = Object.getOwnPropertyDescriptor(m2, k);
|
|
37215
|
+
if (!desc || ("get" in desc ? !m2.__esModule : desc.writable || desc.configurable)) {
|
|
37216
|
+
desc = { enumerable: true, get: function() {
|
|
37217
|
+
return m2[k];
|
|
37218
|
+
} };
|
|
37219
|
+
}
|
|
37220
|
+
Object.defineProperty(o, k2, desc);
|
|
37221
|
+
} : function(o, m2, k, k2) {
|
|
37222
|
+
if (k2 === void 0) k2 = k;
|
|
37223
|
+
o[k2] = m2[k];
|
|
37224
|
+
});
|
|
37225
|
+
var __setModuleDefault = exports2 && exports2.__setModuleDefault || (Object.create ? function(o, v2) {
|
|
37226
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v2 });
|
|
37227
|
+
} : function(o, v2) {
|
|
37228
|
+
o["default"] = v2;
|
|
37229
|
+
});
|
|
37230
|
+
var __importStar = exports2 && exports2.__importStar || /* @__PURE__ */ function() {
|
|
37231
|
+
var ownKeys = function(o) {
|
|
37232
|
+
ownKeys = Object.getOwnPropertyNames || function(o2) {
|
|
37233
|
+
var ar = [];
|
|
37234
|
+
for (var k in o2) if (Object.prototype.hasOwnProperty.call(o2, k)) ar[ar.length] = k;
|
|
37235
|
+
return ar;
|
|
37236
|
+
};
|
|
37237
|
+
return ownKeys(o);
|
|
37238
|
+
};
|
|
37239
|
+
return function(mod2) {
|
|
37240
|
+
if (mod2 && mod2.__esModule) return mod2;
|
|
37241
|
+
var result = {};
|
|
37242
|
+
if (mod2 != null) {
|
|
37243
|
+
for (var k = ownKeys(mod2), i2 = 0; i2 < k.length; i2++) if (k[i2] !== "default") __createBinding(result, mod2, k[i2]);
|
|
37244
|
+
}
|
|
37245
|
+
__setModuleDefault(result, mod2);
|
|
37246
|
+
return result;
|
|
37247
|
+
};
|
|
37248
|
+
}();
|
|
37249
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
37250
|
+
exports2.EXECUTOR_GATE_PROBE_SCENARIOS = exports2.EXECUTOR_GATE_MIN_CALIBRATION = exports2.EXECUTOR_GATE_MISSING_LOGPROB = exports2.EXECUTOR_GATE_PLAN_HEAD_CHARS = exports2.EXECUTOR_GATE_REQUEST_MAX_CHARS = exports2.EXECUTOR_GATE_STATUS_TTL_MS = exports2.EXECUTOR_GATE_TIMEOUT_MS = exports2.EXECUTOR_GATE_PROMPT_VERSION = exports2.EXECUTOR_GATE_SOURCE = void 0;
|
|
37251
|
+
exports2.resolveExecutorGateTarget = resolveExecutorGateTarget;
|
|
37252
|
+
exports2.resolveExecutorGateTargetFromSettings = resolveExecutorGateTargetFromSettings;
|
|
37253
|
+
exports2.executorGateStateFrom = executorGateStateFrom;
|
|
37254
|
+
exports2.renderExecutorGatePrompt = renderExecutorGatePrompt;
|
|
37255
|
+
exports2.executorGateLetterOf = executorGateLetterOf;
|
|
37256
|
+
exports2.parseExecutorGateResponse = parseExecutorGateResponse;
|
|
37257
|
+
exports2.decideExecutorGate = decideExecutorGate;
|
|
37258
|
+
exports2.askExecutorGate = askExecutorGate;
|
|
37259
|
+
exports2.executorGateProbeState = executorGateProbeState;
|
|
37260
|
+
exports2.probeExecutorGate = probeExecutorGate;
|
|
37261
|
+
exports2.describeDuetExecutorGate = describeDuetExecutorGate;
|
|
37262
|
+
exports2.clearDuetExecutorGateCache = clearDuetExecutorGateCache;
|
|
37263
|
+
exports2.describeDuetExecutorGateCached = describeDuetExecutorGateCached2;
|
|
37264
|
+
exports2.createDuetExecutorGate = createDuetExecutorGate2;
|
|
37265
|
+
var os9 = __importStar(__require("node:os"));
|
|
37266
|
+
var customProviders_js_1 = require_customProviders();
|
|
37267
|
+
var duetMode_js_1 = require_duetMode();
|
|
37268
|
+
var duetPlan_js_1 = require_duetPlan();
|
|
37269
|
+
var duetRoutingAdvisor_js_1 = require_duetRoutingAdvisor();
|
|
37270
|
+
var duetEntry_js_1 = require_duetEntry();
|
|
37271
|
+
var duetExecutorGateStatus_js_1 = require_duetExecutorGateStatus();
|
|
37272
|
+
exports2.EXECUTOR_GATE_SOURCE = "executor_gate";
|
|
37273
|
+
exports2.EXECUTOR_GATE_PROMPT_VERSION = "1";
|
|
37274
|
+
exports2.EXECUTOR_GATE_TIMEOUT_MS = 8e3;
|
|
37275
|
+
exports2.EXECUTOR_GATE_STATUS_TTL_MS = 5 * 6e4;
|
|
37276
|
+
exports2.EXECUTOR_GATE_REQUEST_MAX_CHARS = 2e3;
|
|
37277
|
+
exports2.EXECUTOR_GATE_PLAN_HEAD_CHARS = 1200;
|
|
37278
|
+
exports2.EXECUTOR_GATE_MISSING_LOGPROB = -30;
|
|
37279
|
+
exports2.EXECUTOR_GATE_MIN_CALIBRATION = 3;
|
|
37280
|
+
var DEFAULT_RESOLVE_DEPS = {
|
|
37281
|
+
choice: (workspaceRoot) => (0, duetMode_js_1.duetExecutorWireForSegment)(workspaceRoot),
|
|
37282
|
+
routing: (provider) => (0, customProviders_js_1.endpointRoutingFor)(provider),
|
|
37283
|
+
alive: (workspaceRoot) => (0, customProviders_js_1.duetExecutorEndpointForSegment)(workspaceRoot) !== void 0
|
|
37284
|
+
};
|
|
37285
|
+
function resolveExecutorGateTarget(workspaceRoot, deps2 = DEFAULT_RESOLVE_DEPS) {
|
|
37286
|
+
try {
|
|
37287
|
+
const choice = deps2.choice(workspaceRoot);
|
|
37288
|
+
if (choice === void 0 || !(0, customProviders_js_1.isCustomProviderRef)(choice.provider))
|
|
37289
|
+
return { state: "platform" };
|
|
37290
|
+
const name2 = (0, customProviders_js_1.parseCustomProviderRef)(choice.provider) ?? "";
|
|
37291
|
+
const routing = deps2.routing(choice.provider);
|
|
37292
|
+
if (routing === void 0) {
|
|
37293
|
+
return { state: "unavailable", reason: "not_resolved", problem: "the executor's endpoint is not configured", name: name2 };
|
|
37294
|
+
}
|
|
37295
|
+
if (!(0, customProviders_js_1.isLoopbackEndpoint)(routing.baseUrl)) {
|
|
37296
|
+
return { state: "unavailable", reason: "not_loopback", problem: "the executor is not on this machine", name: name2 };
|
|
37297
|
+
}
|
|
37298
|
+
if (!deps2.alive(workspaceRoot)) {
|
|
37299
|
+
return { state: "unavailable", reason: "unreachable", problem: "the executor is not answering", name: name2 };
|
|
37300
|
+
}
|
|
37301
|
+
return {
|
|
37302
|
+
state: "ready",
|
|
37303
|
+
target: {
|
|
37304
|
+
name: routing.name,
|
|
37305
|
+
baseUrl: routing.baseUrl,
|
|
37306
|
+
...routing.apiKey ? { apiKey: routing.apiKey } : {},
|
|
37307
|
+
model: choice.model,
|
|
37308
|
+
threshold: routing.executorGate?.threshold ?? customProviders_js_1.EXECUTOR_GATE_DEFAULT_THRESHOLD
|
|
37309
|
+
}
|
|
37310
|
+
};
|
|
37311
|
+
} catch {
|
|
37312
|
+
return { state: "unavailable", reason: "error", problem: "the executor could not be resolved" };
|
|
37313
|
+
}
|
|
37314
|
+
}
|
|
37315
|
+
async function resolveExecutorGateTargetFromSettings(opts) {
|
|
37316
|
+
try {
|
|
37317
|
+
const tiers = { workspaceRoot: opts.workspaceRoot ?? null, ...opts.homeDir ? { homeDir: opts.homeDir } : {} };
|
|
37318
|
+
const choice = await (0, duetMode_js_1.loadDuetExecutor)(tiers);
|
|
37319
|
+
if (choice === null || !(0, customProviders_js_1.isCustomProviderRef)(choice.provider))
|
|
37320
|
+
return { state: "platform" };
|
|
37321
|
+
const name2 = (0, customProviders_js_1.parseCustomProviderRef)(choice.provider) ?? "";
|
|
37322
|
+
const entry = await (0, customProviders_js_1.getCustomProvider)(name2, tiers);
|
|
37323
|
+
if (entry === null) {
|
|
37324
|
+
return { state: "unavailable", reason: "not_resolved", problem: "the executor's endpoint is not configured", name: name2 };
|
|
37325
|
+
}
|
|
37326
|
+
if (!(0, customProviders_js_1.isLoopbackEndpoint)(entry.baseUrl)) {
|
|
37327
|
+
return { state: "unavailable", reason: "not_loopback", problem: "the executor is not on this machine", name: name2 };
|
|
37328
|
+
}
|
|
37329
|
+
const apiKey = await (0, customProviders_js_1.resolveApiKey)(entry);
|
|
37330
|
+
if (!await (0, customProviders_js_1.endpointIsReachable)(entry.baseUrl, apiKey, opts.fetchImpl)) {
|
|
37331
|
+
return { state: "unavailable", reason: "unreachable", problem: "the executor is not answering", name: name2 };
|
|
37332
|
+
}
|
|
37333
|
+
return {
|
|
37334
|
+
state: "ready",
|
|
37335
|
+
target: {
|
|
37336
|
+
name: entry.name,
|
|
37337
|
+
baseUrl: entry.baseUrl,
|
|
37338
|
+
...apiKey ? { apiKey } : {},
|
|
37339
|
+
model: choice.model,
|
|
37340
|
+
threshold: entry.executorGate?.threshold ?? customProviders_js_1.EXECUTOR_GATE_DEFAULT_THRESHOLD
|
|
37341
|
+
}
|
|
37342
|
+
};
|
|
37343
|
+
} catch {
|
|
37344
|
+
return { state: "unavailable", reason: "error", problem: "the executor could not be resolved" };
|
|
37345
|
+
}
|
|
37346
|
+
}
|
|
37347
|
+
function clipCodePoints(text, max) {
|
|
37348
|
+
const points = Array.from(text);
|
|
37349
|
+
return points.length <= max ? text : `${points.slice(0, max - 1).join("")}\u2026`;
|
|
37350
|
+
}
|
|
37351
|
+
function executorGateStateFrom(record, request) {
|
|
37352
|
+
const standing = record != null && (0, duetPlan_js_1.duetPlanWireForSegment)(record) !== void 0 ? record : null;
|
|
37353
|
+
return {
|
|
37354
|
+
planVersion: standing?.version ?? 0,
|
|
37355
|
+
planValid: standing !== null,
|
|
37356
|
+
planHead: standing === null ? "" : clipCodePoints(standing.plan.trim(), exports2.EXECUTOR_GATE_PLAN_HEAD_CHARS),
|
|
37357
|
+
assumptions: standing === null ? [] : (0, duetRoutingAdvisor_js_1.parsePlanAssumptions)(standing.plan).map((a) => ({ id: a.id, text: a.text })),
|
|
37358
|
+
planningFailures: standing?.planningFailures ?? 0,
|
|
37359
|
+
executorFailures: standing?.executorFailures ?? 0,
|
|
37360
|
+
scopeChanged: standing?.scopeChanged ?? false,
|
|
37361
|
+
architectureDecisionRequired: standing?.architectureDecisionRequired ?? false,
|
|
37362
|
+
userNegativeFeedback: standing?.userNegativeFeedback ?? false,
|
|
37363
|
+
request: clipCodePoints(request.trim(), exports2.EXECUTOR_GATE_REQUEST_MAX_CHARS)
|
|
37364
|
+
};
|
|
37365
|
+
}
|
|
37366
|
+
function stableJson(value) {
|
|
37367
|
+
const sort = (v2) => {
|
|
37368
|
+
if (Array.isArray(v2))
|
|
37369
|
+
return v2.map(sort);
|
|
37370
|
+
if (typeof v2 === "object" && v2 !== null) {
|
|
37371
|
+
return Object.fromEntries(Object.keys(v2).sort().map((k) => [k, sort(v2[k])]));
|
|
37372
|
+
}
|
|
37373
|
+
return v2;
|
|
37374
|
+
};
|
|
37375
|
+
return JSON.stringify(sort(value));
|
|
37376
|
+
}
|
|
37377
|
+
function renderExecutorGatePrompt(state) {
|
|
37378
|
+
const taskState = stableJson({
|
|
37379
|
+
plan_version: state.planVersion,
|
|
37380
|
+
plan_valid: state.planValid,
|
|
37381
|
+
planning_failures: state.planningFailures,
|
|
37382
|
+
executor_failures: state.executorFailures,
|
|
37383
|
+
flags: {
|
|
37384
|
+
scope_changed: state.scopeChanged,
|
|
37385
|
+
architecture_decision_required: state.architectureDecisionRequired,
|
|
37386
|
+
user_negative_feedback: state.userNegativeFeedback
|
|
37387
|
+
}
|
|
37388
|
+
});
|
|
37389
|
+
const capsule = stableJson({ assumptions: state.assumptions });
|
|
37390
|
+
const unresolved = state.executorFailures > 0 || state.planningFailures > 0 ? `${state.executorFailures} executor failure(s) and ${state.planningFailures} planning failure(s) under this plan` : "none";
|
|
37391
|
+
const corrections = state.userNegativeFeedback ? "the user pushed back on the current approach" : "none";
|
|
37392
|
+
return [
|
|
37393
|
+
"Routing gate for a coding agent. Decide if the current turn can be executed",
|
|
37394
|
+
"with the existing plan, or needs a new plan from the senior planner.",
|
|
37395
|
+
"",
|
|
37396
|
+
"E = EXECUTION_ONLY - the current plan is valid and local execution continues",
|
|
37397
|
+
"P = PLAN_REQUIRED - a new or revised plan would materially help",
|
|
37398
|
+
"",
|
|
37399
|
+
"Prefer E unless planning is genuinely needed.",
|
|
37400
|
+
"",
|
|
37401
|
+
"--- TASK STATE ---",
|
|
37402
|
+
taskState,
|
|
37403
|
+
"--- CONTEXT CAPSULE ---",
|
|
37404
|
+
capsule,
|
|
37405
|
+
"--- CURRENT PLAN ---",
|
|
37406
|
+
state.planHead === "" ? "(none)" : state.planHead,
|
|
37407
|
+
"--- UNRESOLVED ERRORS ---",
|
|
37408
|
+
unresolved,
|
|
37409
|
+
"--- RECENT USER CORRECTIONS ---",
|
|
37410
|
+
corrections,
|
|
37411
|
+
"--- LATEST USER REQUEST ---",
|
|
37412
|
+
state.request,
|
|
37413
|
+
"",
|
|
37414
|
+
"Answer with exactly one letter, E or P.",
|
|
37415
|
+
"Answer:"
|
|
37416
|
+
].join("\n");
|
|
37417
|
+
}
|
|
37418
|
+
function executorGateLetterOf(token) {
|
|
37419
|
+
const bare2 = token.replace(/^[\s▁Ġ]+/u, "").replace(/\s+$/u, "");
|
|
37420
|
+
return bare2 === "E" || bare2 === "P" ? bare2 : null;
|
|
37421
|
+
}
|
|
37422
|
+
function topLogprobs(choice) {
|
|
37423
|
+
const lp = choice.logprobs;
|
|
37424
|
+
if (typeof lp !== "object" || lp === null)
|
|
37425
|
+
return null;
|
|
37426
|
+
const out2 = {};
|
|
37427
|
+
const add = (token, logprob) => {
|
|
37428
|
+
if (typeof token === "string" && typeof logprob === "number" && Number.isFinite(logprob)) {
|
|
37429
|
+
out2[token] = Math.max(out2[token] ?? Number.NEGATIVE_INFINITY, logprob);
|
|
37430
|
+
}
|
|
37431
|
+
};
|
|
37432
|
+
const legacy = lp.top_logprobs;
|
|
37433
|
+
if (Array.isArray(legacy) && typeof legacy[0] === "object" && legacy[0] !== null && !Array.isArray(legacy[0])) {
|
|
37434
|
+
for (const [token, logprob] of Object.entries(legacy[0]))
|
|
37435
|
+
add(token, logprob);
|
|
37436
|
+
}
|
|
37437
|
+
const content = lp.content;
|
|
37438
|
+
if (Array.isArray(content) && typeof content[0] === "object" && content[0] !== null) {
|
|
37439
|
+
const first = content[0];
|
|
37440
|
+
add(first.token, first.logprob);
|
|
37441
|
+
if (Array.isArray(first.top_logprobs)) {
|
|
37442
|
+
for (const row of first.top_logprobs) {
|
|
37443
|
+
add(row?.token, row?.logprob);
|
|
37444
|
+
}
|
|
37445
|
+
}
|
|
37446
|
+
}
|
|
37447
|
+
const tokens = lp.tokens;
|
|
37448
|
+
const tokenLogprobs = lp.token_logprobs;
|
|
37449
|
+
if (Array.isArray(tokens) && Array.isArray(tokenLogprobs))
|
|
37450
|
+
add(tokens[0], tokenLogprobs[0]);
|
|
37451
|
+
return Object.keys(out2).length > 0 ? out2 : null;
|
|
37452
|
+
}
|
|
37453
|
+
function parseExecutorGateResponse(body2) {
|
|
37454
|
+
const choice = body2?.choices?.[0];
|
|
37455
|
+
if (typeof choice !== "object" || choice === null) {
|
|
37456
|
+
return { ok: false, reason: "unparseable", problem: "the completions response carried no choice" };
|
|
37457
|
+
}
|
|
37458
|
+
const c3 = choice;
|
|
37459
|
+
const message = c3.message;
|
|
37460
|
+
const raw = typeof c3.text === "string" ? c3.text : typeof message?.content === "string" ? message.content : "";
|
|
37461
|
+
const trimmed = raw.trim();
|
|
37462
|
+
if (trimmed.startsWith("<")) {
|
|
37463
|
+
return {
|
|
37464
|
+
ok: false,
|
|
37465
|
+
reason: "thinking",
|
|
37466
|
+
problem: `the executor answered with thinking on (it began "${trimmed.slice(0, 8)}")`
|
|
37467
|
+
};
|
|
37468
|
+
}
|
|
37469
|
+
const letter = executorGateLetterOf(raw);
|
|
37470
|
+
const top = topLogprobs(c3);
|
|
37471
|
+
if (top !== null) {
|
|
37472
|
+
let logE = null;
|
|
37473
|
+
let logP = null;
|
|
37474
|
+
for (const [token, logprob] of Object.entries(top)) {
|
|
37475
|
+
const l3 = executorGateLetterOf(token);
|
|
37476
|
+
if (l3 === "E")
|
|
37477
|
+
logE = Math.max(logE ?? Number.NEGATIVE_INFINITY, logprob);
|
|
37478
|
+
if (l3 === "P")
|
|
37479
|
+
logP = Math.max(logP ?? Number.NEGATIVE_INFINITY, logprob);
|
|
37480
|
+
}
|
|
37481
|
+
if (logE !== null || logP !== null) {
|
|
37482
|
+
return {
|
|
37483
|
+
ok: true,
|
|
37484
|
+
answer: {
|
|
37485
|
+
mode: "logprob",
|
|
37486
|
+
letter,
|
|
37487
|
+
logE: logE ?? exports2.EXECUTOR_GATE_MISSING_LOGPROB,
|
|
37488
|
+
logP: logP ?? exports2.EXECUTOR_GATE_MISSING_LOGPROB,
|
|
37489
|
+
raw
|
|
37490
|
+
}
|
|
37491
|
+
};
|
|
37492
|
+
}
|
|
37493
|
+
}
|
|
37494
|
+
if (letter !== null)
|
|
37495
|
+
return { ok: true, answer: { mode: "greedy", letter, logE: null, logP: null, raw } };
|
|
37496
|
+
return {
|
|
37497
|
+
ok: false,
|
|
37498
|
+
reason: "unparseable",
|
|
37499
|
+
problem: `the executor answered "${trimmed.slice(0, 16)}", not E or P`
|
|
37500
|
+
};
|
|
37501
|
+
}
|
|
37502
|
+
function decideExecutorGate(answer, threshold) {
|
|
37503
|
+
if (answer.mode === "logprob" && answer.logE !== null && answer.logP !== null) {
|
|
37504
|
+
const margin = answer.logP - answer.logE;
|
|
37505
|
+
return { plan: margin >= threshold, margin, pPlan: 1 / (1 + Math.exp(-margin)) };
|
|
37506
|
+
}
|
|
37507
|
+
if (answer.letter === null)
|
|
37508
|
+
return null;
|
|
37509
|
+
return { plan: answer.letter === "P", margin: null, pPlan: answer.letter === "P" ? 1 : 0 };
|
|
37510
|
+
}
|
|
37511
|
+
async function askExecutorGate(target, prompt, opts = {}) {
|
|
37512
|
+
const started = Date.now();
|
|
37513
|
+
const doFetch = opts.fetchImpl ?? fetch;
|
|
37514
|
+
const headers = { "Content-Type": "application/json" };
|
|
37515
|
+
if (target.apiKey)
|
|
37516
|
+
headers.Authorization = `Bearer ${target.apiKey}`;
|
|
37517
|
+
try {
|
|
37518
|
+
const res = await doFetch(`${target.baseUrl.replace(/\/+$/, "")}/completions`, {
|
|
37519
|
+
method: "POST",
|
|
37520
|
+
headers,
|
|
37521
|
+
body: JSON.stringify({
|
|
37522
|
+
model: target.model,
|
|
37523
|
+
prompt,
|
|
37524
|
+
max_tokens: 1,
|
|
37525
|
+
temperature: 0,
|
|
37526
|
+
logprobs: 5,
|
|
37527
|
+
stream: false
|
|
37528
|
+
}),
|
|
37529
|
+
signal: AbortSignal.timeout(opts.timeoutMs ?? exports2.EXECUTOR_GATE_TIMEOUT_MS)
|
|
37530
|
+
});
|
|
37531
|
+
const latencyMs = Date.now() - started;
|
|
37532
|
+
if (res.status === 404 || res.status === 405 || res.status === 501) {
|
|
37533
|
+
return {
|
|
37534
|
+
ok: false,
|
|
37535
|
+
reason: "no_completions",
|
|
37536
|
+
problem: `the executor has no completions route (${res.status})`,
|
|
37537
|
+
latencyMs
|
|
37538
|
+
};
|
|
37539
|
+
}
|
|
37540
|
+
if (!res.ok)
|
|
37541
|
+
return { ok: false, reason: "error", problem: `the executor answered ${res.status}`, latencyMs };
|
|
37542
|
+
const parsed = parseExecutorGateResponse(await res.json());
|
|
37543
|
+
if (!parsed.ok)
|
|
37544
|
+
return { ok: false, reason: parsed.reason, problem: parsed.problem, latencyMs };
|
|
37545
|
+
return { ok: true, answer: parsed.answer, latencyMs };
|
|
37546
|
+
} catch (e) {
|
|
37547
|
+
const timedOut = e instanceof Error && e.name === "TimeoutError";
|
|
37548
|
+
return {
|
|
37549
|
+
ok: false,
|
|
37550
|
+
reason: "error",
|
|
37551
|
+
problem: timedOut ? "the gate call timed out" : `the gate call failed (${e instanceof Error ? e.message : String(e)})`,
|
|
37552
|
+
latencyMs: Date.now() - started
|
|
37553
|
+
};
|
|
37554
|
+
}
|
|
37555
|
+
}
|
|
37556
|
+
exports2.EXECUTOR_GATE_PROBE_SCENARIOS = [
|
|
37557
|
+
{ request: "Create this application with auth, billing and audit logging", expect: "P" },
|
|
37558
|
+
{ request: "Implement the next endpoint", expect: "E" },
|
|
37559
|
+
{ request: "We can no longer use the current authentication architecture", expect: "P" },
|
|
37560
|
+
{ request: "continue", expect: "E" }
|
|
37561
|
+
];
|
|
37562
|
+
function executorGateProbeState(request) {
|
|
37563
|
+
return {
|
|
37564
|
+
planVersion: 3,
|
|
37565
|
+
planValid: true,
|
|
37566
|
+
planHead: "# Plan: orders-service (FastAPI)\n1. Add POST /orders and GET /orders/{id}\n2. Wire the billing call behind a feature flag\n3. Tests for both endpoints",
|
|
37567
|
+
assumptions: [
|
|
37568
|
+
{ id: "A1", text: "the service keeps its central authentication middleware" },
|
|
37569
|
+
{ id: "A2", text: "billing stays behind the existing Stripe client" }
|
|
37570
|
+
],
|
|
37571
|
+
planningFailures: 0,
|
|
37572
|
+
executorFailures: 0,
|
|
37573
|
+
scopeChanged: false,
|
|
37574
|
+
architectureDecisionRequired: false,
|
|
37575
|
+
userNegativeFeedback: false,
|
|
37576
|
+
request
|
|
37577
|
+
};
|
|
37578
|
+
}
|
|
37579
|
+
async function probeExecutorGate(target, opts = {}) {
|
|
37580
|
+
const started = Date.now();
|
|
37581
|
+
let mode = null;
|
|
37582
|
+
const failed = [];
|
|
37583
|
+
for (const scenario of exports2.EXECUTOR_GATE_PROBE_SCENARIOS) {
|
|
37584
|
+
const asked = await askExecutorGate(target, renderExecutorGatePrompt(executorGateProbeState(scenario.request)), opts);
|
|
37585
|
+
if (!asked.ok)
|
|
37586
|
+
return { state: "unavailable", reason: asked.reason, problem: asked.problem, name: target.name };
|
|
37587
|
+
mode ??= asked.answer.mode;
|
|
37588
|
+
const decision = decideExecutorGate(asked.answer, target.threshold);
|
|
37589
|
+
if (decision === null || (decision.plan ? "P" : "E") !== scenario.expect)
|
|
37590
|
+
failed.push(scenario.request);
|
|
37591
|
+
}
|
|
37592
|
+
const calibration = {
|
|
37593
|
+
passed: exports2.EXECUTOR_GATE_PROBE_SCENARIOS.length - failed.length,
|
|
37594
|
+
total: exports2.EXECUTOR_GATE_PROBE_SCENARIOS.length,
|
|
37595
|
+
failed
|
|
37596
|
+
};
|
|
37597
|
+
const common = {
|
|
37598
|
+
target: { name: target.name, model: target.model },
|
|
37599
|
+
mode: mode ?? "greedy",
|
|
37600
|
+
threshold: target.threshold,
|
|
37601
|
+
calibration,
|
|
37602
|
+
latencyMs: Date.now() - started
|
|
37603
|
+
};
|
|
37604
|
+
return calibration.passed >= exports2.EXECUTOR_GATE_MIN_CALIBRATION ? { state: "ready", ...common } : { state: "miscalibrated", ...common };
|
|
37605
|
+
}
|
|
37606
|
+
async function describeDuetExecutorGate(opts = {}) {
|
|
37607
|
+
const resolved = await resolveExecutorGateTargetFromSettings(opts);
|
|
37608
|
+
if (resolved.state !== "ready")
|
|
37609
|
+
return resolved;
|
|
37610
|
+
return probeExecutorGate(resolved.target, { fetchImpl: opts.fetchImpl, timeoutMs: opts.timeoutMs });
|
|
37611
|
+
}
|
|
37612
|
+
var describeCache = /* @__PURE__ */ new Map();
|
|
37613
|
+
function clearDuetExecutorGateCache() {
|
|
37614
|
+
describeCache.clear();
|
|
37615
|
+
}
|
|
37616
|
+
async function describeDuetExecutorGateCached2(opts = {}) {
|
|
37617
|
+
const now2 = opts.now ?? Date.now;
|
|
37618
|
+
const key = `${opts.homeDir ?? os9.homedir()}\0${opts.workspaceRoot ?? ""}`;
|
|
37619
|
+
const hit = describeCache.get(key);
|
|
37620
|
+
if (!opts.refresh && hit !== void 0 && now2() - hit.at < (opts.ttlMs ?? exports2.EXECUTOR_GATE_STATUS_TTL_MS)) {
|
|
37621
|
+
return hit.status;
|
|
37622
|
+
}
|
|
37623
|
+
const status = await describeDuetExecutorGate(opts);
|
|
37624
|
+
describeCache.set(key, { at: now2(), status });
|
|
37625
|
+
return status;
|
|
37626
|
+
}
|
|
37627
|
+
function createDuetExecutorGate2(opts = {}) {
|
|
37628
|
+
const now2 = opts.now ?? Date.now;
|
|
37629
|
+
const ttl = opts.statusTtlMs ?? exports2.EXECUTOR_GATE_STATUS_TTL_MS;
|
|
37630
|
+
let cached = null;
|
|
37631
|
+
let noted = false;
|
|
37632
|
+
const downgrade = (why) => {
|
|
37633
|
+
const note = noted ? null : (0, duetExecutorGateStatus_js_1.executorGateDowngradeNote)(why);
|
|
37634
|
+
noted = true;
|
|
37635
|
+
return { ...(0, duetEntry_js_1.effectiveDuetEntry)("executor", void 0, "unavailable"), verdict: null, note };
|
|
37636
|
+
};
|
|
37637
|
+
return {
|
|
37638
|
+
async status(o = {}) {
|
|
37639
|
+
const resolved = await resolveExecutorGateTargetFromSettings({
|
|
37640
|
+
workspaceRoot: o.workspaceRoot,
|
|
37641
|
+
...opts.homeDir ? { homeDir: opts.homeDir } : {},
|
|
37642
|
+
fetchImpl: opts.fetchImpl
|
|
37643
|
+
});
|
|
37644
|
+
if (resolved.state !== "ready")
|
|
37645
|
+
return resolved;
|
|
37646
|
+
const key = `${resolved.target.baseUrl} ${resolved.target.model} ${resolved.target.threshold}`;
|
|
37647
|
+
if (!o.refresh && cached !== null && cached.key === key && now2() - cached.at < ttl)
|
|
37648
|
+
return cached.status;
|
|
37649
|
+
const status = await probeExecutorGate(resolved.target, { fetchImpl: opts.fetchImpl, timeoutMs: opts.timeoutMs });
|
|
37650
|
+
cached = { at: now2(), key, status };
|
|
37651
|
+
return status;
|
|
37652
|
+
},
|
|
37653
|
+
async prepareTurn(text, ctx) {
|
|
37654
|
+
if (text.trim() === "")
|
|
37655
|
+
return { entry: "executor", verdict: null, note: null };
|
|
37656
|
+
const resolved = resolveExecutorGateTarget(ctx.workspaceRoot, opts.resolveDeps);
|
|
37657
|
+
if (resolved.state !== "ready") {
|
|
37658
|
+
opts.onError?.("resolve", resolved.state === "platform" ? "platform executor" : resolved.problem);
|
|
37659
|
+
return downgrade(resolved);
|
|
37660
|
+
}
|
|
37661
|
+
const { target } = resolved;
|
|
37662
|
+
const prompt = renderExecutorGatePrompt(executorGateStateFrom(ctx.record, text));
|
|
37663
|
+
const asked = await askExecutorGate(target, prompt, { fetchImpl: opts.fetchImpl, timeoutMs: opts.timeoutMs });
|
|
37664
|
+
if (!asked.ok) {
|
|
37665
|
+
opts.onError?.("ask", asked.problem);
|
|
37666
|
+
return downgrade({ state: "unavailable", reason: asked.reason, problem: asked.problem });
|
|
37667
|
+
}
|
|
37668
|
+
const decision = decideExecutorGate(asked.answer, target.threshold);
|
|
37669
|
+
if (decision === null) {
|
|
37670
|
+
const said = asked.answer.raw.trim();
|
|
37671
|
+
opts.onError?.("ask", `undecidable answer "${said}"`);
|
|
37672
|
+
return downgrade({ state: "unavailable", reason: "unparseable", problem: `the executor answered "${said}"` });
|
|
37673
|
+
}
|
|
37674
|
+
noted = false;
|
|
37675
|
+
const verdict = {
|
|
37676
|
+
source: exports2.EXECUTOR_GATE_SOURCE,
|
|
37677
|
+
verdict: decision.plan ? "plan" : "execute",
|
|
37678
|
+
pPlan: decision.pPlan,
|
|
37679
|
+
asksForPlan: false,
|
|
37680
|
+
highRisk: false,
|
|
37681
|
+
reason: exports2.EXECUTOR_GATE_SOURCE,
|
|
37682
|
+
model: target.model,
|
|
37683
|
+
version: exports2.EXECUTOR_GATE_PROMPT_VERSION,
|
|
37684
|
+
latencyMs: asked.latencyMs,
|
|
37685
|
+
mode: asked.answer.mode,
|
|
37686
|
+
...decision.margin !== null ? { margin: decision.margin } : {}
|
|
37687
|
+
};
|
|
37688
|
+
return { entry: "executor", verdict, note: null };
|
|
37689
|
+
},
|
|
37690
|
+
invalidate() {
|
|
37691
|
+
cached = null;
|
|
37692
|
+
noted = false;
|
|
37693
|
+
}
|
|
37694
|
+
};
|
|
37695
|
+
}
|
|
37696
|
+
}
|
|
37697
|
+
});
|
|
37698
|
+
|
|
37699
|
+
// ../packages/orion-client-core/dist/runs/common.js
|
|
37700
|
+
var require_common = __commonJS({
|
|
37701
|
+
"../packages/orion-client-core/dist/runs/common.js"(exports2) {
|
|
37702
|
+
"use strict";
|
|
37703
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
37704
|
+
exports2.mintRunId = mintRunId;
|
|
37705
|
+
exports2.runsRootFor = runsRootFor2;
|
|
37706
|
+
exports2.readJsonFile = readJsonFile;
|
|
37707
|
+
exports2.writeJsonFile = writeJsonFile;
|
|
37708
|
+
exports2.ensureDirFor = ensureDirFor;
|
|
37709
|
+
exports2.listDirNames = listDirNames;
|
|
37710
|
+
exports2.dayKey = dayKey;
|
|
37711
|
+
exports2.clipTail = clipTail;
|
|
37712
|
+
var fs_1 = __require("fs");
|
|
37713
|
+
var os_1 = __require("os");
|
|
37714
|
+
var path_1 = __require("path");
|
|
37715
|
+
var atomicWrite_js_1 = require_atomicWrite();
|
|
37716
|
+
var experienceStore_js_1 = require_experienceStore();
|
|
37717
|
+
var ID_ALPHABET = "abcdefghijklmnopqrstuvwxyz0123456789";
|
|
37718
|
+
var ID_SUFFIX_LEN = 6;
|
|
37719
|
+
function mintRunId(prefix, nowMs = Date.now(), rand = Math.random) {
|
|
37720
|
+
let suffix = "";
|
|
37721
|
+
for (let i2 = 0; i2 < ID_SUFFIX_LEN; i2 += 1) {
|
|
37722
|
+
suffix += ID_ALPHABET[Math.floor(rand() * ID_ALPHABET.length) % ID_ALPHABET.length];
|
|
37723
|
+
}
|
|
37724
|
+
return `${prefix}_${String(nowMs).padStart(13, "0")}_${suffix}`;
|
|
37725
|
+
}
|
|
37726
|
+
function runsRootFor2(kind, workspaceRoot, home = (0, os_1.homedir)()) {
|
|
37727
|
+
return (0, path_1.join)((0, experienceStore_js_1.projectDirFor)(workspaceRoot, home), "runs", kind);
|
|
37728
|
+
}
|
|
37729
|
+
async function readJsonFile(path14) {
|
|
37730
|
+
try {
|
|
37731
|
+
const raw = await fs_1.promises.readFile(path14, "utf8");
|
|
37732
|
+
return JSON.parse(raw);
|
|
37733
|
+
} catch {
|
|
37734
|
+
return null;
|
|
37735
|
+
}
|
|
37736
|
+
}
|
|
37737
|
+
async function writeJsonFile(path14, value) {
|
|
37738
|
+
await ensureDirFor(path14);
|
|
37739
|
+
await (0, atomicWrite_js_1.atomicWriteFile)(path14, JSON.stringify(value, null, 2));
|
|
37740
|
+
}
|
|
37741
|
+
async function ensureDirFor(path14) {
|
|
37742
|
+
await fs_1.promises.mkdir((0, path_1.dirname)(path14), { recursive: true });
|
|
37743
|
+
}
|
|
37744
|
+
async function listDirNames(path14) {
|
|
37745
|
+
try {
|
|
37746
|
+
return await fs_1.promises.readdir(path14);
|
|
37747
|
+
} catch {
|
|
37748
|
+
return [];
|
|
37749
|
+
}
|
|
37750
|
+
}
|
|
37751
|
+
function dayKey(nowMs = Date.now()) {
|
|
37752
|
+
const d2 = new Date(nowMs);
|
|
37753
|
+
const month = `${d2.getMonth() + 1}`.padStart(2, "0");
|
|
37754
|
+
const day = `${d2.getDate()}`.padStart(2, "0");
|
|
37755
|
+
return `${d2.getFullYear()}-${month}-${day}`;
|
|
37756
|
+
}
|
|
37757
|
+
function clipTail(text, max) {
|
|
37758
|
+
if (text.length <= max)
|
|
37759
|
+
return text;
|
|
37760
|
+
return `\u2026${text.slice(text.length - (max - 1))}`;
|
|
37761
|
+
}
|
|
37762
|
+
}
|
|
37763
|
+
});
|
|
37764
|
+
|
|
37765
|
+
// ../packages/orion-client-core/dist/customProviderModels.js
|
|
37766
|
+
var require_customProviderModels = __commonJS({
|
|
37767
|
+
"../packages/orion-client-core/dist/customProviderModels.js"(exports2) {
|
|
37768
|
+
"use strict";
|
|
37769
|
+
var __createBinding = exports2 && exports2.__createBinding || (Object.create ? function(o, m2, k, k2) {
|
|
37770
|
+
if (k2 === void 0) k2 = k;
|
|
37771
|
+
var desc = Object.getOwnPropertyDescriptor(m2, k);
|
|
37772
|
+
if (!desc || ("get" in desc ? !m2.__esModule : desc.writable || desc.configurable)) {
|
|
37773
|
+
desc = { enumerable: true, get: function() {
|
|
37774
|
+
return m2[k];
|
|
37775
|
+
} };
|
|
37776
|
+
}
|
|
37777
|
+
Object.defineProperty(o, k2, desc);
|
|
37778
|
+
} : function(o, m2, k, k2) {
|
|
37779
|
+
if (k2 === void 0) k2 = k;
|
|
37780
|
+
o[k2] = m2[k];
|
|
37781
|
+
});
|
|
37782
|
+
var __setModuleDefault = exports2 && exports2.__setModuleDefault || (Object.create ? function(o, v2) {
|
|
37783
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v2 });
|
|
37784
|
+
} : function(o, v2) {
|
|
37785
|
+
o["default"] = v2;
|
|
37786
|
+
});
|
|
37787
|
+
var __importStar = exports2 && exports2.__importStar || /* @__PURE__ */ function() {
|
|
37788
|
+
var ownKeys = function(o) {
|
|
37789
|
+
ownKeys = Object.getOwnPropertyNames || function(o2) {
|
|
37790
|
+
var ar = [];
|
|
37791
|
+
for (var k in o2) if (Object.prototype.hasOwnProperty.call(o2, k)) ar[ar.length] = k;
|
|
37792
|
+
return ar;
|
|
37793
|
+
};
|
|
37794
|
+
return ownKeys(o);
|
|
37795
|
+
};
|
|
37796
|
+
return function(mod2) {
|
|
37797
|
+
if (mod2 && mod2.__esModule) return mod2;
|
|
37798
|
+
var result = {};
|
|
37799
|
+
if (mod2 != null) {
|
|
37800
|
+
for (var k = ownKeys(mod2), i2 = 0; i2 < k.length; i2++) if (k[i2] !== "default") __createBinding(result, mod2, k[i2]);
|
|
37801
|
+
}
|
|
37802
|
+
__setModuleDefault(result, mod2);
|
|
37803
|
+
return result;
|
|
37804
|
+
};
|
|
37805
|
+
}();
|
|
37806
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
37807
|
+
exports2.CATALOG_GC_MS = exports2.CATALOG_TTL_MS = exports2.CATALOG_SCHEMA_VERSION = void 0;
|
|
37808
|
+
exports2.catalogPathFor = catalogPathFor;
|
|
37809
|
+
exports2.endpointCatalog = endpointCatalog2;
|
|
37810
|
+
exports2.findProbedModel = findProbedModel;
|
|
37811
|
+
exports2.resolveModelSettings = resolveModelSettings2;
|
|
37812
|
+
exports2.catalogModelIds = catalogModelIds2;
|
|
37813
|
+
exports2.clearEndpointCatalog = clearEndpointCatalog3;
|
|
37814
|
+
exports2.endpointModelViews = endpointModelViews2;
|
|
37815
|
+
exports2.updateCustomProviderModels = updateCustomProviderModels2;
|
|
37816
|
+
var node_crypto_1 = __require("node:crypto");
|
|
37817
|
+
var os9 = __importStar(__require("node:os"));
|
|
37818
|
+
var path14 = __importStar(__require("node:path"));
|
|
37819
|
+
var customProviders_1 = require_customProviders();
|
|
37820
|
+
var common_1 = require_common();
|
|
37821
|
+
exports2.CATALOG_SCHEMA_VERSION = 1;
|
|
37822
|
+
exports2.CATALOG_TTL_MS = 9e5;
|
|
37823
|
+
exports2.CATALOG_GC_MS = 45 * 24 * 60 * 60 * 1e3;
|
|
37824
|
+
function catalogPathFor(baseUrl, homeDir = os9.homedir()) {
|
|
37825
|
+
const digest = (0, node_crypto_1.createHash)("sha256").update(normalizeBaseUrl(baseUrl)).digest("hex").slice(0, 16);
|
|
37826
|
+
return path14.join(homeDir, ".orion", "cache", "models", `${digest}.json`);
|
|
37827
|
+
}
|
|
37828
|
+
function normalizeBaseUrl(baseUrl) {
|
|
37829
|
+
return baseUrl.trim().replace(/\/+$/, "");
|
|
37830
|
+
}
|
|
37831
|
+
async function readRecordFromDisk(baseUrl) {
|
|
37832
|
+
const record = await (0, common_1.readJsonFile)(catalogPathFor(baseUrl));
|
|
37833
|
+
if (record === null)
|
|
37170
37834
|
return null;
|
|
37171
|
-
if (
|
|
37172
|
-
return
|
|
37173
|
-
|
|
37835
|
+
if (record.version !== exports2.CATALOG_SCHEMA_VERSION)
|
|
37836
|
+
return null;
|
|
37837
|
+
if (normalizeBaseUrl(record.baseUrl ?? "") !== normalizeBaseUrl(baseUrl))
|
|
37838
|
+
return null;
|
|
37839
|
+
if (!Array.isArray(record.models))
|
|
37840
|
+
return null;
|
|
37841
|
+
return record;
|
|
37174
37842
|
}
|
|
37175
|
-
|
|
37176
|
-
|
|
37843
|
+
var sweptThisProcess = false;
|
|
37844
|
+
async function gcEndpointCatalogs(now2, homeDir = os9.homedir()) {
|
|
37845
|
+
if (sweptThisProcess)
|
|
37177
37846
|
return;
|
|
37847
|
+
sweptThisProcess = true;
|
|
37178
37848
|
try {
|
|
37179
|
-
|
|
37849
|
+
const dir = path14.dirname(catalogPathFor("x", homeDir));
|
|
37850
|
+
const fs15 = await Promise.resolve().then(() => __importStar(__require("node:fs/promises")));
|
|
37851
|
+
for (const name2 of await fs15.readdir(dir)) {
|
|
37852
|
+
if (!name2.endsWith(".json"))
|
|
37853
|
+
continue;
|
|
37854
|
+
const file = path14.join(dir, name2);
|
|
37855
|
+
try {
|
|
37856
|
+
const record = await (0, common_1.readJsonFile)(file);
|
|
37857
|
+
const age = typeof record?.fetchedAt === "number" ? now2 - record.fetchedAt : now2 - (await fs15.stat(file)).mtimeMs;
|
|
37858
|
+
if (age > exports2.CATALOG_GC_MS)
|
|
37859
|
+
await fs15.rm(file, { force: true });
|
|
37860
|
+
} catch {
|
|
37861
|
+
}
|
|
37862
|
+
}
|
|
37180
37863
|
} catch {
|
|
37181
37864
|
}
|
|
37182
37865
|
}
|
|
37183
|
-
function
|
|
37184
|
-
|
|
37185
|
-
|
|
37186
|
-
|
|
37187
|
-
if ((0, duetPlan_js_1.highRiskRequest)(text))
|
|
37188
|
-
return { verdict: "plan", reason: "plan_invalid" };
|
|
37189
|
-
return entry === "planner" ? { verdict: "plan", reason: "planner_entry" } : { verdict: "execute", reason: "no_plan" };
|
|
37190
|
-
}
|
|
37191
|
-
if (record.scopeChanged)
|
|
37192
|
-
return { verdict: "plan", reason: "scope_changed" };
|
|
37193
|
-
if (record.architectureDecisionRequired) {
|
|
37194
|
-
return { verdict: "plan", reason: "architecture_decision_required" };
|
|
37195
|
-
}
|
|
37196
|
-
if (record.planningFailures >= 2)
|
|
37197
|
-
return { verdict: "plan", reason: "failed_attempts" };
|
|
37198
|
-
if (record.userNegativeFeedback)
|
|
37199
|
-
return { verdict: "plan", reason: "negative_feedback" };
|
|
37200
|
-
if (entry === "planner") {
|
|
37201
|
-
return (0, duetPlan_js_1.continuationRequest)(text) ? { verdict: "execute", reason: "continuation" } : { verdict: "plan", reason: "planner_entry" };
|
|
37866
|
+
async function writeRecordToDisk(record) {
|
|
37867
|
+
try {
|
|
37868
|
+
await (0, common_1.writeJsonFile)(catalogPathFor(record.baseUrl), record);
|
|
37869
|
+
} catch {
|
|
37202
37870
|
}
|
|
37203
|
-
|
|
37871
|
+
void gcEndpointCatalogs(record.fetchedAt);
|
|
37204
37872
|
}
|
|
37205
|
-
|
|
37206
|
-
|
|
37207
|
-
|
|
37208
|
-
const models = local ? (0, customProviders_js_1.endpointRoutingFor)(choice.provider)?.routingModels : void 0;
|
|
37873
|
+
var memory = /* @__PURE__ */ new Map();
|
|
37874
|
+
var inFlight2 = /* @__PURE__ */ new Map();
|
|
37875
|
+
function depsWith(deps2) {
|
|
37209
37876
|
return {
|
|
37210
|
-
|
|
37211
|
-
|
|
37212
|
-
|
|
37213
|
-
|
|
37214
|
-
judge: models?.judge !== void 0
|
|
37215
|
-
}
|
|
37877
|
+
now: deps2.now ?? (() => Date.now()),
|
|
37878
|
+
probe: deps2.probe ?? customProviders_1.probeModels,
|
|
37879
|
+
readRecord: deps2.readRecord ?? readRecordFromDisk,
|
|
37880
|
+
writeRecord: deps2.writeRecord ?? writeRecordToDisk
|
|
37216
37881
|
};
|
|
37217
37882
|
}
|
|
37218
|
-
function
|
|
37219
|
-
const
|
|
37220
|
-
|
|
37221
|
-
|
|
37222
|
-
|
|
37223
|
-
|
|
37224
|
-
|
|
37225
|
-
|
|
37226
|
-
|
|
37227
|
-
|
|
37228
|
-
|
|
37229
|
-
|
|
37230
|
-
|
|
37231
|
-
|
|
37232
|
-
|
|
37233
|
-
|
|
37234
|
-
|
|
37883
|
+
async function probeAndStore(entry, d2) {
|
|
37884
|
+
const key = normalizeBaseUrl(entry.baseUrl);
|
|
37885
|
+
const existing = inFlight2.get(key);
|
|
37886
|
+
if (existing !== void 0)
|
|
37887
|
+
return existing;
|
|
37888
|
+
const run3 = (async () => {
|
|
37889
|
+
const models = await d2.probe(entry.baseUrl, await (0, customProviders_1.resolveApiKey)(entry));
|
|
37890
|
+
if (models === null || models.length === 0)
|
|
37891
|
+
return models;
|
|
37892
|
+
const record = {
|
|
37893
|
+
version: exports2.CATALOG_SCHEMA_VERSION,
|
|
37894
|
+
baseUrl: entry.baseUrl,
|
|
37895
|
+
fetchedAt: d2.now(),
|
|
37896
|
+
models
|
|
37897
|
+
};
|
|
37898
|
+
memory.set(key, record);
|
|
37899
|
+
await d2.writeRecord(record);
|
|
37900
|
+
return models;
|
|
37901
|
+
})().finally(() => inFlight2.delete(key));
|
|
37902
|
+
inFlight2.set(key, run3);
|
|
37903
|
+
return run3;
|
|
37235
37904
|
}
|
|
37236
|
-
function
|
|
37237
|
-
const
|
|
37238
|
-
|
|
37239
|
-
|
|
37240
|
-
|
|
37241
|
-
|
|
37242
|
-
|
|
37243
|
-
|
|
37244
|
-
|
|
37245
|
-
|
|
37246
|
-
|
|
37247
|
-
|
|
37905
|
+
async function endpointCatalog2(entry, options = {}) {
|
|
37906
|
+
const d2 = depsWith(options);
|
|
37907
|
+
const key = normalizeBaseUrl(entry.baseUrl);
|
|
37908
|
+
let record = memory.get(key) ?? null;
|
|
37909
|
+
if (record === null) {
|
|
37910
|
+
record = await d2.readRecord(entry.baseUrl);
|
|
37911
|
+
if (record !== null)
|
|
37912
|
+
memory.set(key, record);
|
|
37913
|
+
}
|
|
37914
|
+
if (options.cachedOnly === true)
|
|
37915
|
+
return record?.models ?? [];
|
|
37916
|
+
const fresh = record !== null && d2.now() - record.fetchedAt < exports2.CATALOG_TTL_MS;
|
|
37917
|
+
if (record !== null && fresh && options.force !== true)
|
|
37918
|
+
return record.models;
|
|
37919
|
+
if (record !== null) {
|
|
37920
|
+
void probeAndStore(entry, d2).catch(() => void 0);
|
|
37921
|
+
return record.models;
|
|
37922
|
+
}
|
|
37923
|
+
return await probeAndStore(entry, d2) ?? [];
|
|
37248
37924
|
}
|
|
37249
|
-
function
|
|
37250
|
-
|
|
37251
|
-
|
|
37925
|
+
function findProbedModel(models, id) {
|
|
37926
|
+
return models.find((model) => model.id === id);
|
|
37927
|
+
}
|
|
37928
|
+
function resolveModelSettings2(entry, modelId, catalog = []) {
|
|
37929
|
+
const declared = entry.modelConfig?.[modelId];
|
|
37930
|
+
const probed = findProbedModel(catalog, modelId);
|
|
37931
|
+
const resolved = {};
|
|
37932
|
+
const contextWindow = declared?.contextWindow ?? probed?.contextWindow;
|
|
37933
|
+
if (contextWindow !== void 0)
|
|
37934
|
+
resolved.contextWindow = contextWindow;
|
|
37935
|
+
const maxOutputTokens = declared?.maxOutputTokens ?? probed?.maxOutputTokens;
|
|
37936
|
+
if (maxOutputTokens !== void 0)
|
|
37937
|
+
resolved.maxOutputTokens = maxOutputTokens;
|
|
37938
|
+
if (probed?.reasoning !== void 0)
|
|
37939
|
+
resolved.reasoning = probed.reasoning;
|
|
37940
|
+
for (const knob of ["temperature", "topP", "topK", "repetitionPenalty"]) {
|
|
37941
|
+
const value = declared?.[knob];
|
|
37942
|
+
if (typeof value === "number")
|
|
37943
|
+
resolved[knob] = value;
|
|
37944
|
+
}
|
|
37945
|
+
return resolved;
|
|
37946
|
+
}
|
|
37947
|
+
function catalogModelIds2(entry, catalog) {
|
|
37948
|
+
return entry.models?.length ? entry.models : catalog.map((model) => model.id);
|
|
37949
|
+
}
|
|
37950
|
+
function clearEndpointCatalog3(baseUrl) {
|
|
37951
|
+
if (baseUrl === void 0) {
|
|
37952
|
+
memory.clear();
|
|
37953
|
+
inFlight2.clear();
|
|
37954
|
+
sweptThisProcess = false;
|
|
37252
37955
|
return;
|
|
37253
|
-
|
|
37254
|
-
|
|
37255
|
-
|
|
37256
|
-
|
|
37257
|
-
at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
37258
|
-
verdict: verdict.verdict,
|
|
37259
|
-
...verdict.verdict === "hand_off" ? { brief: verdict.brief } : {}
|
|
37260
|
-
});
|
|
37956
|
+
}
|
|
37957
|
+
const key = normalizeBaseUrl(baseUrl);
|
|
37958
|
+
memory.delete(key);
|
|
37959
|
+
inFlight2.delete(key);
|
|
37261
37960
|
}
|
|
37262
|
-
async function
|
|
37263
|
-
const
|
|
37264
|
-
const
|
|
37265
|
-
const
|
|
37266
|
-
|
|
37267
|
-
|
|
37268
|
-
|
|
37269
|
-
|
|
37270
|
-
|
|
37271
|
-
|
|
37272
|
-
|
|
37273
|
-
|
|
37274
|
-
|
|
37275
|
-
|
|
37276
|
-
|
|
37277
|
-
|
|
37278
|
-
|
|
37279
|
-
|
|
37280
|
-
try {
|
|
37281
|
-
const text = input.text.trim();
|
|
37282
|
-
const standing = (0, duetPlan_js_1.duetPlanWireForSegment)(record) !== void 0 ? record : null;
|
|
37283
|
-
if (state.last !== null) {
|
|
37284
|
-
emit(sink, followupRow(state.last, standing, text, at));
|
|
37285
|
-
state.last = null;
|
|
37286
|
-
}
|
|
37287
|
-
const journal = (stage12, advisor, route, assumptions2) => {
|
|
37288
|
-
const id = (0, duetRoutingLog_js_1.newDecisionId)();
|
|
37289
|
-
const session = (0, duetRoutingLog_js_1.sessionKey)(input.sessionId);
|
|
37290
|
-
emit(sink, {
|
|
37291
|
-
kind: "decision",
|
|
37292
|
-
v: duetRoutingLog_js_1.DUET_ROUTING_LOG_SCHEMA,
|
|
37293
|
-
id,
|
|
37294
|
-
at,
|
|
37295
|
-
...session !== void 0 ? { session } : {},
|
|
37296
|
-
entry,
|
|
37297
|
-
planVersion: standing?.version ?? 0,
|
|
37298
|
-
turnUnderVersion: state.turnsUnderVersion,
|
|
37299
|
-
prompt: text,
|
|
37300
|
-
assumptions: assumptions2,
|
|
37301
|
-
...executorContext(input.workspaceRoot),
|
|
37302
|
-
stage1: stage12,
|
|
37303
|
-
router: routerVerdict,
|
|
37304
|
-
advisor: advisor === null ? null : {
|
|
37305
|
-
stage: advisor.stage,
|
|
37306
|
-
signals: advisor.signals,
|
|
37307
|
-
guards: advisor.guards,
|
|
37308
|
-
flagged: advisor.flagged,
|
|
37309
|
-
reason: advisor.reason
|
|
37310
|
-
},
|
|
37311
|
-
route,
|
|
37312
|
-
latencyMs: Math.max(0, now2() - started)
|
|
37313
|
-
});
|
|
37314
|
-
state.last = {
|
|
37315
|
-
decisionId: id,
|
|
37316
|
-
prompt: text,
|
|
37317
|
-
route,
|
|
37318
|
-
planVersion: standing?.version ?? 0,
|
|
37319
|
-
planText: standing?.plan ?? null,
|
|
37320
|
-
scopeChanged: standing?.scopeChanged ?? false,
|
|
37321
|
-
planningFailures: standing?.planningFailures ?? 0,
|
|
37322
|
-
executorFailures: standing?.executorFailures ?? 0
|
|
37323
|
-
};
|
|
37324
|
-
};
|
|
37325
|
-
if (standing === null) {
|
|
37326
|
-
resetForVersion(state, null);
|
|
37327
|
-
if (text !== "") {
|
|
37328
|
-
const stage12 = stage1Verdict(null, text, entry);
|
|
37329
|
-
journal(stage12, null, stage12.verdict, []);
|
|
37330
|
-
}
|
|
37331
|
-
return untouched(record);
|
|
37332
|
-
}
|
|
37333
|
-
const plan = standing;
|
|
37334
|
-
if (state.planVersion !== plan.version)
|
|
37335
|
-
resetForVersion(state, plan.version);
|
|
37336
|
-
state.turnsUnderVersion += 1;
|
|
37337
|
-
if (text === "")
|
|
37338
|
-
return untouched(record);
|
|
37339
|
-
const assumptions = parsePlanAssumptions(plan.plan);
|
|
37340
|
-
const stage1 = stage1Verdict(plan, text, entry);
|
|
37341
|
-
if (stage1.verdict === "plan") {
|
|
37342
|
-
journal(stage1, null, "plan", assumptions);
|
|
37343
|
-
return untouched(record);
|
|
37344
|
-
}
|
|
37345
|
-
if (entry === "planner") {
|
|
37346
|
-
journal(stage1, null, "execute", assumptions);
|
|
37347
|
-
return untouched(record);
|
|
37348
|
-
}
|
|
37349
|
-
const decision = {
|
|
37350
|
-
at,
|
|
37351
|
-
planVersion: plan.version,
|
|
37352
|
-
turnUnderVersion: state.turnsUnderVersion,
|
|
37353
|
-
text: text.length > DECISION_TEXT_HEAD ? `${text.slice(0, DECISION_TEXT_HEAD - 1)}\u2026` : text,
|
|
37354
|
-
stage: "cues",
|
|
37355
|
-
signals: {},
|
|
37356
|
-
guards: {},
|
|
37357
|
-
flagged: null,
|
|
37358
|
-
reason: null,
|
|
37359
|
-
latencyMs: 0
|
|
37360
|
-
};
|
|
37361
|
-
let candidate = null;
|
|
37362
|
-
const feedbackCue = negativeFeedbackCueIn(text);
|
|
37363
|
-
const negationCue = negationCueIn(text);
|
|
37364
|
-
if (feedbackCue !== null)
|
|
37365
|
-
decision.signals.feedbackCue = feedbackCue;
|
|
37366
|
-
if (negationCue !== null)
|
|
37367
|
-
decision.signals.negationCue = negationCue;
|
|
37368
|
-
if (feedbackCue !== null) {
|
|
37369
|
-
candidate = { flag: "user_negative_feedback", reason: "negative_feedback_cue", ids: [] };
|
|
37370
|
-
}
|
|
37371
|
-
if (candidate === null) {
|
|
37372
|
-
const endpoint = await advisorEndpoint(input.workspaceRoot);
|
|
37373
|
-
const models = endpoint?.routing.routingModels;
|
|
37374
|
-
if (endpoint !== null && models !== void 0) {
|
|
37375
|
-
candidate = await semanticStages({
|
|
37376
|
-
plan,
|
|
37377
|
-
assumptions,
|
|
37378
|
-
text,
|
|
37379
|
-
negationCue,
|
|
37380
|
-
dial: { baseUrl: endpoint.routing.baseUrl, apiKey: endpoint.routing.apiKey },
|
|
37381
|
-
models,
|
|
37382
|
-
executorModel: endpoint.executorModel,
|
|
37383
|
-
state,
|
|
37384
|
-
decision,
|
|
37385
|
-
fetchImpl: input.fetchImpl
|
|
37386
|
-
}, now2);
|
|
37387
|
-
}
|
|
37388
|
-
}
|
|
37389
|
-
if (candidate !== null && state.turnsUnderVersion < exports2.DUET_ADVISOR_THRESHOLDS.cooldownTurns) {
|
|
37390
|
-
decision.guards.cooldown = true;
|
|
37391
|
-
candidate = null;
|
|
37392
|
-
}
|
|
37393
|
-
let advised = plan;
|
|
37394
|
-
if (candidate !== null) {
|
|
37395
|
-
advised = candidate.flag === "user_negative_feedback" ? { ...plan, userNegativeFeedback: true } : { ...plan, architectureDecisionRequired: true };
|
|
37396
|
-
decision.flagged = candidate.flag;
|
|
37397
|
-
decision.reason = candidate.reason;
|
|
37961
|
+
async function endpointModelViews2(entry, options = {}) {
|
|
37962
|
+
const catalog = await endpointCatalog2(entry, options);
|
|
37963
|
+
const pinned = new Set(entry.models ?? []);
|
|
37964
|
+
const ids = [...pinned, ...catalog.map((model) => model.id).filter((id) => !pinned.has(id))];
|
|
37965
|
+
return ids.map((id) => {
|
|
37966
|
+
const resolved = resolveModelSettings2(entry, id, catalog);
|
|
37967
|
+
const declared = entry.modelConfig?.[id];
|
|
37968
|
+
const view = { id, pinned: pinned.has(id) };
|
|
37969
|
+
if (resolved.contextWindow !== void 0)
|
|
37970
|
+
view.contextWindow = resolved.contextWindow;
|
|
37971
|
+
if (resolved.maxOutputTokens !== void 0)
|
|
37972
|
+
view.maxOutputTokens = resolved.maxOutputTokens;
|
|
37973
|
+
if (resolved.reasoning !== void 0)
|
|
37974
|
+
view.reasoning = resolved.reasoning;
|
|
37975
|
+
if (declared?.contextWindow !== void 0 || declared?.maxOutputTokens !== void 0) {
|
|
37976
|
+
view.source = "user";
|
|
37977
|
+
} else if (view.contextWindow !== void 0 || view.maxOutputTokens !== void 0) {
|
|
37978
|
+
view.source = "endpoint";
|
|
37398
37979
|
}
|
|
37399
|
-
|
|
37400
|
-
|
|
37401
|
-
return {
|
|
37402
|
-
record: advised,
|
|
37403
|
-
flagged: decision.flagged,
|
|
37404
|
-
reason: decision.reason,
|
|
37405
|
-
assumptionIds: candidate?.ids ?? [],
|
|
37406
|
-
decision,
|
|
37407
|
-
note: duetRoutingAdviceNote(decision.reason, candidate?.ids ?? [])
|
|
37408
|
-
};
|
|
37409
|
-
} catch {
|
|
37410
|
-
return untouched(record);
|
|
37411
|
-
}
|
|
37980
|
+
return view;
|
|
37981
|
+
});
|
|
37412
37982
|
}
|
|
37413
|
-
function
|
|
37414
|
-
|
|
37983
|
+
async function updateCustomProviderModels2(name2, update, tier = "user", opts = {}) {
|
|
37984
|
+
const entry = await (0, customProviders_1.getCustomProvider)(name2, opts);
|
|
37985
|
+
if (entry === null)
|
|
37986
|
+
return false;
|
|
37987
|
+
const next = { ...entry };
|
|
37988
|
+
if (update.models !== void 0) {
|
|
37989
|
+
if (update.models.length)
|
|
37990
|
+
next.models = update.models;
|
|
37991
|
+
else
|
|
37992
|
+
delete next.models;
|
|
37993
|
+
}
|
|
37994
|
+
if (update.modelConfig !== void 0) {
|
|
37995
|
+
const kept = Object.entries(update.modelConfig).map(([id, raw]) => [id, (0, customProviders_1.normalizeModelConfig)(raw)]).filter(([, value]) => value !== void 0 && Object.keys(value).length > 0);
|
|
37996
|
+
if (kept.length)
|
|
37997
|
+
next.modelConfig = Object.fromEntries(kept);
|
|
37998
|
+
else
|
|
37999
|
+
delete next.modelConfig;
|
|
38000
|
+
}
|
|
38001
|
+
await (0, customProviders_1.saveCustomProvider)(next, tier, opts);
|
|
38002
|
+
clearEndpointCatalog3(entry.baseUrl);
|
|
38003
|
+
return true;
|
|
37415
38004
|
}
|
|
37416
|
-
|
|
38005
|
+
}
|
|
38006
|
+
});
|
|
38007
|
+
|
|
38008
|
+
// ../packages/orion-client-core/dist/duetExecutorCatalog.js
|
|
38009
|
+
var require_duetExecutorCatalog = __commonJS({
|
|
38010
|
+
"../packages/orion-client-core/dist/duetExecutorCatalog.js"(exports2) {
|
|
38011
|
+
"use strict";
|
|
38012
|
+
Object.defineProperty(exports2, "__esModule", { value: true });
|
|
38013
|
+
exports2.LOCAL_EXECUTOR_READ_BUDGET_MS = void 0;
|
|
38014
|
+
exports2.localExecutorOptions = localExecutorOptions2;
|
|
38015
|
+
exports2.duetExecutorChoiceFor = duetExecutorChoiceFor2;
|
|
38016
|
+
exports2.isLocalExecutorChoice = isLocalExecutorChoice;
|
|
38017
|
+
exports2.resolveDuetExecutorChoice = resolveDuetExecutorChoice2;
|
|
38018
|
+
var customProviders_js_1 = require_customProviders();
|
|
38019
|
+
var customProviderModels_js_1 = require_customProviderModels();
|
|
38020
|
+
exports2.LOCAL_EXECUTOR_READ_BUDGET_MS = 3e3;
|
|
38021
|
+
async function localExecutorOptions2(input = {}) {
|
|
38022
|
+
const { catalog, timeoutMs, ...opts } = input;
|
|
38023
|
+
let entries;
|
|
37417
38024
|
try {
|
|
37418
|
-
|
|
37419
|
-
if (choice === null || !(0, customProviders_js_1.isCustomProviderRef)(choice.provider))
|
|
37420
|
-
return { kind: "platform" };
|
|
37421
|
-
const name2 = (0, customProviders_js_1.parseCustomProviderRef)(choice.provider) ?? "";
|
|
37422
|
-
const entry = await (0, customProviders_js_1.getCustomProvider)(name2, { workspaceRoot: workspaceRoot ?? null });
|
|
37423
|
-
if (entry === null)
|
|
37424
|
-
return { kind: "missing", name: name2 };
|
|
37425
|
-
return {
|
|
37426
|
-
kind: "local",
|
|
37427
|
-
name: name2,
|
|
37428
|
-
loopback: (0, customProviders_js_1.isLoopbackEndpoint)(entry.baseUrl),
|
|
37429
|
-
embeddings: entry.routingModels?.embeddings !== void 0,
|
|
37430
|
-
rerank: entry.routingModels?.rerank !== void 0,
|
|
37431
|
-
judge: entry.routingModels?.judge ?? null
|
|
37432
|
-
};
|
|
38025
|
+
entries = await (0, customProviders_js_1.loadCustomProviders)(opts);
|
|
37433
38026
|
} catch {
|
|
37434
|
-
return
|
|
38027
|
+
return [];
|
|
37435
38028
|
}
|
|
37436
|
-
|
|
37437
|
-
|
|
37438
|
-
|
|
37439
|
-
|
|
37440
|
-
|
|
37441
|
-
|
|
37442
|
-
|
|
37443
|
-
|
|
37444
|
-
|
|
37445
|
-
|
|
37446
|
-
|
|
37447
|
-
|
|
37448
|
-
|
|
37449
|
-
|
|
37450
|
-
|
|
37451
|
-
|
|
37452
|
-
|
|
37453
|
-
|
|
37454
|
-
|
|
37455
|
-
|
|
37456
|
-
}
|
|
37457
|
-
if (rerank) {
|
|
37458
|
-
parts2.push("plan-assumption checks");
|
|
37459
|
-
via.push("rerank");
|
|
37460
|
-
}
|
|
37461
|
-
return `Duet routing: rules + ${parts2.join(" + ")} (${via.join(" + ")} on '${name2}').`;
|
|
38029
|
+
if (entries.length === 0)
|
|
38030
|
+
return [];
|
|
38031
|
+
const read = (options) => Promise.all(entries.map(async (entry) => {
|
|
38032
|
+
try {
|
|
38033
|
+
const views = await (0, customProviderModels_js_1.endpointModelViews)(entry, options);
|
|
38034
|
+
return views.map((view) => {
|
|
38035
|
+
const option = {
|
|
38036
|
+
provider: `custom:${entry.name}`,
|
|
38037
|
+
endpoint: entry.name,
|
|
38038
|
+
model: view.id,
|
|
38039
|
+
pinned: view.pinned
|
|
38040
|
+
};
|
|
38041
|
+
if (view.contextWindow !== void 0)
|
|
38042
|
+
option.contextWindow = view.contextWindow;
|
|
38043
|
+
if (view.maxOutputTokens !== void 0)
|
|
38044
|
+
option.maxOutputTokens = view.maxOutputTokens;
|
|
38045
|
+
return option;
|
|
38046
|
+
});
|
|
38047
|
+
} catch {
|
|
38048
|
+
return [];
|
|
37462
38049
|
}
|
|
38050
|
+
})).then((perEndpoint) => perEndpoint.flat());
|
|
38051
|
+
const full = read(catalog ?? {});
|
|
38052
|
+
const budget = timeoutMs ?? exports2.LOCAL_EXECUTOR_READ_BUDGET_MS;
|
|
38053
|
+
if (catalog?.cachedOnly === true || budget <= 0)
|
|
38054
|
+
return full;
|
|
38055
|
+
let timer;
|
|
38056
|
+
const fallback = new Promise((resolve5) => {
|
|
38057
|
+
timer = setTimeout(() => resolve5(read({ ...catalog, cachedOnly: true })), budget);
|
|
38058
|
+
});
|
|
38059
|
+
try {
|
|
38060
|
+
return await Promise.race([full, fallback]);
|
|
38061
|
+
} finally {
|
|
38062
|
+
if (timer !== void 0)
|
|
38063
|
+
clearTimeout(timer);
|
|
38064
|
+
void full.catch(() => void 0);
|
|
37463
38065
|
}
|
|
37464
38066
|
}
|
|
38067
|
+
function duetExecutorChoiceFor2(option) {
|
|
38068
|
+
return {
|
|
38069
|
+
provider: option.provider,
|
|
38070
|
+
model: option.model,
|
|
38071
|
+
...option.contextWindow !== void 0 ? { contextWindow: option.contextWindow } : {}
|
|
38072
|
+
};
|
|
38073
|
+
}
|
|
38074
|
+
function isLocalExecutorChoice(choice) {
|
|
38075
|
+
return typeof choice?.provider === "string" && choice.provider.startsWith("custom:");
|
|
38076
|
+
}
|
|
38077
|
+
async function resolveDuetExecutorChoice2(choice, input = {}) {
|
|
38078
|
+
if (!isLocalExecutorChoice(choice) || choice.contextWindow !== void 0)
|
|
38079
|
+
return choice;
|
|
38080
|
+
const found = (await localExecutorOptions2(input)).find((option) => option.provider === choice.provider && option.model === choice.model);
|
|
38081
|
+
return found === void 0 ? choice : { ...choice, ...duetExecutorChoiceFor2(found), ...choice.effort ? { effort: choice.effort } : {} };
|
|
38082
|
+
}
|
|
37465
38083
|
}
|
|
37466
38084
|
});
|
|
37467
38085
|
|
|
@@ -70770,6 +71388,8 @@ var require_dist = __commonJS({
|
|
|
70770
71388
|
__exportStar(require_duetEntry(), exports2);
|
|
70771
71389
|
__exportStar(require_duetRouterModel(), exports2);
|
|
70772
71390
|
__exportStar(require_duetRouterInstall(), exports2);
|
|
71391
|
+
__exportStar(require_duetExecutorGate(), exports2);
|
|
71392
|
+
__exportStar(require_duetExecutorGateStatus(), exports2);
|
|
70773
71393
|
__exportStar(require_duetPlan(), exports2);
|
|
70774
71394
|
__exportStar(require_duetPlanners(), exports2);
|
|
70775
71395
|
__exportStar(require_repoIdentity(), exports2);
|
|
@@ -91458,18 +92078,20 @@ ${(0, import_client_core20.duetRoutingSummaryLine)(await (0, import_client_core2
|
|
|
91458
92078
|
kind: "local",
|
|
91459
92079
|
name: "duet-entry",
|
|
91460
92080
|
aliases: ["entry"],
|
|
91461
|
-
description: "Choose who decides plan vs execute in Duet mode \u2014 the planner, or
|
|
91462
|
-
keywords: ["duet", "planner", "router", "plan", "execute", "hand off"],
|
|
91463
|
-
argumentHint: "[planner|router]",
|
|
92081
|
+
description: "Choose who decides plan vs execute in Duet mode \u2014 the planner, the router, or your executor",
|
|
92082
|
+
keywords: ["duet", "planner", "router", "executor", "plan", "execute", "hand off"],
|
|
92083
|
+
argumentHint: "[planner|router|executor]",
|
|
91464
92084
|
run: async (args2, ctx) => {
|
|
91465
92085
|
const workspaceRoot = ctx.config?.workspaceRoot;
|
|
91466
92086
|
const typed = (0, import_client_core20.normalizeDuetEntry)(args2);
|
|
91467
92087
|
const routerStatus = await (0, import_client_core20.describeDuetRouterModel)().catch(() => null);
|
|
92088
|
+
const executorStatus = await (0, import_client_core20.describeDuetExecutorGateCached)({ workspaceRoot }).catch(() => null);
|
|
91468
92089
|
const save = async (entry) => {
|
|
91469
|
-
const availability = (0, import_client_core20.duetEntryOptionAvailability)(entry, routerStatus);
|
|
92090
|
+
const availability = (0, import_client_core20.duetEntryOptionAvailability)(entry, routerStatus, executorStatus);
|
|
91470
92091
|
if (availability.disabled) {
|
|
91471
92092
|
ctx.print(`${(0, import_client_core20.duetEntryLabel)(entry)}: ${availability.note ?? "unavailable"}`, "warning");
|
|
91472
|
-
if (routerStatus !== null) ctx.print((0, import_client_core20.duetRouterStatusLine)(routerStatus), "info");
|
|
92093
|
+
if (entry === "router" && routerStatus !== null) ctx.print((0, import_client_core20.duetRouterStatusLine)(routerStatus), "info");
|
|
92094
|
+
if (entry === "executor" && executorStatus !== null) ctx.print((0, import_client_core20.executorGateStatusLine)(executorStatus), "info");
|
|
91473
92095
|
return;
|
|
91474
92096
|
}
|
|
91475
92097
|
await (0, import_client_core20.setDuetEntry)(entry);
|
|
@@ -91481,7 +92103,7 @@ ${(0, import_client_core20.duetRoutingSummaryLine)(await (0, import_client_core2
|
|
|
91481
92103
|
return;
|
|
91482
92104
|
}
|
|
91483
92105
|
if (args2.trim() !== "") {
|
|
91484
|
-
ctx.print("Usage: /duet-entry [planner|router]", "warning");
|
|
92106
|
+
ctx.print("Usage: /duet-entry [planner|router|executor]", "warning");
|
|
91485
92107
|
return;
|
|
91486
92108
|
}
|
|
91487
92109
|
const active = await (0, import_client_core20.loadDuetEntry)({ workspaceRoot });
|
|
@@ -91491,7 +92113,7 @@ ${(0, import_client_core20.duetRoutingSummaryLine)(await (0, import_client_core2
|
|
|
91491
92113
|
kind: "select",
|
|
91492
92114
|
title: `${import_client_core20.DUET_ENTRY_INFO.label} \xB7 current: ${(0, import_client_core20.duetEntryLabel)(active)}`,
|
|
91493
92115
|
options: import_client_core20.DUET_ENTRY_OPTIONS.map((option) => {
|
|
91494
|
-
const availability = (0, import_client_core20.duetEntryOptionAvailability)(option.value, routerStatus);
|
|
92116
|
+
const availability = (0, import_client_core20.duetEntryOptionAvailability)(option.value, routerStatus, executorStatus);
|
|
91495
92117
|
return {
|
|
91496
92118
|
label: option.label,
|
|
91497
92119
|
value: option.value,
|
|
@@ -111165,7 +111787,7 @@ function OrionRing() {
|
|
|
111165
111787
|
|
|
111166
111788
|
// src/services/version.ts
|
|
111167
111789
|
function tuiVersion() {
|
|
111168
|
-
return "0.1.
|
|
111790
|
+
return "0.1.24".length > 0 ? "0.1.24" : null;
|
|
111169
111791
|
}
|
|
111170
111792
|
|
|
111171
111793
|
// src/components/layout/WelcomeCard.tsx
|
|
@@ -118253,6 +118875,11 @@ async function main() {
|
|
|
118253
118875
|
const duetAdvisorState = (0, import_client_core49.createDuetAdvisorState)();
|
|
118254
118876
|
const duetRouterGate = (0, import_client_core49.createDuetRouterGate)({
|
|
118255
118877
|
loadEncoder: (0, import_client_core49.createDefaultDuetRouterEncoder)(),
|
|
118878
|
+
// "Executor decides": the same gate object owns the executor's one-token scorer, so the
|
|
118879
|
+
// turn path below has ONE call whichever entry is set (`duetExecutorGate.ts`).
|
|
118880
|
+
executorGate: (0, import_client_core49.createDuetExecutorGate)({
|
|
118881
|
+
onError: (stage, problem) => console.error(`[duet-executor-gate] ${stage} failed: ${problem}`)
|
|
118882
|
+
}),
|
|
118256
118883
|
onError: (stage, error) => (
|
|
118257
118884
|
// Same breadcrumb the IDE and the Power App leave (the log redirect captures it, so it
|
|
118258
118885
|
// never corrupts the alt screen): without it a load or classify failure is invisible
|
|
@@ -119226,7 +119853,11 @@ async function main() {
|
|
|
119226
119853
|
if (appStore.getState().mode === "duet") {
|
|
119227
119854
|
const routed = await duetRouterGate.prepareTurn(
|
|
119228
119855
|
(0, import_client_core49.duetEntryWireForSegment)(config.workspaceRoot),
|
|
119229
|
-
routerText
|
|
119856
|
+
routerText,
|
|
119857
|
+
// What the executor gate's prompt is built from: the standing record as it stands
|
|
119858
|
+
// BEFORE the advisor runs (the advisor may flag it for this turn; the gate asks the
|
|
119859
|
+
// executor about the request under the plan the user actually approved).
|
|
119860
|
+
{ workspaceRoot: config.workspaceRoot, record: appStore.getState().duetPlan }
|
|
119230
119861
|
);
|
|
119231
119862
|
duetEntry = routed.entry;
|
|
119232
119863
|
duetRouterVerdict = routed.verdict;
|