zelari-code 2.34.0 → 2.34.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/councilDispatcher.js +1 -0
- package/dist/cli/councilDispatcher.js.map +1 -1
- package/dist/cli/headless/liveTurnAbort.js +67 -0
- package/dist/cli/headless/liveTurnAbort.js.map +1 -0
- package/dist/cli/headless/runOneTurn.js +5 -1
- package/dist/cli/headless/runOneTurn.js.map +1 -1
- package/dist/cli/headless.js.map +1 -1
- package/dist/cli/main.bundled.js +819 -401
- package/dist/cli/main.bundled.js.map +4 -4
- package/dist/cli/runHeadless.js +55 -7
- package/dist/cli/runHeadless.js.map +1 -1
- package/dist/cli/serve/askUserBridge.js +59 -0
- package/dist/cli/serve/askUserBridge.js.map +1 -0
- package/dist/cli/serve/harnessServer.js +14 -2
- package/dist/cli/serve/harnessServer.js.map +1 -1
- package/dist/cli/serve/permissionBridge.js +64 -8
- package/dist/cli/serve/permissionBridge.js.map +1 -1
- package/dist/cli/serve/sessionControl.js +5 -3
- package/dist/cli/serve/sessionControl.js.map +1 -1
- package/dist/cli/toolRegistry.js +32 -17
- package/dist/cli/toolRegistry.js.map +1 -1
- package/dist/cli/tools/krakenModel.js +18 -0
- package/dist/cli/tools/krakenModel.js.map +1 -1
- package/dist/cli/tools/taskTool.js +59 -9
- package/dist/cli/tools/taskTool.js.map +1 -1
- package/dist/cli/utils/doctor.js +24 -3
- package/dist/cli/utils/doctor.js.map +1 -1
- package/dist/cli/utils/fixPath.js +18 -14
- package/dist/cli/utils/fixPath.js.map +1 -1
- package/dist/cli/utils/streamScrub.js +5 -3
- package/dist/cli/utils/streamScrub.js.map +1 -1
- package/dist/cli/zelariMission.js +14 -0
- package/dist/cli/zelariMission.js.map +1 -1
- package/package.json +2 -2
package/dist/cli/main.bundled.js
CHANGED
|
@@ -28372,6 +28372,136 @@ var init_textLoopDetect = __esm({
|
|
|
28372
28372
|
}
|
|
28373
28373
|
});
|
|
28374
28374
|
|
|
28375
|
+
// packages/core/dist/agents/council/outputCleaning.js
|
|
28376
|
+
function extractBalancedJsonObject(s) {
|
|
28377
|
+
const start = s.indexOf("{");
|
|
28378
|
+
if (start < 0)
|
|
28379
|
+
return null;
|
|
28380
|
+
let depth = 0;
|
|
28381
|
+
let inString = false;
|
|
28382
|
+
let escape = false;
|
|
28383
|
+
for (let i = start; i < s.length; i++) {
|
|
28384
|
+
const ch = s[i];
|
|
28385
|
+
if (inString) {
|
|
28386
|
+
if (escape) {
|
|
28387
|
+
escape = false;
|
|
28388
|
+
continue;
|
|
28389
|
+
}
|
|
28390
|
+
if (ch === "\\") {
|
|
28391
|
+
escape = true;
|
|
28392
|
+
continue;
|
|
28393
|
+
}
|
|
28394
|
+
if (ch === '"')
|
|
28395
|
+
inString = false;
|
|
28396
|
+
continue;
|
|
28397
|
+
}
|
|
28398
|
+
if (ch === '"') {
|
|
28399
|
+
inString = true;
|
|
28400
|
+
continue;
|
|
28401
|
+
}
|
|
28402
|
+
if (ch === "{")
|
|
28403
|
+
depth++;
|
|
28404
|
+
else if (ch === "}") {
|
|
28405
|
+
depth--;
|
|
28406
|
+
if (depth === 0)
|
|
28407
|
+
return s.slice(start, i + 1);
|
|
28408
|
+
}
|
|
28409
|
+
}
|
|
28410
|
+
return null;
|
|
28411
|
+
}
|
|
28412
|
+
function parseClarificationRequest(text) {
|
|
28413
|
+
const start = text.indexOf(QUESTION_MARKER);
|
|
28414
|
+
if (start < 0)
|
|
28415
|
+
return null;
|
|
28416
|
+
const rest = text.slice(start + QUESTION_MARKER.length);
|
|
28417
|
+
const end = rest.indexOf(QUESTION_END_MARKER);
|
|
28418
|
+
const block = end >= 0 ? rest.slice(0, end) : rest;
|
|
28419
|
+
const cleaned = block.replace(/```json\n?/g, "").replace(/```\n?/g, "").trim();
|
|
28420
|
+
const jsonText = extractBalancedJsonObject(cleaned) ?? (() => {
|
|
28421
|
+
const objStart = cleaned.indexOf("{");
|
|
28422
|
+
const objEnd = cleaned.lastIndexOf("}");
|
|
28423
|
+
return objStart >= 0 && objEnd > objStart ? cleaned.slice(objStart, objEnd + 1) : cleaned;
|
|
28424
|
+
})();
|
|
28425
|
+
try {
|
|
28426
|
+
const parsed = JSON.parse(jsonText);
|
|
28427
|
+
if (typeof parsed.question !== "string" || !parsed.question.trim())
|
|
28428
|
+
return null;
|
|
28429
|
+
return {
|
|
28430
|
+
question: parsed.question.trim(),
|
|
28431
|
+
choices: Array.isArray(parsed.choices) ? parsed.choices.filter((c) => typeof c === "string" && c.trim().length > 0).map((c) => c.trim()) : void 0,
|
|
28432
|
+
context: typeof parsed.context === "string" ? parsed.context.trim() : void 0
|
|
28433
|
+
};
|
|
28434
|
+
} catch {
|
|
28435
|
+
return null;
|
|
28436
|
+
}
|
|
28437
|
+
}
|
|
28438
|
+
function hasInteractiveClarification(text) {
|
|
28439
|
+
const c = parseClarificationRequest(text);
|
|
28440
|
+
return !!(c && c.choices && c.choices.length >= 2);
|
|
28441
|
+
}
|
|
28442
|
+
function stripQuestionBlocks(text) {
|
|
28443
|
+
let out = "";
|
|
28444
|
+
let rest = text;
|
|
28445
|
+
while (true) {
|
|
28446
|
+
const start = rest.indexOf(QUESTION_MARKER);
|
|
28447
|
+
if (start < 0) {
|
|
28448
|
+
out += rest;
|
|
28449
|
+
break;
|
|
28450
|
+
}
|
|
28451
|
+
out += rest.slice(0, start);
|
|
28452
|
+
const afterMarker = rest.slice(start + QUESTION_MARKER.length);
|
|
28453
|
+
const trimmed = afterMarker.replace(/^\s+/, "");
|
|
28454
|
+
if (!trimmed.startsWith("{")) {
|
|
28455
|
+
out += QUESTION_MARKER;
|
|
28456
|
+
rest = afterMarker;
|
|
28457
|
+
continue;
|
|
28458
|
+
}
|
|
28459
|
+
const endIdx = afterMarker.indexOf(QUESTION_END_MARKER);
|
|
28460
|
+
if (endIdx >= 0) {
|
|
28461
|
+
rest = afterMarker.slice(endIdx + QUESTION_END_MARKER.length);
|
|
28462
|
+
continue;
|
|
28463
|
+
}
|
|
28464
|
+
const json3 = extractBalancedJsonObject(trimmed);
|
|
28465
|
+
if (json3) {
|
|
28466
|
+
const jsonAt = afterMarker.indexOf(json3);
|
|
28467
|
+
rest = afterMarker.slice(jsonAt + json3.length);
|
|
28468
|
+
continue;
|
|
28469
|
+
}
|
|
28470
|
+
break;
|
|
28471
|
+
}
|
|
28472
|
+
return out.replace(/\n{3,}/g, "\n\n").trim();
|
|
28473
|
+
}
|
|
28474
|
+
function parseThinking(text) {
|
|
28475
|
+
const complete = text.match(/<think(?:ing)?>([\s\S]*?)<\/think(?:ing)?>/i);
|
|
28476
|
+
if (complete)
|
|
28477
|
+
return complete[1].trim();
|
|
28478
|
+
const open2 = text.match(/<think(?:ing)?>([\s\S]*)$/i);
|
|
28479
|
+
return open2 ? open2[1].trim() : "";
|
|
28480
|
+
}
|
|
28481
|
+
function cleanAgentContent(text, opts = {}) {
|
|
28482
|
+
const stripQuestion = opts.stripQuestion !== false;
|
|
28483
|
+
const stripThink = opts.stripThink !== false;
|
|
28484
|
+
let out = text;
|
|
28485
|
+
if (stripThink) {
|
|
28486
|
+
out = out.replace(/<think(?:ing)?>[\s\S]*?<\/think(?:ing)?>/gi, "").replace(/<think(?:ing)?>[\s\S]*$/gi, "").replace(/<\/think(?:ing)?>/gi, "");
|
|
28487
|
+
}
|
|
28488
|
+
out = out.replace(/<minimax:tool_call>[\s\S]*?<\/minimax:tool_call>/gi, "").replace(/<\/?minimax:tool_call>/gi, "").replace(/<tool_call>[\s\S]*?<\/tool_call>/gi, "").replace(/<\/?tool_call>/gi, "").replace(/<function_call>[\s\S]*?<\/function_call>/gi, "").replace(/<\/?function_call>/gi, "").replace(/<invoke\b[^>]*>[\s\S]*?<\/invoke>/gi, "").replace(/<\/invoke>/gi, "").replace(/<parameter\b[^>]*>[\s\S]*?<\/parameter>/gi, "").replace(/<\/parameter>/gi, "").replace(/\]\s*<\]\s*minimax\s*\[>\s*\[?<invoke\b[^>]*>[\s\S]*?<\/invoke>/gi, "").replace(/<minimax:tool_call>[\s\S]*$/gi, "").replace(/<tool_call>[\s\S]*$/gi, "").replace(/<function_call>[\s\S]*$/gi, "").replace(/<invoke\b[^>]*>[\s\S]*$/gi, "").replace(/\]\s*<\]\s*minimax\s*\[>[\s\S]*$/gi, "").replace(/^\s*\]\s*<\]\s*minimax\s*\[>.*$/gim, "").replace(/^\s*<\/?(?:tool_call|function_call|invoke|parameter|minimax:tool_call)\b[^>]*>\s*$/gim, "");
|
|
28489
|
+
if (stripQuestion) {
|
|
28490
|
+
out = stripQuestionBlocks(out);
|
|
28491
|
+
}
|
|
28492
|
+
out = out.replace(/\n{3,}/g, "\n\n").trim();
|
|
28493
|
+
return scrubProprietaryLeak(out);
|
|
28494
|
+
}
|
|
28495
|
+
var QUESTION_MARKER, QUESTION_END_MARKER;
|
|
28496
|
+
var init_outputCleaning = __esm({
|
|
28497
|
+
"packages/core/dist/agents/council/outputCleaning.js"() {
|
|
28498
|
+
"use strict";
|
|
28499
|
+
init_secrecyPolicy();
|
|
28500
|
+
QUESTION_MARKER = "---QUESTION---";
|
|
28501
|
+
QUESTION_END_MARKER = "---END---";
|
|
28502
|
+
}
|
|
28503
|
+
});
|
|
28504
|
+
|
|
28375
28505
|
// packages/core/dist/core/AgentHarness.js
|
|
28376
28506
|
function gateAdvice(hardLimit) {
|
|
28377
28507
|
return hardLimit ? "Finalize now with the evidence already collected; no further tool calls will run this turn." : "Prioritize verification/repair actions (test, typecheck, build, read failures) or finalize honestly.";
|
|
@@ -28668,6 +28798,7 @@ var init_AgentHarness = __esm({
|
|
|
28668
28798
|
init_requestSnapshot();
|
|
28669
28799
|
init_textLoopDetect();
|
|
28670
28800
|
init_ObserverBus();
|
|
28801
|
+
init_outputCleaning();
|
|
28671
28802
|
init_textLoopDetect();
|
|
28672
28803
|
TOOL_CALL_TRUNCATED_RECOVERY_MARKER = "[harness] Previous tool call was truncated";
|
|
28673
28804
|
TOOL_CALL_TRUNCATED_RECOVERY_USER = `${TOOL_CALL_TRUNCATED_RECOVERY_MARKER} by the provider before completion (finish_reason=tool_calls but no complete tool_call arrived). Retry with a shorter payload or split the work into smaller tool calls.`;
|
|
@@ -29562,7 +29693,7 @@ ${cached2}`
|
|
|
29562
29693
|
}
|
|
29563
29694
|
pendingNativeTools.length = 0;
|
|
29564
29695
|
}
|
|
29565
|
-
const clarificationPause =
|
|
29696
|
+
const clarificationPause = hasInteractiveClarification(turnText);
|
|
29566
29697
|
if (clarificationPause) {
|
|
29567
29698
|
finishRef.value = "stop";
|
|
29568
29699
|
finishRef.clarificationRequested = true;
|
|
@@ -32128,101 +32259,36 @@ var init_types7 = __esm({
|
|
|
32128
32259
|
}
|
|
32129
32260
|
});
|
|
32130
32261
|
|
|
32131
|
-
// packages/core/dist/agents/council/
|
|
32132
|
-
function
|
|
32133
|
-
|
|
32134
|
-
if (start < 0)
|
|
32135
|
-
return null;
|
|
32136
|
-
let depth = 0;
|
|
32137
|
-
let inString = false;
|
|
32138
|
-
let escape = false;
|
|
32139
|
-
for (let i = start; i < s.length; i++) {
|
|
32140
|
-
const ch = s[i];
|
|
32141
|
-
if (inString) {
|
|
32142
|
-
if (escape) {
|
|
32143
|
-
escape = false;
|
|
32144
|
-
continue;
|
|
32145
|
-
}
|
|
32146
|
-
if (ch === "\\") {
|
|
32147
|
-
escape = true;
|
|
32148
|
-
continue;
|
|
32149
|
-
}
|
|
32150
|
-
if (ch === '"')
|
|
32151
|
-
inString = false;
|
|
32152
|
-
continue;
|
|
32153
|
-
}
|
|
32154
|
-
if (ch === '"') {
|
|
32155
|
-
inString = true;
|
|
32156
|
-
continue;
|
|
32157
|
-
}
|
|
32158
|
-
if (ch === "{")
|
|
32159
|
-
depth++;
|
|
32160
|
-
else if (ch === "}") {
|
|
32161
|
-
depth--;
|
|
32162
|
-
if (depth === 0)
|
|
32163
|
-
return s.slice(start, i + 1);
|
|
32164
|
-
}
|
|
32165
|
-
}
|
|
32166
|
-
return null;
|
|
32262
|
+
// packages/core/dist/agents/council/cancel.js
|
|
32263
|
+
function isCouncilCancelled(signal) {
|
|
32264
|
+
return signal?.aborted === true;
|
|
32167
32265
|
}
|
|
32168
|
-
function
|
|
32169
|
-
|
|
32170
|
-
|
|
32171
|
-
|
|
32172
|
-
|
|
32173
|
-
|
|
32174
|
-
const block = end >= 0 ? rest.slice(0, end) : rest;
|
|
32175
|
-
const cleaned = block.replace(/```json\n?/g, "").replace(/```\n?/g, "").trim();
|
|
32176
|
-
const jsonText = extractBalancedJsonObject(cleaned) ?? (() => {
|
|
32177
|
-
const objStart = cleaned.indexOf("{");
|
|
32178
|
-
const objEnd = cleaned.lastIndexOf("}");
|
|
32179
|
-
return objStart >= 0 && objEnd > objStart ? cleaned.slice(objStart, objEnd + 1) : cleaned;
|
|
32180
|
-
})();
|
|
32181
|
-
try {
|
|
32182
|
-
const parsed = JSON.parse(jsonText);
|
|
32183
|
-
if (typeof parsed.question !== "string" || !parsed.question.trim())
|
|
32184
|
-
return null;
|
|
32185
|
-
return {
|
|
32186
|
-
question: parsed.question.trim(),
|
|
32187
|
-
choices: Array.isArray(parsed.choices) ? parsed.choices.filter((c) => typeof c === "string" && c.trim().length > 0).map((c) => c.trim()) : void 0,
|
|
32188
|
-
context: typeof parsed.context === "string" ? parsed.context.trim() : void 0
|
|
32189
|
-
};
|
|
32190
|
-
} catch {
|
|
32191
|
-
return null;
|
|
32266
|
+
function bindHarnessAbort(harness, signal) {
|
|
32267
|
+
if (!signal)
|
|
32268
|
+
return () => void 0;
|
|
32269
|
+
if (signal.aborted) {
|
|
32270
|
+
harness.cancel();
|
|
32271
|
+
return () => void 0;
|
|
32192
32272
|
}
|
|
32273
|
+
const onAbort = () => {
|
|
32274
|
+
harness.cancel();
|
|
32275
|
+
};
|
|
32276
|
+
signal.addEventListener("abort", onAbort);
|
|
32277
|
+
return () => {
|
|
32278
|
+
signal.removeEventListener("abort", onAbort);
|
|
32279
|
+
};
|
|
32193
32280
|
}
|
|
32194
|
-
function
|
|
32195
|
-
const
|
|
32196
|
-
|
|
32197
|
-
|
|
32198
|
-
|
|
32199
|
-
|
|
32200
|
-
if (complete)
|
|
32201
|
-
return complete[1].trim();
|
|
32202
|
-
const open2 = text.match(/<think(?:ing)?>([\s\S]*)$/i);
|
|
32203
|
-
return open2 ? open2[1].trim() : "";
|
|
32204
|
-
}
|
|
32205
|
-
function cleanAgentContent(text, opts = {}) {
|
|
32206
|
-
const stripQuestion = opts.stripQuestion !== false;
|
|
32207
|
-
const stripThink = opts.stripThink !== false;
|
|
32208
|
-
let out = text;
|
|
32209
|
-
if (stripThink) {
|
|
32210
|
-
out = out.replace(/<think(?:ing)?>[\s\S]*?<\/think(?:ing)?>/gi, "").replace(/<think(?:ing)?>[\s\S]*$/gi, "").replace(/<\/think(?:ing)?>/gi, "");
|
|
32211
|
-
}
|
|
32212
|
-
out = out.replace(/<minimax:tool_call>[\s\S]*?<\/minimax:tool_call>/gi, "").replace(/<\/?minimax:tool_call>/gi, "").replace(/<tool_call>[\s\S]*?<\/tool_call>/gi, "").replace(/<\/?tool_call>/gi, "").replace(/<function_call>[\s\S]*?<\/function_call>/gi, "").replace(/<\/?function_call>/gi, "").replace(/<invoke\b[^>]*>[\s\S]*?<\/invoke>/gi, "").replace(/<\/invoke>/gi, "").replace(/<parameter\b[^>]*>[\s\S]*?<\/parameter>/gi, "").replace(/<\/parameter>/gi, "").replace(/\]\s*<\]\s*minimax\s*\[>\s*\[?<invoke\b[^>]*>[\s\S]*?<\/invoke>/gi, "").replace(/<minimax:tool_call>[\s\S]*$/gi, "").replace(/<tool_call>[\s\S]*$/gi, "").replace(/<function_call>[\s\S]*$/gi, "").replace(/<invoke\b[^>]*>[\s\S]*$/gi, "").replace(/\]\s*<\]\s*minimax\s*\[>[\s\S]*$/gi, "").replace(/^\s*\]\s*<\]\s*minimax\s*\[>.*$/gim, "").replace(/^\s*<\/?(?:tool_call|function_call|invoke|parameter|minimax:tool_call)\b[^>]*>\s*$/gim, "");
|
|
32213
|
-
if (stripQuestion) {
|
|
32214
|
-
out = out.replace(/---QUESTION---[\s\S]*?---END---/g, "").replace(/---QUESTION---[\s\S]*$/g, "");
|
|
32281
|
+
async function* runHarnessWithAbort(harness, signal) {
|
|
32282
|
+
const unbind = bindHarnessAbort(harness, signal);
|
|
32283
|
+
try {
|
|
32284
|
+
yield* harness.run();
|
|
32285
|
+
} finally {
|
|
32286
|
+
unbind();
|
|
32215
32287
|
}
|
|
32216
|
-
out = out.replace(/\n{3,}/g, "\n\n").trim();
|
|
32217
|
-
return scrubProprietaryLeak(out);
|
|
32218
32288
|
}
|
|
32219
|
-
var
|
|
32220
|
-
|
|
32221
|
-
"packages/core/dist/agents/council/outputCleaning.js"() {
|
|
32289
|
+
var init_cancel = __esm({
|
|
32290
|
+
"packages/core/dist/agents/council/cancel.js"() {
|
|
32222
32291
|
"use strict";
|
|
32223
|
-
init_secrecyPolicy();
|
|
32224
|
-
QUESTION_MARKER = "---QUESTION---";
|
|
32225
|
-
QUESTION_END_MARKER = "---END---";
|
|
32226
32292
|
}
|
|
32227
32293
|
});
|
|
32228
32294
|
|
|
@@ -32531,6 +32597,8 @@ function buildRetryPrompt(missingToolNames) {
|
|
|
32531
32597
|
return `You did not emit the required workspace tools: ${names}. Call ${names} NOW with concrete arguments. No prose. No search.`;
|
|
32532
32598
|
}
|
|
32533
32599
|
async function* runRetryTurnForMember(args) {
|
|
32600
|
+
if (isCouncilCancelled(args.signal))
|
|
32601
|
+
return [];
|
|
32534
32602
|
const executableMissing = args.executableTools ? args.missingToolNames.filter((n) => args.executableTools.has(n)) : args.missingToolNames;
|
|
32535
32603
|
if (executableMissing.length === 0) {
|
|
32536
32604
|
return [];
|
|
@@ -32566,7 +32634,7 @@ async function* runRetryTurnForMember(args) {
|
|
|
32566
32634
|
providerStream: (params) => args.providerStream(params)
|
|
32567
32635
|
});
|
|
32568
32636
|
const retryEmitted = [];
|
|
32569
|
-
for await (const event of retryHarness.
|
|
32637
|
+
for await (const event of runHarnessWithAbort(retryHarness, args.signal)) {
|
|
32570
32638
|
if (event.type === "tool_execution_start") {
|
|
32571
32639
|
retryEmitted.push(event.toolName);
|
|
32572
32640
|
}
|
|
@@ -32575,6 +32643,8 @@ async function* runRetryTurnForMember(args) {
|
|
|
32575
32643
|
return retryEmitted;
|
|
32576
32644
|
}
|
|
32577
32645
|
async function* applyRetryIfMissing(args) {
|
|
32646
|
+
if (isCouncilCancelled(args.config.signal))
|
|
32647
|
+
return;
|
|
32578
32648
|
if (args.check.ok)
|
|
32579
32649
|
return;
|
|
32580
32650
|
const missingToolNames = args.check.missing.map((m) => m.split(" ")[0]);
|
|
@@ -32607,7 +32677,8 @@ async function* applyRetryIfMissing(args) {
|
|
|
32607
32677
|
toolRegistry: args.config.tools,
|
|
32608
32678
|
providerStream: args.config.providerStream,
|
|
32609
32679
|
runMode: args.config.runMode,
|
|
32610
|
-
languageModule: args.languageModule
|
|
32680
|
+
languageModule: args.languageModule,
|
|
32681
|
+
signal: args.config.signal
|
|
32611
32682
|
});
|
|
32612
32683
|
for await (const event of retryGenerator) {
|
|
32613
32684
|
if (event.type === "tool_execution_start") {
|
|
@@ -32626,6 +32697,7 @@ var init_retryTurn = __esm({
|
|
|
32626
32697
|
"packages/core/dist/agents/council/retryTurn.js"() {
|
|
32627
32698
|
"use strict";
|
|
32628
32699
|
init_AgentHarness();
|
|
32700
|
+
init_cancel();
|
|
32629
32701
|
init_toolSchemas();
|
|
32630
32702
|
init_memberMessages();
|
|
32631
32703
|
init_toolEmission();
|
|
@@ -32635,6 +32707,8 @@ var init_retryTurn = __esm({
|
|
|
32635
32707
|
|
|
32636
32708
|
// packages/core/dist/agents/council/chairmanDelivery.js
|
|
32637
32709
|
async function* applyCompletionRetry(args) {
|
|
32710
|
+
if (isCouncilCancelled(args.config.signal))
|
|
32711
|
+
return;
|
|
32638
32712
|
const check2 = checkImplementationCompletion(args.emittedToolNames);
|
|
32639
32713
|
if (check2.ok)
|
|
32640
32714
|
return;
|
|
@@ -32664,7 +32738,8 @@ async function* applyCompletionRetry(args) {
|
|
|
32664
32738
|
providerStream: args.config.providerStream,
|
|
32665
32739
|
runMode: args.config.runMode,
|
|
32666
32740
|
retryPrompt: buildImplementationVerifyRetryPrompt(retryTool),
|
|
32667
|
-
languageModule: args.languageModule
|
|
32741
|
+
languageModule: args.languageModule,
|
|
32742
|
+
signal: args.config.signal
|
|
32668
32743
|
});
|
|
32669
32744
|
for await (const event of retryGenerator) {
|
|
32670
32745
|
if (event.type === "tool_execution_start") {
|
|
@@ -32697,6 +32772,8 @@ ${blocks}
|
|
|
32697
32772
|
Rules: animate ONLY transform and opacity. Replace any box-shadow / background / background-position / filter / color / border-color / width / height / grid-template-rows used in @keyframes or transitions with transform/opacity equivalents (e.g. render a glow via a pseudo-element that scales and fades). For every classList.add('x') in the script, add a matching '.x' CSS rule. Use read_file to see the exact lines, then edit_file. When the listed items are fixed, stop \u2014 no summary.`;
|
|
32698
32773
|
}
|
|
32699
32774
|
async function* applyImplementationWriteRetry(args) {
|
|
32775
|
+
if (isCouncilCancelled(args.config.signal))
|
|
32776
|
+
return;
|
|
32700
32777
|
if (args.check.ok)
|
|
32701
32778
|
return;
|
|
32702
32779
|
if (!shouldRetryMember(["write_file"], 0))
|
|
@@ -32723,7 +32800,8 @@ async function* applyImplementationWriteRetry(args) {
|
|
|
32723
32800
|
providerStream: args.config.providerStream,
|
|
32724
32801
|
runMode: "implementation",
|
|
32725
32802
|
retryPrompt: buildImplementationWriteRetryPrompt(args.userMessage),
|
|
32726
|
-
languageModule: args.languageModule
|
|
32803
|
+
languageModule: args.languageModule,
|
|
32804
|
+
signal: args.config.signal
|
|
32727
32805
|
});
|
|
32728
32806
|
for await (const event of retryGenerator) {
|
|
32729
32807
|
if (event.type === "tool_execution_start")
|
|
@@ -32751,6 +32829,8 @@ async function* runChairmanDeliveryLoop(args) {
|
|
|
32751
32829
|
const zelariRoot = `${args.projectRoot}/.zelari`;
|
|
32752
32830
|
let attempt = 0;
|
|
32753
32831
|
while (attempt < maxAttempts) {
|
|
32832
|
+
if (isCouncilCancelled(args.config.signal))
|
|
32833
|
+
return false;
|
|
32754
32834
|
const report = runImplementationVerification({
|
|
32755
32835
|
projectRoot: args.projectRoot,
|
|
32756
32836
|
zelariRoot
|
|
@@ -32793,7 +32873,8 @@ async function* runChairmanDeliveryLoop(args) {
|
|
|
32793
32873
|
providerStream: args.config.providerStream,
|
|
32794
32874
|
runMode: "implementation",
|
|
32795
32875
|
retryPrompt: buildDeliveryFixPrompt(blocking, args.userMessage),
|
|
32796
|
-
languageModule: args.languageModule
|
|
32876
|
+
languageModule: args.languageModule,
|
|
32877
|
+
signal: args.config.signal
|
|
32797
32878
|
});
|
|
32798
32879
|
for await (const event of fixGenerator) {
|
|
32799
32880
|
if (event.type === "tool_execution_start")
|
|
@@ -32826,6 +32907,7 @@ var init_chairmanDelivery = __esm({
|
|
|
32826
32907
|
init_runChecks();
|
|
32827
32908
|
init_inlineJsAutofix();
|
|
32828
32909
|
init_retryTurn();
|
|
32910
|
+
init_cancel();
|
|
32829
32911
|
MAX_DELIVERY_ATTEMPTS = 2;
|
|
32830
32912
|
}
|
|
32831
32913
|
});
|
|
@@ -32887,6 +32969,8 @@ async function* runChairmanFixLoop(args) {
|
|
|
32887
32969
|
let current = Array.from(args.violations.values());
|
|
32888
32970
|
let attempt = 0;
|
|
32889
32971
|
while (current.length > 0 && attempt < maxAttempts) {
|
|
32972
|
+
if (isCouncilCancelled(args.config.signal))
|
|
32973
|
+
return;
|
|
32890
32974
|
attempt++;
|
|
32891
32975
|
try {
|
|
32892
32976
|
const fixGenerator = runRetryTurnForMember({
|
|
@@ -32907,7 +32991,8 @@ async function* runChairmanFixLoop(args) {
|
|
|
32907
32991
|
providerStream: args.config.providerStream,
|
|
32908
32992
|
runMode: "implementation",
|
|
32909
32993
|
retryPrompt: buildMotionFixPrompt(current),
|
|
32910
|
-
languageModule: args.languageModule
|
|
32994
|
+
languageModule: args.languageModule,
|
|
32995
|
+
signal: args.config.signal
|
|
32911
32996
|
});
|
|
32912
32997
|
for await (const event of fixGenerator) {
|
|
32913
32998
|
if (event.type === "tool_execution_start")
|
|
@@ -32935,6 +33020,7 @@ var init_chairmanFixLoop = __esm({
|
|
|
32935
33020
|
init_microGate();
|
|
32936
33021
|
init_chairmanDelivery();
|
|
32937
33022
|
init_retryTurn();
|
|
33023
|
+
init_cancel();
|
|
32938
33024
|
}
|
|
32939
33025
|
});
|
|
32940
33026
|
|
|
@@ -32976,6 +33062,17 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
32976
33062
|
model: config2.model,
|
|
32977
33063
|
provider: config2.provider ?? "minimax"
|
|
32978
33064
|
};
|
|
33065
|
+
if (isCouncilCancelled(config2.signal)) {
|
|
33066
|
+
yield {
|
|
33067
|
+
type: "agent_end",
|
|
33068
|
+
id: crypto.randomUUID(),
|
|
33069
|
+
ts: Date.now(),
|
|
33070
|
+
sessionId: sessionId2,
|
|
33071
|
+
reason: "cancelled",
|
|
33072
|
+
durationMs: 0
|
|
33073
|
+
};
|
|
33074
|
+
return;
|
|
33075
|
+
}
|
|
32979
33076
|
const emitMemberCost = (input) => {
|
|
32980
33077
|
const usage = input.usage;
|
|
32981
33078
|
const prompt = usage?.promptTokens ?? 0;
|
|
@@ -33005,6 +33102,8 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33005
33102
|
const oracle = agents.find((a) => a.id === "minos") ?? (config2.skipSpecialists ? getAgent("minos") : void 0);
|
|
33006
33103
|
const chairman = agents.find((a) => a.id === "lucifer") ?? (config2.skipSpecialists ? getAgent("lucifer") : void 0);
|
|
33007
33104
|
for (const agent of specialists) {
|
|
33105
|
+
if (isCouncilCancelled(config2.signal))
|
|
33106
|
+
break;
|
|
33008
33107
|
if (completedIds.has(agent.id))
|
|
33009
33108
|
continue;
|
|
33010
33109
|
callbacks.onAgentStart?.(agent);
|
|
@@ -33050,7 +33149,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33050
33149
|
const emittedToolNames = [];
|
|
33051
33150
|
const memberStart = Date.now();
|
|
33052
33151
|
try {
|
|
33053
|
-
for await (const event of harness.
|
|
33152
|
+
for await (const event of runHarnessWithAbort(harness, config2.signal)) {
|
|
33054
33153
|
yield event;
|
|
33055
33154
|
if (event.type === "tool_execution_start") {
|
|
33056
33155
|
toolCalls += 1;
|
|
@@ -33072,7 +33171,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33072
33171
|
fullText = `Error: ${err instanceof Error ? err.message : "Unknown"}`;
|
|
33073
33172
|
errored = true;
|
|
33074
33173
|
}
|
|
33075
|
-
if (isDesignPhase && !errored && !NON_RETRY_AGENTS.has(agent.id)) {
|
|
33174
|
+
if (isDesignPhase && !errored && !NON_RETRY_AGENTS.has(agent.id) && !isCouncilCancelled(config2.signal)) {
|
|
33076
33175
|
const specialistCheck = enforceDesignPhaseToolEmissions(agent.id, emittedToolNames);
|
|
33077
33176
|
yield* applyRetryIfMissing({
|
|
33078
33177
|
agent,
|
|
@@ -33155,7 +33254,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33155
33254
|
}
|
|
33156
33255
|
}
|
|
33157
33256
|
}
|
|
33158
|
-
if (oracle && !completedIds.has(oracle.id)) {
|
|
33257
|
+
if (oracle && !completedIds.has(oracle.id) && !isCouncilCancelled(config2.signal)) {
|
|
33159
33258
|
callbacks.onAgentStart?.(oracle);
|
|
33160
33259
|
const override = config2.agentModels?.[oracle.id];
|
|
33161
33260
|
const effectiveProvider = override?.providerId ?? config2.provider ?? "minimax";
|
|
@@ -33204,7 +33303,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33204
33303
|
const emittedToolNames = [];
|
|
33205
33304
|
const memberStart = Date.now();
|
|
33206
33305
|
try {
|
|
33207
|
-
for await (const event of harness.
|
|
33306
|
+
for await (const event of runHarnessWithAbort(harness, config2.signal)) {
|
|
33208
33307
|
yield event;
|
|
33209
33308
|
if (event.type === "tool_execution_start") {
|
|
33210
33309
|
toolCalls += 1;
|
|
@@ -33226,7 +33325,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33226
33325
|
fullText = `Review error: ${err instanceof Error ? err.message : "Unknown"}`;
|
|
33227
33326
|
errored = true;
|
|
33228
33327
|
}
|
|
33229
|
-
if (isDesignPhase && !errored) {
|
|
33328
|
+
if (isDesignPhase && !errored && !isCouncilCancelled(config2.signal)) {
|
|
33230
33329
|
const oracleCheck = enforceDesignPhaseToolEmissions(oracle.id, emittedToolNames);
|
|
33231
33330
|
yield* applyRetryIfMissing({
|
|
33232
33331
|
agent: oracle,
|
|
@@ -33286,7 +33385,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33286
33385
|
});
|
|
33287
33386
|
agentOutputs.push({ name: oracle.name, role: oracle.role, content: cleaned });
|
|
33288
33387
|
}
|
|
33289
|
-
if (chairman && !completedIds.has(chairman.id)) {
|
|
33388
|
+
if (chairman && !completedIds.has(chairman.id) && !isCouncilCancelled(config2.signal)) {
|
|
33290
33389
|
callbacks.onSynthesisStart?.();
|
|
33291
33390
|
callbacks.onAgentStart?.(chairman);
|
|
33292
33391
|
const override = config2.agentModels?.[chairman.id];
|
|
@@ -33333,7 +33432,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33333
33432
|
let chairmanProjectRoot = parseProjectRootFromWorkspaceContext(config2.workspaceContext ?? "");
|
|
33334
33433
|
const memberStart = Date.now();
|
|
33335
33434
|
try {
|
|
33336
|
-
for await (const event of chairmanHarness.
|
|
33435
|
+
for await (const event of runHarnessWithAbort(chairmanHarness, config2.signal)) {
|
|
33337
33436
|
yield event;
|
|
33338
33437
|
if (event.type === "tool_execution_start") {
|
|
33339
33438
|
toolCalls += 1;
|
|
@@ -33397,7 +33496,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33397
33496
|
errored = true;
|
|
33398
33497
|
lastErrorMessage = err instanceof Error ? err.message : String(err);
|
|
33399
33498
|
}
|
|
33400
|
-
if (isDesignPhase && !errored) {
|
|
33499
|
+
if (isDesignPhase && !errored && !isCouncilCancelled(config2.signal)) {
|
|
33401
33500
|
const chairmanCheck = enforceDesignPhaseToolEmissions(chairman.id, emittedToolNames);
|
|
33402
33501
|
yield* applyRetryIfMissing({
|
|
33403
33502
|
agent: chairman,
|
|
@@ -33418,7 +33517,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33418
33517
|
});
|
|
33419
33518
|
} else if (isDesignPhase) {
|
|
33420
33519
|
enforceDesignPhaseToolEmissions(chairman.id, emittedToolNames);
|
|
33421
|
-
} else if (!errored) {
|
|
33520
|
+
} else if (!errored && !isCouncilCancelled(config2.signal)) {
|
|
33422
33521
|
if (chairmanProjectRoot) {
|
|
33423
33522
|
const zelariRoot = `${chairmanProjectRoot}/.zelari`;
|
|
33424
33523
|
const spec = loadNfrSpec(zelariRoot) ?? DEFAULT_NFR_SPEC;
|
|
@@ -33547,7 +33646,7 @@ async function* runCouncilPure(userMessage, config2, callbacks = {}) {
|
|
|
33547
33646
|
id: crypto.randomUUID(),
|
|
33548
33647
|
ts: Date.now(),
|
|
33549
33648
|
sessionId: sessionId2,
|
|
33550
|
-
reason: "completed",
|
|
33649
|
+
reason: isCouncilCancelled(config2.signal) ? "cancelled" : "completed",
|
|
33551
33650
|
durationMs: 0
|
|
33552
33651
|
};
|
|
33553
33652
|
}
|
|
@@ -33566,6 +33665,7 @@ var init_councilApi = __esm({
|
|
|
33566
33665
|
init_runChecks();
|
|
33567
33666
|
init_implementationDelivery();
|
|
33568
33667
|
init_types7();
|
|
33668
|
+
init_cancel();
|
|
33569
33669
|
init_types7();
|
|
33570
33670
|
init_outputCleaning();
|
|
33571
33671
|
init_outputCleaning();
|
|
@@ -34572,6 +34672,7 @@ __export(council_exports, {
|
|
|
34572
34672
|
shouldRetryMember: () => shouldRetryMember,
|
|
34573
34673
|
slugify: () => slugify2,
|
|
34574
34674
|
stripClarificationProtocol: () => stripClarificationProtocol,
|
|
34675
|
+
stripQuestionBlocks: () => stripQuestionBlocks,
|
|
34575
34676
|
swapMembers: () => swapMembers,
|
|
34576
34677
|
systemMessagesFromSplit: () => systemMessagesFromSplit,
|
|
34577
34678
|
taskMatchesNfrKeywords: () => taskMatchesNfrKeywords,
|
|
@@ -38114,7 +38215,7 @@ var CORE_VERSION;
|
|
|
38114
38215
|
var init_version = __esm({
|
|
38115
38216
|
"packages/core/dist/version.js"() {
|
|
38116
38217
|
"use strict";
|
|
38117
|
-
CORE_VERSION = "2.34.
|
|
38218
|
+
CORE_VERSION = "2.34.1";
|
|
38118
38219
|
}
|
|
38119
38220
|
});
|
|
38120
38221
|
|
|
@@ -38626,6 +38727,7 @@ __export(dist_exports, {
|
|
|
38626
38727
|
strictBuildGate: () => strictBuildGate,
|
|
38627
38728
|
stripAnsi: () => stripAnsi,
|
|
38628
38729
|
stripClarificationProtocol: () => stripClarificationProtocol,
|
|
38730
|
+
stripQuestionBlocks: () => stripQuestionBlocks,
|
|
38629
38731
|
swapMembers: () => swapMembers,
|
|
38630
38732
|
systemMessagesFromSplit: () => systemMessagesFromSplit,
|
|
38631
38733
|
taskMatchesNfrKeywords: () => taskMatchesNfrKeywords,
|
|
@@ -44116,6 +44218,7 @@ __export(krakenModel_exports, {
|
|
|
44116
44218
|
inferModelFamily: () => inferModelFamily,
|
|
44117
44219
|
isCheapModelId: () => isCheapModelId,
|
|
44118
44220
|
isKrakenAutoModelEnabled: () => isKrakenAutoModelEnabled,
|
|
44221
|
+
isUnknownModelError: () => isUnknownModelError,
|
|
44119
44222
|
parseQualifiedModelRef: () => parseQualifiedModelRef,
|
|
44120
44223
|
pickCheapModel: () => pickCheapModel,
|
|
44121
44224
|
pickDifferentFamily: () => pickDifferentFamily,
|
|
@@ -44227,6 +44330,12 @@ function resolveKrakenSubModel(agent, parentModel, env = process.env, opts = {})
|
|
|
44227
44330
|
}
|
|
44228
44331
|
return parentModel;
|
|
44229
44332
|
}
|
|
44333
|
+
function isUnknownModelError(message) {
|
|
44334
|
+
if (!message) return false;
|
|
44335
|
+
const m = message.toLowerCase();
|
|
44336
|
+
if (!/model/.test(m)) return false;
|
|
44337
|
+
return /http\s*404/.test(m) || /not-found/.test(m) || /not_found/.test(m) || /does not exist/.test(m) || /unknown model/.test(m) || /model_not_found/.test(m);
|
|
44338
|
+
}
|
|
44230
44339
|
function resolveKrakenPlannerModel(parentModel, env = process.env) {
|
|
44231
44340
|
const specific = env.ZELARI_KRAKEN_PLANNER_MODEL?.trim();
|
|
44232
44341
|
if (specific) return specific;
|
|
@@ -46026,6 +46135,12 @@ ${failed.error ?? "unknown error"}`,
|
|
|
46026
46135
|
// src/cli/tools/taskTool.ts
|
|
46027
46136
|
import { existsSync as existsSync26 } from "node:fs";
|
|
46028
46137
|
import { randomUUID as randomUUID4 } from "node:crypto";
|
|
46138
|
+
function permissionsForTaskAgent(agent) {
|
|
46139
|
+
const kind2 = agent ?? "explore";
|
|
46140
|
+
if (kind2 === "general") return ["read", "write", "execute", "network"];
|
|
46141
|
+
if (kind2 === "verify") return ["read", "execute", "network"];
|
|
46142
|
+
return ["read"];
|
|
46143
|
+
}
|
|
46029
46144
|
function resetTaskSpawnCount() {
|
|
46030
46145
|
const g = globalThis;
|
|
46031
46146
|
g.__zelariTaskSpawnCount = 0;
|
|
@@ -46507,17 +46622,45 @@ ${taskUserContent}`,
|
|
|
46507
46622
|
};
|
|
46508
46623
|
}
|
|
46509
46624
|
const startedTools = /* @__PURE__ */ new Map();
|
|
46510
|
-
const
|
|
46625
|
+
const onHarnessEvent = (ev) => {
|
|
46626
|
+
if (ev.type === "tool_execution_start") {
|
|
46627
|
+
startedTools.set(ev.toolCallId, ev.toolName);
|
|
46628
|
+
emitActivity({ type: "agent_tool", agentId: liveId, toolCallId: ev.toolCallId, tool: ev.toolName, status: "started", ...ev.args ? { summary: toolCommandHint(ev.args) } : {}, ts: Date.now() });
|
|
46629
|
+
} else if (ev.type === "tool_execution_end") {
|
|
46630
|
+
emitActivity({ type: "agent_tool", agentId: liveId, toolCallId: ev.toolCallId, tool: startedTools.get(ev.toolCallId) ?? "unknown", status: ev.isError ? "failed" : "completed", durationMs: ev.durationMs, ts: Date.now() });
|
|
46631
|
+
}
|
|
46632
|
+
};
|
|
46633
|
+
let { result, error: error51, aborted: aborted2, usage, toolTrace } = await runSubAgent(harness, {
|
|
46511
46634
|
...opts.signal ? { signal: opts.signal } : {},
|
|
46512
|
-
onEvent:
|
|
46513
|
-
|
|
46514
|
-
|
|
46515
|
-
|
|
46516
|
-
|
|
46517
|
-
|
|
46635
|
+
onEvent: onHarnessEvent
|
|
46636
|
+
});
|
|
46637
|
+
if (!aborted2 && !result && sub.fallback && sub.fallback.model !== sub.model) {
|
|
46638
|
+
const { isUnknownModelError: isUnknownModelError2 } = await Promise.resolve().then(() => (init_krakenModel(), krakenModel_exports));
|
|
46639
|
+
if (isUnknownModelError2(error51)) {
|
|
46640
|
+
emitPhase(`model ${sub.model} unavailable \u2014 retrying with ${sub.fallback.model}`);
|
|
46641
|
+
const retryConfig = {
|
|
46642
|
+
...config2,
|
|
46643
|
+
model: sub.fallback.model,
|
|
46644
|
+
provider: sub.fallback.provider,
|
|
46645
|
+
providerStream: sub.fallback.providerStream
|
|
46646
|
+
};
|
|
46647
|
+
try {
|
|
46648
|
+
harness = deps.harnessFactory ? deps.harnessFactory(retryConfig) : new (await Promise.resolve().then(() => (init_harness(), harness_exports))).AgentHarness(retryConfig);
|
|
46649
|
+
const retry = await runSubAgent(harness, {
|
|
46650
|
+
...opts.signal ? { signal: opts.signal } : {},
|
|
46651
|
+
onEvent: onHarnessEvent
|
|
46652
|
+
});
|
|
46653
|
+
result = retry.result;
|
|
46654
|
+
error51 = retry.error;
|
|
46655
|
+
aborted2 = retry.aborted;
|
|
46656
|
+
usage = retry.usage;
|
|
46657
|
+
toolTrace = retry.toolTrace;
|
|
46658
|
+
sub = { ...sub, model: sub.fallback.model, provider: sub.fallback.provider };
|
|
46659
|
+
} catch (err) {
|
|
46660
|
+
error51 = err instanceof Error ? err.message : String(err);
|
|
46518
46661
|
}
|
|
46519
46662
|
}
|
|
46520
|
-
}
|
|
46663
|
+
}
|
|
46521
46664
|
const durationMs = Date.now() - started;
|
|
46522
46665
|
if (aborted2) {
|
|
46523
46666
|
if (worktree && !shouldKeepWorktree()) await cleanupKrakenWorktree(worktree);
|
|
@@ -54082,6 +54225,7 @@ function createBuiltinToolRegistry(options = {}) {
|
|
|
54082
54225
|
// registry's own policy (permPolicy above) — they can never
|
|
54083
54226
|
// exceed it.
|
|
54084
54227
|
parentPolicy: permPolicy,
|
|
54228
|
+
...options.onPermissionAsk ? { onPermissionAsk: options.onPermissionAsk } : {},
|
|
54085
54229
|
...options.subAgentProvider ? { provider: options.subAgentProvider } : {},
|
|
54086
54230
|
...options.subAgentModel ? { model: options.subAgentModel } : {}
|
|
54087
54231
|
}),
|
|
@@ -54181,12 +54325,13 @@ function taskAgentToProfile(agent) {
|
|
|
54181
54325
|
return "explore";
|
|
54182
54326
|
}
|
|
54183
54327
|
function createKrakenSubAgentContextFactory(opts) {
|
|
54184
|
-
const { root, audit, sessionId: sessionId2, provider: providerOverride, model: modelOverride, parentPolicy } = opts;
|
|
54328
|
+
const { root, audit, sessionId: sessionId2, provider: providerOverride, model: modelOverride, parentPolicy, onPermissionAsk } = opts;
|
|
54185
54329
|
return async ({ agent, cwd: subCwd }) => {
|
|
54186
54330
|
const cfg = providerOverride ? await providerConfigFor(providerOverride) : await providerFromEnv();
|
|
54187
54331
|
if (!cfg) return null;
|
|
54188
54332
|
const { resolveKrakenSubModel: resolveKrakenSubModel2, parseQualifiedModelRef: parseQualifiedModelRef2 } = await Promise.resolve().then(() => (init_krakenModel(), krakenModel_exports));
|
|
54189
|
-
const
|
|
54333
|
+
const parentModel = modelOverride || cfg.model;
|
|
54334
|
+
const resolvedModel = resolveKrakenSubModel2(agent, parentModel);
|
|
54190
54335
|
let effCfg = cfg;
|
|
54191
54336
|
let model = resolvedModel;
|
|
54192
54337
|
const ref = parseQualifiedModelRef2(resolvedModel);
|
|
@@ -54215,6 +54360,7 @@ function createKrakenSubAgentContextFactory(opts) {
|
|
|
54215
54360
|
diagnostics: false,
|
|
54216
54361
|
lspProvider: null,
|
|
54217
54362
|
permissionPolicy: effectiveSubPolicy,
|
|
54363
|
+
...onPermissionAsk ? { onPermissionAsk } : {},
|
|
54218
54364
|
// P0.5: the tentacle's agent identity drives per-agent policy rules.
|
|
54219
54365
|
policyAgent: agent
|
|
54220
54366
|
});
|
|
@@ -54222,6 +54368,13 @@ function createKrakenSubAgentContextFactory(opts) {
|
|
|
54222
54368
|
providerStream: buildProviderStream(subCfg),
|
|
54223
54369
|
model,
|
|
54224
54370
|
provider: subCfg.providerId,
|
|
54371
|
+
...model !== parentModel ? {
|
|
54372
|
+
fallback: {
|
|
54373
|
+
model: parentModel,
|
|
54374
|
+
provider: cfg.providerId,
|
|
54375
|
+
providerStream: buildProviderStream({ ...cfg, model: parentModel })
|
|
54376
|
+
}
|
|
54377
|
+
} : {},
|
|
54225
54378
|
registry: subRegistry,
|
|
54226
54379
|
tools: subRegistry.toOpenAITools().map((t) => ({
|
|
54227
54380
|
name: t.function.name,
|
|
@@ -54241,11 +54394,14 @@ function wrapWithPermissions(original, policy, onAsk, agentLayers, precedence =
|
|
|
54241
54394
|
return {
|
|
54242
54395
|
...original,
|
|
54243
54396
|
execute: async (input, ctx) => {
|
|
54244
|
-
const
|
|
54397
|
+
const requiredNow = original.name === "task" ? permissionsForTaskAgent(
|
|
54398
|
+
input?.agent
|
|
54399
|
+
) : required2;
|
|
54400
|
+
const decision = resolveToolPermission(original.name, requiredNow, policy);
|
|
54245
54401
|
const rule = agentLayers ? matchAgentPolicyRuleLayered(
|
|
54246
54402
|
agentLayers,
|
|
54247
54403
|
precedence,
|
|
54248
|
-
|
|
54404
|
+
requiredNow,
|
|
54249
54405
|
input ?? {},
|
|
54250
54406
|
root ?? process.cwd()
|
|
54251
54407
|
) : null;
|
|
@@ -54257,25 +54413,25 @@ function wrapWithPermissions(original, policy, onAsk, agentLayers, precedence =
|
|
|
54257
54413
|
root ?? process.cwd()
|
|
54258
54414
|
) : void 0;
|
|
54259
54415
|
const contractRule = matchContractCapabilityRule(
|
|
54260
|
-
|
|
54416
|
+
requiredNow,
|
|
54261
54417
|
input ?? {},
|
|
54262
54418
|
root ?? process.cwd()
|
|
54263
54419
|
);
|
|
54264
54420
|
let action = intersectEffects(mergeRuleEffect(decision.action, rule), claims?.effect, contractRule?.effect);
|
|
54265
54421
|
let actionReason = decision.reason;
|
|
54266
|
-
if (action !== "deny" && (
|
|
54422
|
+
if (action !== "deny" && (requiredNow.includes("write") || requiredNow.includes("execute"))) {
|
|
54267
54423
|
const provHit = provenanceMatchIn(JSON.stringify(input ?? {}));
|
|
54268
|
-
if (provHit && provenanceAppliesTo(provHit.source,
|
|
54424
|
+
if (provHit && provenanceAppliesTo(provHit.source, requiredNow)) {
|
|
54269
54425
|
const provNote = `[provenance] args embed non-user ${provHit.source} content (via ${provHit.tool})`;
|
|
54270
54426
|
if (action === "allow") {
|
|
54271
54427
|
action = "ask";
|
|
54272
|
-
actionReason = `${provNote} \u2014 confirm before ${
|
|
54428
|
+
actionReason = `${provNote} \u2014 confirm before ${requiredNow.join("+")}`;
|
|
54273
54429
|
} else {
|
|
54274
54430
|
actionReason = `${decision.reason} \xB7 ${provNote}`;
|
|
54275
54431
|
}
|
|
54276
54432
|
}
|
|
54277
54433
|
}
|
|
54278
|
-
if (action === "allow" &&
|
|
54434
|
+
if (action === "allow" && requiredNow.includes("execute") && activePermissionPreset() !== "yolo" && !isSessionGranted(original.name, requiredNow)) {
|
|
54279
54435
|
const destructiveHit = destructiveCommandHit(input ?? {});
|
|
54280
54436
|
if (destructiveHit) {
|
|
54281
54437
|
action = "ask";
|
|
@@ -54318,7 +54474,7 @@ function wrapWithPermissions(original, policy, onAsk, agentLayers, precedence =
|
|
|
54318
54474
|
}
|
|
54319
54475
|
}
|
|
54320
54476
|
const outcome = await original.execute(input, ctx);
|
|
54321
|
-
recordResultForProvenance(original.name,
|
|
54477
|
+
recordResultForProvenance(original.name, requiredNow, outcome);
|
|
54322
54478
|
return outcome;
|
|
54323
54479
|
}
|
|
54324
54480
|
};
|
|
@@ -55654,6 +55810,25 @@ var init_spineTelemetry = __esm({
|
|
|
55654
55810
|
}
|
|
55655
55811
|
});
|
|
55656
55812
|
|
|
55813
|
+
// src/cli/hooks/askUserTimeout.ts
|
|
55814
|
+
function askUserTimeoutMs() {
|
|
55815
|
+
const raw = process.env.ZELARI_ASK_USER_TIMEOUT_MS?.trim();
|
|
55816
|
+
if (!raw) return 3e5;
|
|
55817
|
+
const n = Number.parseInt(raw, 10);
|
|
55818
|
+
if (!Number.isFinite(n) || n < 0) return 3e5;
|
|
55819
|
+
return n;
|
|
55820
|
+
}
|
|
55821
|
+
function armPickerTimeout(onFire, ms) {
|
|
55822
|
+
if (ms <= 0) return () => void 0;
|
|
55823
|
+
const id3 = setTimeout(onFire, ms);
|
|
55824
|
+
return () => clearTimeout(id3);
|
|
55825
|
+
}
|
|
55826
|
+
var init_askUserTimeout = __esm({
|
|
55827
|
+
"src/cli/hooks/askUserTimeout.ts"() {
|
|
55828
|
+
"use strict";
|
|
55829
|
+
}
|
|
55830
|
+
});
|
|
55831
|
+
|
|
55657
55832
|
// src/cli/state/fileStateStore.ts
|
|
55658
55833
|
import { createHash as createHash17, randomUUID as randomUUID5 } from "node:crypto";
|
|
55659
55834
|
import { promises as fs26 } from "node:fs";
|
|
@@ -61040,7 +61215,8 @@ async function* dispatchCouncil(userMessage, options) {
|
|
|
61040
61215
|
maxToolLoopIterations: options.maxToolLoopIterations,
|
|
61041
61216
|
maxToolLoopHardCap: options.maxToolLoopHardCap,
|
|
61042
61217
|
skipSpecialists: options.skipSpecialists,
|
|
61043
|
-
feedbackStore: options.feedbackStore
|
|
61218
|
+
feedbackStore: options.feedbackStore,
|
|
61219
|
+
signal: options.signal
|
|
61044
61220
|
};
|
|
61045
61221
|
if (!options.disableWorkspaceTools) {
|
|
61046
61222
|
const { setWorkspaceStubs: setWorkspaceStubs2 } = await Promise.resolve().then(() => (init_skills2(), skills_exports));
|
|
@@ -62798,6 +62974,13 @@ async function runZelariMission(userMessage, brief, deps) {
|
|
|
62798
62974
|
let forcePivot = false;
|
|
62799
62975
|
const missionStartMs = now().getTime();
|
|
62800
62976
|
while (true) {
|
|
62977
|
+
if (deps.signal?.aborted) {
|
|
62978
|
+
state3.status = "cancelled";
|
|
62979
|
+
state3.updatedAt = now().toISOString();
|
|
62980
|
+
await persist();
|
|
62981
|
+
deps.emit("[zelari] missione cancellata.");
|
|
62982
|
+
return state3;
|
|
62983
|
+
}
|
|
62801
62984
|
const runMode = pendingDesign ? "design-phase" : "implementation";
|
|
62802
62985
|
if (runMode === "implementation") {
|
|
62803
62986
|
deps.onMissionPhase?.("build", `impl-${implStep + 1}`);
|
|
@@ -62854,6 +63037,13 @@ async function runZelariMission(userMessage, brief, deps) {
|
|
|
62854
63037
|
);
|
|
62855
63038
|
return state3;
|
|
62856
63039
|
}
|
|
63040
|
+
if (deps.signal?.aborted) {
|
|
63041
|
+
state3.status = "cancelled";
|
|
63042
|
+
state3.updatedAt = now().toISOString();
|
|
63043
|
+
await persist();
|
|
63044
|
+
deps.emit("[zelari] missione cancellata.");
|
|
63045
|
+
return state3;
|
|
63046
|
+
}
|
|
62857
63047
|
if (typeof result.costUsd === "number") cumulativeCostUsd += result.costUsd;
|
|
62858
63048
|
if (typeof result.costTokens === "number") cumulativeTokens += result.costTokens;
|
|
62859
63049
|
await deps.memory.add(
|
|
@@ -65972,11 +66162,12 @@ var init_facts = __esm({
|
|
|
65972
66162
|
});
|
|
65973
66163
|
|
|
65974
66164
|
// src/cli/utils/streamScrub.ts
|
|
65975
|
-
function createStreamScrubber2() {
|
|
66165
|
+
function createStreamScrubber2(opts = {}) {
|
|
66166
|
+
const stripQuestion = opts.stripQuestion !== false;
|
|
65976
66167
|
let rawBuf = "";
|
|
65977
66168
|
let emittedLen = 0;
|
|
65978
66169
|
const snapshot = () => {
|
|
65979
|
-
const cleaned = cleanAgentContent(rawBuf);
|
|
66170
|
+
const cleaned = cleanAgentContent(rawBuf, { stripQuestion });
|
|
65980
66171
|
if (cleaned.length <= emittedLen) return "";
|
|
65981
66172
|
const delta = cleaned.slice(emittedLen);
|
|
65982
66173
|
emittedLen = cleaned.length;
|
|
@@ -66214,215 +66405,39 @@ var init_harnessStateEmit = __esm({
|
|
|
66214
66405
|
}
|
|
66215
66406
|
});
|
|
66216
66407
|
|
|
66217
|
-
// src/cli/
|
|
66218
|
-
import {
|
|
66219
|
-
|
|
66220
|
-
|
|
66221
|
-
if (isPolicyEngineDisabled()) return { blocked: false, warnings: [] };
|
|
66222
|
-
try {
|
|
66223
|
-
const set2 = loadPolicySet(root, opts);
|
|
66224
|
-
return { blocked: false, warnings: set2.warnings };
|
|
66225
|
-
} catch (err) {
|
|
66226
|
-
if (!(err instanceof PolicyLoadError)) throw err;
|
|
66227
|
-
const file2 = isAbsolute5(err.file) ? err.file : resolve7(root, err.file);
|
|
66228
|
-
return {
|
|
66229
|
-
blocked: true,
|
|
66230
|
-
warnings: [],
|
|
66231
|
-
block: {
|
|
66232
|
-
reason: POLICY_LOAD_BLOCK_REASON,
|
|
66233
|
-
exitCode: POLICY_LOAD_EXIT_CODE,
|
|
66234
|
-
code: err.code,
|
|
66235
|
-
file: file2,
|
|
66236
|
-
...err.message ? { detail: err.message } : {}
|
|
66237
|
-
}
|
|
66238
|
-
};
|
|
66239
|
-
}
|
|
66240
|
-
}
|
|
66241
|
-
function reportPolicyLoadBlocked(block, output) {
|
|
66242
|
-
const where = `${block.file}${block.detail ? ` \u2014 ${block.detail}` : ""}`;
|
|
66243
|
-
process.stderr.write(`[zelari-code --headless] ${block.reason}: ${where}
|
|
66244
|
-
`);
|
|
66245
|
-
if (output === "json") {
|
|
66246
|
-
emitEvent({
|
|
66247
|
-
type: "error",
|
|
66248
|
-
severity: "fatal",
|
|
66249
|
-
message: `${block.reason}: ${where}`,
|
|
66250
|
-
code: block.reason
|
|
66251
|
-
});
|
|
66252
|
-
}
|
|
66253
|
-
}
|
|
66254
|
-
async function recordPolicyLoadBlockedOnSpine(block, opts = {}) {
|
|
66255
|
-
try {
|
|
66256
|
-
const { openHeadlessSpine: openHeadlessSpine2 } = await Promise.resolve().then(() => (init_headlessSpine(), headlessSpine_exports));
|
|
66257
|
-
const sessionId2 = opts.resumeSessionId ?? randomUUID9();
|
|
66258
|
-
const spine = await openHeadlessSpine2({
|
|
66259
|
-
sessionId: sessionId2,
|
|
66260
|
-
...opts.mode ? { mode: opts.mode } : {},
|
|
66261
|
-
...opts.profile ? { profile: opts.profile } : {},
|
|
66262
|
-
workspace: opts.workspace ?? process.cwd()
|
|
66263
|
-
});
|
|
66264
|
-
if (opts.mode === "zelari") {
|
|
66265
|
-
spine.missionPhase("dispatch", block.reason);
|
|
66266
|
-
}
|
|
66267
|
-
spine.note(block.reason, {
|
|
66268
|
-
code: block.code,
|
|
66269
|
-
file: block.file,
|
|
66270
|
-
exitCode: block.exitCode,
|
|
66271
|
-
...block.detail ? { detail: block.detail } : {}
|
|
66272
|
-
});
|
|
66273
|
-
await spine.close("error");
|
|
66274
|
-
} catch {
|
|
66275
|
-
}
|
|
66276
|
-
}
|
|
66277
|
-
var init_policyGate = __esm({
|
|
66278
|
-
"src/cli/headless/policyGate.ts"() {
|
|
66279
|
-
"use strict";
|
|
66280
|
-
init_policyEngine();
|
|
66281
|
-
init_policyLoadMode();
|
|
66282
|
-
init_headless();
|
|
66283
|
-
}
|
|
66284
|
-
});
|
|
66285
|
-
|
|
66286
|
-
// src/cli/kraken/verifierResolution.ts
|
|
66287
|
-
function verifierOverrideToModelSelection(override) {
|
|
66288
|
-
if (override && typeof override.provider === "string" && typeof override.model === "string" && override.provider.trim().length > 0 && override.model.trim().length > 0) {
|
|
66289
|
-
return {
|
|
66290
|
-
mode: "fixed",
|
|
66291
|
-
provider: override.provider.trim(),
|
|
66292
|
-
model: override.model.trim()
|
|
66293
|
-
};
|
|
66294
|
-
}
|
|
66295
|
-
return { mode: "inherit" };
|
|
66296
|
-
}
|
|
66297
|
-
function loadVerifierModelSelection() {
|
|
66298
|
-
return verifierOverrideToModelSelection(getKrakenVerifierOverride());
|
|
66299
|
-
}
|
|
66300
|
-
var init_verifierResolution = __esm({
|
|
66301
|
-
"src/cli/kraken/verifierResolution.ts"() {
|
|
66302
|
-
"use strict";
|
|
66303
|
-
init_providerConfig();
|
|
66304
|
-
}
|
|
66305
|
-
});
|
|
66306
|
-
|
|
66307
|
-
// src/cli/kraken/verifierLifecycle.ts
|
|
66308
|
-
function verifierReviewEnabled(selection = loadVerifierModelSelection(), env = process.env) {
|
|
66309
|
-
const v = env.ZELARI_VERIFIER_REVIEW?.toLowerCase();
|
|
66310
|
-
if (v === "0" || v === "false" || v === "off") return false;
|
|
66311
|
-
if (v === "1" || v === "true" || v === "on") return true;
|
|
66312
|
-
return selection.mode === "fixed";
|
|
66408
|
+
// src/cli/serve/sessionControl.ts
|
|
66409
|
+
import { AsyncLocalStorage } from "node:async_hooks";
|
|
66410
|
+
function runWithSession(sessionId2, fn) {
|
|
66411
|
+
return dispatchContext.run({ sessionId: sessionId2, token: {} }, fn);
|
|
66313
66412
|
}
|
|
66314
|
-
function
|
|
66315
|
-
|
|
66316
|
-
|
|
66317
|
-
|
|
66318
|
-
|
|
66413
|
+
function registerLiveTurnControl(control) {
|
|
66414
|
+
const store6 = dispatchContext.getStore();
|
|
66415
|
+
if (!store6) return void 0;
|
|
66416
|
+
const registered = { ...control, token: store6.token };
|
|
66417
|
+
liveTurns.set(store6.sessionId, registered);
|
|
66418
|
+
return () => {
|
|
66419
|
+
if (liveTurns.get(store6.sessionId) === registered) {
|
|
66420
|
+
liveTurns.delete(store6.sessionId);
|
|
66319
66421
|
}
|
|
66320
|
-
const { text } = await collectProviderText(stream, {
|
|
66321
|
-
messages: [
|
|
66322
|
-
{ role: "system", content: system },
|
|
66323
|
-
{ role: "user", content: user }
|
|
66324
|
-
],
|
|
66325
|
-
model: identity.model,
|
|
66326
|
-
provider: identity.provider,
|
|
66327
|
-
tools: [],
|
|
66328
|
-
signal: AbortSignal.timeout(timeoutMs2)
|
|
66329
|
-
});
|
|
66330
|
-
return { text, provider: identity.provider, model: identity.model };
|
|
66331
66422
|
};
|
|
66332
66423
|
}
|
|
66333
|
-
function
|
|
66334
|
-
|
|
66335
|
-
return ["test", "typecheck", "build", "lint"].some((k) => id3.includes(k));
|
|
66336
|
-
}
|
|
66337
|
-
function extractTestOutputExcerpt(results, maxChars = 4e3) {
|
|
66338
|
-
const lines = [];
|
|
66339
|
-
for (const r of results) {
|
|
66340
|
-
if (!isTestEvidenceCriterion(r.criterionId)) continue;
|
|
66341
|
-
lines.push([r.criterionId, r.status, r.detail].filter(Boolean).join(" \u2014 "));
|
|
66342
|
-
}
|
|
66343
|
-
if (lines.length === 0) return "";
|
|
66344
|
-
return lines.join("\n").slice(0, maxChars);
|
|
66345
|
-
}
|
|
66346
|
-
async function buildBlindReviewInput(evaluation, deps) {
|
|
66347
|
-
const results = evaluation.results ?? [];
|
|
66348
|
-
const passed = results.filter((r) => r.status === "pass").length;
|
|
66349
|
-
const verdict = evaluation.evaluation?.verdict ?? "UNKNOWN";
|
|
66350
|
-
const summary = `Kraken BUILD turn \u2014 deterministic evidence: ${passed}/${results.length} criteria pass, completion verdict ${verdict}.`;
|
|
66351
|
-
const task = deps.task?.trim();
|
|
66352
|
-
const testOutputExcerpt = extractTestOutputExcerpt(results);
|
|
66353
|
-
let diffSummary;
|
|
66354
|
-
try {
|
|
66355
|
-
const res = await (deps.getDiff ?? getWorkingDiff)({
|
|
66356
|
-
cwd: deps.cwd ?? process.cwd(),
|
|
66357
|
-
maxChars: 8e3,
|
|
66358
|
-
staged: true
|
|
66359
|
-
});
|
|
66360
|
-
if (res && !res.empty && res.diff) diffSummary = res.diff;
|
|
66361
|
-
} catch {
|
|
66362
|
-
}
|
|
66363
|
-
return {
|
|
66364
|
-
...task ? { task } : {},
|
|
66365
|
-
summary,
|
|
66366
|
-
...diffSummary !== void 0 ? { diffSummary } : {},
|
|
66367
|
-
...testOutputExcerpt ? { testOutputExcerpt } : {},
|
|
66368
|
-
results
|
|
66369
|
-
};
|
|
66424
|
+
function getLiveTurnControl(sessionId2) {
|
|
66425
|
+
return liveTurns.get(sessionId2);
|
|
66370
66426
|
}
|
|
66371
|
-
|
|
66372
|
-
|
|
66373
|
-
|
|
66374
|
-
const
|
|
66375
|
-
if (
|
|
66376
|
-
|
|
66377
|
-
if (risk === "low") return null;
|
|
66378
|
-
const route = resolveVerifierRouting(
|
|
66379
|
-
selection.mode === "fixed" ? { provider: selection.provider, model: selection.model } : null,
|
|
66380
|
-
risk,
|
|
66381
|
-
{
|
|
66382
|
-
selectionMode: selection.mode === "fixed" ? "fixed" : "inherit",
|
|
66383
|
-
session: deps.session ?? null,
|
|
66384
|
-
familyCandidates: deps.familyCandidates,
|
|
66385
|
-
env
|
|
66386
|
-
}
|
|
66387
|
-
);
|
|
66388
|
-
const reviewers = route.reviewers;
|
|
66389
|
-
let callModel = deps.callModel;
|
|
66390
|
-
if (reviewers.length === 0 || !callModel && !deps.loadStream) return null;
|
|
66391
|
-
const blind = await buildBlindReviewInput(evaluation, deps);
|
|
66392
|
-
const reviews = [];
|
|
66393
|
-
for (const reviewer of reviewers) {
|
|
66394
|
-
const call = callModel ?? makeVerifierCallModel(deps.loadStream, reviewer.identity, deps.timeoutMs);
|
|
66395
|
-
const service = new VerifierService({
|
|
66396
|
-
callModel: call,
|
|
66397
|
-
config: {
|
|
66398
|
-
enabled: true,
|
|
66399
|
-
model: selection,
|
|
66400
|
-
progressScoring: false,
|
|
66401
|
-
bon: { enabled: false, n: 3 }
|
|
66402
|
-
},
|
|
66403
|
-
emit: deps.emit,
|
|
66404
|
-
env
|
|
66405
|
-
});
|
|
66406
|
-
reviews.push(await service.reviewCompletion({ ...blind, session: deps.session }));
|
|
66407
|
-
}
|
|
66408
|
-
const review = reviews.length > 1 ? mergeVerifierVerdicts(reviews) : reviews[0];
|
|
66409
|
-
evaluation.review = review;
|
|
66410
|
-
if (reviews.length > 1 && risk === "critical") {
|
|
66411
|
-
evaluation.reviewDivergence = divergenceFromReviews(
|
|
66412
|
-
reviews,
|
|
66413
|
-
reviewers.map((r) => ({ family: r.family, role: r.role }))
|
|
66414
|
-
);
|
|
66427
|
+
function clearSessionTurnControl(sessionId2) {
|
|
66428
|
+
const store6 = dispatchContext.getStore();
|
|
66429
|
+
if (!store6 || store6.sessionId !== sessionId2) return;
|
|
66430
|
+
const registered = liveTurns.get(sessionId2);
|
|
66431
|
+
if (registered && registered.token === store6.token) {
|
|
66432
|
+
liveTurns.delete(sessionId2);
|
|
66415
66433
|
}
|
|
66416
|
-
return review;
|
|
66417
66434
|
}
|
|
66418
|
-
var
|
|
66419
|
-
|
|
66435
|
+
var dispatchContext, liveTurns;
|
|
66436
|
+
var init_sessionControl = __esm({
|
|
66437
|
+
"src/cli/serve/sessionControl.ts"() {
|
|
66420
66438
|
"use strict";
|
|
66421
|
-
|
|
66422
|
-
|
|
66423
|
-
init_gitOps();
|
|
66424
|
-
init_verifierResolution();
|
|
66425
|
-
init_verifierRouting();
|
|
66439
|
+
dispatchContext = new AsyncLocalStorage();
|
|
66440
|
+
liveTurns = /* @__PURE__ */ new Map();
|
|
66426
66441
|
}
|
|
66427
66442
|
});
|
|
66428
66443
|
|
|
@@ -66652,39 +66667,277 @@ var init_controlBridge = __esm({
|
|
|
66652
66667
|
}
|
|
66653
66668
|
});
|
|
66654
66669
|
|
|
66655
|
-
// src/cli/
|
|
66656
|
-
|
|
66657
|
-
|
|
66658
|
-
|
|
66670
|
+
// src/cli/headless/liveTurnAbort.ts
|
|
66671
|
+
function attachHeadlessLiveCancel(opts) {
|
|
66672
|
+
const abort = new AbortController();
|
|
66673
|
+
const controlQueue = new RuntimeControlQueue();
|
|
66674
|
+
const cancel = () => {
|
|
66675
|
+
if (!abort.signal.aborted) abort.abort();
|
|
66676
|
+
return true;
|
|
66677
|
+
};
|
|
66678
|
+
const controlPlane = opts?.output === "json" && process.stdin.isTTY !== true && process.env.ZELARI_SERVE_HARNESS !== "1" ? (() => {
|
|
66679
|
+
emitEvent(protocolInfoEvent());
|
|
66680
|
+
return attachControlPlane({
|
|
66681
|
+
input: process.stdin,
|
|
66682
|
+
queue: controlQueue,
|
|
66683
|
+
emit: emitEvent,
|
|
66684
|
+
onCancel: () => {
|
|
66685
|
+
cancel();
|
|
66686
|
+
}
|
|
66687
|
+
});
|
|
66688
|
+
})() : void 0;
|
|
66689
|
+
const unregister = process.env.ZELARI_SERVE_HARNESS === "1" ? registerLiveTurnControl({
|
|
66690
|
+
queue: controlQueue,
|
|
66691
|
+
cancel
|
|
66692
|
+
}) : void 0;
|
|
66693
|
+
if (unregister) {
|
|
66694
|
+
const appliedBoundary = {
|
|
66695
|
+
steer: "turn-end",
|
|
66696
|
+
follow_up: "run-end",
|
|
66697
|
+
cancel: "cancel"
|
|
66698
|
+
};
|
|
66699
|
+
controlQueue.onDrained = (events) => {
|
|
66700
|
+
for (const event of events) {
|
|
66701
|
+
emitEvent(
|
|
66702
|
+
controlAppliedEvent(
|
|
66703
|
+
event.id,
|
|
66704
|
+
event.type,
|
|
66705
|
+
appliedBoundary[event.type] ?? "unknown"
|
|
66706
|
+
)
|
|
66707
|
+
);
|
|
66708
|
+
}
|
|
66709
|
+
};
|
|
66710
|
+
}
|
|
66711
|
+
return {
|
|
66712
|
+
signal: abort.signal,
|
|
66713
|
+
cancel,
|
|
66714
|
+
dispose() {
|
|
66715
|
+
controlPlane?.finalize();
|
|
66716
|
+
controlPlane?.dispose();
|
|
66717
|
+
unregister?.();
|
|
66718
|
+
}
|
|
66719
|
+
};
|
|
66659
66720
|
}
|
|
66660
|
-
|
|
66661
|
-
|
|
66662
|
-
|
|
66663
|
-
|
|
66664
|
-
|
|
66665
|
-
|
|
66666
|
-
|
|
66667
|
-
|
|
66721
|
+
var init_liveTurnAbort = __esm({
|
|
66722
|
+
"src/cli/headless/liveTurnAbort.ts"() {
|
|
66723
|
+
"use strict";
|
|
66724
|
+
init_runtime();
|
|
66725
|
+
init_sessionControl();
|
|
66726
|
+
init_controlBridge();
|
|
66727
|
+
init_protocol2();
|
|
66728
|
+
init_headless();
|
|
66729
|
+
}
|
|
66730
|
+
});
|
|
66731
|
+
|
|
66732
|
+
// src/cli/headless/policyGate.ts
|
|
66733
|
+
import { isAbsolute as isAbsolute5, resolve as resolve7 } from "node:path";
|
|
66734
|
+
import { randomUUID as randomUUID9 } from "node:crypto";
|
|
66735
|
+
function checkStrictPolicyLoad(root, opts) {
|
|
66736
|
+
if (isPolicyEngineDisabled()) return { blocked: false, warnings: [] };
|
|
66737
|
+
try {
|
|
66738
|
+
const set2 = loadPolicySet(root, opts);
|
|
66739
|
+
return { blocked: false, warnings: set2.warnings };
|
|
66740
|
+
} catch (err) {
|
|
66741
|
+
if (!(err instanceof PolicyLoadError)) throw err;
|
|
66742
|
+
const file2 = isAbsolute5(err.file) ? err.file : resolve7(root, err.file);
|
|
66743
|
+
return {
|
|
66744
|
+
blocked: true,
|
|
66745
|
+
warnings: [],
|
|
66746
|
+
block: {
|
|
66747
|
+
reason: POLICY_LOAD_BLOCK_REASON,
|
|
66748
|
+
exitCode: POLICY_LOAD_EXIT_CODE,
|
|
66749
|
+
code: err.code,
|
|
66750
|
+
file: file2,
|
|
66751
|
+
...err.message ? { detail: err.message } : {}
|
|
66752
|
+
}
|
|
66753
|
+
};
|
|
66754
|
+
}
|
|
66755
|
+
}
|
|
66756
|
+
function reportPolicyLoadBlocked(block, output) {
|
|
66757
|
+
const where = `${block.file}${block.detail ? ` \u2014 ${block.detail}` : ""}`;
|
|
66758
|
+
process.stderr.write(`[zelari-code --headless] ${block.reason}: ${where}
|
|
66759
|
+
`);
|
|
66760
|
+
if (output === "json") {
|
|
66761
|
+
emitEvent({
|
|
66762
|
+
type: "error",
|
|
66763
|
+
severity: "fatal",
|
|
66764
|
+
message: `${block.reason}: ${where}`,
|
|
66765
|
+
code: block.reason
|
|
66766
|
+
});
|
|
66767
|
+
}
|
|
66768
|
+
}
|
|
66769
|
+
async function recordPolicyLoadBlockedOnSpine(block, opts = {}) {
|
|
66770
|
+
try {
|
|
66771
|
+
const { openHeadlessSpine: openHeadlessSpine2 } = await Promise.resolve().then(() => (init_headlessSpine(), headlessSpine_exports));
|
|
66772
|
+
const sessionId2 = opts.resumeSessionId ?? randomUUID9();
|
|
66773
|
+
const spine = await openHeadlessSpine2({
|
|
66774
|
+
sessionId: sessionId2,
|
|
66775
|
+
...opts.mode ? { mode: opts.mode } : {},
|
|
66776
|
+
...opts.profile ? { profile: opts.profile } : {},
|
|
66777
|
+
workspace: opts.workspace ?? process.cwd()
|
|
66778
|
+
});
|
|
66779
|
+
if (opts.mode === "zelari") {
|
|
66780
|
+
spine.missionPhase("dispatch", block.reason);
|
|
66668
66781
|
}
|
|
66782
|
+
spine.note(block.reason, {
|
|
66783
|
+
code: block.code,
|
|
66784
|
+
file: block.file,
|
|
66785
|
+
exitCode: block.exitCode,
|
|
66786
|
+
...block.detail ? { detail: block.detail } : {}
|
|
66787
|
+
});
|
|
66788
|
+
await spine.close("error");
|
|
66789
|
+
} catch {
|
|
66790
|
+
}
|
|
66791
|
+
}
|
|
66792
|
+
var init_policyGate = __esm({
|
|
66793
|
+
"src/cli/headless/policyGate.ts"() {
|
|
66794
|
+
"use strict";
|
|
66795
|
+
init_policyEngine();
|
|
66796
|
+
init_policyLoadMode();
|
|
66797
|
+
init_headless();
|
|
66798
|
+
}
|
|
66799
|
+
});
|
|
66800
|
+
|
|
66801
|
+
// src/cli/kraken/verifierResolution.ts
|
|
66802
|
+
function verifierOverrideToModelSelection(override) {
|
|
66803
|
+
if (override && typeof override.provider === "string" && typeof override.model === "string" && override.provider.trim().length > 0 && override.model.trim().length > 0) {
|
|
66804
|
+
return {
|
|
66805
|
+
mode: "fixed",
|
|
66806
|
+
provider: override.provider.trim(),
|
|
66807
|
+
model: override.model.trim()
|
|
66808
|
+
};
|
|
66809
|
+
}
|
|
66810
|
+
return { mode: "inherit" };
|
|
66811
|
+
}
|
|
66812
|
+
function loadVerifierModelSelection() {
|
|
66813
|
+
return verifierOverrideToModelSelection(getKrakenVerifierOverride());
|
|
66814
|
+
}
|
|
66815
|
+
var init_verifierResolution = __esm({
|
|
66816
|
+
"src/cli/kraken/verifierResolution.ts"() {
|
|
66817
|
+
"use strict";
|
|
66818
|
+
init_providerConfig();
|
|
66819
|
+
}
|
|
66820
|
+
});
|
|
66821
|
+
|
|
66822
|
+
// src/cli/kraken/verifierLifecycle.ts
|
|
66823
|
+
function verifierReviewEnabled(selection = loadVerifierModelSelection(), env = process.env) {
|
|
66824
|
+
const v = env.ZELARI_VERIFIER_REVIEW?.toLowerCase();
|
|
66825
|
+
if (v === "0" || v === "false" || v === "off") return false;
|
|
66826
|
+
if (v === "1" || v === "true" || v === "on") return true;
|
|
66827
|
+
return selection.mode === "fixed";
|
|
66828
|
+
}
|
|
66829
|
+
function makeVerifierCallModel(loadStream, identity, timeoutMs2 = 12e4) {
|
|
66830
|
+
return async ({ system, user }) => {
|
|
66831
|
+
const stream = await loadStream(identity.provider, identity.model);
|
|
66832
|
+
if (!stream) {
|
|
66833
|
+
throw new Error(`no provider config for verifier "${identity.provider}"`);
|
|
66834
|
+
}
|
|
66835
|
+
const { text } = await collectProviderText(stream, {
|
|
66836
|
+
messages: [
|
|
66837
|
+
{ role: "system", content: system },
|
|
66838
|
+
{ role: "user", content: user }
|
|
66839
|
+
],
|
|
66840
|
+
model: identity.model,
|
|
66841
|
+
provider: identity.provider,
|
|
66842
|
+
tools: [],
|
|
66843
|
+
signal: AbortSignal.timeout(timeoutMs2)
|
|
66844
|
+
});
|
|
66845
|
+
return { text, provider: identity.provider, model: identity.model };
|
|
66669
66846
|
};
|
|
66670
66847
|
}
|
|
66671
|
-
function
|
|
66672
|
-
|
|
66848
|
+
function isTestEvidenceCriterion(criterionId2) {
|
|
66849
|
+
const id3 = criterionId2.toLowerCase();
|
|
66850
|
+
return ["test", "typecheck", "build", "lint"].some((k) => id3.includes(k));
|
|
66673
66851
|
}
|
|
66674
|
-
function
|
|
66675
|
-
const
|
|
66676
|
-
|
|
66677
|
-
|
|
66678
|
-
|
|
66679
|
-
|
|
66852
|
+
function extractTestOutputExcerpt(results, maxChars = 4e3) {
|
|
66853
|
+
const lines = [];
|
|
66854
|
+
for (const r of results) {
|
|
66855
|
+
if (!isTestEvidenceCriterion(r.criterionId)) continue;
|
|
66856
|
+
lines.push([r.criterionId, r.status, r.detail].filter(Boolean).join(" \u2014 "));
|
|
66857
|
+
}
|
|
66858
|
+
if (lines.length === 0) return "";
|
|
66859
|
+
return lines.join("\n").slice(0, maxChars);
|
|
66860
|
+
}
|
|
66861
|
+
async function buildBlindReviewInput(evaluation, deps) {
|
|
66862
|
+
const results = evaluation.results ?? [];
|
|
66863
|
+
const passed = results.filter((r) => r.status === "pass").length;
|
|
66864
|
+
const verdict = evaluation.evaluation?.verdict ?? "UNKNOWN";
|
|
66865
|
+
const summary = `Kraken BUILD turn \u2014 deterministic evidence: ${passed}/${results.length} criteria pass, completion verdict ${verdict}.`;
|
|
66866
|
+
const task = deps.task?.trim();
|
|
66867
|
+
const testOutputExcerpt = extractTestOutputExcerpt(results);
|
|
66868
|
+
let diffSummary;
|
|
66869
|
+
try {
|
|
66870
|
+
const res = await (deps.getDiff ?? getWorkingDiff)({
|
|
66871
|
+
cwd: deps.cwd ?? process.cwd(),
|
|
66872
|
+
maxChars: 8e3,
|
|
66873
|
+
staged: true
|
|
66874
|
+
});
|
|
66875
|
+
if (res && !res.empty && res.diff) diffSummary = res.diff;
|
|
66876
|
+
} catch {
|
|
66680
66877
|
}
|
|
66878
|
+
return {
|
|
66879
|
+
...task ? { task } : {},
|
|
66880
|
+
summary,
|
|
66881
|
+
...diffSummary !== void 0 ? { diffSummary } : {},
|
|
66882
|
+
...testOutputExcerpt ? { testOutputExcerpt } : {},
|
|
66883
|
+
results
|
|
66884
|
+
};
|
|
66681
66885
|
}
|
|
66682
|
-
|
|
66683
|
-
|
|
66684
|
-
|
|
66886
|
+
async function runAdvisoryVerifierReview(evaluation, deps = {}) {
|
|
66887
|
+
if (!evaluation.evaluation || !evaluation.results) return null;
|
|
66888
|
+
const env = deps.env ?? process.env;
|
|
66889
|
+
const selection = deps.selection ?? loadVerifierModelSelection();
|
|
66890
|
+
if (!verifierReviewEnabled(selection, env)) return null;
|
|
66891
|
+
const risk = deps.risk ?? activeRisk(env);
|
|
66892
|
+
if (risk === "low") return null;
|
|
66893
|
+
const route = resolveVerifierRouting(
|
|
66894
|
+
selection.mode === "fixed" ? { provider: selection.provider, model: selection.model } : null,
|
|
66895
|
+
risk,
|
|
66896
|
+
{
|
|
66897
|
+
selectionMode: selection.mode === "fixed" ? "fixed" : "inherit",
|
|
66898
|
+
session: deps.session ?? null,
|
|
66899
|
+
familyCandidates: deps.familyCandidates,
|
|
66900
|
+
env
|
|
66901
|
+
}
|
|
66902
|
+
);
|
|
66903
|
+
const reviewers = route.reviewers;
|
|
66904
|
+
let callModel = deps.callModel;
|
|
66905
|
+
if (reviewers.length === 0 || !callModel && !deps.loadStream) return null;
|
|
66906
|
+
const blind = await buildBlindReviewInput(evaluation, deps);
|
|
66907
|
+
const reviews = [];
|
|
66908
|
+
for (const reviewer of reviewers) {
|
|
66909
|
+
const call = callModel ?? makeVerifierCallModel(deps.loadStream, reviewer.identity, deps.timeoutMs);
|
|
66910
|
+
const service = new VerifierService({
|
|
66911
|
+
callModel: call,
|
|
66912
|
+
config: {
|
|
66913
|
+
enabled: true,
|
|
66914
|
+
model: selection,
|
|
66915
|
+
progressScoring: false,
|
|
66916
|
+
bon: { enabled: false, n: 3 }
|
|
66917
|
+
},
|
|
66918
|
+
emit: deps.emit,
|
|
66919
|
+
env
|
|
66920
|
+
});
|
|
66921
|
+
reviews.push(await service.reviewCompletion({ ...blind, session: deps.session }));
|
|
66922
|
+
}
|
|
66923
|
+
const review = reviews.length > 1 ? mergeVerifierVerdicts(reviews) : reviews[0];
|
|
66924
|
+
evaluation.review = review;
|
|
66925
|
+
if (reviews.length > 1 && risk === "critical") {
|
|
66926
|
+
evaluation.reviewDivergence = divergenceFromReviews(
|
|
66927
|
+
reviews,
|
|
66928
|
+
reviewers.map((r) => ({ family: r.family, role: r.role }))
|
|
66929
|
+
);
|
|
66930
|
+
}
|
|
66931
|
+
return review;
|
|
66932
|
+
}
|
|
66933
|
+
var init_verifierLifecycle = __esm({
|
|
66934
|
+
"src/cli/kraken/verifierLifecycle.ts"() {
|
|
66685
66935
|
"use strict";
|
|
66686
|
-
|
|
66687
|
-
|
|
66936
|
+
init_verification();
|
|
66937
|
+
init_krakenSelectTool();
|
|
66938
|
+
init_gitOps();
|
|
66939
|
+
init_verifierResolution();
|
|
66940
|
+
init_verifierRouting();
|
|
66688
66941
|
}
|
|
66689
66942
|
});
|
|
66690
66943
|
|
|
@@ -67046,6 +67299,7 @@ async function runOneTurn(opts, provider, model, providerStream, extras) {
|
|
|
67046
67299
|
// an interactive approval (permission.request over NDJSON) instead of
|
|
67047
67300
|
// the fail-closed typedErr. Absent handler ⇒ unchanged fail-closed.
|
|
67048
67301
|
...opts.onPermissionAsk ? { onPermissionAsk: opts.onPermissionAsk } : {},
|
|
67302
|
+
...opts.onAskUser ? { onAskUser: opts.onAskUser } : {},
|
|
67049
67303
|
permissionPolicy: defaultPermissionPolicy2(),
|
|
67050
67304
|
...nativeMemory ? { memoryService: nativeMemory } : {},
|
|
67051
67305
|
memoryAutoWrite,
|
|
@@ -67272,7 +67526,7 @@ async function runOneTurn(opts, provider, model, providerStream, extras) {
|
|
|
67272
67526
|
let finalReason = "completed";
|
|
67273
67527
|
let exitCode = 0;
|
|
67274
67528
|
const textBuffer = [];
|
|
67275
|
-
const scrub = createStreamScrubber2();
|
|
67529
|
+
const scrub = createStreamScrubber2({ stripQuestion: opts.output !== "json" });
|
|
67276
67530
|
try {
|
|
67277
67531
|
for await (const event of harness.run()) {
|
|
67278
67532
|
progressRuntime.observe(event);
|
|
@@ -68814,6 +69068,7 @@ async function runHeadlessKrakenGraph(opts, provider, model) {
|
|
|
68814
69068
|
// ask without a UI fails closed), so this intersection actually
|
|
68815
69069
|
// bites: tentacles can never exceed the preset.
|
|
68816
69070
|
parentPolicy: defaultPermissionPolicy2(),
|
|
69071
|
+
...opts.onPermissionAsk ? { onPermissionAsk: opts.onPermissionAsk } : {},
|
|
68817
69072
|
// Anchor every tentacle to the SAME provider/model this run
|
|
68818
69073
|
// resolved (Desktop's selector, or --provider/--model), instead
|
|
68819
69074
|
// of the persisted provider.json default the factory falls back
|
|
@@ -68930,6 +69185,8 @@ async function buildCouncilToolRegistry(planMode, opts, memoryService, memoryAut
|
|
|
68930
69185
|
planMode,
|
|
68931
69186
|
...extras?.lspProvider ? { lspProvider: extras.lspProvider } : {},
|
|
68932
69187
|
permissionPolicy: defaultPermissionPolicy2(),
|
|
69188
|
+
...opts?.onPermissionAsk ? { onPermissionAsk: opts.onPermissionAsk } : {},
|
|
69189
|
+
...opts?.onAskUser ? { onAskUser: opts.onAskUser } : {},
|
|
68933
69190
|
...memoryService ? { memoryService } : {},
|
|
68934
69191
|
memoryAutoWrite
|
|
68935
69192
|
});
|
|
@@ -68949,6 +69206,14 @@ async function buildCouncilToolRegistry(planMode, opts, memoryService, memoryAut
|
|
|
68949
69206
|
return { toolRegistry, workspaceCtx: realCtx };
|
|
68950
69207
|
}
|
|
68951
69208
|
async function runHeadlessCouncil(opts, provider, model, providerStream, extras) {
|
|
69209
|
+
const live = attachHeadlessLiveCancel({ output: opts.output });
|
|
69210
|
+
try {
|
|
69211
|
+
return await runHeadlessCouncilBody(opts, provider, model, providerStream, extras, live.signal);
|
|
69212
|
+
} finally {
|
|
69213
|
+
live.dispose();
|
|
69214
|
+
}
|
|
69215
|
+
}
|
|
69216
|
+
async function runHeadlessCouncilBody(opts, provider, model, providerStream, extras, signal) {
|
|
68952
69217
|
const { dispatchCouncil: dispatchCouncil2 } = await Promise.resolve().then(() => (init_councilDispatcher(), councilDispatcher_exports));
|
|
68953
69218
|
const sessionId2 = crypto.randomUUID();
|
|
68954
69219
|
const cwd = resolveHeadlessCwd(opts);
|
|
@@ -69024,7 +69289,7 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69024
69289
|
const effectiveTask = buildCouncilTaskWithHistory(opts.task, historySeed);
|
|
69025
69290
|
if (opts.task) spine.userMessage(effectiveTask);
|
|
69026
69291
|
let exitCode = 0;
|
|
69027
|
-
const scrub = createStreamScrubber2();
|
|
69292
|
+
const scrub = createStreamScrubber2({ stripQuestion: opts.output !== "json" });
|
|
69028
69293
|
let lastAssistantText = "";
|
|
69029
69294
|
let currentAssistantText = "";
|
|
69030
69295
|
try {
|
|
@@ -69059,6 +69324,7 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69059
69324
|
tools: toolRegistry,
|
|
69060
69325
|
feedbackStore,
|
|
69061
69326
|
runMode: councilRunMode,
|
|
69327
|
+
signal,
|
|
69062
69328
|
// t23: an auto-SELECTED council runs the LITE tier (3 members) unless
|
|
69063
69329
|
// ZELARI_COUNCIL_TIER / ZELARI_COUNCIL_SIZE explicitly opt into full.
|
|
69064
69330
|
...opts.orchestrationDecision?.strategy === "council" && process.env["ZELARI_COUNCIL_TIER"] === void 0 && process.env["ZELARI_COUNCIL_SIZE"] === void 0 ? { councilSize: COUNCIL_TIER_SIZES.lite } : {},
|
|
@@ -69117,7 +69383,9 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69117
69383
|
return 2;
|
|
69118
69384
|
}
|
|
69119
69385
|
try {
|
|
69120
|
-
await spine.close(
|
|
69386
|
+
await spine.close(
|
|
69387
|
+
signal.aborted ? "stopped" : exitCode === 0 ? "completed" : "error"
|
|
69388
|
+
);
|
|
69121
69389
|
} catch {
|
|
69122
69390
|
}
|
|
69123
69391
|
try {
|
|
@@ -69129,7 +69397,7 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69129
69397
|
at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
69130
69398
|
mode: "shadow",
|
|
69131
69399
|
taskClass: classifyTask2({ prompt: effectiveTask }).taskClass,
|
|
69132
|
-
verdict: exitCode === 0 ? "PASS" : exitCode === 3 ? "FAIL" : "UNKNOWN"
|
|
69400
|
+
verdict: signal.aborted ? "UNKNOWN" : exitCode === 0 ? "PASS" : exitCode === 3 ? "FAIL" : "UNKNOWN"
|
|
69133
69401
|
});
|
|
69134
69402
|
}
|
|
69135
69403
|
} catch {
|
|
@@ -69148,7 +69416,7 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69148
69416
|
} catch {
|
|
69149
69417
|
}
|
|
69150
69418
|
}
|
|
69151
|
-
if (nativeMemory && memoryAutoWrite && lastAssistantText) {
|
|
69419
|
+
if (nativeMemory && memoryAutoWrite && lastAssistantText && !signal.aborted) {
|
|
69152
69420
|
try {
|
|
69153
69421
|
await nativeMemory.remember({
|
|
69154
69422
|
kind: councilRunMode === "design-phase" ? "decision" : "outcome",
|
|
@@ -69175,6 +69443,14 @@ async function runHeadlessCouncil(opts, provider, model, providerStream, extras)
|
|
|
69175
69443
|
return exitCode;
|
|
69176
69444
|
}
|
|
69177
69445
|
async function runHeadlessZelari(opts, provider, model, providerStream, extras) {
|
|
69446
|
+
const live = attachHeadlessLiveCancel({ output: opts.output });
|
|
69447
|
+
try {
|
|
69448
|
+
return await runHeadlessZelariBody(opts, provider, model, providerStream, extras, live.signal);
|
|
69449
|
+
} finally {
|
|
69450
|
+
live.dispose();
|
|
69451
|
+
}
|
|
69452
|
+
}
|
|
69453
|
+
async function runHeadlessZelariBody(opts, provider, model, providerStream, extras, signal) {
|
|
69178
69454
|
const projectRoot = resolveHeadlessCwd(opts);
|
|
69179
69455
|
const sessionId2 = opts.resumeSessionId ?? crypto.randomUUID();
|
|
69180
69456
|
const spine = await openHeadlessSpine({
|
|
@@ -69285,6 +69561,7 @@ ${JSON.stringify({ deliverable: brief.deliverableThisMission, mvp: brief.sliceMv
|
|
|
69285
69561
|
memory,
|
|
69286
69562
|
emit,
|
|
69287
69563
|
buildViaAgent,
|
|
69564
|
+
signal,
|
|
69288
69565
|
onMissionPhase: (phase2, note) => spine.missionPhase(phase2, note),
|
|
69289
69566
|
onMissionProgress: (advice, iteration) => spine.missionProgress({
|
|
69290
69567
|
recommendation: advice.recommendation,
|
|
@@ -69310,7 +69587,7 @@ ${ragContext}` : slicePrompt;
|
|
|
69310
69587
|
let writeCount = 0;
|
|
69311
69588
|
let chairmanErrored = false;
|
|
69312
69589
|
let membersCompleted = 0;
|
|
69313
|
-
const scrub = createStreamScrubber2();
|
|
69590
|
+
const scrub = createStreamScrubber2({ stripQuestion: opts.output !== "json" });
|
|
69314
69591
|
const { composeProjectContext: composeProjectContext3 } = await Promise.resolve().then(() => (init_composeContext(), composeContext_exports));
|
|
69315
69592
|
const { loadDurableContext: loadDurableContext3 } = await Promise.resolve().then(() => (init_loadDurableContext(), loadDurableContext_exports));
|
|
69316
69593
|
const memOnly = ragContext?.trim() ? ragContext : void 0;
|
|
@@ -69333,6 +69610,7 @@ ${ragContext}` : slicePrompt;
|
|
|
69333
69610
|
tools: toolRegistry,
|
|
69334
69611
|
feedbackStore,
|
|
69335
69612
|
runMode: effectiveRunMode,
|
|
69613
|
+
signal,
|
|
69336
69614
|
maxToolCallsChairman: chairmanBudget,
|
|
69337
69615
|
...implementerRetry ? { skipSpecialists: true } : {},
|
|
69338
69616
|
workspaceContext: composed2.workspaceContext,
|
|
@@ -69380,11 +69658,20 @@ ${ragContext}` : slicePrompt;
|
|
|
69380
69658
|
}
|
|
69381
69659
|
let completionOk = false;
|
|
69382
69660
|
let degraded = false;
|
|
69661
|
+
if (signal.aborted) {
|
|
69662
|
+
return {
|
|
69663
|
+
completionOk: false,
|
|
69664
|
+
ran: membersCompleted > 0 || synthesisText.length > 0,
|
|
69665
|
+
synthesisText: synthesisText || void 0,
|
|
69666
|
+
writeCount,
|
|
69667
|
+
degraded: true
|
|
69668
|
+
};
|
|
69669
|
+
}
|
|
69383
69670
|
try {
|
|
69384
69671
|
const { detectDegradedRun: detectDegradedRun3 } = await Promise.resolve().then(() => (init_council(), council_exports));
|
|
69385
69672
|
const d = detectDegradedRun3({
|
|
69386
69673
|
chairmanErrored,
|
|
69387
|
-
councilAborted:
|
|
69674
|
+
councilAborted: signal.aborted,
|
|
69388
69675
|
luciferWriteCount: writeCount,
|
|
69389
69676
|
synthesisText,
|
|
69390
69677
|
runMode: effectiveRunMode
|
|
@@ -69451,7 +69738,9 @@ ${ragContext}` : slicePrompt;
|
|
|
69451
69738
|
const { registry: agentRegistry } = createBuiltinToolRegistry2({
|
|
69452
69739
|
root: projectRoot,
|
|
69453
69740
|
planMode: false,
|
|
69454
|
-
permissionPolicy: defaultPermissionPolicy2()
|
|
69741
|
+
permissionPolicy: defaultPermissionPolicy2(),
|
|
69742
|
+
...opts.onPermissionAsk ? { onPermissionAsk: opts.onPermissionAsk } : {},
|
|
69743
|
+
...opts.onAskUser ? { onAskUser: opts.onAskUser } : {}
|
|
69455
69744
|
});
|
|
69456
69745
|
await registerHeadlessMcp(agentRegistry, opts);
|
|
69457
69746
|
const durableState = await loadDurableContext2(projectRoot);
|
|
@@ -69518,7 +69807,10 @@ ${ragContext}` : slicePrompt;
|
|
|
69518
69807
|
}
|
|
69519
69808
|
});
|
|
69520
69809
|
if (state3.status === "error") exitCode = exitCode || 3;
|
|
69521
|
-
else if (state3.status === "
|
|
69810
|
+
else if (state3.status === "cancelled") {
|
|
69811
|
+
exitCode = 0;
|
|
69812
|
+
spine.missionPhase("verification", "mission-cancelled");
|
|
69813
|
+
} else if (state3.status === "success") {
|
|
69522
69814
|
const missionGate = await evaluateStrictBuildGate("build", {
|
|
69523
69815
|
emit: (input) => spine.appendEvent(input),
|
|
69524
69816
|
surface: "mission",
|
|
@@ -69556,7 +69848,8 @@ ${ragContext}` : slicePrompt;
|
|
|
69556
69848
|
}
|
|
69557
69849
|
await memory.close().catch(() => void 0);
|
|
69558
69850
|
try {
|
|
69559
|
-
if (
|
|
69851
|
+
if (signal.aborted) await spine.close("stopped");
|
|
69852
|
+
else if (exitCode === 0) await spine.close("completed");
|
|
69560
69853
|
else await spine.close(exitCode === 2 ? "error" : "stopped");
|
|
69561
69854
|
} catch {
|
|
69562
69855
|
}
|
|
@@ -69603,6 +69896,7 @@ var init_runHeadless = __esm({
|
|
|
69603
69896
|
init_metrics3();
|
|
69604
69897
|
init_headlessSpine();
|
|
69605
69898
|
init_harnessStateEmit();
|
|
69899
|
+
init_liveTurnAbort();
|
|
69606
69900
|
init_policyGate();
|
|
69607
69901
|
init_policyLoadMode();
|
|
69608
69902
|
init_runOneTurn();
|
|
@@ -71190,38 +71484,61 @@ function applyTurnPermissionPreset(input) {
|
|
|
71190
71484
|
process.env[PRESET_ENV] = value;
|
|
71191
71485
|
return true;
|
|
71192
71486
|
}
|
|
71487
|
+
function isPermissionDecision(value) {
|
|
71488
|
+
return typeof value === "string" && PERMISSION_DECISIONS.includes(value);
|
|
71489
|
+
}
|
|
71193
71490
|
function createServePermissionBridge(write, timeoutMs2 = 12e4) {
|
|
71194
71491
|
const pending = /* @__PURE__ */ new Map();
|
|
71195
71492
|
let seq = 0;
|
|
71196
|
-
const settle = (requestId, decision) => {
|
|
71493
|
+
const settle = (requestId, decision, timedOut = false) => {
|
|
71197
71494
|
const entry = pending.get(requestId);
|
|
71198
71495
|
if (!entry) return false;
|
|
71199
71496
|
pending.delete(requestId);
|
|
71200
71497
|
clearTimeout(entry.timer);
|
|
71498
|
+
write(
|
|
71499
|
+
JSON.stringify({
|
|
71500
|
+
type: "permission.settled",
|
|
71501
|
+
requestId,
|
|
71502
|
+
decision,
|
|
71503
|
+
...timedOut ? { timedOut: true } : {}
|
|
71504
|
+
})
|
|
71505
|
+
);
|
|
71201
71506
|
entry.resolve(decision);
|
|
71202
71507
|
return true;
|
|
71203
71508
|
};
|
|
71204
71509
|
return {
|
|
71205
71510
|
onPermissionAsk(payload) {
|
|
71206
71511
|
const requestId = `perm-${Date.now()}-${++seq}`;
|
|
71512
|
+
const categories = payload.categories && payload.categories.length > 0 ? payload.categories : payload.category ? payload.category.split(",").map((c) => c.trim()).filter(Boolean) : [];
|
|
71207
71513
|
return new Promise((resolve9) => {
|
|
71208
71514
|
const timer = setTimeout(() => {
|
|
71209
|
-
settle(requestId, "deny");
|
|
71515
|
+
settle(requestId, "deny", true);
|
|
71210
71516
|
}, timeoutMs2);
|
|
71211
|
-
pending.set(requestId, { resolve: resolve9, timer });
|
|
71517
|
+
pending.set(requestId, { resolve: resolve9, timer, payload });
|
|
71212
71518
|
write(
|
|
71213
71519
|
JSON.stringify({
|
|
71214
71520
|
type: "permission.request",
|
|
71215
71521
|
requestId,
|
|
71216
71522
|
tool: payload.tool,
|
|
71217
71523
|
category: payload.category,
|
|
71524
|
+
categories,
|
|
71218
71525
|
...payload.inputPreview !== void 0 ? { inputPreview: payload.inputPreview } : {},
|
|
71219
71526
|
...payload.reason !== void 0 ? { reason: payload.reason } : {}
|
|
71220
71527
|
})
|
|
71221
71528
|
);
|
|
71222
71529
|
});
|
|
71223
71530
|
},
|
|
71224
|
-
respond: settle,
|
|
71531
|
+
respond: (requestId, decision) => settle(requestId, decision, false),
|
|
71532
|
+
releaseGranted() {
|
|
71533
|
+
let n = 0;
|
|
71534
|
+
for (const [id3, entry] of [...pending]) {
|
|
71535
|
+
const cats = entry.payload.categories && entry.payload.categories.length > 0 ? entry.payload.categories : entry.payload.category ? entry.payload.category.split(",").map((c) => c.trim()).filter(Boolean) : [];
|
|
71536
|
+
if (isSessionGranted(entry.payload.tool, cats)) {
|
|
71537
|
+
if (settle(id3, "allow", false)) n += 1;
|
|
71538
|
+
}
|
|
71539
|
+
}
|
|
71540
|
+
return n;
|
|
71541
|
+
},
|
|
71225
71542
|
pendingCount: () => pending.size
|
|
71226
71543
|
};
|
|
71227
71544
|
}
|
|
@@ -71233,8 +71550,11 @@ function servePermissionRespond(bridge, params) {
|
|
|
71233
71550
|
if (typeof requestId !== "string" || requestId.length === 0) {
|
|
71234
71551
|
return { accepted: false, reason: "permission.respond requires a non-empty string requestId" };
|
|
71235
71552
|
}
|
|
71236
|
-
if (decision
|
|
71237
|
-
return {
|
|
71553
|
+
if (!isPermissionDecision(decision)) {
|
|
71554
|
+
return {
|
|
71555
|
+
accepted: false,
|
|
71556
|
+
reason: "permission.respond decision must be 'allow' | 'deny' | 'always-tool' | 'always-category'"
|
|
71557
|
+
};
|
|
71238
71558
|
}
|
|
71239
71559
|
return { accepted: bridge.respond(requestId, decision) };
|
|
71240
71560
|
}
|
|
@@ -71244,18 +71564,104 @@ function asRegistryAskHandler(bridge) {
|
|
|
71244
71564
|
const decision = await bridge.onPermissionAsk({
|
|
71245
71565
|
tool: req.toolName,
|
|
71246
71566
|
category: req.categories.join(",") || "other",
|
|
71567
|
+
categories: req.categories,
|
|
71247
71568
|
reason,
|
|
71248
71569
|
...req.claims && req.claims.length > 0 ? { inputPreview: req.claims.map((c) => c.summary).join(" \xB7 ") } : {}
|
|
71249
71570
|
});
|
|
71250
|
-
|
|
71571
|
+
if (decision === "deny") return false;
|
|
71572
|
+
if (decision === "always-tool") {
|
|
71573
|
+
grantSessionTool(req.toolName);
|
|
71574
|
+
bridge.releaseGranted();
|
|
71575
|
+
} else if (decision === "always-category") {
|
|
71576
|
+
for (const cat of req.categories) {
|
|
71577
|
+
grantSessionCategory(cat);
|
|
71578
|
+
}
|
|
71579
|
+
grantSessionTool(req.toolName);
|
|
71580
|
+
bridge.releaseGranted();
|
|
71581
|
+
}
|
|
71582
|
+
return true;
|
|
71251
71583
|
};
|
|
71252
71584
|
}
|
|
71253
|
-
var SERVE_PERMISSION_PRESETS, PRESET_ENV;
|
|
71585
|
+
var SERVE_PERMISSION_PRESETS, PRESET_ENV, PERMISSION_DECISIONS;
|
|
71254
71586
|
var init_permissionBridge = __esm({
|
|
71255
71587
|
"src/cli/serve/permissionBridge.ts"() {
|
|
71256
71588
|
"use strict";
|
|
71589
|
+
init_toolPermissions();
|
|
71257
71590
|
SERVE_PERMISSION_PRESETS = ["standard", "strict", "yolo"];
|
|
71258
71591
|
PRESET_ENV = "ZELARI_PERMISSION_PRESET";
|
|
71592
|
+
PERMISSION_DECISIONS = [
|
|
71593
|
+
"allow",
|
|
71594
|
+
"deny",
|
|
71595
|
+
"always-tool",
|
|
71596
|
+
"always-category"
|
|
71597
|
+
];
|
|
71598
|
+
}
|
|
71599
|
+
});
|
|
71600
|
+
|
|
71601
|
+
// src/cli/serve/askUserBridge.ts
|
|
71602
|
+
function createServeAskUserBridge(write, timeoutMs2 = askUserTimeoutMs()) {
|
|
71603
|
+
const pending = /* @__PURE__ */ new Map();
|
|
71604
|
+
let seq = 0;
|
|
71605
|
+
const settle = (requestId, answer, timedOut = false) => {
|
|
71606
|
+
const entry = pending.get(requestId);
|
|
71607
|
+
if (!entry) return false;
|
|
71608
|
+
pending.delete(requestId);
|
|
71609
|
+
clearTimeout(entry.timer);
|
|
71610
|
+
write(
|
|
71611
|
+
JSON.stringify({
|
|
71612
|
+
type: "ask_user.settled",
|
|
71613
|
+
requestId,
|
|
71614
|
+
answer,
|
|
71615
|
+
...timedOut ? { timedOut: true } : {}
|
|
71616
|
+
})
|
|
71617
|
+
);
|
|
71618
|
+
entry.resolve(answer);
|
|
71619
|
+
return true;
|
|
71620
|
+
};
|
|
71621
|
+
return {
|
|
71622
|
+
onAskUser(req) {
|
|
71623
|
+
const question = req.question.trim();
|
|
71624
|
+
const choices = req.choices.map((c) => c.trim()).filter(Boolean);
|
|
71625
|
+
if (choices.length < 2) return Promise.resolve(null);
|
|
71626
|
+
const requestId = `ask-${Date.now()}-${++seq}`;
|
|
71627
|
+
return new Promise((resolve9) => {
|
|
71628
|
+
const timer = setTimeout(() => {
|
|
71629
|
+
settle(requestId, null, true);
|
|
71630
|
+
}, timeoutMs2);
|
|
71631
|
+
pending.set(requestId, { resolve: resolve9, timer });
|
|
71632
|
+
write(
|
|
71633
|
+
JSON.stringify({
|
|
71634
|
+
type: "ask_user.request",
|
|
71635
|
+
requestId,
|
|
71636
|
+
question,
|
|
71637
|
+
choices,
|
|
71638
|
+
...req.context ? { context: req.context } : {}
|
|
71639
|
+
})
|
|
71640
|
+
);
|
|
71641
|
+
});
|
|
71642
|
+
},
|
|
71643
|
+
respond: (requestId, answer) => settle(requestId, answer, false),
|
|
71644
|
+
pendingCount: () => pending.size
|
|
71645
|
+
};
|
|
71646
|
+
}
|
|
71647
|
+
function serveAskUserRespond(bridge, params) {
|
|
71648
|
+
if (!params || typeof params !== "object") {
|
|
71649
|
+
return { accepted: false, reason: "ask_user.respond requires an object params" };
|
|
71650
|
+
}
|
|
71651
|
+
const { requestId, answer } = params;
|
|
71652
|
+
if (typeof requestId !== "string" || requestId.length === 0) {
|
|
71653
|
+
return { accepted: false, reason: "ask_user.respond requires a non-empty string requestId" };
|
|
71654
|
+
}
|
|
71655
|
+
if (answer !== null && typeof answer !== "string") {
|
|
71656
|
+
return { accepted: false, reason: "ask_user.respond answer must be a string or null" };
|
|
71657
|
+
}
|
|
71658
|
+
const text = typeof answer === "string" ? answer.trim() : null;
|
|
71659
|
+
return { accepted: bridge.respond(requestId, text && text.length > 0 ? text : null) };
|
|
71660
|
+
}
|
|
71661
|
+
var init_askUserBridge = __esm({
|
|
71662
|
+
"src/cli/serve/askUserBridge.ts"() {
|
|
71663
|
+
"use strict";
|
|
71664
|
+
init_askUserTimeout();
|
|
71259
71665
|
}
|
|
71260
71666
|
});
|
|
71261
71667
|
|
|
@@ -71372,7 +71778,7 @@ function resolveTurnLspProvider(services) {
|
|
|
71372
71778
|
const candidate = services?.lspManager;
|
|
71373
71779
|
return candidate instanceof LspManager ? candidate : void 0;
|
|
71374
71780
|
}
|
|
71375
|
-
function createCliRunTurn(onPermissionAsk) {
|
|
71781
|
+
function createCliRunTurn(onPermissionAsk, onAskUser) {
|
|
71376
71782
|
let streamPromise = null;
|
|
71377
71783
|
const ensureStream = () => {
|
|
71378
71784
|
if (!streamPromise) {
|
|
@@ -71399,6 +71805,7 @@ function createCliRunTurn(onPermissionAsk) {
|
|
|
71399
71805
|
const { provider, model, stream } = await ensureStream();
|
|
71400
71806
|
const opts = bindHarnessTurnOptions(input, deps.session.workspaceRoot);
|
|
71401
71807
|
if (onPermissionAsk) opts.onPermissionAsk = onPermissionAsk;
|
|
71808
|
+
if (onAskUser) opts.onAskUser = onAskUser;
|
|
71402
71809
|
applyTurnPermissionPreset(input);
|
|
71403
71810
|
const lspProvider = resolveTurnLspProvider(deps.services);
|
|
71404
71811
|
const exitCode = await dispatchHeadlessTurn(
|
|
@@ -71434,6 +71841,7 @@ function startHarnessServer(options = {}) {
|
|
|
71434
71841
|
write(JSON.stringify(envelope));
|
|
71435
71842
|
};
|
|
71436
71843
|
const permissionBridge = createServePermissionBridge(write);
|
|
71844
|
+
const askUserBridge = createServeAskUserBridge(write);
|
|
71437
71845
|
const dispatch = async (req) => {
|
|
71438
71846
|
if (typeof req.method !== "string") {
|
|
71439
71847
|
return { id: req.id ?? null, ok: false, error: { code: "bad_request", message: "missing method" } };
|
|
@@ -71447,11 +71855,21 @@ function startHarnessServer(options = {}) {
|
|
|
71447
71855
|
result: servePermissionRespond(permissionBridge, params)
|
|
71448
71856
|
};
|
|
71449
71857
|
}
|
|
71858
|
+
case "ask_user.respond": {
|
|
71859
|
+
return {
|
|
71860
|
+
id: req.id ?? null,
|
|
71861
|
+
ok: true,
|
|
71862
|
+
result: serveAskUserRespond(askUserBridge, params)
|
|
71863
|
+
};
|
|
71864
|
+
}
|
|
71450
71865
|
case "session.create": {
|
|
71451
71866
|
const root = typeof params.workspaceRoot === "string" ? params.workspaceRoot : process.cwd();
|
|
71452
71867
|
const session = server.createSession({
|
|
71453
71868
|
workspaceRoot: root,
|
|
71454
|
-
runTurn: options.runTurn ?? createCliRunTurn(
|
|
71869
|
+
runTurn: options.runTurn ?? createCliRunTurn(
|
|
71870
|
+
asRegistryAskHandler(permissionBridge),
|
|
71871
|
+
askUserBridge.onAskUser
|
|
71872
|
+
)
|
|
71455
71873
|
});
|
|
71456
71874
|
return { id: req.id ?? null, ok: true, result: { sessionId: session.id, workspaceRoot: session.workspaceRoot } };
|
|
71457
71875
|
}
|
|
@@ -71605,6 +72023,7 @@ var init_harnessServer = __esm({
|
|
|
71605
72023
|
init_policyGate();
|
|
71606
72024
|
init_policyLoadMode();
|
|
71607
72025
|
init_permissionBridge();
|
|
72026
|
+
init_askUserBridge();
|
|
71608
72027
|
init_spineLockSweep();
|
|
71609
72028
|
}
|
|
71610
72029
|
});
|
|
@@ -72647,7 +73066,12 @@ function readPackageJson4() {
|
|
|
72647
73066
|
}
|
|
72648
73067
|
}
|
|
72649
73068
|
function getGlobalPrefix() {
|
|
72650
|
-
|
|
73069
|
+
const fromNpm = tryExec("npm prefix -g");
|
|
73070
|
+
if (fromNpm) return fromNpm;
|
|
73071
|
+
return (process.env.npm_config_prefix || process.env.NPM_CONFIG_PREFIX || "").trim();
|
|
73072
|
+
}
|
|
73073
|
+
function isSourceCheckout() {
|
|
73074
|
+
return existsSync62(path95.join(packageRoot, "src", "cli", "main.ts")) && existsSync62(path95.join(packageRoot, "apps", "desktop", "package.json"));
|
|
72651
73075
|
}
|
|
72652
73076
|
function checkShim(pkgName) {
|
|
72653
73077
|
const prefix = getGlobalPrefix();
|
|
@@ -72658,6 +73082,14 @@ function checkShim(pkgName) {
|
|
|
72658
73082
|
const shimName = isWin ? "zelari-code.cmd" : "zelari-code";
|
|
72659
73083
|
const shimPath = path95.join(prefix, shimName);
|
|
72660
73084
|
if (!existsSync62(shimPath)) {
|
|
73085
|
+
const localBin = path95.join(packageRoot, "bin", "zelari-code.js");
|
|
73086
|
+
if (isSourceCheckout() && existsSync62(localBin)) {
|
|
73087
|
+
return WARN(
|
|
73088
|
+
`global shim not found at ${shimPath}
|
|
73089
|
+
source checkout \u2014 using ${localBin}
|
|
73090
|
+
optional: npm install -g ${pkgName}@latest --force`
|
|
73091
|
+
);
|
|
73092
|
+
}
|
|
72661
73093
|
return FAIL(
|
|
72662
73094
|
`shim not found at ${shimPath}
|
|
72663
73095
|
fix: npm install -g ${pkgName}@latest --force`
|
|
@@ -73052,16 +73484,15 @@ __export(fixPath_exports, {
|
|
|
73052
73484
|
});
|
|
73053
73485
|
import { spawnSync as spawnSync3 } from "node:child_process";
|
|
73054
73486
|
function getGlobalPrefix2() {
|
|
73055
|
-
|
|
73056
|
-
|
|
73057
|
-
|
|
73058
|
-
|
|
73059
|
-
|
|
73060
|
-
|
|
73061
|
-
|
|
73062
|
-
|
|
73063
|
-
|
|
73064
|
-
})();
|
|
73487
|
+
try {
|
|
73488
|
+
const fromNpm = spawnSync3("npm", ["prefix", "-g"], {
|
|
73489
|
+
encoding: "utf8",
|
|
73490
|
+
stdio: ["ignore", "pipe", "ignore"]
|
|
73491
|
+
}).stdout?.trim() ?? "";
|
|
73492
|
+
if (fromNpm) return fromNpm;
|
|
73493
|
+
} catch {
|
|
73494
|
+
}
|
|
73495
|
+
return (process.env.npm_config_prefix || process.env.NPM_CONFIG_PREFIX || "").trim();
|
|
73065
73496
|
}
|
|
73066
73497
|
function powershell(script) {
|
|
73067
73498
|
try {
|
|
@@ -76700,22 +77131,7 @@ init_spineTelemetry();
|
|
|
76700
77131
|
|
|
76701
77132
|
// src/cli/hooks/permissionPicker.ts
|
|
76702
77133
|
init_toolPermissions();
|
|
76703
|
-
|
|
76704
|
-
// src/cli/hooks/askUserTimeout.ts
|
|
76705
|
-
function askUserTimeoutMs() {
|
|
76706
|
-
const raw = process.env.ZELARI_ASK_USER_TIMEOUT_MS?.trim();
|
|
76707
|
-
if (!raw) return 3e5;
|
|
76708
|
-
const n = Number.parseInt(raw, 10);
|
|
76709
|
-
if (!Number.isFinite(n) || n < 0) return 3e5;
|
|
76710
|
-
return n;
|
|
76711
|
-
}
|
|
76712
|
-
function armPickerTimeout(onFire, ms) {
|
|
76713
|
-
if (ms <= 0) return () => void 0;
|
|
76714
|
-
const id3 = setTimeout(onFire, ms);
|
|
76715
|
-
return () => clearTimeout(id3);
|
|
76716
|
-
}
|
|
76717
|
-
|
|
76718
|
-
// src/cli/hooks/permissionPicker.ts
|
|
77134
|
+
init_askUserTimeout();
|
|
76719
77135
|
function createPermissionAskHandler(opts) {
|
|
76720
77136
|
const { setPicker: setPicker2, appendSystem: appendSystem2 } = opts;
|
|
76721
77137
|
return (req) => new Promise((resolve9) => {
|
|
@@ -76808,6 +77224,7 @@ ${detail}${note}${claimsBlock}
|
|
|
76808
77224
|
}
|
|
76809
77225
|
|
|
76810
77226
|
// src/cli/hooks/useChatTurn.ts
|
|
77227
|
+
init_askUserTimeout();
|
|
76811
77228
|
init_toolPermissions();
|
|
76812
77229
|
init_skills2();
|
|
76813
77230
|
init_fileStateStore();
|
|
@@ -78737,6 +79154,7 @@ init_permissionBroker();
|
|
|
78737
79154
|
init_brokerHandlers();
|
|
78738
79155
|
import { useEffect as useEffect5, useRef as useRef5 } from "react";
|
|
78739
79156
|
init_messageHelpers();
|
|
79157
|
+
init_askUserTimeout();
|
|
78740
79158
|
function usePermissionBroker(opts) {
|
|
78741
79159
|
const { setPicker: setPicker2, setMessages } = opts;
|
|
78742
79160
|
const handleRef = useRef5(null);
|