jinzd-ai-cli 0.4.193 → 0.4.195
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/{batch-M6367YB4.js → batch-46RLXVR7.js} +2 -2
- package/dist/{chunk-PO3ZY3PN.js → chunk-4ZRGTTO4.js} +1 -1
- package/dist/{chunk-P3PTUSP4.js → chunk-6RWXUT74.js} +1 -1
- package/dist/{chunk-7PX3ZX4G.js → chunk-6WUIOZGL.js} +1 -1
- package/dist/{chunk-IFETB4PY.js → chunk-7YZXAPHE.js} +1 -1
- package/dist/{chunk-SI5EO3NJ.js → chunk-A2P7LQEX.js} +4 -4
- package/dist/{chunk-VQT27CZK.js → chunk-KRP2XBJ3.js} +1 -1
- package/dist/{chunk-SHI5UFUH.js → chunk-KT6PA3NH.js} +1 -1
- package/dist/{chunk-BGXQGCEO.js → chunk-VWZMVWA4.js} +1 -1
- package/dist/{chunk-MI23I43Y.js → chunk-XTL6I7J3.js} +2 -2
- package/dist/{chunk-JOR572WG.js → chunk-YZH2QQXJ.js} +14 -0
- package/dist/{ci-4MJ4EGKQ.js → ci-FBTIW7YY.js} +4 -4
- package/dist/{constants-LEU54VQQ.js → constants-5LJTWBPU.js} +1 -1
- package/dist/{doctor-cli-4RKSIH7N.js → doctor-cli-2JM5LE3J.js} +6 -6
- package/dist/electron-server.js +46 -7
- package/dist/{hub-XMUI5HMK.js → hub-ZIYP65L7.js} +1 -1
- package/dist/index.js +65 -24
- package/dist/{run-tests-IL4342SV.js → run-tests-2H2G7VPL.js} +2 -2
- package/dist/{run-tests-4QWMA4ZF.js → run-tests-RY4GBMDM.js} +1 -1
- package/dist/{server-Y7TCCIGA.js → server-6ZDQTDLT.js} +5 -5
- package/dist/{server-KE7X3BHW.js → server-VJYNMQOR.js} +45 -14
- package/dist/{task-orchestrator-RI63ZZNN.js → task-orchestrator-PA5PWQFE.js} +5 -5
- package/dist/{usage-CG7PJ3AB.js → usage-CF37QUOV.js} +2 -2
- package/package.json +1 -1
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
ConfigManager
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-KRP2XBJ3.js";
|
|
5
5
|
import "./chunk-TZQHYZKT.js";
|
|
6
|
-
import "./chunk-
|
|
6
|
+
import "./chunk-6RWXUT74.js";
|
|
7
7
|
import {
|
|
8
8
|
atomicWriteFileSync
|
|
9
9
|
} from "./chunk-IW3Q7AE5.js";
|
|
@@ -5,15 +5,15 @@ import {
|
|
|
5
5
|
} from "./chunk-T2NL5ZIA.js";
|
|
6
6
|
import {
|
|
7
7
|
runTestsTool
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-6WUIOZGL.js";
|
|
9
9
|
import {
|
|
10
10
|
runTool
|
|
11
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-KT6PA3NH.js";
|
|
12
12
|
import {
|
|
13
13
|
getDangerLevel,
|
|
14
14
|
isFileWriteTool,
|
|
15
15
|
runLeanAgentLoop
|
|
16
|
-
} from "./chunk-
|
|
16
|
+
} from "./chunk-YZH2QQXJ.js";
|
|
17
17
|
import {
|
|
18
18
|
EnvLoader,
|
|
19
19
|
NetworkError,
|
|
@@ -26,7 +26,7 @@ import {
|
|
|
26
26
|
SUBAGENT_ALLOWED_TOOLS,
|
|
27
27
|
SUBAGENT_DEFAULT_MAX_ROUNDS,
|
|
28
28
|
SUBAGENT_MAX_ROUNDS_LIMIT
|
|
29
|
-
} from "./chunk-
|
|
29
|
+
} from "./chunk-6RWXUT74.js";
|
|
30
30
|
import {
|
|
31
31
|
fileCheckpoints
|
|
32
32
|
} from "./chunk-4BKXL7SM.js";
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
truncateForPersist
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-A2P7LQEX.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-
|
|
14
|
+
} from "./chunk-6RWXUT74.js";
|
|
15
15
|
|
|
16
16
|
// src/mcp/client.ts
|
|
17
17
|
import { spawn } from "child_process";
|
|
@@ -483,6 +483,11 @@ function isCleanDocumentBody(content) {
|
|
|
483
483
|
function teeFileStats(content) {
|
|
484
484
|
return { lines: content.split("\n").length, bytes: Buffer.byteLength(content, "utf-8") };
|
|
485
485
|
}
|
|
486
|
+
function freshPriorContent(current, baselineAtTurnStart) {
|
|
487
|
+
if (!current) return void 0;
|
|
488
|
+
if (current === baselineAtTurnStart) return void 0;
|
|
489
|
+
return current;
|
|
490
|
+
}
|
|
486
491
|
function evaluateTeeContent(rawContent, saveToFile, priorContent) {
|
|
487
492
|
const fallback = (matched) => {
|
|
488
493
|
if (priorContent && priorContent !== rawContent && isCleanDocumentBody(priorContent)) {
|
|
@@ -536,6 +541,12 @@ This fresh stream has NO tools \u2014 output is captured verbatim. STOP emitting
|
|
|
536
541
|
summary: `File saved: ${saveToFile} (${lines} lines, ${bytes} bytes)`
|
|
537
542
|
};
|
|
538
543
|
}
|
|
544
|
+
function buildDeferredSaveInstruction(saveToFile) {
|
|
545
|
+
return `[save_last_response \u65E0\u6CD5\u81EA\u52A8\u751F\u6210\u6587\u6863]
|
|
546
|
+
content-only \u6D41\u4EA7\u51FA\u7684\u662F\u5DE5\u5177\u8C03\u7528\u6807\u8BB0 / \u5185\u5FC3\u72EC\u767D\u800C\u975E\u6587\u6863\u6B63\u6587\uFF0C${saveToFile} \u672A\u4FDD\u5B58\u3002
|
|
547
|
+
|
|
548
|
+
\u4E0D\u8981\u518D\u8C03\u7528 save_last_response\u3002\u8BF7\u76F4\u63A5\u7528**\u666E\u901A\u6587\u672C\u56DE\u590D**\u628A\u5B8C\u6574\u6587\u6863\u5199\u51FA\u6765\uFF1A\u7EAF markdown\uFF0C\u7B2C\u4E00\u4E2A\u5B57\u7B26\u5C31\u662F\u9876\u7EA7\u6807\u9898\uFF08\u5982 "# \u5BA1\u8BA1\u62A5\u544A"\uFF09\uFF0C\u4E0D\u8981\u4EFB\u4F55\u5DE5\u5177\u8C03\u7528\u3001\u4E0D\u8981\u524D\u8A00\u94FA\u57AB\u3002\u7CFB\u7EDF\u4F1A\u81EA\u52A8\u628A\u4F60\u8FD9\u6761\u56DE\u590D\u4FDD\u5B58\u5230 ${saveToFile}\u3002`;
|
|
549
|
+
}
|
|
539
550
|
function teeStreamErrorSummary(saveToFile, errMsg) {
|
|
540
551
|
return `[save_last_response failed] streaming was interrupted: ${errMsg}. ${saveToFile} (partial) was deleted. Retry \u2014 and consider producing a more compact output (split very large reports across multiple save_last_response calls if the previous attempt timed out).`;
|
|
541
552
|
}
|
|
@@ -1046,7 +1057,10 @@ export {
|
|
|
1046
1057
|
stripToolCallReminder,
|
|
1047
1058
|
TEE_FINAL_USER_NUDGE,
|
|
1048
1059
|
CONTENT_ONLY_STREAM_REMINDER,
|
|
1060
|
+
isCleanDocumentBody,
|
|
1061
|
+
freshPriorContent,
|
|
1049
1062
|
evaluateTeeContent,
|
|
1063
|
+
buildDeferredSaveInstruction,
|
|
1050
1064
|
teeStreamErrorSummary,
|
|
1051
1065
|
ThinkTagFilter,
|
|
1052
1066
|
repairToolCallArguments,
|
|
@@ -6,15 +6,15 @@ import {
|
|
|
6
6
|
} from "./chunk-HLWUDRBO.js";
|
|
7
7
|
import {
|
|
8
8
|
ProviderRegistry
|
|
9
|
-
} from "./chunk-
|
|
10
|
-
import "./chunk-
|
|
9
|
+
} from "./chunk-VWZMVWA4.js";
|
|
10
|
+
import "./chunk-YZH2QQXJ.js";
|
|
11
11
|
import {
|
|
12
12
|
ConfigManager
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-KRP2XBJ3.js";
|
|
14
14
|
import "./chunk-TZQHYZKT.js";
|
|
15
15
|
import {
|
|
16
16
|
VERSION
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-6RWXUT74.js";
|
|
18
18
|
|
|
19
19
|
// src/cli/ci.ts
|
|
20
20
|
import { execFileSync, execSync } from "child_process";
|
|
@@ -2,26 +2,26 @@
|
|
|
2
2
|
import {
|
|
3
3
|
getConfigDirUsage,
|
|
4
4
|
listRecentCrashes
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-4ZRGTTO4.js";
|
|
6
6
|
import {
|
|
7
7
|
ProviderRegistry
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-VWZMVWA4.js";
|
|
9
9
|
import {
|
|
10
10
|
getStatsSnapshot,
|
|
11
11
|
getTopFailingTools,
|
|
12
12
|
getTopUsedTools,
|
|
13
13
|
resetStats
|
|
14
|
-
} from "./chunk-
|
|
15
|
-
import "./chunk-
|
|
14
|
+
} from "./chunk-KT6PA3NH.js";
|
|
15
|
+
import "./chunk-YZH2QQXJ.js";
|
|
16
16
|
import {
|
|
17
17
|
ConfigManager
|
|
18
|
-
} from "./chunk-
|
|
18
|
+
} from "./chunk-KRP2XBJ3.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-
|
|
24
|
+
} from "./chunk-6RWXUT74.js";
|
|
25
25
|
import "./chunk-IW3Q7AE5.js";
|
|
26
26
|
|
|
27
27
|
// src/diagnostics/doctor-cli.ts
|
package/dist/electron-server.js
CHANGED
|
@@ -36,7 +36,7 @@ import {
|
|
|
36
36
|
VERSION,
|
|
37
37
|
buildUserIdentityPrompt,
|
|
38
38
|
runTestsTool
|
|
39
|
-
} from "./chunk-
|
|
39
|
+
} from "./chunk-7YZXAPHE.js";
|
|
40
40
|
import {
|
|
41
41
|
hasSemanticIndex,
|
|
42
42
|
semanticSearch
|
|
@@ -1974,6 +1974,11 @@ function isCleanDocumentBody(content) {
|
|
|
1974
1974
|
function teeFileStats(content) {
|
|
1975
1975
|
return { lines: content.split("\n").length, bytes: Buffer.byteLength(content, "utf-8") };
|
|
1976
1976
|
}
|
|
1977
|
+
function freshPriorContent(current, baselineAtTurnStart) {
|
|
1978
|
+
if (!current) return void 0;
|
|
1979
|
+
if (current === baselineAtTurnStart) return void 0;
|
|
1980
|
+
return current;
|
|
1981
|
+
}
|
|
1977
1982
|
function evaluateTeeContent(rawContent, saveToFile, priorContent) {
|
|
1978
1983
|
const fallback = (matched) => {
|
|
1979
1984
|
if (priorContent && priorContent !== rawContent && isCleanDocumentBody(priorContent)) {
|
|
@@ -2027,6 +2032,12 @@ This fresh stream has NO tools \u2014 output is captured verbatim. STOP emitting
|
|
|
2027
2032
|
summary: `File saved: ${saveToFile} (${lines} lines, ${bytes} bytes)`
|
|
2028
2033
|
};
|
|
2029
2034
|
}
|
|
2035
|
+
function buildDeferredSaveInstruction(saveToFile) {
|
|
2036
|
+
return `[save_last_response \u65E0\u6CD5\u81EA\u52A8\u751F\u6210\u6587\u6863]
|
|
2037
|
+
content-only \u6D41\u4EA7\u51FA\u7684\u662F\u5DE5\u5177\u8C03\u7528\u6807\u8BB0 / \u5185\u5FC3\u72EC\u767D\u800C\u975E\u6587\u6863\u6B63\u6587\uFF0C${saveToFile} \u672A\u4FDD\u5B58\u3002
|
|
2038
|
+
|
|
2039
|
+
\u4E0D\u8981\u518D\u8C03\u7528 save_last_response\u3002\u8BF7\u76F4\u63A5\u7528**\u666E\u901A\u6587\u672C\u56DE\u590D**\u628A\u5B8C\u6574\u6587\u6863\u5199\u51FA\u6765\uFF1A\u7EAF markdown\uFF0C\u7B2C\u4E00\u4E2A\u5B57\u7B26\u5C31\u662F\u9876\u7EA7\u6807\u9898\uFF08\u5982 "# \u5BA1\u8BA1\u62A5\u544A"\uFF09\uFF0C\u4E0D\u8981\u4EFB\u4F55\u5DE5\u5177\u8C03\u7528\u3001\u4E0D\u8981\u524D\u8A00\u94FA\u57AB\u3002\u7CFB\u7EDF\u4F1A\u81EA\u52A8\u628A\u4F60\u8FD9\u6761\u56DE\u590D\u4FDD\u5B58\u5230 ${saveToFile}\u3002`;
|
|
2040
|
+
}
|
|
2030
2041
|
function teeStreamErrorSummary(saveToFile, errMsg) {
|
|
2031
2042
|
return `[save_last_response failed] streaming was interrupted: ${errMsg}. ${saveToFile} (partial) was deleted. Retry \u2014 and consider producing a more compact output (split very large reports across multiple save_last_response calls if the previous attempt timed out).`;
|
|
2032
2043
|
}
|
|
@@ -12760,6 +12771,8 @@ ${mcpBudgetNote}` : "");
|
|
|
12760
12771
|
const supportsStreamingTools = typeof provider.chatWithToolsStream === "function";
|
|
12761
12772
|
const ac = new AbortController();
|
|
12762
12773
|
this.abortController = ac;
|
|
12774
|
+
let pendingTeeSave = null;
|
|
12775
|
+
const lastAssistantAtTurnStart = lastAssistantText(apiMessages);
|
|
12763
12776
|
try {
|
|
12764
12777
|
const loopResult = await runAgentLoop({
|
|
12765
12778
|
maxToolRounds,
|
|
@@ -12903,6 +12916,18 @@ Try: /compact to reduce context, /clear to reset, or switch to a larger-context
|
|
|
12903
12916
|
},
|
|
12904
12917
|
onFinalContent: (content, { reasoningContent }) => {
|
|
12905
12918
|
this.send({ type: "response_done", content, usage });
|
|
12919
|
+
if (pendingTeeSave && isCleanDocumentBody(content)) {
|
|
12920
|
+
try {
|
|
12921
|
+
mkdirSync10(dirname5(pendingTeeSave), { recursive: true });
|
|
12922
|
+
writeFileSync7(pendingTeeSave, content, "utf-8");
|
|
12923
|
+
undoStack.push(pendingTeeSave, `save_last_response (deferred): ${pendingTeeSave}`);
|
|
12924
|
+
const lines = content.split("\n").length;
|
|
12925
|
+
this.send({ type: "info", message: `\u2705 Saved (from reply): ${pendingTeeSave} (${lines} lines, ${content.length} chars)` });
|
|
12926
|
+
} catch (saveErr) {
|
|
12927
|
+
this.send({ type: "info", message: `\u2717 Could not save to ${pendingTeeSave}: ${saveErr.message ?? saveErr}` });
|
|
12928
|
+
}
|
|
12929
|
+
pendingTeeSave = null;
|
|
12930
|
+
}
|
|
12906
12931
|
session.addMessage({
|
|
12907
12932
|
role: "assistant",
|
|
12908
12933
|
content,
|
|
@@ -12960,6 +12985,16 @@ ${summaryContent}`,
|
|
|
12960
12985
|
// 与 REPL 不同:Web 端 tee 成功后继续 agentic 循环(返回 'continue'),
|
|
12961
12986
|
// 让模型基于工具结果给出最终文本。
|
|
12962
12987
|
runSaveLastResponseTee: async ({ toolCalls, call, saveToFile, extraMessages, reasoningContent }) => {
|
|
12988
|
+
if (pendingTeeSave === saveToFile) {
|
|
12989
|
+
const results = toolCalls.map((tc) => ({
|
|
12990
|
+
callId: tc.id,
|
|
12991
|
+
content: tc.id === call.id ? buildDeferredSaveInstruction(saveToFile) : "[skipped: write the document as plain text, not via tools]",
|
|
12992
|
+
isError: tc.id === call.id
|
|
12993
|
+
}));
|
|
12994
|
+
extraMessages.push(...provider.buildToolResultMessages(toolCalls, results, reasoningContent));
|
|
12995
|
+
return "continue";
|
|
12996
|
+
}
|
|
12997
|
+
const freshPrior = freshPriorContent(lastAssistantText(apiMessages), lastAssistantAtTurnStart);
|
|
12963
12998
|
const teeResult = await this.runSaveLastResponseTee(
|
|
12964
12999
|
provider,
|
|
12965
13000
|
call,
|
|
@@ -12970,8 +13005,10 @@ ${summaryContent}`,
|
|
|
12970
13005
|
systemPromptVolatile,
|
|
12971
13006
|
modelParams,
|
|
12972
13007
|
ac,
|
|
12973
|
-
usage
|
|
13008
|
+
usage,
|
|
13009
|
+
freshPrior
|
|
12974
13010
|
);
|
|
13011
|
+
if (teeResult.deferred) pendingTeeSave = saveToFile;
|
|
12975
13012
|
const teeToolResults = toolCalls.map((tc) => {
|
|
12976
13013
|
if (tc.id === call.id) {
|
|
12977
13014
|
return {
|
|
@@ -13027,7 +13064,8 @@ ${summaryContent}`,
|
|
|
13027
13064
|
* - 同一轮其余 tool_calls 会被标记为 skipped——AI 通常只调一个工具,多并发
|
|
13028
13065
|
* 场景极少。
|
|
13029
13066
|
*/
|
|
13030
|
-
async runSaveLastResponseTee(provider, call, saveToFile, apiMessages, extraMessages, systemPrompt, systemPromptVolatile, modelParams, ac, roundUsage) {
|
|
13067
|
+
async runSaveLastResponseTee(provider, call, saveToFile, apiMessages, extraMessages, systemPrompt, systemPromptVolatile, modelParams, ac, roundUsage, priorContent) {
|
|
13068
|
+
let deferred = false;
|
|
13031
13069
|
this.send({
|
|
13032
13070
|
type: "tool_call_start",
|
|
13033
13071
|
callId: call.id,
|
|
@@ -13076,11 +13114,12 @@ ${summaryContent}`,
|
|
|
13076
13114
|
await new Promise((resolve7, reject) => {
|
|
13077
13115
|
fileStream.end((err) => err ? reject(err) : resolve7());
|
|
13078
13116
|
});
|
|
13079
|
-
const verdict = evaluateTeeContent(fullContent, saveToFile,
|
|
13117
|
+
const verdict = evaluateTeeContent(fullContent, saveToFile, priorContent);
|
|
13080
13118
|
if (verdict.kind === "reject") {
|
|
13081
13119
|
cleanupRejectedTeeFile(saveToFile);
|
|
13082
13120
|
isError = true;
|
|
13083
|
-
|
|
13121
|
+
deferred = true;
|
|
13122
|
+
summary = buildDeferredSaveInstruction(saveToFile);
|
|
13084
13123
|
fullContent = "";
|
|
13085
13124
|
} else {
|
|
13086
13125
|
if (verdict.kind === "salvaged" || verdict.kind === "fallback") {
|
|
@@ -13115,7 +13154,7 @@ ${summaryContent}`,
|
|
|
13115
13154
|
content: summary,
|
|
13116
13155
|
isError
|
|
13117
13156
|
});
|
|
13118
|
-
return { content: fullContent, summary, isError };
|
|
13157
|
+
return { content: fullContent, summary, isError, deferred };
|
|
13119
13158
|
}
|
|
13120
13159
|
/**
|
|
13121
13160
|
* Consume streaming tool call events and forward to client.
|
|
@@ -14149,7 +14188,7 @@ ${undoResults.map((r) => ` \u2022 ${r}`).join("\n")}` });
|
|
|
14149
14188
|
case "test": {
|
|
14150
14189
|
this.send({ type: "info", message: "\u{1F9EA} Running tests..." });
|
|
14151
14190
|
try {
|
|
14152
|
-
const { executeTests } = await import("./run-tests-
|
|
14191
|
+
const { executeTests } = await import("./run-tests-RY4GBMDM.js");
|
|
14153
14192
|
const argStr = args.join(" ").trim();
|
|
14154
14193
|
let testArgs = {};
|
|
14155
14194
|
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-
|
|
157
|
+
const { TaskOrchestrator } = await import("./task-orchestrator-PA5PWQFE.js");
|
|
158
158
|
const orchestrator = new TaskOrchestrator(config, providers, configManager);
|
|
159
159
|
let interrupted = false;
|
|
160
160
|
const onSigint = () => {
|
package/dist/index.js
CHANGED
|
@@ -15,7 +15,7 @@ import {
|
|
|
15
15
|
saveDevState,
|
|
16
16
|
sessionHasMeaningfulContent,
|
|
17
17
|
setupProxy
|
|
18
|
-
} from "./chunk-
|
|
18
|
+
} from "./chunk-XTL6I7J3.js";
|
|
19
19
|
import {
|
|
20
20
|
ToolExecutor,
|
|
21
21
|
ToolRegistry,
|
|
@@ -35,10 +35,10 @@ import {
|
|
|
35
35
|
spawnAgentContext,
|
|
36
36
|
theme,
|
|
37
37
|
undoStack
|
|
38
|
-
} from "./chunk-
|
|
38
|
+
} from "./chunk-A2P7LQEX.js";
|
|
39
39
|
import "./chunk-T2NL5ZIA.js";
|
|
40
40
|
import "./chunk-BXP6YZ2P.js";
|
|
41
|
-
import "./chunk-
|
|
41
|
+
import "./chunk-6WUIOZGL.js";
|
|
42
42
|
import {
|
|
43
43
|
SessionManager,
|
|
44
44
|
getContentText
|
|
@@ -55,34 +55,37 @@ import {
|
|
|
55
55
|
getConfigDirUsage,
|
|
56
56
|
listRecentCrashes,
|
|
57
57
|
writeCrashLog
|
|
58
|
-
} from "./chunk-
|
|
58
|
+
} from "./chunk-4ZRGTTO4.js";
|
|
59
59
|
import {
|
|
60
60
|
ProviderRegistry
|
|
61
|
-
} from "./chunk-
|
|
61
|
+
} from "./chunk-VWZMVWA4.js";
|
|
62
62
|
import {
|
|
63
63
|
getStatsSnapshot,
|
|
64
64
|
getTopFailingTools,
|
|
65
65
|
getTopUsedTools,
|
|
66
66
|
installFlushOnExit
|
|
67
|
-
} from "./chunk-
|
|
67
|
+
} from "./chunk-KT6PA3NH.js";
|
|
68
68
|
import {
|
|
69
69
|
CONTENT_ONLY_STREAM_REMINDER,
|
|
70
70
|
TEE_FINAL_USER_NUDGE,
|
|
71
71
|
TOOL_CALL_REMINDER,
|
|
72
72
|
ThinkTagFilter,
|
|
73
73
|
accumulateUsage,
|
|
74
|
+
buildDeferredSaveInstruction,
|
|
74
75
|
buildRoundBudgetHint,
|
|
75
76
|
buildWriteRoundReminder,
|
|
76
77
|
consumeToolCallStream,
|
|
77
78
|
evaluateTeeContent,
|
|
78
79
|
extractWrittenFilePaths,
|
|
80
|
+
freshPriorContent,
|
|
81
|
+
isCleanDocumentBody,
|
|
79
82
|
runAgentLoop,
|
|
80
83
|
stripToolCallReminder,
|
|
81
84
|
teeStreamErrorSummary
|
|
82
|
-
} from "./chunk-
|
|
85
|
+
} from "./chunk-YZH2QQXJ.js";
|
|
83
86
|
import {
|
|
84
87
|
ConfigManager
|
|
85
|
-
} from "./chunk-
|
|
88
|
+
} from "./chunk-KRP2XBJ3.js";
|
|
86
89
|
import {
|
|
87
90
|
AuthError,
|
|
88
91
|
ProviderError,
|
|
@@ -109,7 +112,7 @@ import {
|
|
|
109
112
|
SKILLS_DIR_NAME,
|
|
110
113
|
VERSION,
|
|
111
114
|
buildUserIdentityPrompt
|
|
112
|
-
} from "./chunk-
|
|
115
|
+
} from "./chunk-6RWXUT74.js";
|
|
113
116
|
import {
|
|
114
117
|
formatGitContextForPrompt,
|
|
115
118
|
getGitContext,
|
|
@@ -138,7 +141,7 @@ import { program } from "commander";
|
|
|
138
141
|
|
|
139
142
|
// src/repl/repl.ts
|
|
140
143
|
import * as readline from "readline";
|
|
141
|
-
import { existsSync as existsSync4, readFileSync as readFileSync3, readdirSync as readdirSync3, statSync as statSync3, writeFileSync as writeFileSync2 } from "fs";
|
|
144
|
+
import { existsSync as existsSync4, readFileSync as readFileSync3, readdirSync as readdirSync3, statSync as statSync3, writeFileSync as writeFileSync2, mkdirSync as mkdirSync4 } from "fs";
|
|
142
145
|
import { join as join4, resolve as resolve2, extname as extname2, dirname as dirname3, basename as basename2 } from "path";
|
|
143
146
|
import chalk4 from "chalk";
|
|
144
147
|
|
|
@@ -1824,7 +1827,7 @@ No tools match "${filter}".
|
|
|
1824
1827
|
const { join: join5 } = await import("path");
|
|
1825
1828
|
const { existsSync: existsSync5 } = await import("fs");
|
|
1826
1829
|
const { getGitRoot: getGitRoot2 } = await import("./git-context-EXOEHQSF.js");
|
|
1827
|
-
const { MCP_PROJECT_CONFIG_NAME: MCP_PROJECT_CONFIG_NAME2 } = await import("./constants-
|
|
1830
|
+
const { MCP_PROJECT_CONFIG_NAME: MCP_PROJECT_CONFIG_NAME2 } = await import("./constants-5LJTWBPU.js");
|
|
1828
1831
|
const { approveProject, hashMcpFile } = await import("./project-trust-NKYHL3VZ.js");
|
|
1829
1832
|
const cwd = process.cwd();
|
|
1830
1833
|
const projectRoot = getGitRoot2(cwd) ?? cwd;
|
|
@@ -2885,7 +2888,7 @@ ${hint}` : "")
|
|
|
2885
2888
|
usage: "/test [command|filter]",
|
|
2886
2889
|
async execute(args, ctx) {
|
|
2887
2890
|
try {
|
|
2888
|
-
const { executeTests } = await import("./run-tests-
|
|
2891
|
+
const { executeTests } = await import("./run-tests-2H2G7VPL.js");
|
|
2889
2892
|
const argStr = args.join(" ").trim();
|
|
2890
2893
|
let testArgs = {};
|
|
2891
2894
|
if (argStr) {
|
|
@@ -6395,6 +6398,8 @@ ${mcpBudgetNote}` : "");
|
|
|
6395
6398
|
const supportsStreamingTools = useStreaming && typeof provider.chatWithToolsStream === "function";
|
|
6396
6399
|
let lastToolCallSignature = "";
|
|
6397
6400
|
let repeatedToolCallCount = 0;
|
|
6401
|
+
let pendingTeeSave = null;
|
|
6402
|
+
const lastResponseAtTurnStart = lastResponseStore.content;
|
|
6398
6403
|
this.setupInterjectionListener();
|
|
6399
6404
|
try {
|
|
6400
6405
|
const loopResult = await runAgentLoop({
|
|
@@ -6633,6 +6638,28 @@ ${decision.displayMessage}
|
|
|
6633
6638
|
process.stdout.write("\n\n");
|
|
6634
6639
|
}
|
|
6635
6640
|
lastResponseStore.content = content;
|
|
6641
|
+
if (pendingTeeSave && isCleanDocumentBody(content)) {
|
|
6642
|
+
try {
|
|
6643
|
+
mkdirSync4(dirname3(pendingTeeSave), { recursive: true });
|
|
6644
|
+
writeFileSync2(pendingTeeSave, content, "utf-8");
|
|
6645
|
+
undoStack.push(pendingTeeSave, `save_last_response (deferred): ${pendingTeeSave}`);
|
|
6646
|
+
const lines = content.split("\n").length;
|
|
6647
|
+
process.stdout.write(theme.success(
|
|
6648
|
+
`
|
|
6649
|
+
\u2705 Saved (from your reply): ${pendingTeeSave} (${lines} lines, ${content.length} chars)
|
|
6650
|
+
|
|
6651
|
+
`
|
|
6652
|
+
));
|
|
6653
|
+
} catch (saveErr) {
|
|
6654
|
+
process.stdout.write(theme.error(
|
|
6655
|
+
`
|
|
6656
|
+
\u2717 Could not save to ${pendingTeeSave}: ${saveErr.message ?? saveErr}
|
|
6657
|
+
|
|
6658
|
+
`
|
|
6659
|
+
));
|
|
6660
|
+
}
|
|
6661
|
+
pendingTeeSave = null;
|
|
6662
|
+
}
|
|
6636
6663
|
session.addMessage({
|
|
6637
6664
|
role: "assistant",
|
|
6638
6665
|
content,
|
|
@@ -6782,6 +6809,15 @@ Tip: You can continue the conversation by asking the AI to proceed.`
|
|
|
6782
6809
|
// 'continue' 让模型重试
|
|
6783
6810
|
runSaveLastResponseTee: async ({ toolCalls, saveToFile, extraMessages, reasoningContent }) => {
|
|
6784
6811
|
spinner.stop();
|
|
6812
|
+
if (pendingTeeSave === saveToFile) {
|
|
6813
|
+
const results = toolCalls.map((tc) => ({
|
|
6814
|
+
callId: tc.id,
|
|
6815
|
+
content: tc.name === "save_last_response" ? buildDeferredSaveInstruction(saveToFile) : `[skipped: write the document as plain text, not via tools]`,
|
|
6816
|
+
isError: tc.name === "save_last_response"
|
|
6817
|
+
}));
|
|
6818
|
+
extraMessages.push(...provider.buildToolResultMessages(toolCalls, results, reasoningContent));
|
|
6819
|
+
return "continue";
|
|
6820
|
+
}
|
|
6785
6821
|
const teeAc = this.setupStreamInterrupt();
|
|
6786
6822
|
try {
|
|
6787
6823
|
const teeSystemPrompt = stripToolCallReminder(systemPrompt ?? "") + CONTENT_ONLY_STREAM_REMINDER;
|
|
@@ -6832,20 +6868,25 @@ Tip: You can continue the conversation by asking the AI to proceed.`
|
|
|
6832
6868
|
return "continue";
|
|
6833
6869
|
}
|
|
6834
6870
|
if (genUsage) accumulateUsage(usage, genUsage);
|
|
6835
|
-
const verdict = evaluateTeeContent(
|
|
6871
|
+
const verdict = evaluateTeeContent(
|
|
6872
|
+
genContent,
|
|
6873
|
+
saveToFile,
|
|
6874
|
+
freshPriorContent(lastResponseStore.content, lastResponseAtTurnStart)
|
|
6875
|
+
);
|
|
6836
6876
|
if (verdict.kind === "reject") {
|
|
6837
6877
|
cleanupRejectedTeeFile(saveToFile);
|
|
6838
6878
|
const label = verdict.reason === "meta-narration" ? "meta-narration / leaked reasoning, not document body" : "pseudo-tool-call markup with no usable document body";
|
|
6839
|
-
|
|
6879
|
+
pendingTeeSave = saveToFile;
|
|
6880
|
+
process.stdout.write(theme.warning(
|
|
6840
6881
|
`
|
|
6841
|
-
\
|
|
6842
|
-
${saveToFile} was deleted
|
|
6882
|
+
\u26A0 Rejected save: response was ${label} (matched: ${verdict.matched})
|
|
6883
|
+
${saveToFile} was deleted. Asking the model to write the document as plain text instead (will auto-save).
|
|
6843
6884
|
|
|
6844
6885
|
`
|
|
6845
6886
|
));
|
|
6846
6887
|
const errorResults = toolCalls.map((tc) => ({
|
|
6847
6888
|
callId: tc.id,
|
|
6848
|
-
content: tc.name === "save_last_response" ?
|
|
6889
|
+
content: tc.name === "save_last_response" ? buildDeferredSaveInstruction(saveToFile) : `[skipped: save_last_response was rejected and other parallel calls are abandoned]`,
|
|
6849
6890
|
isError: tc.name === "save_last_response"
|
|
6850
6891
|
}));
|
|
6851
6892
|
extraMessages.push(...provider.buildToolResultMessages(toolCalls, errorResults, reasoningContent));
|
|
@@ -7209,7 +7250,7 @@ program.command("web").description("Start Web UI server with browser-based chat
|
|
|
7209
7250
|
console.error("Error: Invalid port number. Must be between 1 and 65535.");
|
|
7210
7251
|
process.exit(1);
|
|
7211
7252
|
}
|
|
7212
|
-
const { startWebServer } = await import("./server-
|
|
7253
|
+
const { startWebServer } = await import("./server-VJYNMQOR.js");
|
|
7213
7254
|
await startWebServer({ port, host: options.host });
|
|
7214
7255
|
});
|
|
7215
7256
|
program.command("user [action] [username]").description("Manage Web UI users (list | create <name> | delete <name> | reset-password <name> | logout-all <name> | migrate <name>)").action(async (action, username) => {
|
|
@@ -7376,16 +7417,16 @@ program.command("sessions").description("List recent conversation sessions").opt
|
|
|
7376
7417
|
console.log(footer + "\n");
|
|
7377
7418
|
});
|
|
7378
7419
|
program.command("usage").description("Show token + cost usage grouped by provider/model (cross-session)").option("--days <n>", "Only the last N days (inclusive of today)").option("--month <ym>", "Only a specific month, format YYYY-MM (e.g. 2026-06)").option("--json", "Output as JSON (for scripting)").action(async (options) => {
|
|
7379
|
-
const { runUsageCli } = await import("./usage-
|
|
7420
|
+
const { runUsageCli } = await import("./usage-CF37QUOV.js");
|
|
7380
7421
|
await runUsageCli(options);
|
|
7381
7422
|
});
|
|
7382
7423
|
program.command("doctor").description("Health check: API keys, config, MCP, recent crashes, tool usage, disk usage").option("--json", "Output as JSON (for scripting)").option("--reset-stats", "Reset accumulated tool usage statistics").action(async (options) => {
|
|
7383
|
-
const { runDoctorCli } = await import("./doctor-cli-
|
|
7424
|
+
const { runDoctorCli } = await import("./doctor-cli-2JM5LE3J.js");
|
|
7384
7425
|
await runDoctorCli({ json: !!options.json, resetStats: !!options.resetStats });
|
|
7385
7426
|
});
|
|
7386
7427
|
program.command("batch <action> [arg] [arg2]").description("Anthropic Message Batches: submit | list | status <id> | results <id> [out] | cancel <id>").option("--dry-run", "Parse and validate input without submitting (submit only)").action(async (action, arg, arg2, options) => {
|
|
7387
7428
|
try {
|
|
7388
|
-
const batch = await import("./batch-
|
|
7429
|
+
const batch = await import("./batch-46RLXVR7.js");
|
|
7389
7430
|
switch (action) {
|
|
7390
7431
|
case "submit":
|
|
7391
7432
|
if (!arg) {
|
|
@@ -7428,7 +7469,7 @@ program.command("batch <action> [arg] [arg2]").description("Anthropic Message Ba
|
|
|
7428
7469
|
}
|
|
7429
7470
|
});
|
|
7430
7471
|
program.command("mcp-serve").description("Start an MCP server over STDIO, exposing aicli's built-in tools to Claude Desktop / Cursor / other MCP clients").option("--allow-destructive", "Allow bash / run_interactive / task_create (always destructive in MCP mode)").option("--allow-outside-cwd", "Allow tool path arguments to escape the sandbox root \u2014 disabled by default").option("--tools <list>", "Comma-separated whitelist of tools to expose (default: all eligible tools)").option("--cwd <path>", "Working directory AND sandbox root (default: current directory)").action(async (options) => {
|
|
7431
|
-
const { startMcpServer } = await import("./server-
|
|
7472
|
+
const { startMcpServer } = await import("./server-6ZDQTDLT.js");
|
|
7432
7473
|
await startMcpServer({
|
|
7433
7474
|
allowDestructive: !!options.allowDestructive,
|
|
7434
7475
|
allowOutsideCwd: !!options.allowOutsideCwd,
|
|
@@ -7437,7 +7478,7 @@ program.command("mcp-serve").description("Start an MCP server over STDIO, exposi
|
|
|
7437
7478
|
});
|
|
7438
7479
|
});
|
|
7439
7480
|
program.command("ci").description("Headless PR review (code + security) \u2014 reads git/gh diff, optionally posts to PR. Designed for GitHub Actions.").option("--pr <num>", "PR number; diff fetched via `gh pr diff <num>`", (v) => parseInt(v, 10)).option("--base <ref>", "Base ref for `git diff <ref>...HEAD` (ignored when --pr set)").option("--post", "Post review as a PR comment (requires gh CLI + GH_TOKEN, needs --pr)").option("--no-update", "Always create a new comment instead of updating the previous aicli review").option("--skip-code", "Skip the code review section").option("--skip-security", "Skip the security review section").option("--detailed", "Use the detailed code-review prompt").option("--max-diff <n>", "Max diff chars sent to the model (default 30000)", (v) => parseInt(v, 10)).option("--provider <id>", "Override provider (default: config.defaultProvider)").option("--model <id>", "Override model").option("--dry-run", "Print result to stdout instead of posting (overrides --post)").action(async (options) => {
|
|
7440
|
-
const { runCi } = await import("./ci-
|
|
7481
|
+
const { runCi } = await import("./ci-FBTIW7YY.js");
|
|
7441
7482
|
const result = await runCi({
|
|
7442
7483
|
pr: options.pr,
|
|
7443
7484
|
base: options.base,
|
|
@@ -7583,7 +7624,7 @@ program.command("hub [topic]").description("Start multi-agent hub (discuss / bra
|
|
|
7583
7624
|
}),
|
|
7584
7625
|
config.get("customProviders")
|
|
7585
7626
|
);
|
|
7586
|
-
const { startHub } = await import("./hub-
|
|
7627
|
+
const { startHub } = await import("./hub-ZIYP65L7.js");
|
|
7587
7628
|
await startHub(
|
|
7588
7629
|
{
|
|
7589
7630
|
topic: topic ?? "",
|
|
@@ -1,21 +1,21 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
3
|
ToolRegistry
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-A2P7LQEX.js";
|
|
5
5
|
import "./chunk-T2NL5ZIA.js";
|
|
6
6
|
import "./chunk-BXP6YZ2P.js";
|
|
7
|
-
import "./chunk-
|
|
7
|
+
import "./chunk-6WUIOZGL.js";
|
|
8
8
|
import {
|
|
9
9
|
runTool
|
|
10
|
-
} from "./chunk-
|
|
10
|
+
} from "./chunk-KT6PA3NH.js";
|
|
11
11
|
import {
|
|
12
12
|
getDangerLevel,
|
|
13
13
|
schemaToJsonSchema
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-YZH2QQXJ.js";
|
|
15
15
|
import "./chunk-TZQHYZKT.js";
|
|
16
16
|
import {
|
|
17
17
|
VERSION
|
|
18
|
-
} from "./chunk-
|
|
18
|
+
} from "./chunk-6RWXUT74.js";
|
|
19
19
|
import "./chunk-4BKXL7SM.js";
|
|
20
20
|
import "./chunk-TB4W4Y4T.js";
|
|
21
21
|
import "./chunk-KHYD3WXE.js";
|
|
@@ -19,7 +19,7 @@ import {
|
|
|
19
19
|
loadDevState,
|
|
20
20
|
persistToolRound,
|
|
21
21
|
setupProxy
|
|
22
|
-
} from "./chunk-
|
|
22
|
+
} from "./chunk-XTL6I7J3.js";
|
|
23
23
|
import {
|
|
24
24
|
ToolExecutor,
|
|
25
25
|
ToolRegistry,
|
|
@@ -38,10 +38,10 @@ import {
|
|
|
38
38
|
spawnAgentContext,
|
|
39
39
|
truncateOutput,
|
|
40
40
|
undoStack
|
|
41
|
-
} from "./chunk-
|
|
41
|
+
} from "./chunk-A2P7LQEX.js";
|
|
42
42
|
import "./chunk-T2NL5ZIA.js";
|
|
43
43
|
import "./chunk-BXP6YZ2P.js";
|
|
44
|
-
import "./chunk-
|
|
44
|
+
import "./chunk-6WUIOZGL.js";
|
|
45
45
|
import {
|
|
46
46
|
SessionManager,
|
|
47
47
|
getContentText
|
|
@@ -52,25 +52,28 @@ import {
|
|
|
52
52
|
} from "./chunk-V37XOYOE.js";
|
|
53
53
|
import {
|
|
54
54
|
ProviderRegistry
|
|
55
|
-
} from "./chunk-
|
|
55
|
+
} from "./chunk-VWZMVWA4.js";
|
|
56
56
|
import {
|
|
57
57
|
runTool
|
|
58
|
-
} from "./chunk-
|
|
58
|
+
} from "./chunk-KT6PA3NH.js";
|
|
59
59
|
import {
|
|
60
60
|
CONTENT_ONLY_STREAM_REMINDER,
|
|
61
61
|
TEE_FINAL_USER_NUDGE,
|
|
62
62
|
TOOL_CALL_REMINDER,
|
|
63
|
+
buildDeferredSaveInstruction,
|
|
63
64
|
buildRoundBudgetHint,
|
|
64
65
|
consumeToolCallStream,
|
|
65
66
|
evaluateTeeContent,
|
|
67
|
+
freshPriorContent,
|
|
66
68
|
getDangerLevel,
|
|
69
|
+
isCleanDocumentBody,
|
|
67
70
|
runAgentLoop,
|
|
68
71
|
stripToolCallReminder,
|
|
69
72
|
teeStreamErrorSummary
|
|
70
|
-
} from "./chunk-
|
|
73
|
+
} from "./chunk-YZH2QQXJ.js";
|
|
71
74
|
import {
|
|
72
75
|
ConfigManager
|
|
73
|
-
} from "./chunk-
|
|
76
|
+
} from "./chunk-KRP2XBJ3.js";
|
|
74
77
|
import "./chunk-TZQHYZKT.js";
|
|
75
78
|
import {
|
|
76
79
|
AGENTIC_BEHAVIOR_GUIDELINE,
|
|
@@ -90,7 +93,7 @@ import {
|
|
|
90
93
|
SKILLS_DIR_NAME,
|
|
91
94
|
VERSION,
|
|
92
95
|
buildUserIdentityPrompt
|
|
93
|
-
} from "./chunk-
|
|
96
|
+
} from "./chunk-6RWXUT74.js";
|
|
94
97
|
import {
|
|
95
98
|
formatGitContextForPrompt,
|
|
96
99
|
getGitContext,
|
|
@@ -1023,6 +1026,8 @@ ${mcpBudgetNote}` : "");
|
|
|
1023
1026
|
const supportsStreamingTools = typeof provider.chatWithToolsStream === "function";
|
|
1024
1027
|
const ac = new AbortController();
|
|
1025
1028
|
this.abortController = ac;
|
|
1029
|
+
let pendingTeeSave = null;
|
|
1030
|
+
const lastAssistantAtTurnStart = lastAssistantText(apiMessages);
|
|
1026
1031
|
try {
|
|
1027
1032
|
const loopResult = await runAgentLoop({
|
|
1028
1033
|
maxToolRounds,
|
|
@@ -1166,6 +1171,18 @@ Try: /compact to reduce context, /clear to reset, or switch to a larger-context
|
|
|
1166
1171
|
},
|
|
1167
1172
|
onFinalContent: (content, { reasoningContent }) => {
|
|
1168
1173
|
this.send({ type: "response_done", content, usage });
|
|
1174
|
+
if (pendingTeeSave && isCleanDocumentBody(content)) {
|
|
1175
|
+
try {
|
|
1176
|
+
mkdirSync(dirname(pendingTeeSave), { recursive: true });
|
|
1177
|
+
writeFileSync(pendingTeeSave, content, "utf-8");
|
|
1178
|
+
undoStack.push(pendingTeeSave, `save_last_response (deferred): ${pendingTeeSave}`);
|
|
1179
|
+
const lines = content.split("\n").length;
|
|
1180
|
+
this.send({ type: "info", message: `\u2705 Saved (from reply): ${pendingTeeSave} (${lines} lines, ${content.length} chars)` });
|
|
1181
|
+
} catch (saveErr) {
|
|
1182
|
+
this.send({ type: "info", message: `\u2717 Could not save to ${pendingTeeSave}: ${saveErr.message ?? saveErr}` });
|
|
1183
|
+
}
|
|
1184
|
+
pendingTeeSave = null;
|
|
1185
|
+
}
|
|
1169
1186
|
session.addMessage({
|
|
1170
1187
|
role: "assistant",
|
|
1171
1188
|
content,
|
|
@@ -1223,6 +1240,16 @@ ${summaryContent}`,
|
|
|
1223
1240
|
// 与 REPL 不同:Web 端 tee 成功后继续 agentic 循环(返回 'continue'),
|
|
1224
1241
|
// 让模型基于工具结果给出最终文本。
|
|
1225
1242
|
runSaveLastResponseTee: async ({ toolCalls, call, saveToFile, extraMessages, reasoningContent }) => {
|
|
1243
|
+
if (pendingTeeSave === saveToFile) {
|
|
1244
|
+
const results = toolCalls.map((tc) => ({
|
|
1245
|
+
callId: tc.id,
|
|
1246
|
+
content: tc.id === call.id ? buildDeferredSaveInstruction(saveToFile) : "[skipped: write the document as plain text, not via tools]",
|
|
1247
|
+
isError: tc.id === call.id
|
|
1248
|
+
}));
|
|
1249
|
+
extraMessages.push(...provider.buildToolResultMessages(toolCalls, results, reasoningContent));
|
|
1250
|
+
return "continue";
|
|
1251
|
+
}
|
|
1252
|
+
const freshPrior = freshPriorContent(lastAssistantText(apiMessages), lastAssistantAtTurnStart);
|
|
1226
1253
|
const teeResult = await this.runSaveLastResponseTee(
|
|
1227
1254
|
provider,
|
|
1228
1255
|
call,
|
|
@@ -1233,8 +1260,10 @@ ${summaryContent}`,
|
|
|
1233
1260
|
systemPromptVolatile,
|
|
1234
1261
|
modelParams,
|
|
1235
1262
|
ac,
|
|
1236
|
-
usage
|
|
1263
|
+
usage,
|
|
1264
|
+
freshPrior
|
|
1237
1265
|
);
|
|
1266
|
+
if (teeResult.deferred) pendingTeeSave = saveToFile;
|
|
1238
1267
|
const teeToolResults = toolCalls.map((tc) => {
|
|
1239
1268
|
if (tc.id === call.id) {
|
|
1240
1269
|
return {
|
|
@@ -1290,7 +1319,8 @@ ${summaryContent}`,
|
|
|
1290
1319
|
* - 同一轮其余 tool_calls 会被标记为 skipped——AI 通常只调一个工具,多并发
|
|
1291
1320
|
* 场景极少。
|
|
1292
1321
|
*/
|
|
1293
|
-
async runSaveLastResponseTee(provider, call, saveToFile, apiMessages, extraMessages, systemPrompt, systemPromptVolatile, modelParams, ac, roundUsage) {
|
|
1322
|
+
async runSaveLastResponseTee(provider, call, saveToFile, apiMessages, extraMessages, systemPrompt, systemPromptVolatile, modelParams, ac, roundUsage, priorContent) {
|
|
1323
|
+
let deferred = false;
|
|
1294
1324
|
this.send({
|
|
1295
1325
|
type: "tool_call_start",
|
|
1296
1326
|
callId: call.id,
|
|
@@ -1339,11 +1369,12 @@ ${summaryContent}`,
|
|
|
1339
1369
|
await new Promise((resolve3, reject) => {
|
|
1340
1370
|
fileStream.end((err) => err ? reject(err) : resolve3());
|
|
1341
1371
|
});
|
|
1342
|
-
const verdict = evaluateTeeContent(fullContent, saveToFile,
|
|
1372
|
+
const verdict = evaluateTeeContent(fullContent, saveToFile, priorContent);
|
|
1343
1373
|
if (verdict.kind === "reject") {
|
|
1344
1374
|
cleanupRejectedTeeFile(saveToFile);
|
|
1345
1375
|
isError = true;
|
|
1346
|
-
|
|
1376
|
+
deferred = true;
|
|
1377
|
+
summary = buildDeferredSaveInstruction(saveToFile);
|
|
1347
1378
|
fullContent = "";
|
|
1348
1379
|
} else {
|
|
1349
1380
|
if (verdict.kind === "salvaged" || verdict.kind === "fallback") {
|
|
@@ -1378,7 +1409,7 @@ ${summaryContent}`,
|
|
|
1378
1409
|
content: summary,
|
|
1379
1410
|
isError
|
|
1380
1411
|
});
|
|
1381
|
-
return { content: fullContent, summary, isError };
|
|
1412
|
+
return { content: fullContent, summary, isError, deferred };
|
|
1382
1413
|
}
|
|
1383
1414
|
/**
|
|
1384
1415
|
* Consume streaming tool call events and forward to client.
|
|
@@ -2412,7 +2443,7 @@ ${undoResults.map((r) => ` \u2022 ${r}`).join("\n")}` });
|
|
|
2412
2443
|
case "test": {
|
|
2413
2444
|
this.send({ type: "info", message: "\u{1F9EA} Running tests..." });
|
|
2414
2445
|
try {
|
|
2415
|
-
const { executeTests } = await import("./run-tests-
|
|
2446
|
+
const { executeTests } = await import("./run-tests-2H2G7VPL.js");
|
|
2416
2447
|
const argStr = args.join(" ").trim();
|
|
2417
2448
|
let testArgs = {};
|
|
2418
2449
|
if (argStr) {
|
|
@@ -3,21 +3,21 @@ import {
|
|
|
3
3
|
ToolRegistry,
|
|
4
4
|
googleSearchContext,
|
|
5
5
|
truncateOutput
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-A2P7LQEX.js";
|
|
7
7
|
import "./chunk-T2NL5ZIA.js";
|
|
8
8
|
import "./chunk-BXP6YZ2P.js";
|
|
9
|
-
import "./chunk-
|
|
9
|
+
import "./chunk-6WUIOZGL.js";
|
|
10
10
|
import {
|
|
11
11
|
runTool
|
|
12
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-KT6PA3NH.js";
|
|
13
13
|
import {
|
|
14
14
|
getDangerLevel,
|
|
15
15
|
runLeanAgentLoop
|
|
16
|
-
} from "./chunk-
|
|
16
|
+
} from "./chunk-YZH2QQXJ.js";
|
|
17
17
|
import "./chunk-TZQHYZKT.js";
|
|
18
18
|
import {
|
|
19
19
|
SUBAGENT_ALLOWED_TOOLS
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-6RWXUT74.js";
|
|
21
21
|
import "./chunk-4BKXL7SM.js";
|
|
22
22
|
import "./chunk-TB4W4Y4T.js";
|
|
23
23
|
import "./chunk-KHYD3WXE.js";
|
|
@@ -8,9 +8,9 @@ import {
|
|
|
8
8
|
} from "./chunk-V37XOYOE.js";
|
|
9
9
|
import {
|
|
10
10
|
ConfigManager
|
|
11
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-KRP2XBJ3.js";
|
|
12
12
|
import "./chunk-TZQHYZKT.js";
|
|
13
|
-
import "./chunk-
|
|
13
|
+
import "./chunk-6RWXUT74.js";
|
|
14
14
|
import "./chunk-IW3Q7AE5.js";
|
|
15
15
|
|
|
16
16
|
// src/cli/usage.ts
|