@cydm/pie 2.7.0 → 2.7.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +17 -1
- package/dist/builtin/extensions/ask-user/index.js +3 -3
- package/dist/builtin/extensions/plan-mode/index.js +3 -3
- package/dist/builtin/extensions/subagent/index.js +15 -5
- package/dist/builtin/extensions/todo/index.js +3 -3
- package/dist/builtin/skills/computer-use-axi/SKILL.md +89 -4
- package/dist/builtin/skills/computer-use-axi/computer-use-axi-broker.js +11004 -0
- package/dist/builtin/skills/computer-use-axi/computer-use-axi-runtime.js +449 -9256
- package/dist/chunks/{chunk-6RBSTII7.js → chunk-65B6P5J5.js} +862 -265
- package/dist/chunks/{chunk-R5I2QLF2.js → chunk-BRFP5WZ6.js} +606 -97
- package/dist/chunks/{chunk-IPNAFMOJ.js → chunk-GECAIKZL.js} +70 -3
- package/dist/chunks/{chunk-TWILEFLD.js → chunk-GZDAIW6F.js} +1 -1
- package/dist/chunks/{src-E7NCXMU5.js → src-PRKTGADX.js} +2 -2
- package/dist/chunks/{test-stream-BWBJTFNI.js → test-stream-BGAEVPRX.js} +1 -1
- package/dist/cli.js +530 -145
- package/models.schema.json +28 -2
- package/package.json +2 -2
package/dist/cli.js
CHANGED
|
@@ -6,6 +6,8 @@ import {
|
|
|
6
6
|
createBashTool,
|
|
7
7
|
createCliHostCapabilities,
|
|
8
8
|
createCliWebResearchHealthStore,
|
|
9
|
+
createTraceTransportSink,
|
|
10
|
+
createTransportDiagnosticsStreamFn,
|
|
9
11
|
formatSize,
|
|
10
12
|
getAgentDir,
|
|
11
13
|
getBuiltinDir,
|
|
@@ -18,9 +20,10 @@ import {
|
|
|
18
20
|
getSessionsDir,
|
|
19
21
|
getSettingsPath,
|
|
20
22
|
getThemesDir,
|
|
23
|
+
logTransportLifecycle,
|
|
21
24
|
migrateConfigFromAgentDir,
|
|
22
25
|
truncateHeadTail
|
|
23
|
-
} from "./chunks/chunk-
|
|
26
|
+
} from "./chunks/chunk-GECAIKZL.js";
|
|
24
27
|
import {
|
|
25
28
|
resolveCliProjectRoot
|
|
26
29
|
} from "./chunks/chunk-WLFOBECN.js";
|
|
@@ -29,6 +32,7 @@ import {
|
|
|
29
32
|
AgentSessionController,
|
|
30
33
|
AttentionCoordinator,
|
|
31
34
|
BUILTIN_TOOL_CAPABILITY_METADATA,
|
|
35
|
+
DEFAULT_COMPACTION_CONFIG,
|
|
32
36
|
ExtensionResourceScope,
|
|
33
37
|
FileSessionStore,
|
|
34
38
|
SessionTraceSnapshotWriter,
|
|
@@ -72,6 +76,7 @@ import {
|
|
|
72
76
|
maybeAdvanceTodoExecutionState,
|
|
73
77
|
modalityForReadFileUnderstandingKind,
|
|
74
78
|
pauseExecutionState,
|
|
79
|
+
prepareSessionCompaction,
|
|
75
80
|
registerInteractionHandler,
|
|
76
81
|
requestInteraction,
|
|
77
82
|
resolveExtensionIdentity,
|
|
@@ -79,9 +84,10 @@ import {
|
|
|
79
84
|
setEnablementInMap,
|
|
80
85
|
setExtensionEnabledInSettings,
|
|
81
86
|
shouldPreserveExecutionStateForUserText,
|
|
82
|
-
supersedeExecutionState
|
|
83
|
-
|
|
84
|
-
|
|
87
|
+
supersedeExecutionState,
|
|
88
|
+
verifyPreparedCompactionCommit
|
|
89
|
+
} from "./chunks/chunk-65B6P5J5.js";
|
|
90
|
+
import "./chunks/chunk-GZDAIW6F.js";
|
|
85
91
|
import {
|
|
86
92
|
Deref,
|
|
87
93
|
EMPTY_ASSISTANT_CONTENT_ERROR,
|
|
@@ -106,7 +112,7 @@ import {
|
|
|
106
112
|
sortToolModelCandidatesByCapability,
|
|
107
113
|
streamSimple,
|
|
108
114
|
type_exports
|
|
109
|
-
} from "./chunks/chunk-
|
|
115
|
+
} from "./chunks/chunk-BRFP5WZ6.js";
|
|
110
116
|
import {
|
|
111
117
|
IsArray,
|
|
112
118
|
IsBigInt,
|
|
@@ -52509,6 +52515,9 @@ function validateCompat(value, label) {
|
|
|
52509
52515
|
"store",
|
|
52510
52516
|
"supportsEncryptedReasoning",
|
|
52511
52517
|
"responsesContinuation",
|
|
52518
|
+
"supportsReasoningSummary",
|
|
52519
|
+
"reasoningSummary",
|
|
52520
|
+
"timeoutReplay",
|
|
52512
52521
|
"supportsStore",
|
|
52513
52522
|
"supportsDeveloperRole",
|
|
52514
52523
|
"supportsReasoningEffort",
|
|
@@ -52525,10 +52534,16 @@ function validateCompat(value, label) {
|
|
|
52525
52534
|
if (value.forcedReasoningEffort !== void 0 && value.forcedReasoningEffort !== "none") {
|
|
52526
52535
|
throw new Error(`${label}.forcedReasoningEffort must be "none"`);
|
|
52527
52536
|
}
|
|
52537
|
+
if (value.reasoningSummary !== void 0 && !["auto", "concise", "detailed", "none"].includes(String(value.reasoningSummary))) {
|
|
52538
|
+
throw new Error(`${label}.reasoningSummary must be auto | concise | detailed | none`);
|
|
52539
|
+
}
|
|
52528
52540
|
for (const field of [
|
|
52529
52541
|
"store",
|
|
52530
52542
|
"supportsEncryptedReasoning",
|
|
52531
52543
|
"responsesContinuation",
|
|
52544
|
+
"supportsReasoningSummary",
|
|
52545
|
+
"reasoningSummary",
|
|
52546
|
+
"timeoutReplay",
|
|
52532
52547
|
"supportsStore",
|
|
52533
52548
|
"supportsDeveloperRole",
|
|
52534
52549
|
"supportsReasoningEffort",
|
|
@@ -52576,8 +52591,8 @@ function validateRemoteModel(profileId, model) {
|
|
|
52576
52591
|
throw new Error(`Remote profile "${profileId}" model "${model.id}" has invalid input capabilities`);
|
|
52577
52592
|
}
|
|
52578
52593
|
if (!isPlainRecord(model.cost)) throw new Error(`Remote profile "${profileId}" model "${model.id}" has invalid cost values`);
|
|
52579
|
-
assertOnlyKeys(model.cost, ["input", "output", "cacheRead", "cacheWrite"], `Remote profile "${profileId}" model "${model.id}" cost`);
|
|
52580
|
-
if ([model.cost.input, model.cost.output, model.cost.cacheRead, model.cost.cacheWrite].some((value) => typeof value !== "number" || !Number.isFinite(value) || value < 0)) {
|
|
52594
|
+
assertOnlyKeys(model.cost, ["input", "output", "cacheRead", "cacheWrite", "cacheWriteLong"], `Remote profile "${profileId}" model "${model.id}" cost`);
|
|
52595
|
+
if ([model.cost.input, model.cost.output, model.cost.cacheRead, model.cost.cacheWrite, model.cost.cacheWriteLong].some((value) => value !== void 0 && (typeof value !== "number" || !Number.isFinite(value) || value < 0))) {
|
|
52581
52596
|
throw new Error(`Remote profile "${profileId}" model "${model.id}" has invalid cost values`);
|
|
52582
52597
|
}
|
|
52583
52598
|
if (!Number.isSafeInteger(model.contextWindow) || Number(model.contextWindow) <= 0 || !Number.isSafeInteger(model.maxTokens) || Number(model.maxTokens) <= 0 || Number(model.maxTokens) > Number(model.contextWindow)) {
|
|
@@ -52689,7 +52704,8 @@ function sanitizeRemotePayload(decoded, remote, catalogUrl, allowLocallyInjected
|
|
|
52689
52704
|
input: model.cost.input,
|
|
52690
52705
|
output: model.cost.output,
|
|
52691
52706
|
cacheRead: model.cost.cacheRead,
|
|
52692
|
-
cacheWrite: model.cost.cacheWrite
|
|
52707
|
+
cacheWrite: model.cost.cacheWrite,
|
|
52708
|
+
...model.cost.cacheWriteLong === void 0 ? {} : { cacheWriteLong: model.cost.cacheWriteLong }
|
|
52693
52709
|
},
|
|
52694
52710
|
contextWindow: model.contextWindow,
|
|
52695
52711
|
maxTokens: model.maxTokens,
|
|
@@ -52756,8 +52772,8 @@ function validateModelOverrides(value) {
|
|
|
52756
52772
|
if (override.maxTokens !== void 0 && (!Number.isInteger(override.maxTokens) || Number(override.maxTokens) < 1)) throw new Error(`models.json modelOverrides["${key}"].maxTokens is invalid`);
|
|
52757
52773
|
if (override.cost !== void 0) {
|
|
52758
52774
|
if (!isPlainRecord(override.cost)) throw new Error(`models.json modelOverrides["${key}"].cost must be an object`);
|
|
52759
|
-
for (const field of ["input", "output", "cacheRead", "cacheWrite"]) {
|
|
52760
|
-
if (override.cost[field] !== void 0 && (typeof override.cost[field] !== "number" || Number.
|
|
52775
|
+
for (const field of ["input", "output", "cacheRead", "cacheWrite", "cacheWriteLong"]) {
|
|
52776
|
+
if (override.cost[field] !== void 0 && (typeof override.cost[field] !== "number" || !Number.isFinite(override.cost[field]) || override.cost[field] < 0)) throw new Error(`models.json modelOverrides["${key}"].cost.${field} must be a non-negative finite number`);
|
|
52761
52777
|
}
|
|
52762
52778
|
}
|
|
52763
52779
|
if (override.headers !== void 0) {
|
|
@@ -53856,6 +53872,16 @@ var SettingsManager = class {
|
|
|
53856
53872
|
this.settings.autoCompactReserveTokens = tokens;
|
|
53857
53873
|
this.writeSettings();
|
|
53858
53874
|
}
|
|
53875
|
+
/** Undefined means "no CLI override": the provider default applies. */
|
|
53876
|
+
getPromptCacheRetention() {
|
|
53877
|
+
const retention = this.settings.promptCacheRetention;
|
|
53878
|
+
return retention === "none" || retention === "short" || retention === "long" ? retention : void 0;
|
|
53879
|
+
}
|
|
53880
|
+
setPromptCacheRetention(retention) {
|
|
53881
|
+
if (retention === void 0) delete this.settings.promptCacheRetention;
|
|
53882
|
+
else this.settings.promptCacheRetention = retention;
|
|
53883
|
+
this.writeSettings();
|
|
53884
|
+
}
|
|
53859
53885
|
getWebSearchMode() {
|
|
53860
53886
|
const mode = this.settings.tools?.webSearch?.mode;
|
|
53861
53887
|
if (mode === "disabled" || mode === "cached" || mode === "live") {
|
|
@@ -55575,10 +55601,11 @@ async function forkStoredSession(params) {
|
|
|
55575
55601
|
timestamp: entry.timestamp
|
|
55576
55602
|
};
|
|
55577
55603
|
if (copy.compactionData) {
|
|
55604
|
+
const selfAnchored = copy.compactionData.firstKeptEntryId === entry.id;
|
|
55578
55605
|
const keptId = idMap.get(copy.compactionData.firstKeptEntryId);
|
|
55579
55606
|
copy.compactionData = {
|
|
55580
55607
|
...copy.compactionData,
|
|
55581
|
-
firstKeptEntryId: keptId ?? firstCopiedId ?? copy.id
|
|
55608
|
+
firstKeptEntryId: selfAnchored ? copy.id : keptId ?? firstCopiedId ?? copy.id
|
|
55582
55609
|
};
|
|
55583
55610
|
}
|
|
55584
55611
|
idMap.set(summary.id, copy.id);
|
|
@@ -65073,6 +65100,23 @@ function buildCliFileAccessOptions(params) {
|
|
|
65073
65100
|
};
|
|
65074
65101
|
}
|
|
65075
65102
|
|
|
65103
|
+
// src/runtime/computer-use-owner.ts
|
|
65104
|
+
var COMPUTER_USE_OWNER_ENV = "PIE_COMPUTER_USE_OWNER_ID";
|
|
65105
|
+
var COMPUTER_USE_EXECUTION_ENV = "PIE_COMPUTER_USE_EXECUTION_ID";
|
|
65106
|
+
var COMPUTER_USE_STANDALONE_OWNER = "standalone";
|
|
65107
|
+
var OWNER_PATTERN = /^[A-Za-z0-9][A-Za-z0-9._:@-]{0,255}$/;
|
|
65108
|
+
function normalizeComputerUseOwner(value) {
|
|
65109
|
+
if (typeof value !== "string") return COMPUTER_USE_STANDALONE_OWNER;
|
|
65110
|
+
const trimmed = value.trim();
|
|
65111
|
+
if (!trimmed) return COMPUTER_USE_STANDALONE_OWNER;
|
|
65112
|
+
return OWNER_PATTERN.test(trimmed) ? trimmed : COMPUTER_USE_STANDALONE_OWNER;
|
|
65113
|
+
}
|
|
65114
|
+
function computerUseOwnerEnv(ownerId, executionId) {
|
|
65115
|
+
const env = { [COMPUTER_USE_OWNER_ENV]: normalizeComputerUseOwner(ownerId) };
|
|
65116
|
+
if (executionId) env[COMPUTER_USE_EXECUTION_ENV] = executionId;
|
|
65117
|
+
return env;
|
|
65118
|
+
}
|
|
65119
|
+
|
|
65076
65120
|
// src/theme/theme.ts
|
|
65077
65121
|
import * as fs13 from "node:fs";
|
|
65078
65122
|
import * as path12 from "node:path";
|
|
@@ -70243,19 +70287,25 @@ var SessionTraceWriter = class extends SessionTraceSnapshotWriter {
|
|
|
70243
70287
|
import { createHash as createHash4 } from "crypto";
|
|
70244
70288
|
function applyContextSignalsToFooter(target) {
|
|
70245
70289
|
if (!target.agent?.state) return;
|
|
70290
|
+
const state = target.agent.state;
|
|
70291
|
+
const route = {
|
|
70292
|
+
model: state.model ? `${state.model.provider ?? ""}/${state.model.id ?? ""}` : void 0,
|
|
70293
|
+
thinkingLevel: state.thinkingLevel
|
|
70294
|
+
};
|
|
70246
70295
|
const signals = computeContextSignals(
|
|
70247
70296
|
target,
|
|
70248
|
-
|
|
70249
|
-
|
|
70250
|
-
target.sessionManager.getMessages()
|
|
70297
|
+
state.systemPrompt ?? "",
|
|
70298
|
+
state.tools,
|
|
70299
|
+
target.sessionManager.getMessages(),
|
|
70300
|
+
route
|
|
70251
70301
|
);
|
|
70252
70302
|
target.footer.setState({
|
|
70253
70303
|
prefixHash: signals.prefixHash,
|
|
70254
70304
|
prefixHashChanged: signals.prefixHashChanged,
|
|
70255
|
-
cacheHitRate: signals.cacheHitRate
|
|
70305
|
+
cacheHitRate: signals.recentCacheHitRate ?? signals.cacheHitRate
|
|
70256
70306
|
});
|
|
70257
70307
|
}
|
|
70258
|
-
function computePromptPrefixHash(systemPrompt, tools) {
|
|
70308
|
+
function computePromptPrefixHash(systemPrompt, tools, route) {
|
|
70259
70309
|
return createHash4("sha256").update(
|
|
70260
70310
|
JSON.stringify({
|
|
70261
70311
|
systemPrompt,
|
|
@@ -70263,21 +70313,31 @@ function computePromptPrefixHash(systemPrompt, tools) {
|
|
|
70263
70313
|
name: tool.name,
|
|
70264
70314
|
description: tool.description ?? "",
|
|
70265
70315
|
parameters: tool.parameters ?? null
|
|
70266
|
-
}))
|
|
70316
|
+
})),
|
|
70317
|
+
route: { model: route?.model ?? "", thinkingLevel: route?.thinkingLevel ?? "" }
|
|
70267
70318
|
})
|
|
70268
70319
|
).digest("hex").slice(0, 8);
|
|
70269
70320
|
}
|
|
70270
|
-
function calculateCumulativeCacheHitRate(messages) {
|
|
70271
|
-
|
|
70272
|
-
let cacheRead = 0;
|
|
70321
|
+
function calculateCumulativeCacheHitRate(messages, recentTurns) {
|
|
70322
|
+
const usages = [];
|
|
70273
70323
|
for (const message of messages) {
|
|
70274
70324
|
if (message.role !== "assistant") continue;
|
|
70275
70325
|
const usage = message.usage;
|
|
70276
70326
|
if (!usage) continue;
|
|
70327
|
+
usages.push(usage);
|
|
70328
|
+
}
|
|
70329
|
+
const windowed = recentTurns !== void 0 && usages.length > recentTurns ? usages.slice(-recentTurns) : usages;
|
|
70330
|
+
let input = 0;
|
|
70331
|
+
let cacheRead = 0;
|
|
70332
|
+
let cacheWrite = 0;
|
|
70333
|
+
let cacheWriteLong = 0;
|
|
70334
|
+
for (const usage of windowed) {
|
|
70277
70335
|
input += usage.input;
|
|
70278
70336
|
cacheRead += usage.cacheRead;
|
|
70337
|
+
cacheWrite += usage.cacheWrite;
|
|
70338
|
+
cacheWriteLong += usage.cacheWriteLong ?? 0;
|
|
70279
70339
|
}
|
|
70280
|
-
const base = input + cacheRead;
|
|
70340
|
+
const base = input + cacheRead + cacheWrite + cacheWriteLong;
|
|
70281
70341
|
return base > 0 ? cacheRead / base : null;
|
|
70282
70342
|
}
|
|
70283
70343
|
var signalMemories = /* @__PURE__ */ new WeakMap();
|
|
@@ -70285,14 +70345,16 @@ var lastSignals = /* @__PURE__ */ new WeakMap();
|
|
|
70285
70345
|
function getLastContextSignals(hostKey) {
|
|
70286
70346
|
return lastSignals.get(hostKey) ?? null;
|
|
70287
70347
|
}
|
|
70288
|
-
|
|
70289
|
-
|
|
70348
|
+
var RECENT_HIT_RATE_TURNS = 5;
|
|
70349
|
+
function computeContextSignals(hostKey, systemPrompt, tools, messages, route) {
|
|
70350
|
+
const routeKey = `${route?.model ?? ""}|${route?.thinkingLevel ?? ""}`;
|
|
70351
|
+
const prefixHash = computePromptPrefixHash(systemPrompt, tools, route);
|
|
70290
70352
|
const systemHash = computePromptPrefixHash(systemPrompt, []);
|
|
70291
70353
|
const toolsHash = computePromptPrefixHash("", tools);
|
|
70292
70354
|
const previous = signalMemories.get(hostKey);
|
|
70293
70355
|
const prefixHashChanged = previous !== void 0 && previous.hash !== prefixHash;
|
|
70294
70356
|
if (previous?.hash !== prefixHash) {
|
|
70295
|
-
signalMemories.set(hostKey, { hash: prefixHash, systemHash, toolsHash });
|
|
70357
|
+
signalMemories.set(hostKey, { hash: prefixHash, systemHash, toolsHash, routeKey });
|
|
70296
70358
|
}
|
|
70297
70359
|
const signals = {
|
|
70298
70360
|
prefixHash,
|
|
@@ -70300,7 +70362,9 @@ function computeContextSignals(hostKey, systemPrompt, tools, messages) {
|
|
|
70300
70362
|
...prefixHashChanged && previous ? { previousPrefixHash: previous.hash } : {},
|
|
70301
70363
|
systemPromptChanged: prefixHashChanged && previous !== void 0 && previous.systemHash !== systemHash,
|
|
70302
70364
|
toolsChanged: prefixHashChanged && previous !== void 0 && previous.toolsHash !== toolsHash,
|
|
70303
|
-
|
|
70365
|
+
routeChanged: prefixHashChanged && previous !== void 0 && previous.routeKey !== routeKey,
|
|
70366
|
+
cacheHitRate: calculateCumulativeCacheHitRate(messages),
|
|
70367
|
+
recentCacheHitRate: calculateCumulativeCacheHitRate(messages, RECENT_HIT_RATE_TURNS)
|
|
70304
70368
|
};
|
|
70305
70369
|
lastSignals.set(hostKey, signals);
|
|
70306
70370
|
return signals;
|
|
@@ -70310,10 +70374,11 @@ function computeContextSignals(hostKey, systemPrompt, tools, messages) {
|
|
|
70310
70374
|
function noteCacheInvalidationInChat(host, signals) {
|
|
70311
70375
|
if (!signals || !signals.prefixHashChanged) return;
|
|
70312
70376
|
const parts = [];
|
|
70377
|
+
if (signals.routeChanged) parts.push(signals.systemPromptChanged || signals.toolsChanged ? "route + prompt rebuilt" : "model/thinking route changed");
|
|
70313
70378
|
if (signals.systemPromptChanged && signals.toolsChanged) parts.push("system prompt + tools rebuilt");
|
|
70314
70379
|
else if (signals.toolsChanged) parts.push("tools rebuilt");
|
|
70315
70380
|
else if (signals.systemPromptChanged) parts.push("system prompt rebuilt");
|
|
70316
|
-
|
|
70381
|
+
if (parts.length === 0) parts.push("prefix rebuilt");
|
|
70317
70382
|
const from = signals.previousPrefixHash ?? "?";
|
|
70318
70383
|
const line = `\u26A1 Prompt cache invalidated: \u2301${from} \u2192 \u2301${signals.prefixHash} (${parts.join(", ")})`;
|
|
70319
70384
|
if (host.chatContainer && host.ui) {
|
|
@@ -70325,7 +70390,8 @@ function noteCacheInvalidationInChat(host, signals) {
|
|
|
70325
70390
|
from,
|
|
70326
70391
|
to: signals.prefixHash,
|
|
70327
70392
|
systemPromptChanged: signals.systemPromptChanged,
|
|
70328
|
-
toolsChanged: signals.toolsChanged
|
|
70393
|
+
toolsChanged: signals.toolsChanged,
|
|
70394
|
+
routeChanged: signals.routeChanged
|
|
70329
70395
|
});
|
|
70330
70396
|
}
|
|
70331
70397
|
function applyContextSignalsWithTrace(host) {
|
|
@@ -70534,6 +70600,11 @@ function formatReportTokens(count) {
|
|
|
70534
70600
|
if (count < 1e7) return `${(count / 1e6).toFixed(1)}M`;
|
|
70535
70601
|
return `${Math.round(count / 1e6)}M`;
|
|
70536
70602
|
}
|
|
70603
|
+
function formatMeasuredTime(timestamp) {
|
|
70604
|
+
const date = new Date(timestamp);
|
|
70605
|
+
const pad = (value) => String(value).padStart(2, "0");
|
|
70606
|
+
return `${pad(date.getHours())}:${pad(date.getMinutes())}:${pad(date.getSeconds())}`;
|
|
70607
|
+
}
|
|
70537
70608
|
function buildSystemPromptBlocks(systemPrompt, skillsSection, knowledgeSection) {
|
|
70538
70609
|
const totalTokens = estimateStringTokens(systemPrompt);
|
|
70539
70610
|
const skillsTokens = skillsSection && systemPrompt.includes(skillsSection.trim()) ? estimateStringTokens(skillsSection) : null;
|
|
@@ -70789,8 +70860,12 @@ ${file.content}`).join("\n\n");
|
|
|
70789
70860
|
messagesTokens,
|
|
70790
70861
|
dynamicContextTokens: 0,
|
|
70791
70862
|
estimatedTotalTokens,
|
|
70792
|
-
|
|
70863
|
+
estimatedCurrentTokens: inputs.estimatedCurrentTokens,
|
|
70864
|
+
providerMeasuredTokens: inputs.providerMeasuredTokens,
|
|
70865
|
+
providerMeasuredAt: inputs.providerMeasuredAt ?? null,
|
|
70866
|
+
measurementMatchesCurrentContext: inputs.measurementMatchesCurrentContext,
|
|
70793
70867
|
contextWindow: inputs.contextWindow,
|
|
70868
|
+
autoCompactEnabled: inputs.autoCompactEnabled,
|
|
70794
70869
|
autoCompactLimitTokens: inputs.autoCompactLimitTokens,
|
|
70795
70870
|
reserveTokens: inputs.reserveTokens,
|
|
70796
70871
|
promptPrefixHash: inputs.promptPrefixHash,
|
|
@@ -70847,13 +70922,14 @@ function buildContextOverviewText(data, themeInput) {
|
|
|
70847
70922
|
}
|
|
70848
70923
|
}
|
|
70849
70924
|
});
|
|
70850
|
-
const autoCompact = data.autoCompactLimitTokens ? `triggers > ~${formatReportTokens(data.autoCompactLimitTokens)} (reserve ${formatReportTokens(data.reserveTokens)})` : "
|
|
70925
|
+
const autoCompact = !data.autoCompactEnabled ? "Off (disabled in settings)" : data.autoCompactLimitTokens ? `On \xB7 triggers > ~${formatReportTokens(data.autoCompactLimitTokens)} (reserve ${formatReportTokens(data.reserveTokens)})` : "On \xB7 threshold unknown (context window unavailable)";
|
|
70851
70926
|
lines.push(
|
|
70852
70927
|
`${padEndVisible(` ${branch(sections.length)} auto-compact`, labelWidth)}${theme2.fg("dim", autoCompact)}`
|
|
70853
70928
|
);
|
|
70854
|
-
const
|
|
70855
|
-
|
|
70856
|
-
|
|
70929
|
+
const measuredAt = data.providerMeasuredAt !== null ? ` \xB7 measured ${formatMeasuredTime(data.providerMeasuredAt)}` : "";
|
|
70930
|
+
const reconciliation = data.providerMeasuredTokens !== null ? data.measurementMatchesCurrentContext ? `est current ~${formatReportTokens(data.estimatedCurrentTokens)} \xB7 provider-measured ${formatReportTokens(data.providerMeasuredTokens)} (last response${measuredAt}) \xB7 est\u2212measured \u2248 ${formatReportTokens(
|
|
70931
|
+
Math.abs(data.estimatedCurrentTokens - data.providerMeasuredTokens)
|
|
70932
|
+
)}${data.estimatedCurrentTokens >= data.providerMeasuredTokens ? " overhead" : " undercount"}` : `est current ~${formatReportTokens(data.estimatedCurrentTokens)} \xB7 provider-measured ${formatReportTokens(data.providerMeasuredTokens)} (last response${measuredAt}) \xB7 not comparable \u2014 context changed since measurement` : `est current ~${formatReportTokens(data.estimatedCurrentTokens)} \xB7 provider usage not reported yet`;
|
|
70857
70933
|
lines.push(` ${theme2.fg("dim", reconciliation)}`);
|
|
70858
70934
|
lines.push(theme2.fg("dim", " /debugs/context \xB7 Enter to drill into a section, Esc to go back"));
|
|
70859
70935
|
return lines.join("\n");
|
|
@@ -70872,23 +70948,37 @@ function buildWindowRows(data) {
|
|
|
70872
70948
|
label: "estimated total (prompt + tools + messages)",
|
|
70873
70949
|
estTokens: data.estimatedTotalTokens,
|
|
70874
70950
|
note: `prompt ~${formatReportTokens(data.systemPromptTokens)} \xB7 tools ~${formatReportTokens(data.toolsTokens)} \xB7 messages ~${formatReportTokens(data.messagesTokens)}`
|
|
70951
|
+
},
|
|
70952
|
+
{
|
|
70953
|
+
id: "window:estimated-current",
|
|
70954
|
+
label: "estimated current context (local estimate + tail)",
|
|
70955
|
+
estTokens: data.estimatedCurrentTokens,
|
|
70956
|
+
note: "local estimate \u2014 not a provider measurement"
|
|
70875
70957
|
}
|
|
70876
70958
|
];
|
|
70877
|
-
if (data.
|
|
70959
|
+
if (data.providerMeasuredTokens !== null) {
|
|
70960
|
+
const measuredAt = data.providerMeasuredAt !== null ? formatMeasuredTime(data.providerMeasuredAt) : "unknown time";
|
|
70878
70961
|
rows.push({
|
|
70879
|
-
id: "window:
|
|
70880
|
-
label: "
|
|
70881
|
-
estTokens: data.
|
|
70882
|
-
valueText: formatReportTokens(data.
|
|
70883
|
-
note: `
|
|
70962
|
+
id: "window:provider-measured",
|
|
70963
|
+
label: "provider-measured (last response)",
|
|
70964
|
+
estTokens: data.providerMeasuredTokens,
|
|
70965
|
+
valueText: formatReportTokens(data.providerMeasuredTokens),
|
|
70966
|
+
note: data.measurementMatchesCurrentContext ? `est\u2212measured \u2248 ${formatReportTokens(Math.abs(data.estimatedCurrentTokens - data.providerMeasuredTokens))} \xB7 ${measuredAt}` : `not comparable \u2014 context changed since measurement \xB7 ${measuredAt}`
|
|
70884
70967
|
});
|
|
70885
70968
|
}
|
|
70886
70969
|
rows.push({
|
|
70887
70970
|
id: "window:auto-compact",
|
|
70971
|
+
label: "auto-compact",
|
|
70972
|
+
estTokens: 0,
|
|
70973
|
+
valueText: data.autoCompactEnabled ? "On" : "Off",
|
|
70974
|
+
note: data.autoCompactEnabled ? "enabled in settings" : "disabled in settings"
|
|
70975
|
+
});
|
|
70976
|
+
rows.push({
|
|
70977
|
+
id: "window:auto-compact-threshold",
|
|
70888
70978
|
label: "auto-compact threshold",
|
|
70889
|
-
estTokens: data.autoCompactLimitTokens ?? 0,
|
|
70890
|
-
valueText: data.autoCompactLimitTokens ? `>${formatReportTokens(data.autoCompactLimitTokens)}` : "
|
|
70891
|
-
note: data.autoCompactLimitTokens ? `reserve ${formatReportTokens(data.reserveTokens)}` : "
|
|
70979
|
+
estTokens: data.autoCompactEnabled ? data.autoCompactLimitTokens ?? 0 : 0,
|
|
70980
|
+
valueText: data.autoCompactEnabled ? data.autoCompactLimitTokens ? `>${formatReportTokens(data.autoCompactLimitTokens)}` : "unknown" : "\u2014",
|
|
70981
|
+
note: data.autoCompactEnabled ? data.autoCompactLimitTokens ? `reserve ${formatReportTokens(data.reserveTokens)}` : "context window unavailable" : "not applied while Off"
|
|
70892
70982
|
});
|
|
70893
70983
|
if (data.promptPrefixHash) {
|
|
70894
70984
|
rows.push({
|
|
@@ -71300,11 +71390,20 @@ var TreeSelectorComponent = class {
|
|
|
71300
71390
|
this.statusMessage = null;
|
|
71301
71391
|
}
|
|
71302
71392
|
}
|
|
71393
|
+
/** Cursor on the resident entry with the highest seq (the newest), not the last rendered row. */
|
|
71394
|
+
selectNewestResidentRow(message) {
|
|
71395
|
+
if (this.filteredRows.length === 0) return;
|
|
71396
|
+
let newestIndex = 0;
|
|
71397
|
+
for (let i = 1; i < this.filteredRows.length; i++) {
|
|
71398
|
+
if (this.filteredRows[i].summary.seq > this.filteredRows[newestIndex].summary.seq) newestIndex = i;
|
|
71399
|
+
}
|
|
71400
|
+
this.selectedIndex = newestIndex;
|
|
71401
|
+
if (message !== null) this.statusMessage = message;
|
|
71402
|
+
}
|
|
71303
71403
|
/** Jump to the newest page. Seqs are 1..total (append-only journal), so the last window starts at total - pageSize. */
|
|
71304
71404
|
jumpToLastPage() {
|
|
71305
71405
|
if (this.pageSummaries.length > 0 && !this.hasNext) {
|
|
71306
|
-
this.
|
|
71307
|
-
this.statusMessage = "latest page - at newest entry";
|
|
71406
|
+
this.selectNewestResidentRow("latest page - at newest entry");
|
|
71308
71407
|
return;
|
|
71309
71408
|
}
|
|
71310
71409
|
let anchor = Math.max(0, this.totalEntries - this.pageSizeValue);
|
|
@@ -71314,8 +71413,7 @@ var TreeSelectorComponent = class {
|
|
|
71314
71413
|
anchor = this.pageSummaries[this.pageSummaries.length - 1].seq;
|
|
71315
71414
|
continue;
|
|
71316
71415
|
}
|
|
71317
|
-
this.
|
|
71318
|
-
this.statusMessage = null;
|
|
71416
|
+
this.selectNewestResidentRow(null);
|
|
71319
71417
|
return;
|
|
71320
71418
|
}
|
|
71321
71419
|
if (anchor === 0 || !this.hasNext) break;
|
|
@@ -72781,7 +72879,9 @@ function calculateSessionUsageTotals(messages) {
|
|
|
72781
72879
|
let output = 0;
|
|
72782
72880
|
let cacheRead = 0;
|
|
72783
72881
|
let cacheWrite = 0;
|
|
72882
|
+
let cacheWriteLong = 0;
|
|
72784
72883
|
let cost = 0;
|
|
72884
|
+
let costEstimated = false;
|
|
72785
72885
|
for (const message of messages) {
|
|
72786
72886
|
if (message.role !== "assistant") continue;
|
|
72787
72887
|
const usage = message.usage;
|
|
@@ -72790,9 +72890,11 @@ function calculateSessionUsageTotals(messages) {
|
|
|
72790
72890
|
output += usage.output;
|
|
72791
72891
|
cacheRead += usage.cacheRead;
|
|
72792
72892
|
cacheWrite += usage.cacheWrite;
|
|
72893
|
+
cacheWriteLong += usage.cacheWriteLong ?? 0;
|
|
72793
72894
|
cost += usage.cost?.total ?? 0;
|
|
72895
|
+
if (usage.cost?.cacheWriteLongEstimated === true) costEstimated = true;
|
|
72794
72896
|
}
|
|
72795
|
-
return { input, output, cacheRead, cacheWrite, cost };
|
|
72897
|
+
return { input, output, cacheRead, cacheWrite, cacheWriteLong, cacheWriteTotal: cacheWrite + cacheWriteLong, cost, costEstimated };
|
|
72796
72898
|
}
|
|
72797
72899
|
function formatTokensCompact(count) {
|
|
72798
72900
|
if (count < 1e3) return String(count);
|
|
@@ -72838,16 +72940,18 @@ ${options.theme.bold("Usage (active context)")}
|
|
|
72838
72940
|
info += `${options.theme.fg("dim", "Cache Read:")} ${totals.cacheRead.toLocaleString()}
|
|
72839
72941
|
`;
|
|
72840
72942
|
}
|
|
72841
|
-
if (totals.
|
|
72842
|
-
|
|
72943
|
+
if (totals.cacheWriteTotal > 0) {
|
|
72944
|
+
const split = totals.cacheWriteLong > 0 ? options.theme.fg("dim", ` (short ${totals.cacheWrite.toLocaleString()} \xB7 long ${totals.cacheWriteLong.toLocaleString()})`) : "";
|
|
72945
|
+
info += `${options.theme.fg("dim", "Cache Write:")} ${totals.cacheWriteTotal.toLocaleString()}${split}
|
|
72843
72946
|
`;
|
|
72844
72947
|
}
|
|
72845
72948
|
if (totals.cost > 0) {
|
|
72846
|
-
|
|
72949
|
+
const estimateNote = totals.costEstimated ? " (long-TTL estimate)" : "";
|
|
72950
|
+
info += `${options.theme.fg("dim", "Cost:")} $${totals.cost.toFixed(4)}${estimateNote}
|
|
72847
72951
|
`;
|
|
72848
72952
|
}
|
|
72849
|
-
const hitRateBase = totals.input + totals.cacheRead;
|
|
72850
|
-
if (hitRateBase > 0
|
|
72953
|
+
const hitRateBase = totals.input + totals.cacheRead + totals.cacheWriteTotal;
|
|
72954
|
+
if (hitRateBase > 0) {
|
|
72851
72955
|
const hitRate = (totals.cacheRead / hitRateBase * 100).toFixed(1);
|
|
72852
72956
|
info += `${options.theme.fg("dim", "Cache Hit Rate:")} ${hitRate}% (~${formatTokensCompact(hitRateBase)} served)
|
|
72853
72957
|
`;
|
|
@@ -72981,7 +73085,9 @@ async function loadSession(host, sessionId) {
|
|
|
72981
73085
|
outputTokens: contextUsage.output,
|
|
72982
73086
|
cacheRead: contextUsage.cacheRead,
|
|
72983
73087
|
cacheWrite: contextUsage.cacheWrite,
|
|
73088
|
+
cacheWriteLong: contextUsage.cacheWriteLong,
|
|
72984
73089
|
cost: contextUsage.cost,
|
|
73090
|
+
costEstimated: contextUsage.costEstimated,
|
|
72985
73091
|
contextPercent,
|
|
72986
73092
|
contextWindow
|
|
72987
73093
|
});
|
|
@@ -74019,7 +74125,9 @@ function bindInteractiveRuntimeEvents(host) {
|
|
|
74019
74125
|
outputTokens: contextUsage.output,
|
|
74020
74126
|
cacheRead: contextUsage.cacheRead,
|
|
74021
74127
|
cacheWrite: contextUsage.cacheWrite,
|
|
74128
|
+
cacheWriteLong: contextUsage.cacheWriteLong,
|
|
74022
74129
|
cost: contextUsage.cost,
|
|
74130
|
+
costEstimated: contextUsage.costEstimated,
|
|
74023
74131
|
contextPercent,
|
|
74024
74132
|
contextWindow
|
|
74025
74133
|
});
|
|
@@ -74200,6 +74308,9 @@ function isControllerRecovering(host) {
|
|
|
74200
74308
|
function handleMessageStart(host, event) {
|
|
74201
74309
|
if (event.message?.role === "assistant") {
|
|
74202
74310
|
host.clearContinuationTimeout("assistant_message_start");
|
|
74311
|
+
for (const [id, component] of host.pendingTools) {
|
|
74312
|
+
if (!component.calm) host.pendingTools.delete(id);
|
|
74313
|
+
}
|
|
74203
74314
|
host.streamingComponent = new AssistantMessageComponent(void 0, host.thinkingLevel === "off");
|
|
74204
74315
|
host.streamingComponent.setCalmMode(host.calmMode);
|
|
74205
74316
|
host.streamingMessageHadToolCalls = false;
|
|
@@ -74771,7 +74882,7 @@ function listDiscoveredSkills(host) {
|
|
|
74771
74882
|
function applyReloadedSkills(host, result) {
|
|
74772
74883
|
host.skills = result.skills.filter((skill) => host.options.settingsManager.isSkillEnabled(skill.name));
|
|
74773
74884
|
host.skillsSection = formatSkillsForPrompt(host.skills);
|
|
74774
|
-
host.applyRuntimeToolMode(
|
|
74885
|
+
host.applyRuntimeToolMode();
|
|
74775
74886
|
host.updateSystemPromptTools();
|
|
74776
74887
|
for (const skill of host.skills) {
|
|
74777
74888
|
const skillPath = ["skills", `skill:${skill.name}`];
|
|
@@ -75199,6 +75310,23 @@ function handleToolsCommand(host, args) {
|
|
|
75199
75310
|
var RESET2 = "\x1B[0m";
|
|
75200
75311
|
var INVERSE2 = "\x1B[7m";
|
|
75201
75312
|
var ROLE_FILTER_CYCLE = ["all", "user", "assistant", "toolResult", "compaction"];
|
|
75313
|
+
function buildWrappedLines(rawLines, contentWidth) {
|
|
75314
|
+
const width = Math.max(1, contentWidth);
|
|
75315
|
+
const lines = [];
|
|
75316
|
+
const sourceStart = [];
|
|
75317
|
+
for (const rawLine of rawLines) {
|
|
75318
|
+
sourceStart.push(lines.length);
|
|
75319
|
+
lines.push(...wrapTextWithAnsi(rawLine, width));
|
|
75320
|
+
}
|
|
75321
|
+
return { lines: lines.length > 0 ? lines : [""], sourceStart };
|
|
75322
|
+
}
|
|
75323
|
+
function anchorFor(scroll, sourceStart, sourceCount) {
|
|
75324
|
+
if (sourceStart.length === 0) return { source: 0, offset: 0 };
|
|
75325
|
+
const target = Math.max(0, Math.min(scroll, sourceCount - 1));
|
|
75326
|
+
let source = sourceStart.length - 1;
|
|
75327
|
+
while (source > 0 && sourceStart[source] > target) source -= 1;
|
|
75328
|
+
return { source, offset: target - sourceStart[source] };
|
|
75329
|
+
}
|
|
75202
75330
|
function createLine2(content, width, isSelected) {
|
|
75203
75331
|
const normalized = content.replace(/[\r\n]+/g, " ");
|
|
75204
75332
|
const body = isSelected ? INVERSE2 + normalized : normalized;
|
|
@@ -75339,12 +75467,33 @@ var ContextReportSelectorComponent = class {
|
|
|
75339
75467
|
this.views.push({
|
|
75340
75468
|
kind: "text",
|
|
75341
75469
|
title,
|
|
75342
|
-
|
|
75470
|
+
rawLines: text.replace(/\r\n/g, "\n").split("\n"),
|
|
75471
|
+
lines: [],
|
|
75472
|
+
sourceStart: [],
|
|
75473
|
+
wrapWidth: 0,
|
|
75343
75474
|
scroll: 0
|
|
75344
75475
|
});
|
|
75345
75476
|
this.selectedIndex = 0;
|
|
75346
75477
|
this.statusMessage = null;
|
|
75347
75478
|
}
|
|
75479
|
+
/** Re-wrap a text view for the current terminal width, preserving the anchor. */
|
|
75480
|
+
ensureTextWrapped(view, width) {
|
|
75481
|
+
const contentWidth = Math.max(1, width - 2);
|
|
75482
|
+
if (view.wrapWidth === contentWidth) return;
|
|
75483
|
+
const previousCount = view.lines.length;
|
|
75484
|
+
const anchor = view.wrapWidth > 0 && previousCount > 0 ? anchorFor(view.scroll, view.sourceStart, previousCount) : { source: 0, offset: 0 };
|
|
75485
|
+
const rebuilt = buildWrappedLines(view.rawLines, contentWidth);
|
|
75486
|
+
view.lines = rebuilt.lines;
|
|
75487
|
+
view.sourceStart = rebuilt.sourceStart;
|
|
75488
|
+
view.wrapWidth = contentWidth;
|
|
75489
|
+
const source = Math.min(anchor.source, Math.max(0, rebuilt.sourceStart.length - 1));
|
|
75490
|
+
const nextSourceStart = rebuilt.sourceStart[source + 1] ?? rebuilt.lines.length;
|
|
75491
|
+
const sourceLineCount = Math.max(1, nextSourceStart - rebuilt.sourceStart[source]);
|
|
75492
|
+
view.scroll = Math.min(
|
|
75493
|
+
Math.max(0, rebuilt.lines.length - 1),
|
|
75494
|
+
rebuilt.sourceStart[source] + Math.min(anchor.offset, sourceLineCount - 1)
|
|
75495
|
+
);
|
|
75496
|
+
}
|
|
75348
75497
|
drillIntoSelected() {
|
|
75349
75498
|
const view = this.currentView;
|
|
75350
75499
|
if (view.kind !== "list") return;
|
|
@@ -75526,6 +75675,8 @@ var ContextReportSelectorComponent = class {
|
|
|
75526
75675
|
)
|
|
75527
75676
|
);
|
|
75528
75677
|
} else {
|
|
75678
|
+
this.ensureTextWrapped(view, width);
|
|
75679
|
+
view.scroll = Math.max(0, Math.min(view.scroll, view.lines.length - 1));
|
|
75529
75680
|
const total = view.lines.length;
|
|
75530
75681
|
const start = Math.min(view.scroll, Math.max(0, total - 1));
|
|
75531
75682
|
const end = Math.min(start + this.maxVisibleLines, total);
|
|
@@ -75690,14 +75841,20 @@ function handleContextReportCommand(host) {
|
|
|
75690
75841
|
const usage = host.calculateContextUsage();
|
|
75691
75842
|
const contextWindow = host.options.model?.contextWindow ?? 0;
|
|
75692
75843
|
const reserveTokens = host.options.settingsManager.getAutoCompactReserveTokens();
|
|
75844
|
+
const autoCompactEnabled = host.options.settingsManager.getAutoCompactEnabled();
|
|
75693
75845
|
const autoCompactLimit = contextWindow > 0 ? getAutoCompactTokenLimit(contextWindow, reserveTokens) ?? null : null;
|
|
75846
|
+
const state = host.agent.state;
|
|
75694
75847
|
const prefixHash = computePromptPrefixHash(
|
|
75695
75848
|
systemPrompt,
|
|
75696
|
-
|
|
75849
|
+
state.tools.map((tool) => ({
|
|
75697
75850
|
name: tool.name,
|
|
75698
75851
|
description: tool.description,
|
|
75699
75852
|
parameters: tool.parameters
|
|
75700
|
-
}))
|
|
75853
|
+
})),
|
|
75854
|
+
{
|
|
75855
|
+
model: state.model ? `${state.model.provider ?? ""}/${state.model.id ?? ""}` : void 0,
|
|
75856
|
+
thinkingLevel: state.thinkingLevel
|
|
75857
|
+
}
|
|
75701
75858
|
);
|
|
75702
75859
|
const lastSignals2 = getLastContextSignals(host);
|
|
75703
75860
|
const promptPrefixChanged = lastSignals2 !== null && lastSignals2.prefixHash !== prefixHash;
|
|
@@ -75721,7 +75878,11 @@ function handleContextReportCommand(host) {
|
|
|
75721
75878
|
entries,
|
|
75722
75879
|
compactionTokensBefore: (entryId) => host.sessionManager.getEntry(entryId)?.compactionData?.tokensBefore,
|
|
75723
75880
|
contextWindow,
|
|
75724
|
-
|
|
75881
|
+
estimatedCurrentTokens: usage.estimatedCurrentTokens,
|
|
75882
|
+
providerMeasuredTokens: usage.providerMeasuredTokens,
|
|
75883
|
+
providerMeasuredAt: usage.providerMeasuredAt,
|
|
75884
|
+
measurementMatchesCurrentContext: usage.measurementMatchesCurrentContext,
|
|
75885
|
+
autoCompactEnabled,
|
|
75725
75886
|
autoCompactLimitTokens: autoCompactLimit,
|
|
75726
75887
|
reserveTokens,
|
|
75727
75888
|
promptPrefixHash: prefixHash,
|
|
@@ -76553,7 +76714,9 @@ async function handleClearCommand(host) {
|
|
|
76553
76714
|
outputTokens: contextUsage.output,
|
|
76554
76715
|
cacheRead: contextUsage.cacheRead,
|
|
76555
76716
|
cacheWrite: contextUsage.cacheWrite,
|
|
76717
|
+
cacheWriteLong: contextUsage.cacheWriteLong,
|
|
76556
76718
|
cost: contextUsage.cost,
|
|
76719
|
+
costEstimated: contextUsage.costEstimated,
|
|
76557
76720
|
contextPercent: contextWindow > 0 && contextUsage.tokens !== null ? contextUsage.tokens / contextWindow * 100 : 0,
|
|
76558
76721
|
contextWindow
|
|
76559
76722
|
});
|
|
@@ -76916,11 +77079,16 @@ async function handleCompactCommand(host) {
|
|
|
76916
77079
|
host.showStatus("Nothing to compact yet");
|
|
76917
77080
|
return;
|
|
76918
77081
|
}
|
|
76919
|
-
const
|
|
76920
|
-
|
|
77082
|
+
const preparation = prepareSessionCompaction({
|
|
77083
|
+
sessionManager: host.sessionManager,
|
|
77084
|
+
messages: existingMessages,
|
|
77085
|
+
budgetTokens: host.options.model?.contextWindow
|
|
77086
|
+
});
|
|
77087
|
+
if (preparation.entries.length === 0) {
|
|
76921
77088
|
host.showStatus("Need at least one real user message before compacting");
|
|
76922
77089
|
return;
|
|
76923
77090
|
}
|
|
77091
|
+
const tokensBefore = calculateTotalTokens(preparation.messages);
|
|
76924
77092
|
const compactOptions = {
|
|
76925
77093
|
model: host.options.model,
|
|
76926
77094
|
apiKey: host.options.apiKey,
|
|
@@ -76939,10 +77107,27 @@ async function handleCompactCommand(host) {
|
|
|
76939
77107
|
if (beforeCompact?.summary) {
|
|
76940
77108
|
summary = beforeCompact.summary;
|
|
76941
77109
|
} else {
|
|
76942
|
-
summary = await createCompactionSummary(
|
|
77110
|
+
summary = await createCompactionSummary(preparation.messages, compactOptions);
|
|
77111
|
+
}
|
|
77112
|
+
const verified = verifyPreparedCompactionCommit({
|
|
77113
|
+
preparation,
|
|
77114
|
+
sessionManager: host.sessionManager,
|
|
77115
|
+
messages: host.agent.state.messages,
|
|
77116
|
+
result: { summary, retainedTail: preparation.retainedTail.retainedTail, tokensBefore }
|
|
77117
|
+
});
|
|
77118
|
+
if (verified.ok === false) {
|
|
77119
|
+
if (verified.kind === "stale") {
|
|
77120
|
+
host.showStatus("Session changed during compaction; nothing was published");
|
|
77121
|
+
return;
|
|
77122
|
+
}
|
|
77123
|
+
throw new Error(`Compaction abandoned: ${verified.reason}`);
|
|
76943
77124
|
}
|
|
76944
|
-
|
|
76945
|
-
|
|
77125
|
+
host.sessionManager.appendCompactionCheckpoint({
|
|
77126
|
+
summary,
|
|
77127
|
+
retainedTail: verified.retainedTail,
|
|
77128
|
+
tokensBefore,
|
|
77129
|
+
excludeFailure: preparation.excludedFailure
|
|
77130
|
+
});
|
|
76946
77131
|
const compactedMessages = host.sessionManager.getMessages();
|
|
76947
77132
|
host.replaceAgentMessagesAndMarkSynced(compactedMessages);
|
|
76948
77133
|
host.resetFileObservationState();
|
|
@@ -76967,7 +77152,9 @@ async function handleCompactCommand(host) {
|
|
|
76967
77152
|
outputTokens: contextUsage.output,
|
|
76968
77153
|
cacheRead: contextUsage.cacheRead,
|
|
76969
77154
|
cacheWrite: contextUsage.cacheWrite,
|
|
77155
|
+
cacheWriteLong: contextUsage.cacheWriteLong,
|
|
76970
77156
|
cost: contextUsage.cost,
|
|
77157
|
+
costEstimated: contextUsage.costEstimated,
|
|
76971
77158
|
contextPercent,
|
|
76972
77159
|
contextWindow
|
|
76973
77160
|
});
|
|
@@ -79350,8 +79537,12 @@ var FooterComponent = class {
|
|
|
79350
79537
|
if (state.inputTokens) statsParts.push(`\u2191${formatTokens(state.inputTokens)}`);
|
|
79351
79538
|
if (state.outputTokens) statsParts.push(`\u2193${formatTokens(state.outputTokens)}`);
|
|
79352
79539
|
if (state.cacheRead) statsParts.push(`R${formatTokens(state.cacheRead)}`);
|
|
79353
|
-
|
|
79354
|
-
|
|
79540
|
+
const cacheWriteShort = state.cacheWrite ?? 0;
|
|
79541
|
+
const cacheWriteLong = state.cacheWriteLong ?? 0;
|
|
79542
|
+
const cacheWriteTotal = cacheWriteShort + cacheWriteLong;
|
|
79543
|
+
if (cacheWriteTotal) statsParts.push(`W${formatTokens(cacheWriteTotal)}`);
|
|
79544
|
+
if (cacheWriteLong) statsParts.push(`W1h${formatTokens(cacheWriteLong)}`);
|
|
79545
|
+
if (state.cost) statsParts.push(`${state.costEstimated ? "~" : ""}$${state.cost.toFixed(3)}`);
|
|
79355
79546
|
if (state.cacheHitRate != null) {
|
|
79356
79547
|
statsParts.push(theme.fg("dim", `ca ${(state.cacheHitRate * 100).toFixed(0)}%`));
|
|
79357
79548
|
}
|
|
@@ -79501,13 +79692,23 @@ function calculateCliContextUsage(params) {
|
|
|
79501
79692
|
const estimate = estimateContextTokens(messages);
|
|
79502
79693
|
const usageMessage = estimate.lastUsageIndex !== null ? messages[estimate.lastUsageIndex] : void 0;
|
|
79503
79694
|
const usage = usageMessage?.role === "assistant" ? usageMessage.usage : void 0;
|
|
79695
|
+
const hasProviderMeasurement = usage !== void 0 && estimate.lastUsageIndex !== null;
|
|
79504
79696
|
return {
|
|
79505
79697
|
tokens: estimate.tokens,
|
|
79698
|
+
estimatedCurrentTokens: estimate.tokens,
|
|
79699
|
+
providerMeasuredTokens: hasProviderMeasurement ? estimate.providerTokens : null,
|
|
79700
|
+
providerMeasuredAt: hasProviderMeasurement && usageMessage ? usageMessage.timestamp : null,
|
|
79701
|
+
// A provider total describes the context AT that response. Any trailing
|
|
79702
|
+
// tool/user message (or a compaction reset, which zeroes stale usage)
|
|
79703
|
+
// makes the two figures different snapshots, so no error may be shown.
|
|
79704
|
+
measurementMatchesCurrentContext: hasProviderMeasurement && estimate.lastUsageIndex === messages.length - 1,
|
|
79506
79705
|
input: usage?.input ?? 0,
|
|
79507
79706
|
output: usage?.output ?? 0,
|
|
79508
79707
|
cacheRead: usage?.cacheRead ?? 0,
|
|
79509
79708
|
cacheWrite: usage?.cacheWrite ?? 0,
|
|
79510
|
-
|
|
79709
|
+
cacheWriteLong: usage?.cacheWriteLong ?? 0,
|
|
79710
|
+
cost: usage?.cost.total ?? 0,
|
|
79711
|
+
costEstimated: usage?.cost?.cacheWriteLongEstimated === true
|
|
79511
79712
|
};
|
|
79512
79713
|
}
|
|
79513
79714
|
function createCliAutoCompactDecision(params) {
|
|
@@ -79538,6 +79739,11 @@ function shouldCliAutoCompactTokens(params) {
|
|
|
79538
79739
|
const tokenLimit = getAutoCompactTokenLimit(params.contextWindow, params.reserveTokens);
|
|
79539
79740
|
return tokenLimit !== void 0 && params.tokens > tokenLimit;
|
|
79540
79741
|
}
|
|
79742
|
+
function createCliCompactionBudget(params) {
|
|
79743
|
+
const contextWindow = params.contextWindow ?? 0;
|
|
79744
|
+
const reserveTokens = params.reserveTokens ?? DEFAULT_COMPACTION_CONFIG.reserveTokens;
|
|
79745
|
+
return () => getAutoCompactTokenLimit(contextWindow, reserveTokens);
|
|
79746
|
+
}
|
|
79541
79747
|
async function createCliAutoCompactionResult(params) {
|
|
79542
79748
|
if (params.context.signal?.aborted) {
|
|
79543
79749
|
return { aborted: true };
|
|
@@ -79546,8 +79752,9 @@ async function createCliAutoCompactionResult(params) {
|
|
|
79546
79752
|
if (!activeEntryId) {
|
|
79547
79753
|
return { aborted: true };
|
|
79548
79754
|
}
|
|
79549
|
-
const
|
|
79550
|
-
|
|
79755
|
+
const legacyCutId = params.context.preparation ? null : findFirstKeptEntrySummaryId(params.context.sessionManager.getActiveContextSummaries());
|
|
79756
|
+
const retainedTail = params.context.preparation ? params.context.preparation.retainedTail.retainedTail : legacyCutId ? { kind: "from-entry", entryId: legacyCutId } : void 0;
|
|
79757
|
+
if (!retainedTail) {
|
|
79551
79758
|
return { aborted: true };
|
|
79552
79759
|
}
|
|
79553
79760
|
const compactOptions = {
|
|
@@ -79562,7 +79769,8 @@ async function createCliAutoCompactionResult(params) {
|
|
|
79562
79769
|
}
|
|
79563
79770
|
return {
|
|
79564
79771
|
summary,
|
|
79565
|
-
|
|
79772
|
+
retainedTail,
|
|
79773
|
+
...retainedTail.kind === "from-entry" ? { firstKeptEntryId: retainedTail.entryId } : {},
|
|
79566
79774
|
tokensBefore: calculateTotalTokens(params.context.messages)
|
|
79567
79775
|
};
|
|
79568
79776
|
}
|
|
@@ -79714,16 +79922,44 @@ function createCliRetryPolicy(isRetryableErrorOverride) {
|
|
|
79714
79922
|
maxRetries: CLI_RETRY_MAX_RETRIES,
|
|
79715
79923
|
baseDelayMs: getCliRetryBaseDelayMs(),
|
|
79716
79924
|
maxDelayMs: getCliRetryMaxDelayMs(),
|
|
79717
|
-
maxRetriesForFailure: (failure) => failure.kind === "transient_network" ? getCliTransientNetworkMaxRetries() : CLI_RETRY_MAX_RETRIES,
|
|
79718
|
-
maxTotalRetries: getCliRetryTotalMaxRetries()
|
|
79925
|
+
maxRetriesForFailure: (failure) => failure.kind === "transient_network" ? getCliTransientNetworkMaxRetries() : failure.replayExempt === true ? getCliTimeoutReplayMaxRetries() : CLI_RETRY_MAX_RETRIES,
|
|
79926
|
+
maxTotalRetries: getCliRetryTotalMaxRetries(),
|
|
79927
|
+
systemicReplayStallLimit: getCliSystemicReplayStallLimit()
|
|
79719
79928
|
};
|
|
79720
79929
|
}
|
|
79930
|
+
var CLI_TIMEOUT_REPLAY_MAX_RETRIES = 5;
|
|
79931
|
+
function getCliTimeoutReplayMaxRetries() {
|
|
79932
|
+
const override = process.env.PIE_TIMEOUT_REPLAY_MAX_RETRIES;
|
|
79933
|
+
if (!override) return CLI_TIMEOUT_REPLAY_MAX_RETRIES;
|
|
79934
|
+
const parsed = Number(override);
|
|
79935
|
+
return Number.isFinite(parsed) && parsed >= 0 ? Math.floor(parsed) : CLI_TIMEOUT_REPLAY_MAX_RETRIES;
|
|
79936
|
+
}
|
|
79937
|
+
var CLI_SYSTEMIC_REPLAY_STALL_LIMIT = 3;
|
|
79938
|
+
function getCliSystemicReplayStallLimit() {
|
|
79939
|
+
const override = process.env.PIE_SYSTEMIC_REPLAY_STALL_LIMIT;
|
|
79940
|
+
if (!override) return CLI_SYSTEMIC_REPLAY_STALL_LIMIT;
|
|
79941
|
+
const parsed = Number(override);
|
|
79942
|
+
return Number.isFinite(parsed) && parsed >= 1 ? Math.floor(parsed) : CLI_SYSTEMIC_REPLAY_STALL_LIMIT;
|
|
79943
|
+
}
|
|
79721
79944
|
|
|
79722
79945
|
// src/runtime/interactive-context-ui.ts
|
|
79723
79946
|
function calculateContextUsage(host) {
|
|
79724
79947
|
const messages = host.agent?.state.messages ?? [];
|
|
79725
79948
|
if (messages.length === 0) {
|
|
79726
|
-
return {
|
|
79949
|
+
return {
|
|
79950
|
+
tokens: 0,
|
|
79951
|
+
estimatedCurrentTokens: 0,
|
|
79952
|
+
providerMeasuredTokens: null,
|
|
79953
|
+
providerMeasuredAt: null,
|
|
79954
|
+
measurementMatchesCurrentContext: false,
|
|
79955
|
+
input: 0,
|
|
79956
|
+
output: 0,
|
|
79957
|
+
cacheRead: 0,
|
|
79958
|
+
cacheWrite: 0,
|
|
79959
|
+
cacheWriteLong: 0,
|
|
79960
|
+
cost: 0,
|
|
79961
|
+
costEstimated: false
|
|
79962
|
+
};
|
|
79727
79963
|
}
|
|
79728
79964
|
return calculateCliContextUsage({
|
|
79729
79965
|
messages,
|
|
@@ -80474,6 +80710,9 @@ function createInteractiveAgentSessionController(host) {
|
|
|
80474
80710
|
}
|
|
80475
80711
|
return void 0;
|
|
80476
80712
|
},
|
|
80713
|
+
// Same auto-compact limit the threshold decision uses; a checkpoint whose
|
|
80714
|
+
// summary + retained tail would still exceed it is refused.
|
|
80715
|
+
getCompactionBudgetTokens: createCliCompactionBudget({ contextWindow: host.options.model?.contextWindow }),
|
|
80477
80716
|
getAutoContinueMessage: () => host.getTodoAutoContinueMessage(),
|
|
80478
80717
|
classifyFailure: (context) => classifyCliFailure(context),
|
|
80479
80718
|
retry: createCliRetryPolicy(
|
|
@@ -80491,9 +80730,16 @@ function createInteractiveAgentSessionController(host) {
|
|
|
80491
80730
|
return { aborted: true };
|
|
80492
80731
|
}
|
|
80493
80732
|
if (beforeCompact?.summary) {
|
|
80494
|
-
const
|
|
80495
|
-
|
|
80496
|
-
|
|
80733
|
+
const retainedTail = context.preparation?.retainedTail.retainedTail ?? (() => {
|
|
80734
|
+
const legacyCutId = findFirstKeptEntrySummaryId(context.sessionManager.getActiveContextSummaries());
|
|
80735
|
+
return legacyCutId ? { kind: "from-entry", entryId: legacyCutId } : void 0;
|
|
80736
|
+
})();
|
|
80737
|
+
if (!retainedTail) return { aborted: true };
|
|
80738
|
+
return {
|
|
80739
|
+
summary: beforeCompact.summary,
|
|
80740
|
+
retainedTail,
|
|
80741
|
+
...retainedTail.kind === "from-entry" ? { firstKeptEntryId: retainedTail.entryId } : {}
|
|
80742
|
+
};
|
|
80497
80743
|
}
|
|
80498
80744
|
autoCompactBeforeStats = summarizeActiveContext(context.sessionManager.getActiveContextSummaries());
|
|
80499
80745
|
return createCliAutoCompactionResult({
|
|
@@ -80655,6 +80901,13 @@ function createInteractiveAgentSessionController(host) {
|
|
|
80655
80901
|
host.isProcessing = true;
|
|
80656
80902
|
host.footer.setState({ status: "processing", lifecycleEvent: "auto_compact" });
|
|
80657
80903
|
host.showStatus(event.reason === "overflow" ? "Context overflow detected, compacting..." : "Auto-compacting context...");
|
|
80904
|
+
} else if (event.type === "compaction_committed") {
|
|
80905
|
+
host.resetFileObservationState();
|
|
80906
|
+
host.resetRuntimeModeBlocks?.();
|
|
80907
|
+
host.sessionTrace.noteRuntimeEvent("compaction_committed", {
|
|
80908
|
+
reason: event.reason,
|
|
80909
|
+
willRetry: event.willRetry
|
|
80910
|
+
});
|
|
80658
80911
|
} else if (event.type === "auto_compaction_end") {
|
|
80659
80912
|
host.isCompacting = false;
|
|
80660
80913
|
host.isProcessing = false;
|
|
@@ -80667,8 +80920,6 @@ function createInteractiveAgentSessionController(host) {
|
|
|
80667
80920
|
autoCompactBeforeStats = null;
|
|
80668
80921
|
return;
|
|
80669
80922
|
}
|
|
80670
|
-
host.resetFileObservationState();
|
|
80671
|
-
host.resetRuntimeModeBlocks?.();
|
|
80672
80923
|
if (!event.result?.aborted) {
|
|
80673
80924
|
host.streamingComponent = void 0;
|
|
80674
80925
|
host.pendingTools.clear();
|
|
@@ -80687,7 +80938,9 @@ function createInteractiveAgentSessionController(host) {
|
|
|
80687
80938
|
outputTokens: contextUsage.output,
|
|
80688
80939
|
cacheRead: contextUsage.cacheRead,
|
|
80689
80940
|
cacheWrite: contextUsage.cacheWrite,
|
|
80941
|
+
cacheWriteLong: contextUsage.cacheWriteLong,
|
|
80690
80942
|
cost: contextUsage.cost,
|
|
80943
|
+
costEstimated: contextUsage.costEstimated,
|
|
80691
80944
|
contextPercent,
|
|
80692
80945
|
contextWindow
|
|
80693
80946
|
});
|
|
@@ -80843,20 +81096,80 @@ function currentDateInZone(timeZone) {
|
|
|
80843
81096
|
const part = (type) => parts.find((p) => p.type === type)?.value ?? "00";
|
|
80844
81097
|
return `${part("year")}-${part("month")}-${part("day")}`;
|
|
80845
81098
|
}
|
|
80846
|
-
var
|
|
81099
|
+
var RUNTIME_MODE_BLOCK_START_MARKER = "<runtime-mode-context>";
|
|
81100
|
+
function leadingRuntimeBlock(text) {
|
|
81101
|
+
const withoutLeadingWhitespace = text.replace(/^[\t ]+/, "");
|
|
81102
|
+
if (!withoutLeadingWhitespace.startsWith(RUNTIME_MODE_BLOCK_START_MARKER)) return null;
|
|
81103
|
+
const markerStart = text.length - withoutLeadingWhitespace.length;
|
|
81104
|
+
const endIndex = text.indexOf(RUNTIME_MODE_CONTEXT_END_MARKER, markerStart);
|
|
81105
|
+
if (endIndex < 0) return null;
|
|
81106
|
+
const block = text.slice(markerStart, endIndex + RUNTIME_MODE_CONTEXT_END_MARKER.length);
|
|
81107
|
+
const rest = text.slice(endIndex + RUNTIME_MODE_CONTEXT_END_MARKER.length).replace(/^[\t ]*(?:\r?\n){0,2}/, "");
|
|
81108
|
+
return { block, rest };
|
|
81109
|
+
}
|
|
81110
|
+
function stripLeadingRuntimeBlock(text) {
|
|
81111
|
+
const leading = leadingRuntimeBlock(text);
|
|
81112
|
+
return leading ? { rest: leading.rest } : null;
|
|
81113
|
+
}
|
|
81114
|
+
function leadingRuntimeBlockOfMessage(message) {
|
|
81115
|
+
if (message.role !== "user") return null;
|
|
81116
|
+
const content = message.content;
|
|
81117
|
+
if (typeof content === "string") return leadingRuntimeBlock(content)?.block ?? null;
|
|
81118
|
+
if (!Array.isArray(content)) return null;
|
|
81119
|
+
const first = content[0];
|
|
81120
|
+
if (first?.type !== "text" || typeof first.text !== "string") return null;
|
|
81121
|
+
return leadingRuntimeBlock(first.text)?.block ?? null;
|
|
81122
|
+
}
|
|
81123
|
+
function lastUserMessageCarriesRuntimeBlock(messages, block) {
|
|
81124
|
+
for (let index = messages.length - 1; index >= 0; index -= 1) {
|
|
81125
|
+
const message = messages[index];
|
|
81126
|
+
if (message?.role !== "user") continue;
|
|
81127
|
+
return leadingRuntimeBlockOfMessage(message) === block;
|
|
81128
|
+
}
|
|
81129
|
+
return false;
|
|
81130
|
+
}
|
|
81131
|
+
function applyRuntimeBlockToText(text, block) {
|
|
81132
|
+
const split = stripLeadingRuntimeBlock(text);
|
|
81133
|
+
const rest = split ? split.rest : text;
|
|
81134
|
+
const next = rest.length > 0 ? `${block}
|
|
81135
|
+
|
|
81136
|
+
${rest}` : block;
|
|
81137
|
+
return next === text ? text : next;
|
|
81138
|
+
}
|
|
81139
|
+
function applyRuntimeBlockToContentArray(content, block) {
|
|
81140
|
+
const first = content[0];
|
|
81141
|
+
if (first && typeof first === "object" && first.type === "text" && typeof first.text === "string") {
|
|
81142
|
+
const text = first.text;
|
|
81143
|
+
if (stripLeadingRuntimeBlock(text)) {
|
|
81144
|
+
const nextText = applyRuntimeBlockToText(text, block);
|
|
81145
|
+
if (nextText === text) return content;
|
|
81146
|
+
const copy = [...content];
|
|
81147
|
+
copy[0] = { ...first, text: nextText };
|
|
81148
|
+
return copy;
|
|
81149
|
+
}
|
|
81150
|
+
}
|
|
81151
|
+
return [{ type: "text", text: block }, ...content];
|
|
81152
|
+
}
|
|
80847
81153
|
function refreshRuntimeModeBlockOnLastUserMessage(messages, block) {
|
|
80848
81154
|
for (let i = messages.length - 1; i >= 0; i--) {
|
|
80849
81155
|
const message = messages[i];
|
|
80850
81156
|
if (message?.role !== "user") continue;
|
|
80851
|
-
const content =
|
|
80852
|
-
|
|
80853
|
-
|
|
80854
|
-
|
|
80855
|
-
|
|
80856
|
-
|
|
80857
|
-
|
|
80858
|
-
|
|
80859
|
-
|
|
81157
|
+
const content = message.content;
|
|
81158
|
+
if (typeof content === "string") {
|
|
81159
|
+
const next = applyRuntimeBlockToText(content, block);
|
|
81160
|
+
if (next === content) return messages;
|
|
81161
|
+
const copy = [...messages];
|
|
81162
|
+
copy[i] = { ...message, content: next };
|
|
81163
|
+
return copy;
|
|
81164
|
+
}
|
|
81165
|
+
if (Array.isArray(content)) {
|
|
81166
|
+
const next = applyRuntimeBlockToContentArray(content, block);
|
|
81167
|
+
if (next === content) return messages;
|
|
81168
|
+
const copy = [...messages];
|
|
81169
|
+
copy[i] = { ...message, content: next };
|
|
81170
|
+
return copy;
|
|
81171
|
+
}
|
|
81172
|
+
return messages;
|
|
80860
81173
|
}
|
|
80861
81174
|
return messages;
|
|
80862
81175
|
}
|
|
@@ -80866,28 +81179,54 @@ var RuntimeModeBlockInjector = class {
|
|
|
80866
81179
|
}
|
|
80867
81180
|
options;
|
|
80868
81181
|
lastKey = null;
|
|
80869
|
-
|
|
81182
|
+
/**
|
|
81183
|
+
* Request-view overlay. While active, the CURRENT block is re-derived on
|
|
81184
|
+
* every request from the live message snapshot and applied to the latest
|
|
81185
|
+
* user message. It is not cached into history and it ends only when a real
|
|
81186
|
+
* user message freezes the current block (see `nextBlock` + the transform),
|
|
81187
|
+
* so consecutive tool rounds after a compaction retry keep the fresh state
|
|
81188
|
+
* instead of losing it after one request.
|
|
81189
|
+
*/
|
|
81190
|
+
overlayActive = false;
|
|
80870
81191
|
reset() {
|
|
80871
81192
|
this.lastKey = null;
|
|
80872
|
-
this.
|
|
81193
|
+
this.overlayActive = true;
|
|
81194
|
+
}
|
|
81195
|
+
/**
|
|
81196
|
+
* Arm the request-view overlay without resetting the frozen-block key. Used
|
|
81197
|
+
* when the runtime shape changed while a turn is still running (compaction
|
|
81198
|
+
* checkpoint committed, plan approval, YOLO toggle inside a tool turn): the
|
|
81199
|
+
* next and subsequent model requests must see the current state even though
|
|
81200
|
+
* no new user message has been accepted yet.
|
|
81201
|
+
*/
|
|
81202
|
+
armRefresh() {
|
|
81203
|
+
this.overlayActive = true;
|
|
80873
81204
|
}
|
|
80874
|
-
/**
|
|
81205
|
+
/**
|
|
81206
|
+
* Block to prepend to the next user message, or null when unchanged. Does
|
|
81207
|
+
* NOT end the overlay: the block is only proof once the message carrying it
|
|
81208
|
+
* reaches the request transform.
|
|
81209
|
+
*/
|
|
80875
81210
|
nextBlock() {
|
|
80876
|
-
|
|
80877
|
-
this.pendingRetryRefresh = false;
|
|
80878
|
-
return block;
|
|
81211
|
+
return this.freshBlock();
|
|
80879
81212
|
}
|
|
80880
81213
|
/**
|
|
80881
|
-
*
|
|
80882
|
-
* after compaction, manual
|
|
80883
|
-
*
|
|
80884
|
-
*
|
|
81214
|
+
* Current block for a request that reuses existing history (overflow retry
|
|
81215
|
+
* after compaction, manual-compact continue, or the tool rounds that follow
|
|
81216
|
+
* a mid-turn mode change). Returns the same block for every request until
|
|
81217
|
+
* the latest user message itself carries that block; then the overlay is
|
|
81218
|
+
* retired and null is returned. Derivation is per request from the given
|
|
81219
|
+
* snapshot; no message array is cached.
|
|
80885
81220
|
*/
|
|
80886
|
-
consumeRetryRefreshBlock() {
|
|
80887
|
-
if (!this.
|
|
80888
|
-
this.pendingRetryRefresh = false;
|
|
81221
|
+
consumeRetryRefreshBlock(messages) {
|
|
81222
|
+
if (!this.overlayActive) return null;
|
|
80889
81223
|
const state = this.options.getState();
|
|
80890
|
-
|
|
81224
|
+
const block = buildRuntimeModeContext(state);
|
|
81225
|
+
if (messages && lastUserMessageCarriesRuntimeBlock(messages, block)) {
|
|
81226
|
+
this.overlayActive = false;
|
|
81227
|
+
return null;
|
|
81228
|
+
}
|
|
81229
|
+
return block;
|
|
80891
81230
|
}
|
|
80892
81231
|
freshBlock() {
|
|
80893
81232
|
const state = this.options.getState();
|
|
@@ -80900,14 +81239,17 @@ var RuntimeModeBlockInjector = class {
|
|
|
80900
81239
|
};
|
|
80901
81240
|
|
|
80902
81241
|
// src/runtime/cache-retention.ts
|
|
80903
|
-
function createCacheRetentionStreamFn(configured) {
|
|
81242
|
+
function createCacheRetentionStreamFn(configured, getConfiguredRetention) {
|
|
80904
81243
|
const base = configured ?? ((model, context, options) => streamSimple(model, context, options));
|
|
80905
|
-
return (model, context, options) =>
|
|
80906
|
-
|
|
80907
|
-
|
|
80908
|
-
|
|
80909
|
-
|
|
80910
|
-
|
|
81244
|
+
return (model, context, options) => {
|
|
81245
|
+
const requested = options?.cacheRetention;
|
|
81246
|
+
const configuredRetention = model.api === "anthropic-messages" ? getConfiguredRetention?.() : void 0;
|
|
81247
|
+
const cacheRetention = requested ?? configuredRetention;
|
|
81248
|
+
return base(model, context, {
|
|
81249
|
+
...options,
|
|
81250
|
+
...cacheRetention === void 0 ? {} : { cacheRetention }
|
|
81251
|
+
});
|
|
81252
|
+
};
|
|
80911
81253
|
}
|
|
80912
81254
|
|
|
80913
81255
|
// src/runtime/guard-advisory-context.ts
|
|
@@ -80931,7 +81273,7 @@ function findLatestUserIndex(messages) {
|
|
|
80931
81273
|
function applyRuntimeRequestTransform(messages, options) {
|
|
80932
81274
|
const advisory = options.takeAdvisory();
|
|
80933
81275
|
let next = advisory ? injectGuardAdvisory(messages, advisory) : stripGuardAdvisories(messages);
|
|
80934
|
-
const retryBlock = options.takeRetryBlock();
|
|
81276
|
+
const retryBlock = options.takeRetryBlock(next);
|
|
80935
81277
|
if (retryBlock) next = refreshRuntimeModeBlockOnLastUserMessage(next, retryBlock);
|
|
80936
81278
|
return next;
|
|
80937
81279
|
}
|
|
@@ -81814,9 +82156,12 @@ async function loadInteractiveExtensions(host) {
|
|
|
81814
82156
|
const activeTools = [...host.agent.state.tools, ...extensionTools];
|
|
81815
82157
|
host.agent.state.tools = wrapToolsWithExtensions(activeTools, host.extensionRunner);
|
|
81816
82158
|
const availableTools = [
|
|
81817
|
-
|
|
82159
|
+
// Prefer the pristine (extension-unwrapped) assembly; re-deriving from
|
|
82160
|
+
// already extension-wrapped `allTools` would nest interceptors.
|
|
82161
|
+
...host.pristineTools && host.pristineTools.length > 0 ? host.pristineTools : host.allTools.length > 0 ? host.allTools : host.originalTools.length > 0 ? host.originalTools : host.agent.state.tools,
|
|
81818
82162
|
...extensionTools
|
|
81819
82163
|
];
|
|
82164
|
+
host.pristineTools = [...availableTools];
|
|
81820
82165
|
host.allTools = wrapToolsWithExtensions(availableTools, host.extensionRunner);
|
|
81821
82166
|
host.originalTools = [...host.allTools];
|
|
81822
82167
|
if (host.options.compositionTrace) {
|
|
@@ -81899,6 +82244,8 @@ var InteractiveMode = class {
|
|
|
81899
82244
|
mentionPickerOptions = [];
|
|
81900
82245
|
attachmentResolver;
|
|
81901
82246
|
yoloMode = false;
|
|
82247
|
+
pristineTools = [];
|
|
82248
|
+
// Pristine (extension-unwrapped) tool assembly: the mode-rebuild source.
|
|
81902
82249
|
/** Calm mode: render only questions and answers (display-only; persisted). */
|
|
81903
82250
|
calmMode = false;
|
|
81904
82251
|
originalTools = [];
|
|
@@ -82064,7 +82411,7 @@ var InteractiveMode = class {
|
|
|
82064
82411
|
const preservedTools = sourceTools.filter(
|
|
82065
82412
|
(tool) => !CLI_FILESYSTEM_TOOL_NAMES.includes(tool.name) && tool.name !== "bash"
|
|
82066
82413
|
);
|
|
82067
|
-
const bashTool = createBashTool(this.options.cwd, { isYoloMode: () => this.yoloMode });
|
|
82414
|
+
const bashTool = createBashTool(this.options.cwd, { isYoloMode: () => this.yoloMode, getEnv: () => computerUseOwnerEnv(this.sessionManager.getActiveSessionId() || COMPUTER_USE_STANDALONE_OWNER, String(process.pid)) });
|
|
82068
82415
|
const fileSystemToolOptions = (allowlistedDirs) => ({
|
|
82069
82416
|
...buildCliFileAccessOptions({
|
|
82070
82417
|
cwd: this.options.cwd,
|
|
@@ -82134,7 +82481,7 @@ var InteractiveMode = class {
|
|
|
82134
82481
|
}
|
|
82135
82482
|
applyRuntimeToolMode(sourceTools) {
|
|
82136
82483
|
if (!this.agent) return;
|
|
82137
|
-
const completeToolSet = sourceTools ?? (this.
|
|
82484
|
+
const completeToolSet = sourceTools ?? ((this.pristineTools?.length ?? 0) > 0 ? this.pristineTools : this.allTools) ?? this.agent.state.tools;
|
|
82138
82485
|
const rebuilt = this.rebuildSkillAwareTools(completeToolSet);
|
|
82139
82486
|
const currentTools = this.extensionRunner ? wrapToolsWithExtensions(rebuilt.currentTools, this.extensionRunner) : rebuilt.currentTools;
|
|
82140
82487
|
const originalTools = this.extensionRunner ? wrapToolsWithExtensions(rebuilt.originalTools, this.extensionRunner) : rebuilt.originalTools;
|
|
@@ -82156,6 +82503,7 @@ var InteractiveMode = class {
|
|
|
82156
82503
|
});
|
|
82157
82504
|
}
|
|
82158
82505
|
noteRuntimeModeChanged(trigger) {
|
|
82506
|
+
this.runtimeModeBlocks?.armRefresh();
|
|
82159
82507
|
const state = this.getRuntimeModeState();
|
|
82160
82508
|
this.sessionTrace.noteRuntimeEvent("runtime_mode_changed", {
|
|
82161
82509
|
trigger,
|
|
@@ -82214,7 +82562,7 @@ var InteractiveMode = class {
|
|
|
82214
82562
|
async init() {
|
|
82215
82563
|
const activeSession = this.sessionManager.getActiveSession();
|
|
82216
82564
|
this.thinkingLevel = resolveInitialThinkingLevel({ session: activeSession, settingsManager: this.options.settingsManager });
|
|
82217
|
-
const { Agent } = await import("./chunks/src-
|
|
82565
|
+
const { Agent } = await import("./chunks/src-PRKTGADX.js");
|
|
82218
82566
|
this.agent = new Agent({
|
|
82219
82567
|
initialState: {
|
|
82220
82568
|
systemPrompt: this.buildSystemPrompt(),
|
|
@@ -82224,14 +82572,14 @@ var InteractiveMode = class {
|
|
|
82224
82572
|
},
|
|
82225
82573
|
apiKey: this.options.apiKey,
|
|
82226
82574
|
sessionId: activeSession?.id,
|
|
82227
|
-
streamFn: createCacheRetentionStreamFn(this.options.streamFn),
|
|
82575
|
+
streamFn: createTransportDiagnosticsStreamFn(createCacheRetentionStreamFn(this.options.streamFn, () => this.options.settingsManager.getPromptCacheRetention()), createTraceTransportSink((type, meta) => this.sessionTrace.noteRuntimeEvent(type, meta))),
|
|
82228
82576
|
transformContext: async (messages) => applyRuntimeRequestTransform(messages, {
|
|
82229
82577
|
takeAdvisory: () => {
|
|
82230
82578
|
const advisory = this.pendingRuntimeGuardAdvisory;
|
|
82231
82579
|
this.pendingRuntimeGuardAdvisory = null;
|
|
82232
82580
|
return advisory;
|
|
82233
82581
|
},
|
|
82234
|
-
takeRetryBlock: () => this.runtimeModeBlocks.consumeRetryRefreshBlock()
|
|
82582
|
+
takeRetryBlock: (snapshot) => this.runtimeModeBlocks.consumeRetryRefreshBlock(snapshot)
|
|
82235
82583
|
})
|
|
82236
82584
|
});
|
|
82237
82585
|
this.agentSessionController = createInteractiveAgentSessionController(this.controllerSetupHost);
|
|
@@ -82324,6 +82672,7 @@ var InteractiveMode = class {
|
|
|
82324
82672
|
}
|
|
82325
82673
|
this.allTools = [...this.options.allTools];
|
|
82326
82674
|
this.originalTools = [...this.options.allTools];
|
|
82675
|
+
this.pristineTools = [...this.options.allTools];
|
|
82327
82676
|
this.agent.state.tools = [...this.options.allTools];
|
|
82328
82677
|
await this.extensionRunner?.dispose("reload");
|
|
82329
82678
|
this.extensionWidgets?.clearAll();
|
|
@@ -82620,6 +82969,7 @@ var InteractiveMode = class {
|
|
|
82620
82969
|
|
|
82621
82970
|
// src/app/runtime-composition.ts
|
|
82622
82971
|
import { existsSync as existsSync18, mkdirSync as mkdirSync13 } from "fs";
|
|
82972
|
+
import { randomUUID } from "crypto";
|
|
82623
82973
|
import * as path31 from "path";
|
|
82624
82974
|
var CliMissingApiKeyError = class extends Error {
|
|
82625
82975
|
constructor(message) {
|
|
@@ -82749,6 +83099,7 @@ async function composeCliRuntime(params) {
|
|
|
82749
83099
|
await sessionManager.save();
|
|
82750
83100
|
}
|
|
82751
83101
|
const sessionId = sessionManager.getActiveSession()?.id;
|
|
83102
|
+
const computerUseExecutionId = randomUUID();
|
|
82752
83103
|
const fileObservationState = createFileObservationState();
|
|
82753
83104
|
if (sessionId) {
|
|
82754
83105
|
if (process.env.PIE_DEBUG && !fileLogger.isEnabled()) {
|
|
@@ -82777,7 +83128,8 @@ async function composeCliRuntime(params) {
|
|
|
82777
83128
|
getWebSearchMode: () => settingsManager.getWebSearchMode(),
|
|
82778
83129
|
resolveToolModel: (purpose) => modelRegistry.resolveToolModel(purpose, getCurrentModel()),
|
|
82779
83130
|
resolveToolModelCandidates: (purpose) => modelRegistry.resolveToolModelCandidates(purpose, getCurrentModel()),
|
|
82780
|
-
configDir: paths.configDir
|
|
83131
|
+
configDir: paths.configDir,
|
|
83132
|
+
getBashEnv: () => computerUseOwnerEnv(sessionManager.getActiveSessionId() || COMPUTER_USE_STANDALONE_OWNER, computerUseExecutionId)
|
|
82781
83133
|
});
|
|
82782
83134
|
const fileSystemToolOptions = {
|
|
82783
83135
|
...buildCliFileAccessOptions({ cwd, configDir: paths.configDir, skills, allowlistedDirs: [paths.configDir] }),
|
|
@@ -82905,6 +83257,38 @@ function createPrintModeRetryStatusReporter() {
|
|
|
82905
83257
|
};
|
|
82906
83258
|
}
|
|
82907
83259
|
|
|
83260
|
+
// src/app/print-mode-compaction.ts
|
|
83261
|
+
function createPrintModeCompactionHandler(params) {
|
|
83262
|
+
return {
|
|
83263
|
+
compact: async (context) => {
|
|
83264
|
+
const beforeCompact = await params.runner.emitSessionBeforeCompact({
|
|
83265
|
+
type: "session:before_compact",
|
|
83266
|
+
reason: context.reason === "overflow" ? "overflow" : "threshold",
|
|
83267
|
+
messageCount: context.messages.length
|
|
83268
|
+
});
|
|
83269
|
+
if (beforeCompact.cancel) return { aborted: true };
|
|
83270
|
+
if (beforeCompact.summary) {
|
|
83271
|
+
const retainedTail = context.preparation?.retainedTail.retainedTail ?? (() => {
|
|
83272
|
+
const legacyCutId = findFirstKeptEntrySummaryId(context.sessionManager.getActiveContextSummaries());
|
|
83273
|
+
return legacyCutId ? { kind: "from-entry", entryId: legacyCutId } : void 0;
|
|
83274
|
+
})();
|
|
83275
|
+
if (!retainedTail) return { aborted: true };
|
|
83276
|
+
return {
|
|
83277
|
+
summary: beforeCompact.summary,
|
|
83278
|
+
retainedTail,
|
|
83279
|
+
...retainedTail.kind === "from-entry" ? { firstKeptEntryId: retainedTail.entryId } : {}
|
|
83280
|
+
};
|
|
83281
|
+
}
|
|
83282
|
+
return createCliAutoCompactionResult({
|
|
83283
|
+
context,
|
|
83284
|
+
model: params.model,
|
|
83285
|
+
apiKey: params.apiKey,
|
|
83286
|
+
systemPrompt: params.systemPrompt
|
|
83287
|
+
});
|
|
83288
|
+
}
|
|
83289
|
+
};
|
|
83290
|
+
}
|
|
83291
|
+
|
|
82908
83292
|
// src/app/print-mode.ts
|
|
82909
83293
|
function createNoOpExtensionUIContext() {
|
|
82910
83294
|
return {
|
|
@@ -83036,7 +83420,7 @@ async function runPrintMode(params) {
|
|
|
83036
83420
|
`);
|
|
83037
83421
|
console.log("Assistant: ");
|
|
83038
83422
|
}
|
|
83039
|
-
const { Agent: AgentClass } = await import("./chunks/src-
|
|
83423
|
+
const { Agent: AgentClass } = await import("./chunks/src-PRKTGADX.js");
|
|
83040
83424
|
let agent;
|
|
83041
83425
|
const printModeExtensions = await loadPrintModeExtensions({
|
|
83042
83426
|
cwd: runtime.cwd,
|
|
@@ -83080,7 +83464,8 @@ async function runPrintMode(params) {
|
|
|
83080
83464
|
thinkingLevel: printThinkingLevel
|
|
83081
83465
|
},
|
|
83082
83466
|
apiKey: runtime.apiKey,
|
|
83083
|
-
|
|
83467
|
+
// Body-free transport timeline for the main (print-mode) agent.
|
|
83468
|
+
streamFn: createTransportDiagnosticsStreamFn(params.streamFn ?? streamSimple, logTransportLifecycle)
|
|
83084
83469
|
});
|
|
83085
83470
|
const sessionTrace = new SessionTraceWriter(runtime.paths.sessionsDir, runtime.sessionManager);
|
|
83086
83471
|
const reportRetryStatus = createPrintModeRetryStatusReporter();
|
|
@@ -83114,28 +83499,16 @@ async function runPrintMode(params) {
|
|
|
83114
83499
|
latestCompactionTimestamp: runtime.sessionManager.getLatestCompactionTimestamp(),
|
|
83115
83500
|
isContextOverflowError: isCliContextOverflowError
|
|
83116
83501
|
}),
|
|
83117
|
-
|
|
83118
|
-
|
|
83119
|
-
|
|
83120
|
-
|
|
83121
|
-
|
|
83122
|
-
|
|
83123
|
-
|
|
83124
|
-
|
|
83125
|
-
|
|
83126
|
-
|
|
83127
|
-
const firstKeptEntryId = activeEntryId ? findFirstKeptEntrySummaryId(context.sessionManager.getActiveContextSummaries()) : void 0;
|
|
83128
|
-
if (!firstKeptEntryId) return { aborted: true };
|
|
83129
|
-
return { summary: beforeCompact.summary, firstKeptEntryId };
|
|
83130
|
-
}
|
|
83131
|
-
return createCliAutoCompactionResult({
|
|
83132
|
-
context,
|
|
83133
|
-
model: runtime.model,
|
|
83134
|
-
apiKey: runtime.apiKey,
|
|
83135
|
-
systemPrompt: agent?.state.systemPrompt ?? baseSystemPrompt
|
|
83136
|
-
});
|
|
83137
|
-
}
|
|
83138
|
-
},
|
|
83502
|
+
getCompactionBudgetTokens: createCliCompactionBudget({
|
|
83503
|
+
contextWindow: runtime.model.contextWindow,
|
|
83504
|
+
reserveTokens: runtime.settingsManager.getAutoCompactReserveTokens()
|
|
83505
|
+
}),
|
|
83506
|
+
compaction: createPrintModeCompactionHandler({
|
|
83507
|
+
runner: printModeExtensions.runner,
|
|
83508
|
+
model: runtime.model,
|
|
83509
|
+
apiKey: runtime.apiKey,
|
|
83510
|
+
systemPrompt: agent?.state.systemPrompt ?? baseSystemPrompt
|
|
83511
|
+
}),
|
|
83139
83512
|
classifyFailure: (context) => classifyCliFailure(context),
|
|
83140
83513
|
onEvent: (event) => {
|
|
83141
83514
|
sessionTrace.noteRuntimeEvent(event.type, event);
|
|
@@ -83143,7 +83516,7 @@ async function runPrintMode(params) {
|
|
|
83143
83516
|
console.error(event.failure.kind === "context_overflow" ? "Context overflow detected, compacting..." : "Auto-compacting context before retry...");
|
|
83144
83517
|
} else if (event.type === "auto_compaction_start") {
|
|
83145
83518
|
console.error(event.reason === "overflow" ? "Context overflow detected, compacting..." : "Auto-compacting context...");
|
|
83146
|
-
} else if (event.type === "
|
|
83519
|
+
} else if (event.type === "compaction_committed") {
|
|
83147
83520
|
runtime.fileObservationState.clear();
|
|
83148
83521
|
} else {
|
|
83149
83522
|
reportRetryStatus(event);
|
|
@@ -83497,6 +83870,9 @@ async function loadJsonModeExtensions(params) {
|
|
|
83497
83870
|
extensionCount: extensions.length
|
|
83498
83871
|
};
|
|
83499
83872
|
}
|
|
83873
|
+
function createJsonEventsTransportStreamFn(streamFn) {
|
|
83874
|
+
return createTransportDiagnosticsStreamFn(streamFn ?? streamSimple, logTransportLifecycle);
|
|
83875
|
+
}
|
|
83500
83876
|
async function runJsonEventsMode(params) {
|
|
83501
83877
|
const eventDetail = params.eventDetail === FULL_DETAIL ? FULL_DETAIL : COMPACT_DETAIL;
|
|
83502
83878
|
const eventStringCap = eventDetail === FULL_DETAIL ? MAX_EVENT_STRING_LENGTH : COMPACT_EVENT_STRING_LENGTH;
|
|
@@ -83897,7 +84273,7 @@ async function runJsonEventsMode(params) {
|
|
|
83897
84273
|
return;
|
|
83898
84274
|
}
|
|
83899
84275
|
const parent = agent;
|
|
83900
|
-
const { Agent: AgentClass } = await import("./chunks/src-
|
|
84276
|
+
const { Agent: AgentClass } = await import("./chunks/src-PRKTGADX.js");
|
|
83901
84277
|
const sideAgent = new AgentClass({
|
|
83902
84278
|
initialState: {
|
|
83903
84279
|
systemPrompt: parent.state.systemPrompt,
|
|
@@ -83907,7 +84283,11 @@ async function runJsonEventsMode(params) {
|
|
|
83907
84283
|
messages: structuredClone(parent.state.messages)
|
|
83908
84284
|
},
|
|
83909
84285
|
apiKey: runtime.apiKey,
|
|
83910
|
-
|
|
84286
|
+
// Same body-free transport timeline as the main agent: a sidechat is
|
|
84287
|
+
// an independent Responses request and previously had no record at all
|
|
84288
|
+
// when it stalled. `streamSimple` matches the host default when the
|
|
84289
|
+
// caller injected no stream function.
|
|
84290
|
+
streamFn: createJsonEventsTransportStreamFn(params.streamFn)
|
|
83911
84291
|
});
|
|
83912
84292
|
sidechatController.signal.addEventListener("abort", () => sideAgent.abort(), { once: true });
|
|
83913
84293
|
const timer = setTimeout(() => {
|
|
@@ -84065,7 +84445,7 @@ async function runJsonEventsMode(params) {
|
|
|
84065
84445
|
}
|
|
84066
84446
|
function handleControllerEvent(event) {
|
|
84067
84447
|
trace?.noteRuntimeEvent(event.type, event);
|
|
84068
|
-
if (event.type === "
|
|
84448
|
+
if (event.type === "compaction_committed") {
|
|
84069
84449
|
runtime?.fileObservationState.clear();
|
|
84070
84450
|
}
|
|
84071
84451
|
if (event.type === "turn_settled" && activeTurn) {
|
|
@@ -84241,7 +84621,7 @@ async function runJsonEventsMode(params) {
|
|
|
84241
84621
|
if (runtime.initialModel.unconfigured || controller) {
|
|
84242
84622
|
return;
|
|
84243
84623
|
}
|
|
84244
|
-
const { Agent: AgentClass } = await import("./chunks/src-
|
|
84624
|
+
const { Agent: AgentClass } = await import("./chunks/src-PRKTGADX.js");
|
|
84245
84625
|
const jsonModeExtensions = await loadJsonModeExtensions({ runtime, getAgent: () => agent });
|
|
84246
84626
|
extensionRunner = jsonModeExtensions.runner;
|
|
84247
84627
|
const tools = [...runtime.tools, ...jsonModeExtensions.extensionTools];
|
|
@@ -84273,7 +84653,8 @@ async function runJsonEventsMode(params) {
|
|
|
84273
84653
|
thinkingLevel
|
|
84274
84654
|
},
|
|
84275
84655
|
apiKey: runtime.apiKey,
|
|
84276
|
-
|
|
84656
|
+
// Body-free transport timeline for the main (JSON-events) agent.
|
|
84657
|
+
streamFn: createJsonEventsTransportStreamFn(params.streamFn)
|
|
84277
84658
|
});
|
|
84278
84659
|
controller = new AgentSessionController({
|
|
84279
84660
|
agent,
|
|
@@ -84302,6 +84683,10 @@ async function runJsonEventsMode(params) {
|
|
|
84302
84683
|
latestCompactionTimestamp: runtime.sessionManager.getLatestCompactionTimestamp(),
|
|
84303
84684
|
isContextOverflowError: isCliContextOverflowError
|
|
84304
84685
|
}),
|
|
84686
|
+
getCompactionBudgetTokens: createCliCompactionBudget({
|
|
84687
|
+
contextWindow: runtime.model.contextWindow,
|
|
84688
|
+
reserveTokens: runtime.settingsManager.getAutoCompactReserveTokens()
|
|
84689
|
+
}),
|
|
84305
84690
|
compaction: {
|
|
84306
84691
|
compact: async (context) => createCliAutoCompactionResult({
|
|
84307
84692
|
context,
|
|
@@ -84835,7 +85220,7 @@ async function runWithJsonEventsConsoleIsolation(fn) {
|
|
|
84835
85220
|
}
|
|
84836
85221
|
async function createCliTestStreamFnFromEnv() {
|
|
84837
85222
|
if (!process.env.PIE_TEST_MOCK_STREAM_SEQUENCE) return void 0;
|
|
84838
|
-
return (await import("./chunks/test-stream-
|
|
85223
|
+
return (await import("./chunks/test-stream-BGAEVPRX.js")).createTestStreamFnFromSequenceEnv();
|
|
84839
85224
|
}
|
|
84840
85225
|
function resolveJsonEventsDetailFlag() {
|
|
84841
85226
|
for (let index = 0; index < process.argv.length; index += 1) {
|