jinzd-ai-cli 0.4.191 → 0.4.193

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.
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  truncateForPersist
4
- } from "./chunk-RQ7JVLFM.js";
4
+ } from "./chunk-SI5EO3NJ.js";
5
5
  import {
6
6
  APP_NAME,
7
7
  CONFIG_DIR_NAME,
@@ -11,7 +11,7 @@ import {
11
11
  MCP_PROTOCOL_VERSION,
12
12
  MCP_TOOL_PREFIX,
13
13
  VERSION
14
- } from "./chunk-ASVBZIUE.js";
14
+ } from "./chunk-P3PTUSP4.js";
15
15
 
16
16
  // src/mcp/client.ts
17
17
  import { spawn } from "child_process";
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
 
3
3
  // src/core/constants.ts
4
- var VERSION = "0.4.191";
4
+ var VERSION = "0.4.193";
5
5
  var APP_NAME = "ai-cli";
6
6
  var CONFIG_DIR_NAME = ".aicli";
7
7
  var CONFIG_FILE_NAME = "config.json";
@@ -2,7 +2,7 @@
2
2
  import {
3
3
  CONFIG_DIR_NAME,
4
4
  VERSION
5
- } from "./chunk-ASVBZIUE.js";
5
+ } from "./chunk-P3PTUSP4.js";
6
6
 
7
7
  // src/diagnostics/crash-log.ts
8
8
  import {
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  CONFIG_DIR_NAME
4
- } from "./chunk-ASVBZIUE.js";
4
+ } from "./chunk-P3PTUSP4.js";
5
5
  import {
6
6
  atomicWriteFileSync
7
7
  } from "./chunk-IW3Q7AE5.js";
@@ -5,14 +5,15 @@ import {
5
5
  } from "./chunk-T2NL5ZIA.js";
6
6
  import {
7
7
  runTestsTool
8
- } from "./chunk-HSQAKOYX.js";
8
+ } from "./chunk-7PX3ZX4G.js";
9
9
  import {
10
10
  runTool
11
- } from "./chunk-Y3PNCW7A.js";
11
+ } from "./chunk-SHI5UFUH.js";
12
12
  import {
13
13
  getDangerLevel,
14
- isFileWriteTool
15
- } from "./chunk-HIU2SH4V.js";
14
+ isFileWriteTool,
15
+ runLeanAgentLoop
16
+ } from "./chunk-JOR572WG.js";
16
17
  import {
17
18
  EnvLoader,
18
19
  NetworkError,
@@ -25,7 +26,7 @@ import {
25
26
  SUBAGENT_ALLOWED_TOOLS,
26
27
  SUBAGENT_DEFAULT_MAX_ROUNDS,
27
28
  SUBAGENT_MAX_ROUNDS_LIMIT
28
- } from "./chunk-ASVBZIUE.js";
29
+ } from "./chunk-P3PTUSP4.js";
29
30
  import {
30
31
  fileCheckpoints
31
32
  } from "./chunk-4BKXL7SM.js";
@@ -3801,9 +3802,19 @@ ${preamble}`;
3801
3802
  }
3802
3803
 
3803
3804
  // src/tools/builtin/save-last-response.ts
3804
- import { writeFileSync as writeFileSync4, mkdirSync as mkdirSync2 } from "fs";
3805
+ import { writeFileSync as writeFileSync4, mkdirSync as mkdirSync2, unlinkSync as unlinkSync2, rmdirSync as rmdirSync2 } from "fs";
3805
3806
  import { dirname as dirname3 } from "path";
3806
3807
  var lastResponseStore = { content: "" };
3808
+ function cleanupRejectedTeeFile(filePath) {
3809
+ try {
3810
+ unlinkSync2(filePath);
3811
+ } catch {
3812
+ }
3813
+ try {
3814
+ rmdirSync2(dirname3(filePath));
3815
+ } catch {
3816
+ }
3817
+ }
3807
3818
  var saveLastResponseTool = {
3808
3819
  definition: {
3809
3820
  name: "save_last_response",
@@ -4345,61 +4356,37 @@ async function runSubAgent(task, maxRounds, agentIndex, ctx) {
4345
4356
  ];
4346
4357
  const subSystemPrompt = buildSubAgentSystemPrompt(task, ctx.systemPrompt);
4347
4358
  const toolDefs = subRegistry.getDefinitions();
4348
- const extraMessages = [];
4349
- const totalUsage = { inputTokens: 0, outputTokens: 0 };
4350
- let finalContent = "";
4351
4359
  printSubAgentHeader(task, maxRounds, agentIndex);
4352
- try {
4353
- for (let round = 0; round < maxRounds; round++) {
4360
+ const loop = await runLeanAgentLoop({
4361
+ provider: ctx.provider,
4362
+ messages: subMessages,
4363
+ model: ctx.model,
4364
+ maxRounds,
4365
+ chatParams: {
4366
+ temperature: ctx.modelParams.temperature,
4367
+ maxTokens: ctx.modelParams.maxTokens,
4368
+ timeout: ctx.modelParams.timeout,
4369
+ thinking: ctx.modelParams.thinking
4370
+ },
4371
+ executeTools: (calls) => subExecutor.executeAll(calls),
4372
+ systemPromptForRound: () => subSystemPrompt,
4373
+ toolDefsForRound: () => toolDefs,
4374
+ onRoundStart: (round) => {
4354
4375
  subExecutor.setRoundInfo(round + 1, maxRounds);
4355
- const result = await ctx.provider.chatWithTools(
4356
- {
4357
- messages: subMessages,
4358
- model: ctx.model,
4359
- systemPrompt: subSystemPrompt,
4360
- stream: false,
4361
- temperature: ctx.modelParams.temperature,
4362
- maxTokens: ctx.modelParams.maxTokens,
4363
- timeout: ctx.modelParams.timeout,
4364
- thinking: ctx.modelParams.thinking,
4365
- ...extraMessages.length > 0 ? { _extraMessages: extraMessages } : {}
4366
- },
4367
- toolDefs
4368
- );
4369
- if (result.usage) {
4370
- totalUsage.inputTokens += result.usage.inputTokens;
4371
- totalUsage.outputTokens += result.usage.outputTokens;
4372
- }
4373
- if ("content" in result) {
4374
- finalContent = result.content;
4375
- break;
4376
- }
4377
4376
  if (ctx.configManager) {
4378
4377
  googleSearchContext.configManager = ctx.configManager;
4379
4378
  }
4380
- const toolResults = await subExecutor.executeAll(result.toolCalls);
4381
- const reasoningContent = "reasoningContent" in result ? result.reasoningContent : void 0;
4382
- const newMsgs = ctx.provider.buildToolResultMessages(
4383
- result.toolCalls,
4384
- toolResults,
4385
- reasoningContent
4386
- );
4387
- extraMessages.push(...newMsgs);
4388
- }
4389
- if (!finalContent) {
4390
- finalContent = `(Sub-agent reached maximum rounds (${maxRounds}) without producing a final response)`;
4391
- }
4392
- } catch (err) {
4393
- const errMsg = err instanceof Error ? err.message : String(err);
4394
- finalContent = `(Sub-agent error: ${errMsg})`;
4395
- process.stderr.write(
4396
- `
4379
+ },
4380
+ onRoundsExhausted: () => `(Sub-agent reached maximum rounds (${maxRounds}) without producing a final response)`,
4381
+ onError: (errMsg) => {
4382
+ process.stderr.write(`
4397
4383
  [spawn_agent] Error in sub-agent loop: ${errMsg}
4398
- `
4399
- );
4400
- }
4401
- printSubAgentFooter(totalUsage, agentIndex);
4402
- return { content: finalContent, usage: totalUsage };
4384
+ `);
4385
+ return `(Sub-agent error: ${errMsg})`;
4386
+ }
4387
+ });
4388
+ printSubAgentFooter(loop.usage, agentIndex);
4389
+ return { content: loop.content, usage: loop.usage };
4403
4390
  }
4404
4391
  var spawnAgentTool = {
4405
4392
  definition: {
@@ -5660,6 +5647,7 @@ export {
5660
5647
  truncateOutput,
5661
5648
  ToolExecutor,
5662
5649
  lastResponseStore,
5650
+ cleanupRejectedTeeFile,
5663
5651
  askUserContext,
5664
5652
  googleSearchContext,
5665
5653
  spawnAgentContext,
@@ -8,7 +8,7 @@ import {
8
8
  CONFIG_FILE_NAME,
9
9
  HISTORY_DIR_NAME,
10
10
  PLUGINS_DIR_NAME
11
- } from "./chunk-ASVBZIUE.js";
11
+ } from "./chunk-P3PTUSP4.js";
12
12
 
13
13
  // src/config/config-manager.ts
14
14
  import { readFileSync, writeFileSync, existsSync, mkdirSync } from "fs";
@@ -6,15 +6,15 @@ import {
6
6
  } from "./chunk-HLWUDRBO.js";
7
7
  import {
8
8
  ProviderRegistry
9
- } from "./chunk-JTLPYPT3.js";
10
- import "./chunk-HIU2SH4V.js";
9
+ } from "./chunk-BGXQGCEO.js";
10
+ import "./chunk-JOR572WG.js";
11
11
  import {
12
12
  ConfigManager
13
- } from "./chunk-XDH5EFWC.js";
13
+ } from "./chunk-VQT27CZK.js";
14
14
  import "./chunk-TZQHYZKT.js";
15
15
  import {
16
16
  VERSION
17
- } from "./chunk-ASVBZIUE.js";
17
+ } from "./chunk-P3PTUSP4.js";
18
18
 
19
19
  // src/cli/ci.ts
20
20
  import { execFileSync, execSync } from "child_process";
@@ -36,7 +36,7 @@ import {
36
36
  TEST_TIMEOUT,
37
37
  VERSION,
38
38
  buildUserIdentityPrompt
39
- } from "./chunk-ASVBZIUE.js";
39
+ } from "./chunk-P3PTUSP4.js";
40
40
  export {
41
41
  AGENTIC_BEHAVIOR_GUIDELINE,
42
42
  APP_NAME,
@@ -2,26 +2,26 @@
2
2
  import {
3
3
  getConfigDirUsage,
4
4
  listRecentCrashes
5
- } from "./chunk-TRV47UK4.js";
5
+ } from "./chunk-PO3ZY3PN.js";
6
6
  import {
7
7
  ProviderRegistry
8
- } from "./chunk-JTLPYPT3.js";
8
+ } from "./chunk-BGXQGCEO.js";
9
9
  import {
10
10
  getStatsSnapshot,
11
11
  getTopFailingTools,
12
12
  getTopUsedTools,
13
13
  resetStats
14
- } from "./chunk-Y3PNCW7A.js";
15
- import "./chunk-HIU2SH4V.js";
14
+ } from "./chunk-SHI5UFUH.js";
15
+ import "./chunk-JOR572WG.js";
16
16
  import {
17
17
  ConfigManager
18
- } from "./chunk-XDH5EFWC.js";
18
+ } from "./chunk-VQT27CZK.js";
19
19
  import "./chunk-TZQHYZKT.js";
20
20
  import {
21
21
  DEV_STATE_FILE_NAME,
22
22
  MEMORY_FILE_NAME,
23
23
  VERSION
24
- } from "./chunk-ASVBZIUE.js";
24
+ } from "./chunk-P3PTUSP4.js";
25
25
  import "./chunk-IW3Q7AE5.js";
26
26
 
27
27
  // src/diagnostics/doctor-cli.ts
@@ -36,7 +36,7 @@ import {
36
36
  VERSION,
37
37
  buildUserIdentityPrompt,
38
38
  runTestsTool
39
- } from "./chunk-6Z42O3DN.js";
39
+ } from "./chunk-IFETB4PY.js";
40
40
  import {
41
41
  hasSemanticIndex,
42
42
  semanticSearch
@@ -1965,13 +1965,32 @@ You are now in a CONTENT-ONLY streaming pass. The file at the configured path wi
1965
1965
  - If you accidentally start a <tool_call>, STOP and produce the document body instead.
1966
1966
 
1967
1967
  The file is closed and named when this stream ends. If your output contains pseudo-tool-call markup, the save will be REJECTED and you will be asked to retry.`;
1968
+ function isCleanDocumentBody(content) {
1969
+ if (!content) return false;
1970
+ if (detectMetaNarration(content)) return false;
1971
+ if (detectPseudoToolCalls(content)) return false;
1972
+ return looksLikeDocumentBody(content);
1973
+ }
1968
1974
  function teeFileStats(content) {
1969
1975
  return { lines: content.split("\n").length, bytes: Buffer.byteLength(content, "utf-8") };
1970
1976
  }
1971
- function evaluateTeeContent(rawContent, saveToFile) {
1977
+ function evaluateTeeContent(rawContent, saveToFile, priorContent) {
1978
+ const fallback = (matched) => {
1979
+ if (priorContent && priorContent !== rawContent && isCleanDocumentBody(priorContent)) {
1980
+ const body = priorContent.trim();
1981
+ const { lines: lines2, bytes: bytes2 } = teeFileStats(body);
1982
+ return {
1983
+ kind: "fallback",
1984
+ content: body,
1985
+ matched,
1986
+ summary: `File saved (fallback to last shown response): ${saveToFile} (${lines2} lines, ${bytes2} bytes). The fresh content-only stream produced no usable document body (matched: ${matched}); saved the response you previously displayed instead. Verify it is the intended document.`
1987
+ };
1988
+ }
1989
+ return null;
1990
+ };
1972
1991
  const metaMatch = detectMetaNarration(rawContent);
1973
1992
  if (metaMatch) {
1974
- return {
1993
+ return fallback(metaMatch) ?? {
1975
1994
  kind: "reject",
1976
1995
  reason: "meta-narration",
1977
1996
  matched: metaMatch,
@@ -1992,7 +2011,7 @@ This fresh stream has NO tools. Produce ONLY the document body: start with a mar
1992
2011
  summary: `File saved (with cleanup): ${saveToFile} (${lines2} lines, ${bytes2} bytes; pseudo-tool-call markup matching ${pseudoMatch} was stripped before save)`
1993
2012
  };
1994
2013
  }
1995
- return {
2014
+ return fallback(pseudoMatch) ?? {
1996
2015
  kind: "reject",
1997
2016
  reason: "pseudo-tool-call",
1998
2017
  matched: pseudoMatch,
@@ -2460,6 +2479,52 @@ function summarizeRecentTools(history, interval) {
2460
2479
  }
2461
2480
  return [...counts.entries()].sort((a, b) => b[1] - a[1]).map(([name, count]) => count > 1 ? `${name}\xD7${count}` : name).join(", ");
2462
2481
  }
2482
+ async function runLeanAgentLoop(opts) {
2483
+ const extraMessages = [];
2484
+ const usage = { inputTokens: 0, outputTokens: 0 };
2485
+ let content = "";
2486
+ let roundsUsed = 0;
2487
+ let toolCallCount = 0;
2488
+ try {
2489
+ for (let round = 0; round < opts.maxRounds; round++) {
2490
+ roundsUsed = round + 1;
2491
+ opts.onRoundStart?.(round, opts.maxRounds);
2492
+ const result = await opts.provider.chatWithTools(
2493
+ {
2494
+ messages: opts.messages,
2495
+ model: opts.model,
2496
+ systemPrompt: opts.systemPromptForRound(round, opts.maxRounds - round),
2497
+ stream: false,
2498
+ temperature: opts.chatParams?.temperature,
2499
+ maxTokens: opts.chatParams?.maxTokens,
2500
+ timeout: opts.chatParams?.timeout,
2501
+ thinking: opts.chatParams?.thinking,
2502
+ ...extraMessages.length > 0 ? { _extraMessages: extraMessages } : {}
2503
+ },
2504
+ opts.toolDefsForRound(round)
2505
+ );
2506
+ if (result.usage) {
2507
+ usage.inputTokens += result.usage.inputTokens;
2508
+ usage.outputTokens += result.usage.outputTokens;
2509
+ }
2510
+ if ("content" in result) {
2511
+ content = result.content;
2512
+ break;
2513
+ }
2514
+ toolCallCount += result.toolCalls.length;
2515
+ const toolResults = await opts.executeTools(result.toolCalls);
2516
+ const reasoningContent = "reasoningContent" in result ? result.reasoningContent : void 0;
2517
+ extraMessages.push(
2518
+ ...opts.provider.buildToolResultMessages(result.toolCalls, toolResults, reasoningContent)
2519
+ );
2520
+ }
2521
+ if (!content) content = opts.onRoundsExhausted(toolCallCount);
2522
+ } catch (err) {
2523
+ const errMsg = err instanceof Error ? err.message : String(err);
2524
+ content = opts.onError(errMsg);
2525
+ }
2526
+ return { content, usage, roundsUsed, toolCallCount };
2527
+ }
2463
2528
 
2464
2529
  // src/providers/openai-compatible.ts
2465
2530
  function toUsage(u) {
@@ -8375,9 +8440,19 @@ ${preamble}`;
8375
8440
  }
8376
8441
 
8377
8442
  // src/tools/builtin/save-last-response.ts
8378
- import { writeFileSync as writeFileSync5, mkdirSync as mkdirSync5 } from "fs";
8443
+ import { writeFileSync as writeFileSync5, mkdirSync as mkdirSync5, unlinkSync as unlinkSync3, rmdirSync as rmdirSync2 } from "fs";
8379
8444
  import { dirname as dirname4 } from "path";
8380
8445
  var lastResponseStore = { content: "" };
8446
+ function cleanupRejectedTeeFile(filePath) {
8447
+ try {
8448
+ unlinkSync3(filePath);
8449
+ } catch {
8450
+ }
8451
+ try {
8452
+ rmdirSync2(dirname4(filePath));
8453
+ } catch {
8454
+ }
8455
+ }
8381
8456
  var saveLastResponseTool = {
8382
8457
  definition: {
8383
8458
  name: "save_last_response",
@@ -8919,61 +8994,37 @@ async function runSubAgent(task, maxRounds, agentIndex, ctx) {
8919
8994
  ];
8920
8995
  const subSystemPrompt = buildSubAgentSystemPrompt(task, ctx.systemPrompt);
8921
8996
  const toolDefs = subRegistry.getDefinitions();
8922
- const extraMessages = [];
8923
- const totalUsage = { inputTokens: 0, outputTokens: 0 };
8924
- let finalContent = "";
8925
8997
  printSubAgentHeader(task, maxRounds, agentIndex);
8926
- try {
8927
- for (let round = 0; round < maxRounds; round++) {
8998
+ const loop = await runLeanAgentLoop({
8999
+ provider: ctx.provider,
9000
+ messages: subMessages,
9001
+ model: ctx.model,
9002
+ maxRounds,
9003
+ chatParams: {
9004
+ temperature: ctx.modelParams.temperature,
9005
+ maxTokens: ctx.modelParams.maxTokens,
9006
+ timeout: ctx.modelParams.timeout,
9007
+ thinking: ctx.modelParams.thinking
9008
+ },
9009
+ executeTools: (calls) => subExecutor.executeAll(calls),
9010
+ systemPromptForRound: () => subSystemPrompt,
9011
+ toolDefsForRound: () => toolDefs,
9012
+ onRoundStart: (round) => {
8928
9013
  subExecutor.setRoundInfo(round + 1, maxRounds);
8929
- const result = await ctx.provider.chatWithTools(
8930
- {
8931
- messages: subMessages,
8932
- model: ctx.model,
8933
- systemPrompt: subSystemPrompt,
8934
- stream: false,
8935
- temperature: ctx.modelParams.temperature,
8936
- maxTokens: ctx.modelParams.maxTokens,
8937
- timeout: ctx.modelParams.timeout,
8938
- thinking: ctx.modelParams.thinking,
8939
- ...extraMessages.length > 0 ? { _extraMessages: extraMessages } : {}
8940
- },
8941
- toolDefs
8942
- );
8943
- if (result.usage) {
8944
- totalUsage.inputTokens += result.usage.inputTokens;
8945
- totalUsage.outputTokens += result.usage.outputTokens;
8946
- }
8947
- if ("content" in result) {
8948
- finalContent = result.content;
8949
- break;
8950
- }
8951
9014
  if (ctx.configManager) {
8952
9015
  googleSearchContext.configManager = ctx.configManager;
8953
9016
  }
8954
- const toolResults = await subExecutor.executeAll(result.toolCalls);
8955
- const reasoningContent = "reasoningContent" in result ? result.reasoningContent : void 0;
8956
- const newMsgs = ctx.provider.buildToolResultMessages(
8957
- result.toolCalls,
8958
- toolResults,
8959
- reasoningContent
8960
- );
8961
- extraMessages.push(...newMsgs);
8962
- }
8963
- if (!finalContent) {
8964
- finalContent = `(Sub-agent reached maximum rounds (${maxRounds}) without producing a final response)`;
8965
- }
8966
- } catch (err) {
8967
- const errMsg = err instanceof Error ? err.message : String(err);
8968
- finalContent = `(Sub-agent error: ${errMsg})`;
8969
- process.stderr.write(
8970
- `
9017
+ },
9018
+ onRoundsExhausted: () => `(Sub-agent reached maximum rounds (${maxRounds}) without producing a final response)`,
9019
+ onError: (errMsg) => {
9020
+ process.stderr.write(`
8971
9021
  [spawn_agent] Error in sub-agent loop: ${errMsg}
8972
- `
8973
- );
8974
- }
8975
- printSubAgentFooter(totalUsage, agentIndex);
8976
- return { content: finalContent, usage: totalUsage };
9022
+ `);
9023
+ return `(Sub-agent error: ${errMsg})`;
9024
+ }
9025
+ });
9026
+ printSubAgentFooter(loop.usage, agentIndex);
9027
+ return { content: loop.content, usage: loop.usage };
8977
9028
  }
8978
9029
  var spawnAgentTool = {
8979
9030
  definition: {
@@ -11220,7 +11271,7 @@ import { existsSync as existsSync19, readFileSync as readFileSync13 } from "fs";
11220
11271
  import { join as join12 } from "path";
11221
11272
 
11222
11273
  // src/repl/dev-state.ts
11223
- import { existsSync as existsSync18, readFileSync as readFileSync12, writeFileSync as writeFileSync6, unlinkSync as unlinkSync3, mkdirSync as mkdirSync9 } from "fs";
11274
+ import { existsSync as existsSync18, readFileSync as readFileSync12, writeFileSync as writeFileSync6, unlinkSync as unlinkSync4, mkdirSync as mkdirSync9 } from "fs";
11224
11275
  import { join as join11 } from "path";
11225
11276
  import { homedir as homedir6 } from "os";
11226
11277
  function getDevStatePath() {
@@ -11494,7 +11545,7 @@ function autoTrimSessionIfNeeded(session, sizeLimit = SESSION_SIZE_LIMIT) {
11494
11545
  }
11495
11546
 
11496
11547
  // src/web/session-handler.ts
11497
- import { existsSync as existsSync21, readFileSync as readFileSync14, appendFileSync as appendFileSync3, writeFileSync as writeFileSync7, mkdirSync as mkdirSync10, readdirSync as readdirSync9, statSync as statSync8, createWriteStream, unlinkSync as unlinkSync4 } from "fs";
11548
+ import { existsSync as existsSync21, readFileSync as readFileSync14, appendFileSync as appendFileSync3, writeFileSync as writeFileSync7, mkdirSync as mkdirSync10, readdirSync as readdirSync9, statSync as statSync8, createWriteStream } from "fs";
11498
11549
  import { join as join15, resolve as resolve5, dirname as dirname5 } from "path";
11499
11550
  import { execSync as execSync3 } from "child_process";
11500
11551
 
@@ -12202,6 +12253,20 @@ async function persistDiscussion(state2, config, defaultProvider, defaultModel)
12202
12253
  }
12203
12254
 
12204
12255
  // src/web/session-handler.ts
12256
+ function lastAssistantText(messages) {
12257
+ for (let i = messages.length - 1; i >= 0; i--) {
12258
+ const m = messages[i];
12259
+ if (!m || m.role !== "assistant") continue;
12260
+ const c = m.content;
12261
+ if (typeof c === "string") return c;
12262
+ if (Array.isArray(c)) {
12263
+ const text = c.filter((p) => p && p.type === "text" && typeof p.text === "string").map((p) => p.text).join("");
12264
+ if (text) return text;
12265
+ }
12266
+ return void 0;
12267
+ }
12268
+ return void 0;
12269
+ }
12205
12270
  var SessionHandler = class _SessionHandler {
12206
12271
  ws;
12207
12272
  config;
@@ -13011,17 +13076,14 @@ ${summaryContent}`,
13011
13076
  await new Promise((resolve7, reject) => {
13012
13077
  fileStream.end((err) => err ? reject(err) : resolve7());
13013
13078
  });
13014
- const verdict = evaluateTeeContent(fullContent, saveToFile);
13079
+ const verdict = evaluateTeeContent(fullContent, saveToFile, lastAssistantText(apiMessages));
13015
13080
  if (verdict.kind === "reject") {
13016
- try {
13017
- unlinkSync4(saveToFile);
13018
- } catch {
13019
- }
13081
+ cleanupRejectedTeeFile(saveToFile);
13020
13082
  isError = true;
13021
13083
  summary = verdict.summary;
13022
13084
  fullContent = "";
13023
13085
  } else {
13024
- if (verdict.kind === "salvaged") {
13086
+ if (verdict.kind === "salvaged" || verdict.kind === "fallback") {
13025
13087
  writeFileSync7(saveToFile, verdict.content, "utf-8");
13026
13088
  fullContent = verdict.content;
13027
13089
  }
@@ -13041,10 +13103,7 @@ ${summaryContent}`,
13041
13103
  } catch {
13042
13104
  }
13043
13105
  }
13044
- try {
13045
- unlinkSync4(saveToFile);
13046
- } catch {
13047
- }
13106
+ cleanupRejectedTeeFile(saveToFile);
13048
13107
  isError = true;
13049
13108
  const msg = err instanceof Error ? err.message : String(err);
13050
13109
  summary = teeStreamErrorSummary(saveToFile, msg);
@@ -14090,7 +14149,7 @@ ${undoResults.map((r) => ` \u2022 ${r}`).join("\n")}` });
14090
14149
  case "test": {
14091
14150
  this.send({ type: "info", message: "\u{1F9EA} Running tests..." });
14092
14151
  try {
14093
- const { executeTests } = await import("./run-tests-H3VCHOJB.js");
14152
+ const { executeTests } = await import("./run-tests-4QWMA4ZF.js");
14094
14153
  const argStr = args.join(" ").trim();
14095
14154
  let testArgs = {};
14096
14155
  if (argStr) {
@@ -154,7 +154,7 @@ ${content}`);
154
154
  }
155
155
  }
156
156
  async function runTaskMode(config, providers, configManager, topic) {
157
- const { TaskOrchestrator } = await import("./task-orchestrator-VFCQGTYA.js");
157
+ const { TaskOrchestrator } = await import("./task-orchestrator-RI63ZZNN.js");
158
158
  const orchestrator = new TaskOrchestrator(config, providers, configManager);
159
159
  let interrupted = false;
160
160
  const onSigint = () => {