@tuanhung303/opencode-acp 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (159) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +166 -0
  3. package/dist/index.d.ts +4 -0
  4. package/dist/index.d.ts.map +1 -0
  5. package/dist/index.js +79 -0
  6. package/dist/index.js.map +1 -0
  7. package/dist/lib/commands/budget.d.ts +15 -0
  8. package/dist/lib/commands/budget.d.ts.map +1 -0
  9. package/dist/lib/commands/budget.js +120 -0
  10. package/dist/lib/commands/budget.js.map +1 -0
  11. package/dist/lib/commands/context.d.ts +49 -0
  12. package/dist/lib/commands/context.d.ts.map +1 -0
  13. package/dist/lib/commands/context.js +191 -0
  14. package/dist/lib/commands/context.js.map +1 -0
  15. package/dist/lib/commands/help.d.ts +15 -0
  16. package/dist/lib/commands/help.d.ts.map +1 -0
  17. package/dist/lib/commands/help.js +28 -0
  18. package/dist/lib/commands/help.js.map +1 -0
  19. package/dist/lib/commands/protected.d.ts +17 -0
  20. package/dist/lib/commands/protected.d.ts.map +1 -0
  21. package/dist/lib/commands/protected.js +50 -0
  22. package/dist/lib/commands/protected.js.map +1 -0
  23. package/dist/lib/commands/stats.d.ts +15 -0
  24. package/dist/lib/commands/stats.d.ts.map +1 -0
  25. package/dist/lib/commands/stats.js +64 -0
  26. package/dist/lib/commands/stats.js.map +1 -0
  27. package/dist/lib/commands/sweep.d.ts +23 -0
  28. package/dist/lib/commands/sweep.d.ts.map +1 -0
  29. package/dist/lib/commands/sweep.js +194 -0
  30. package/dist/lib/commands/sweep.js.map +1 -0
  31. package/dist/lib/config-schema.d.ts +119 -0
  32. package/dist/lib/config-schema.d.ts.map +1 -0
  33. package/dist/lib/config-schema.js +97 -0
  34. package/dist/lib/config-schema.js.map +1 -0
  35. package/dist/lib/config.d.ts +59 -0
  36. package/dist/lib/config.d.ts.map +1 -0
  37. package/dist/lib/config.js +426 -0
  38. package/dist/lib/config.js.map +1 -0
  39. package/dist/lib/hooks.d.ts +31 -0
  40. package/dist/lib/hooks.d.ts.map +1 -0
  41. package/dist/lib/hooks.js +230 -0
  42. package/dist/lib/hooks.js.map +1 -0
  43. package/dist/lib/logger.d.ts +55 -0
  44. package/dist/lib/logger.d.ts.map +1 -0
  45. package/dist/lib/logger.js +230 -0
  46. package/dist/lib/logger.js.map +1 -0
  47. package/dist/lib/messages/index.d.ts +3 -0
  48. package/dist/lib/messages/index.d.ts.map +1 -0
  49. package/dist/lib/messages/index.js +3 -0
  50. package/dist/lib/messages/index.js.map +1 -0
  51. package/dist/lib/messages/inject.d.ts +10 -0
  52. package/dist/lib/messages/inject.d.ts.map +1 -0
  53. package/dist/lib/messages/inject.js +10 -0
  54. package/dist/lib/messages/inject.js.map +1 -0
  55. package/dist/lib/messages/prune.d.ts +13 -0
  56. package/dist/lib/messages/prune.d.ts.map +1 -0
  57. package/dist/lib/messages/prune.js +173 -0
  58. package/dist/lib/messages/prune.js.map +1 -0
  59. package/dist/lib/messages/utils.d.ts +43 -0
  60. package/dist/lib/messages/utils.d.ts.map +1 -0
  61. package/dist/lib/messages/utils.js +262 -0
  62. package/dist/lib/messages/utils.js.map +1 -0
  63. package/dist/lib/prompts/discard-tool-spec.d.ts +2 -0
  64. package/dist/lib/prompts/discard-tool-spec.d.ts.map +1 -0
  65. package/dist/lib/prompts/discard-tool-spec.js +54 -0
  66. package/dist/lib/prompts/discard-tool-spec.js.map +1 -0
  67. package/dist/lib/prompts/extract-tool-spec.d.ts +2 -0
  68. package/dist/lib/prompts/extract-tool-spec.d.ts.map +1 -0
  69. package/dist/lib/prompts/extract-tool-spec.js +56 -0
  70. package/dist/lib/prompts/extract-tool-spec.js.map +1 -0
  71. package/dist/lib/prompts/index.d.ts +2 -0
  72. package/dist/lib/prompts/index.d.ts.map +1 -0
  73. package/dist/lib/prompts/index.js +29 -0
  74. package/dist/lib/prompts/index.js.map +1 -0
  75. package/dist/lib/prompts/restore-tool-spec.d.ts +2 -0
  76. package/dist/lib/prompts/restore-tool-spec.d.ts.map +1 -0
  77. package/dist/lib/prompts/restore-tool-spec.js +37 -0
  78. package/dist/lib/prompts/restore-tool-spec.js.map +1 -0
  79. package/dist/lib/prompts/system/both.d.ts +2 -0
  80. package/dist/lib/prompts/system/both.d.ts.map +1 -0
  81. package/dist/lib/prompts/system/both.js +65 -0
  82. package/dist/lib/prompts/system/both.js.map +1 -0
  83. package/dist/lib/prompts/system/discard.d.ts +2 -0
  84. package/dist/lib/prompts/system/discard.d.ts.map +1 -0
  85. package/dist/lib/prompts/system/discard.js +55 -0
  86. package/dist/lib/prompts/system/discard.js.map +1 -0
  87. package/dist/lib/prompts/system/extract.d.ts +2 -0
  88. package/dist/lib/prompts/system/extract.d.ts.map +1 -0
  89. package/dist/lib/prompts/system/extract.js +55 -0
  90. package/dist/lib/prompts/system/extract.js.map +1 -0
  91. package/dist/lib/protected-file-patterns.d.ts +12 -0
  92. package/dist/lib/protected-file-patterns.d.ts.map +1 -0
  93. package/dist/lib/protected-file-patterns.js +69 -0
  94. package/dist/lib/protected-file-patterns.js.map +1 -0
  95. package/dist/lib/safe-execute.d.ts +20 -0
  96. package/dist/lib/safe-execute.d.ts.map +1 -0
  97. package/dist/lib/safe-execute.js +38 -0
  98. package/dist/lib/safe-execute.js.map +1 -0
  99. package/dist/lib/shared-utils.d.ts +4 -0
  100. package/dist/lib/shared-utils.d.ts.map +1 -0
  101. package/dist/lib/shared-utils.js +14 -0
  102. package/dist/lib/shared-utils.js.map +1 -0
  103. package/dist/lib/state/index.d.ts +4 -0
  104. package/dist/lib/state/index.d.ts.map +1 -0
  105. package/dist/lib/state/index.js +4 -0
  106. package/dist/lib/state/index.js.map +1 -0
  107. package/dist/lib/state/persistence.d.ts +27 -0
  108. package/dist/lib/state/persistence.d.ts.map +1 -0
  109. package/dist/lib/state/persistence.js +165 -0
  110. package/dist/lib/state/persistence.js.map +1 -0
  111. package/dist/lib/state/state.d.ts +8 -0
  112. package/dist/lib/state/state.d.ts.map +1 -0
  113. package/dist/lib/state/state.js +166 -0
  114. package/dist/lib/state/state.js.map +1 -0
  115. package/dist/lib/state/tool-cache.d.ts +15 -0
  116. package/dist/lib/state/tool-cache.d.ts.map +1 -0
  117. package/dist/lib/state/tool-cache.js +99 -0
  118. package/dist/lib/state/tool-cache.js.map +1 -0
  119. package/dist/lib/state/types.d.ts +83 -0
  120. package/dist/lib/state/types.d.ts.map +1 -0
  121. package/dist/lib/state/types.js +2 -0
  122. package/dist/lib/state/types.js.map +1 -0
  123. package/dist/lib/state/utils.d.ts +2 -0
  124. package/dist/lib/state/utils.d.ts.map +1 -0
  125. package/dist/lib/state/utils.js +10 -0
  126. package/dist/lib/state/utils.js.map +1 -0
  127. package/dist/lib/strategies/deduplication.d.ts +11 -0
  128. package/dist/lib/strategies/deduplication.d.ts.map +1 -0
  129. package/dist/lib/strategies/deduplication.js +178 -0
  130. package/dist/lib/strategies/deduplication.js.map +1 -0
  131. package/dist/lib/strategies/index.d.ts +5 -0
  132. package/dist/lib/strategies/index.d.ts.map +1 -0
  133. package/dist/lib/strategies/index.js +5 -0
  134. package/dist/lib/strategies/index.js.map +1 -0
  135. package/dist/lib/strategies/purge-errors.d.ts +13 -0
  136. package/dist/lib/strategies/purge-errors.d.ts.map +1 -0
  137. package/dist/lib/strategies/purge-errors.js +62 -0
  138. package/dist/lib/strategies/purge-errors.js.map +1 -0
  139. package/dist/lib/strategies/supersede-writes.d.ts +13 -0
  140. package/dist/lib/strategies/supersede-writes.d.ts.map +1 -0
  141. package/dist/lib/strategies/supersede-writes.js +90 -0
  142. package/dist/lib/strategies/supersede-writes.js.map +1 -0
  143. package/dist/lib/strategies/tools.d.ts +15 -0
  144. package/dist/lib/strategies/tools.d.ts.map +1 -0
  145. package/dist/lib/strategies/tools.js +288 -0
  146. package/dist/lib/strategies/tools.js.map +1 -0
  147. package/dist/lib/strategies/utils.d.ts +11 -0
  148. package/dist/lib/strategies/utils.d.ts.map +1 -0
  149. package/dist/lib/strategies/utils.js +75 -0
  150. package/dist/lib/strategies/utils.js.map +1 -0
  151. package/dist/lib/ui/notification.d.ts +12 -0
  152. package/dist/lib/ui/notification.d.ts.map +1 -0
  153. package/dist/lib/ui/notification.js +81 -0
  154. package/dist/lib/ui/notification.js.map +1 -0
  155. package/dist/lib/ui/utils.d.ts +10 -0
  156. package/dist/lib/ui/utils.d.ts.map +1 -0
  157. package/dist/lib/ui/utils.js +113 -0
  158. package/dist/lib/ui/utils.js.map +1 -0
  159. package/package.json +62 -0
@@ -0,0 +1,288 @@
1
+ import { tool } from "@opencode-ai/plugin";
2
+ import { sendUnifiedNotification } from "../ui/notification";
3
+ import { formatPruningResultForTool } from "../ui/utils";
4
+ import { ensureSessionInitialized } from "../state";
5
+ import { saveSessionState } from "../state/persistence";
6
+ import { loadPrompt } from "../prompts";
7
+ import { calculateTokensSaved, getCurrentParams } from "./utils";
8
+ import { getFilePathFromParameters, isProtectedFilePath } from "../protected-file-patterns";
9
+ const DISCARD_TOOL_DESCRIPTION = loadPrompt("discard-tool-spec");
10
+ const EXTRACT_TOOL_DESCRIPTION = loadPrompt("extract-tool-spec");
11
+ const RESTORE_TOOL_DESCRIPTION = loadPrompt("restore-tool-spec");
12
+ /**
13
+ * Execute a prune operation using call IDs directly.
14
+ * This is the hash-based version that works with resolved call IDs.
15
+ */
16
+ async function executePruneOperationByCallIds(ctx, toolCtx, callIds, hashes, reason, toolName, distillation) {
17
+ const { client, state, logger, config, workingDirectory } = ctx;
18
+ const sessionId = toolCtx.sessionID;
19
+ logger.info(`${toolName} tool invoked`);
20
+ logger.info(JSON.stringify({ hashes, reason }));
21
+ if (!callIds || callIds.length === 0) {
22
+ logger.debug(`${toolName} tool called but no valid call IDs resolved`);
23
+ throw new Error(`No valid hashes provided. Use hashes from tool outputs (e.g., #r_a1b2c#).`);
24
+ }
25
+ // Fetch messages to calculate tokens
26
+ const messagesResponse = await client.session.messages({
27
+ path: { id: sessionId },
28
+ });
29
+ const messages = messagesResponse.data || messagesResponse;
30
+ await ensureSessionInitialized(ctx.client, state, sessionId, logger, messages);
31
+ const currentParams = getCurrentParams(state, messages, logger);
32
+ // Validate that all call IDs exist in cache and aren't protected
33
+ for (const callId of callIds) {
34
+ const metadata = state.toolParameters.get(callId);
35
+ if (!metadata) {
36
+ const hash = state.callIdToHash.get(callId) || "unknown";
37
+ logger.debug("Rejecting prune request - call ID not in cache", { callId, hash });
38
+ throw new Error(`Invalid hash provided. The tool may have already been discarded.`);
39
+ }
40
+ const allProtectedTools = config.tools.settings.protectedTools;
41
+ if (allProtectedTools.includes(metadata.tool)) {
42
+ const hash = state.callIdToHash.get(callId) || "unknown";
43
+ logger.debug("Rejecting prune request - protected tool", {
44
+ callId,
45
+ hash,
46
+ tool: metadata.tool,
47
+ });
48
+ throw new Error(`Cannot discard: '${metadata.tool}' is a protected tool.\n` +
49
+ `Protected tools: ${allProtectedTools.join(", ")}\n` +
50
+ `To modify protection, update 'tools.settings.protectedTools' in your ACP config.`);
51
+ }
52
+ const filePath = getFilePathFromParameters(metadata.parameters);
53
+ if (isProtectedFilePath(filePath, config.protectedFilePatterns)) {
54
+ const hash = state.callIdToHash.get(callId) || "unknown";
55
+ logger.debug("Rejecting prune request - protected file path", {
56
+ callId,
57
+ hash,
58
+ tool: metadata.tool,
59
+ filePath,
60
+ });
61
+ const protectedPatterns = config.protectedFilePatterns.length > 0
62
+ ? `\nProtected patterns: ${config.protectedFilePatterns.join(", ")}`
63
+ : "";
64
+ throw new Error(`Cannot discard: ${filePath} is a protected file path.${protectedPatterns}\n` +
65
+ `To modify protection, update 'protectedFilePatterns' in your ACP config.`);
66
+ }
67
+ }
68
+ // Add to prune list
69
+ state.prune.toolIds.push(...callIds);
70
+ // Collect metadata for notification
71
+ const toolMetadata = new Map();
72
+ for (const callId of callIds) {
73
+ const toolParameters = state.toolParameters.get(callId);
74
+ if (toolParameters) {
75
+ toolMetadata.set(callId, toolParameters);
76
+ }
77
+ else {
78
+ logger.debug("No metadata found for call ID", { callId });
79
+ }
80
+ }
81
+ // Calculate token savings
82
+ const tokensSaved = calculateTokensSaved(state, messages, callIds);
83
+ state.stats.pruneTokenCounter += tokensSaved;
84
+ state.stats.pruneMessageCounter += callIds.length;
85
+ // Track strategy effectiveness
86
+ if (toolName === "Discard") {
87
+ state.stats.strategyStats.manualDiscard.count += callIds.length;
88
+ state.stats.strategyStats.manualDiscard.tokens += tokensSaved;
89
+ }
90
+ else if (toolName === "Extract") {
91
+ state.stats.strategyStats.extraction.count += callIds.length;
92
+ state.stats.strategyStats.extraction.tokens += tokensSaved;
93
+ }
94
+ // Store stats for display
95
+ state.lastDiscardStats = {
96
+ itemCount: callIds.length,
97
+ tokensSaved: state.stats.pruneTokenCounter,
98
+ };
99
+ // Record in discard history
100
+ state.discardHistory.push({
101
+ timestamp: Date.now(),
102
+ hashes,
103
+ tokensSaved,
104
+ reason,
105
+ });
106
+ await sendUnifiedNotification(client, logger, config, state, sessionId, callIds, toolMetadata, reason, currentParams, workingDirectory, distillation);
107
+ state.stats.totalPruneTokens += state.stats.pruneTokenCounter;
108
+ state.stats.pruneTokenCounter = 0;
109
+ state.stats.totalPruneMessages += state.stats.pruneMessageCounter;
110
+ state.stats.pruneMessageCounter = 0;
111
+ saveSessionState(state, logger).catch((err) => logger.error("Failed to persist state", { error: err.message }));
112
+ return formatPruningResultForTool(callIds, toolMetadata, workingDirectory);
113
+ }
114
+ export function createDiscardTool(ctx) {
115
+ return tool({
116
+ description: DISCARD_TOOL_DESCRIPTION,
117
+ args: {
118
+ reason: tool.schema
119
+ .string()
120
+ .describe("Why you're discarding: 'noise' | 'completion' | 'superseded' | 'exploration' | 'duplicate'"),
121
+ hashes: tool.schema
122
+ .array(tool.schema.string())
123
+ .describe("Hash identifiers from tool outputs (e.g., ['#r_a1b2c#', '#g_d4e5f#'])"),
124
+ },
125
+ async execute(args, toolCtx) {
126
+ const { state, logger } = ctx;
127
+ // Validate reason
128
+ const validReasons = [
129
+ "completion",
130
+ "noise",
131
+ "superseded",
132
+ "exploration",
133
+ "duplicate",
134
+ ];
135
+ if (!args.reason || !validReasons.includes(args.reason)) {
136
+ logger.debug("Invalid discard reason provided: " + args.reason);
137
+ throw new Error(`Invalid reason '${args.reason}'. Use one of: ${validReasons.join(", ")}`);
138
+ }
139
+ // Validate hashes provided
140
+ if (!args.hashes || args.hashes.length === 0) {
141
+ throw new Error("No hashes provided. Use hash identifiers from tool outputs (e.g., #r_a1b2c#).");
142
+ }
143
+ // Resolve hashes to call IDs
144
+ const callIds = [];
145
+ const validHashes = [];
146
+ const unknownHashes = [];
147
+ for (const hash of args.hashes) {
148
+ const callId = state.hashToCallId.get(hash);
149
+ if (callId) {
150
+ // Skip if already pruned
151
+ if (!state.prune.toolIds.includes(callId)) {
152
+ callIds.push(callId);
153
+ validHashes.push(hash);
154
+ }
155
+ else {
156
+ logger.debug(`Hash ${hash} already pruned, skipping`);
157
+ }
158
+ }
159
+ else {
160
+ unknownHashes.push(hash);
161
+ logger.warn(`Unknown hash: ${hash}`);
162
+ }
163
+ }
164
+ if (unknownHashes.length > 0 && callIds.length === 0) {
165
+ throw new Error(`Unknown hashes: ${unknownHashes.join(", ")}. Use hash identifiers from tool outputs.`);
166
+ }
167
+ if (callIds.length === 0) {
168
+ throw new Error("No valid hashes to discard. Tools may have already been discarded.");
169
+ }
170
+ logger.info(`Discard: ${validHashes.length} hashes resolved to ${callIds.length} call IDs`);
171
+ return executePruneOperationByCallIds(ctx, toolCtx, callIds, validHashes, args.reason, "Discard");
172
+ },
173
+ });
174
+ }
175
+ export function createExtractTool(ctx) {
176
+ return tool({
177
+ description: EXTRACT_TOOL_DESCRIPTION,
178
+ args: {
179
+ hashes: tool.schema
180
+ .array(tool.schema.string())
181
+ .describe("Hash identifiers from tool outputs (e.g., ['#r_a1b2c#', '#g_d4e5f#'])"),
182
+ distillation: tool.schema
183
+ .array(tool.schema.string())
184
+ .describe("REQUIRED. Array of strings, one per hash (positional: distillation[0] is for hashes[0], etc.)"),
185
+ preserve: tool.schema
186
+ .boolean()
187
+ .optional()
188
+ .describe("Set to true to keep original tool output after extraction. Default: false"),
189
+ },
190
+ async execute(args, toolCtx) {
191
+ const { state, logger } = ctx;
192
+ if (!args.distillation || args.distillation.length === 0) {
193
+ logger.debug("Extract tool called without distillation: " + JSON.stringify(args));
194
+ throw new Error("Missing distillation. You must provide a distillation string for each hash.");
195
+ }
196
+ if (!args.hashes || args.hashes.length === 0) {
197
+ throw new Error("No hashes provided. Use hash identifiers from tool outputs (e.g., #r_a1b2c#).");
198
+ }
199
+ // Resolve hashes to call IDs
200
+ const callIds = [];
201
+ const validHashes = [];
202
+ for (const hash of args.hashes) {
203
+ const callId = state.hashToCallId.get(hash);
204
+ if (callId && !state.prune.toolIds.includes(callId)) {
205
+ callIds.push(callId);
206
+ validHashes.push(hash);
207
+ }
208
+ else {
209
+ logger.warn(`Unknown or already pruned hash: ${hash}`);
210
+ }
211
+ }
212
+ if (callIds.length === 0) {
213
+ throw new Error("No valid hashes to extract. Tools may have already been discarded.");
214
+ }
215
+ // Log the distillation for debugging/analysis
216
+ logger.info("Distillation data received:");
217
+ logger.info(JSON.stringify(args.distillation, null, 2));
218
+ // If preserve is true, don't prune - just return success with distillation
219
+ if (args.preserve) {
220
+ logger.info(`Extract with preserve=true - not pruning ${callIds.length} tools`);
221
+ return `Extracted knowledge from ${callIds.length} tool(s). Original outputs preserved.\n\nDistilled knowledge:\n${args.distillation.map((d, i) => `${i + 1}. ${d}`).join("\n")}`;
222
+ }
223
+ return executePruneOperationByCallIds(ctx, toolCtx, callIds, validHashes, "extraction", "Extract", args.distillation);
224
+ },
225
+ });
226
+ }
227
+ export function createRestoreTool(ctx) {
228
+ return tool({
229
+ description: RESTORE_TOOL_DESCRIPTION,
230
+ args: {
231
+ hashes: tool.schema
232
+ .array(tool.schema.string())
233
+ .describe("Hash identifiers of pruned tools to restore (e.g., ['#r_a1b2c#', '#g_d4e5f#'])"),
234
+ },
235
+ async execute(args, toolCtx) {
236
+ const { state, logger } = ctx;
237
+ const sessionId = toolCtx.sessionID;
238
+ if (!args.hashes || args.hashes.length === 0) {
239
+ throw new Error("No hashes provided. Use hash identifiers from pruned tool outputs (e.g., #r_a1b2c#).");
240
+ }
241
+ // Resolve hashes to call IDs and restore
242
+ const restored = [];
243
+ const notFound = [];
244
+ const notPruned = [];
245
+ for (const hash of args.hashes) {
246
+ const callId = state.hashToCallId.get(hash);
247
+ if (!callId) {
248
+ notFound.push(hash);
249
+ continue;
250
+ }
251
+ // Check if it's in the prune list
252
+ const pruneIndex = state.prune.toolIds.indexOf(callId);
253
+ if (pruneIndex === -1) {
254
+ notPruned.push(hash);
255
+ continue;
256
+ }
257
+ // Remove from prune list (restore)
258
+ state.prune.toolIds.splice(pruneIndex, 1);
259
+ restored.push(hash);
260
+ logger.info(`Restored tool with hash ${hash} (callId: ${callId})`);
261
+ }
262
+ // Build result message
263
+ const lines = [];
264
+ if (restored.length > 0) {
265
+ lines.push(`Restored ${restored.length} tool(s):`);
266
+ for (const hash of restored) {
267
+ lines.push(` โœ“ ${hash}`);
268
+ }
269
+ }
270
+ if (notFound.length > 0) {
271
+ lines.push(`\nNot found (unknown hash):`);
272
+ for (const hash of notFound) {
273
+ lines.push(` โœ— ${hash}`);
274
+ }
275
+ }
276
+ if (notPruned.length > 0) {
277
+ lines.push(`\nNot pruned (already active):`);
278
+ for (const hash of notPruned) {
279
+ lines.push(` โ—‹ ${hash}`);
280
+ }
281
+ }
282
+ // Save state
283
+ saveSessionState(state, logger).catch((err) => logger.error("Failed to persist state", { error: err.message }));
284
+ return lines.join("\n");
285
+ },
286
+ });
287
+ }
288
+ //# sourceMappingURL=tools.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tools.js","sourceRoot":"","sources":["../../../lib/strategies/tools.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,11 @@
1
+ import { SessionState, WithParts } from "../state";
2
+ import { Logger } from "../logger";
3
+ export declare function getCurrentParams(state: SessionState, messages: WithParts[], logger: Logger): {
4
+ providerId: string | undefined;
5
+ modelId: string | undefined;
6
+ agent: string | undefined;
7
+ variant: string | undefined;
8
+ };
9
+ export declare function countTokens(text: string): number;
10
+ export declare const calculateTokensSaved: (state: SessionState, messages: WithParts[], pruneToolIds: string[]) => number;
11
+ //# sourceMappingURL=utils.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../lib/strategies/utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,SAAS,EAAE,MAAM,UAAU,CAAA;AAElD,OAAO,EAAE,MAAM,EAAE,MAAM,WAAW,CAAA;AAIlC,wBAAgB,gBAAgB,CAC5B,KAAK,EAAE,YAAY,EACnB,QAAQ,EAAE,SAAS,EAAE,EACrB,MAAM,EAAE,MAAM,GACf;IACC,UAAU,EAAE,MAAM,GAAG,SAAS,CAAA;IAC9B,OAAO,EAAE,MAAM,GAAG,SAAS,CAAA;IAC3B,KAAK,EAAE,MAAM,GAAG,SAAS,CAAA;IACzB,OAAO,EAAE,MAAM,GAAG,SAAS,CAAA;CAC9B,CAkBA;AAED,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAOhD;AAMD,eAAO,MAAM,oBAAoB,GAC7B,OAAO,YAAY,EACnB,UAAU,SAAS,EAAE,EACrB,cAAc,MAAM,EAAE,KACvB,MAyCF,CAAA"}
@@ -0,0 +1,75 @@
1
+ import { countTokens as anthropicCountTokens } from "@anthropic-ai/tokenizer";
2
+ import { getLastUserMessage, isMessageCompacted } from "../shared-utils";
3
+ export function getCurrentParams(state, messages, logger) {
4
+ const userMsg = getLastUserMessage(messages);
5
+ if (!userMsg) {
6
+ logger.debug("No user message found when determining current params");
7
+ return {
8
+ providerId: undefined,
9
+ modelId: undefined,
10
+ agent: undefined,
11
+ variant: state.variant,
12
+ };
13
+ }
14
+ const userInfo = userMsg.info;
15
+ const agent = userInfo.agent;
16
+ const providerId = userInfo.model.providerID;
17
+ const modelId = userInfo.model.modelID;
18
+ const variant = state.variant ?? userInfo.variant;
19
+ return { providerId, modelId, agent, variant };
20
+ }
21
+ export function countTokens(text) {
22
+ if (!text)
23
+ return 0;
24
+ try {
25
+ return anthropicCountTokens(text);
26
+ }
27
+ catch {
28
+ return Math.round(text.length / 4);
29
+ }
30
+ }
31
+ function estimateTokensBatch(texts) {
32
+ return texts.map(countTokens);
33
+ }
34
+ export const calculateTokensSaved = (state, messages, pruneToolIds) => {
35
+ try {
36
+ const contents = [];
37
+ for (const msg of messages) {
38
+ if (isMessageCompacted(state, msg)) {
39
+ continue;
40
+ }
41
+ const parts = Array.isArray(msg.parts) ? msg.parts : [];
42
+ for (const part of parts) {
43
+ if (part.type !== "tool" || !pruneToolIds.includes(part.callID)) {
44
+ continue;
45
+ }
46
+ if (part.tool === "question") {
47
+ const questions = part.state.input?.questions;
48
+ if (questions !== undefined) {
49
+ const content = typeof questions === "string" ? questions : JSON.stringify(questions);
50
+ contents.push(content);
51
+ }
52
+ continue;
53
+ }
54
+ if (part.state.status === "completed") {
55
+ const content = typeof part.state.output === "string"
56
+ ? part.state.output
57
+ : JSON.stringify(part.state.output);
58
+ contents.push(content);
59
+ }
60
+ else if (part.state.status === "error") {
61
+ const content = typeof part.state.error === "string"
62
+ ? part.state.error
63
+ : JSON.stringify(part.state.error);
64
+ contents.push(content);
65
+ }
66
+ }
67
+ }
68
+ const tokenCounts = estimateTokensBatch(contents);
69
+ return tokenCounts.reduce((sum, count) => sum + count, 0);
70
+ }
71
+ catch (error) {
72
+ return 0;
73
+ }
74
+ };
75
+ //# sourceMappingURL=utils.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"utils.js","sourceRoot":"","sources":["../../../lib/strategies/utils.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,12 @@
1
+ import type { Logger } from "../logger";
2
+ import type { SessionState } from "../state";
3
+ import { ToolParameterEntry } from "../state";
4
+ import { PluginConfig } from "../config";
5
+ export type PruneReason = "completion" | "noise" | "superseded" | "exploration" | "duplicate" | "extraction";
6
+ export declare const PRUNE_REASON_LABELS: Record<PruneReason, string>;
7
+ export interface NotifyOptions {
8
+ simplified?: boolean;
9
+ }
10
+ export declare function sendUnifiedNotification(client: any, logger: Logger, config: PluginConfig, state: SessionState, sessionId: string, pruneToolIds: string[], toolMetadata: Map<string, ToolParameterEntry>, reason: PruneReason | undefined, params: any, workingDirectory: string, distillation?: string[], options?: NotifyOptions): Promise<boolean>;
11
+ export declare function sendIgnoredMessage(client: any, sessionID: string, text: string, params: any, logger: Logger): Promise<void>;
12
+ //# sourceMappingURL=notification.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"notification.d.ts","sourceRoot":"","sources":["../../../lib/ui/notification.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,WAAW,CAAA;AACvC,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAQ5C,OAAO,EAAE,kBAAkB,EAAE,MAAM,UAAU,CAAA;AAC7C,OAAO,EAAE,YAAY,EAAE,MAAM,WAAW,CAAA;AAExC,MAAM,MAAM,WAAW,GACjB,YAAY,GACZ,OAAO,GACP,YAAY,GACZ,aAAa,GACb,WAAW,GACX,YAAY,CAAA;AAClB,eAAO,MAAM,mBAAmB,EAAE,MAAM,CAAC,WAAW,EAAE,MAAM,CAO3D,CAAA;AA+DD,MAAM,WAAW,aAAa;IAC1B,UAAU,CAAC,EAAE,OAAO,CAAA;CACvB;AAED,wBAAsB,uBAAuB,CACzC,MAAM,EAAE,GAAG,EACX,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,YAAY,EACpB,KAAK,EAAE,YAAY,EACnB,SAAS,EAAE,MAAM,EACjB,YAAY,EAAE,MAAM,EAAE,EACtB,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,kBAAkB,CAAC,EAC7C,MAAM,EAAE,WAAW,GAAG,SAAS,EAC/B,MAAM,EAAE,GAAG,EACX,gBAAgB,EAAE,MAAM,EACxB,YAAY,CAAC,EAAE,MAAM,EAAE,EACvB,OAAO,CAAC,EAAE,aAAa,GACxB,OAAO,CAAC,OAAO,CAAC,CA6BlB;AAED,wBAAsB,kBAAkB,CACpC,MAAM,EAAE,GAAG,EACX,SAAS,EAAE,MAAM,EACjB,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,GAAG,EACX,MAAM,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC,CAiCf"}
@@ -0,0 +1,81 @@
1
+ import { countDistillationTokens, formatExtracted, formatPrunedItemsList, formatStatsHeader, formatTokenCount, } from "./utils";
2
+ export const PRUNE_REASON_LABELS = {
3
+ completion: "Task Complete",
4
+ noise: "Noise Removal",
5
+ superseded: "Superseded",
6
+ exploration: "Dead-end Exploration",
7
+ duplicate: "Duplicate Content",
8
+ extraction: "Extraction",
9
+ };
10
+ function buildMinimalMessage(state, reason, distillation, showDistillation) {
11
+ const extractedTokens = countDistillationTokens(distillation);
12
+ const extractedSuffix = extractedTokens > 0 ? ` (extracted ${formatTokenCount(extractedTokens)})` : "";
13
+ const reasonSuffix = reason && extractedTokens === 0 ? ` โ€” ${PRUNE_REASON_LABELS[reason]}` : "";
14
+ let message = formatStatsHeader(state.stats.totalPruneTokens, state.stats.pruneTokenCounter, state.stats.totalPruneMessages, state.stats.pruneMessageCounter) +
15
+ reasonSuffix +
16
+ extractedSuffix;
17
+ return message + formatExtracted(showDistillation ? distillation : undefined);
18
+ }
19
+ function buildDetailedMessage(state, reason, pruneToolIds, toolMetadata, workingDirectory, distillation, showDistillation, simplified = false) {
20
+ let message = formatStatsHeader(state.stats.totalPruneTokens, state.stats.pruneTokenCounter, state.stats.totalPruneMessages, state.stats.pruneMessageCounter);
21
+ if (pruneToolIds.length > 0) {
22
+ const pruneTokenCounterStr = `~${formatTokenCount(state.stats.pruneTokenCounter)}`;
23
+ const extractedTokens = countDistillationTokens(distillation);
24
+ const extractedSuffix = extractedTokens > 0 ? `, extracted ${formatTokenCount(extractedTokens)}` : "";
25
+ const reasonLabel = reason && extractedTokens === 0 ? ` โ€” ${PRUNE_REASON_LABELS[reason]}` : "";
26
+ message += `\n\nโ–ฃ Pruning (${pruneTokenCounterStr}${extractedSuffix})${reasonLabel}`;
27
+ const itemLines = formatPrunedItemsList(pruneToolIds, toolMetadata, workingDirectory, simplified);
28
+ message += "\n" + itemLines.join("\n");
29
+ }
30
+ return (message + formatExtracted(showDistillation ? distillation : undefined)).trim();
31
+ }
32
+ export async function sendUnifiedNotification(client, logger, config, state, sessionId, pruneToolIds, toolMetadata, reason, params, workingDirectory, distillation, options) {
33
+ const hasPruned = pruneToolIds.length > 0;
34
+ if (!hasPruned) {
35
+ return false;
36
+ }
37
+ if (config.pruneNotification === "off") {
38
+ return false;
39
+ }
40
+ const showDistillation = config.tools.extract.showDistillation;
41
+ const simplified = options?.simplified ?? false;
42
+ const message = config.pruneNotification === "minimal"
43
+ ? buildMinimalMessage(state, reason, distillation, showDistillation)
44
+ : buildDetailedMessage(state, reason, pruneToolIds, toolMetadata, workingDirectory, distillation, showDistillation, simplified);
45
+ await sendIgnoredMessage(client, sessionId, message, params, logger);
46
+ return true;
47
+ }
48
+ export async function sendIgnoredMessage(client, sessionID, text, params, logger) {
49
+ const agent = params.agent || undefined;
50
+ const variant = params.variant || undefined;
51
+ const model = params.providerId && params.modelId
52
+ ? {
53
+ providerID: params.providerId,
54
+ modelID: params.modelId,
55
+ }
56
+ : undefined;
57
+ try {
58
+ await client.session.prompt({
59
+ path: {
60
+ id: sessionID,
61
+ },
62
+ body: {
63
+ noReply: true,
64
+ agent: agent,
65
+ model: model,
66
+ variant: variant,
67
+ parts: [
68
+ {
69
+ type: "text",
70
+ text: text,
71
+ ignored: true,
72
+ },
73
+ ],
74
+ },
75
+ });
76
+ }
77
+ catch (error) {
78
+ logger.error("Failed to send notification", { error: error.message });
79
+ }
80
+ }
81
+ //# sourceMappingURL=notification.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"notification.js","sourceRoot":"","sources":["../../../lib/ui/notification.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ import { ToolParameterEntry } from "../state";
2
+ export declare function countDistillationTokens(distillation?: string[]): number;
3
+ export declare function formatExtracted(distillation?: string[]): string;
4
+ export declare function formatStatsHeader(totalTokensSaved: number, pruneTokenCounter: number, totalMessagesPruned: number, messagesPruned: number): string;
5
+ export declare function formatTokenCount(tokens: number): string;
6
+ export declare function truncate(str: string, maxLen?: number): string;
7
+ export declare function shortenPath(input: string, workingDirectory?: string): string;
8
+ export declare function formatPrunedItemsList(pruneToolIds: string[], toolMetadata: Map<string, ToolParameterEntry>, workingDirectory?: string, simplified?: boolean): string[];
9
+ export declare function formatPruningResultForTool(prunedIds: string[], toolMetadata: Map<string, ToolParameterEntry>, workingDirectory?: string, simplified?: boolean): string;
10
+ //# sourceMappingURL=utils.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../lib/ui/utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,kBAAkB,EAAE,MAAM,UAAU,CAAA;AAI7C,wBAAgB,uBAAuB,CAAC,YAAY,CAAC,EAAE,MAAM,EAAE,GAAG,MAAM,CAGvE;AAED,wBAAgB,eAAe,CAAC,YAAY,CAAC,EAAE,MAAM,EAAE,GAAG,MAAM,CAS/D;AAED,wBAAgB,iBAAiB,CAC7B,gBAAgB,EAAE,MAAM,EACxB,iBAAiB,EAAE,MAAM,EACzB,mBAAmB,EAAE,MAAM,EAC3B,cAAc,EAAE,MAAM,GACvB,MAAM,CAgBR;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAKvD;AAED,wBAAgB,QAAQ,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,GAAE,MAAW,GAAG,MAAM,CAGjE;AAED,wBAAgB,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,gBAAgB,CAAC,EAAE,MAAM,GAAG,MAAM,CAU5E;AAeD,wBAAgB,qBAAqB,CACjC,YAAY,EAAE,MAAM,EAAE,EACtB,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,kBAAkB,CAAC,EAC7C,gBAAgB,CAAC,EAAE,MAAM,EACzB,UAAU,GAAE,OAAe,GAC5B,MAAM,EAAE,CAwCV;AAED,wBAAgB,0BAA0B,CACtC,SAAS,EAAE,MAAM,EAAE,EACnB,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,kBAAkB,CAAC,EAC7C,gBAAgB,CAAC,EAAE,MAAM,EACzB,UAAU,GAAE,OAAe,GAC5B,MAAM,CAWR"}
@@ -0,0 +1,113 @@
1
+ import { extractParameterKey } from "../messages/utils";
2
+ import { countTokens } from "../strategies/utils";
3
+ export function countDistillationTokens(distillation) {
4
+ if (!distillation || distillation.length === 0)
5
+ return 0;
6
+ return countTokens(distillation.join("\n"));
7
+ }
8
+ export function formatExtracted(distillation) {
9
+ if (!distillation || distillation.length === 0) {
10
+ return "";
11
+ }
12
+ let result = `\n\nโ–ฃ Extracted`;
13
+ for (const finding of distillation) {
14
+ result += `\nโ”€โ”€โ”€\n${finding}`;
15
+ }
16
+ return result;
17
+ }
18
+ export function formatStatsHeader(totalTokensSaved, pruneTokenCounter, totalMessagesPruned, messagesPruned) {
19
+ const totalMessages = totalMessagesPruned + messagesPruned;
20
+ const totalTokens = totalTokensSaved + pruneTokenCounter;
21
+ const totalTokensStr = `~${formatTokenCount(totalTokens)}`;
22
+ // Show addition indicator for current operation
23
+ const additionParts = [];
24
+ if (messagesPruned > 0) {
25
+ additionParts.push(`+${messagesPruned} ๐Ÿ’ฌ`);
26
+ }
27
+ if (pruneTokenCounter > 0) {
28
+ additionParts.push(`+${formatTokenCount(pruneTokenCounter)} ๐Ÿช™`);
29
+ }
30
+ const additionSuffix = additionParts.length > 0 ? ` (${additionParts.join(", ")})` : "";
31
+ return `acp - ${totalMessages} ๐Ÿ’ฌ ยท ${totalTokensStr} ๐Ÿช™${additionSuffix}`;
32
+ }
33
+ export function formatTokenCount(tokens) {
34
+ if (tokens >= 1000) {
35
+ return `${(tokens / 1000).toFixed(1)}K`.replace(".0K", "K");
36
+ }
37
+ return tokens.toString();
38
+ }
39
+ export function truncate(str, maxLen = 60) {
40
+ if (str.length <= maxLen)
41
+ return str;
42
+ return str.slice(0, maxLen - 3) + "...";
43
+ }
44
+ export function shortenPath(input, workingDirectory) {
45
+ const inPathMatch = input.match(/^(.+) in (.+)$/);
46
+ if (inPathMatch?.[1] && inPathMatch[2]) {
47
+ const prefix = inPathMatch[1];
48
+ const pathPart = inPathMatch[2];
49
+ const shortenedPath = shortenSinglePath(pathPart, workingDirectory);
50
+ return `${prefix} in ${shortenedPath}`;
51
+ }
52
+ return shortenSinglePath(input, workingDirectory);
53
+ }
54
+ function shortenSinglePath(path, workingDirectory) {
55
+ if (workingDirectory) {
56
+ if (path.startsWith(workingDirectory + "/")) {
57
+ return path.slice(workingDirectory.length + 1);
58
+ }
59
+ if (path === workingDirectory) {
60
+ return ".";
61
+ }
62
+ }
63
+ return path;
64
+ }
65
+ export function formatPrunedItemsList(pruneToolIds, toolMetadata, workingDirectory, simplified = false) {
66
+ const lines = [];
67
+ for (const id of pruneToolIds) {
68
+ const metadata = toolMetadata.get(id);
69
+ if (metadata) {
70
+ const paramKey = extractParameterKey(metadata.tool, metadata.parameters);
71
+ if (paramKey) {
72
+ // Use 60 char limit to match notification style
73
+ const displayKey = truncate(shortenPath(paramKey, workingDirectory), 60);
74
+ if (simplified) {
75
+ lines.push(displayKey);
76
+ }
77
+ else {
78
+ lines.push(`โ†’ ${metadata.tool}: ${displayKey}`);
79
+ }
80
+ }
81
+ else {
82
+ if (simplified) {
83
+ lines.push(metadata.tool);
84
+ }
85
+ else {
86
+ lines.push(`โ†’ ${metadata.tool}`);
87
+ }
88
+ }
89
+ }
90
+ }
91
+ const knownCount = pruneToolIds.filter((id) => toolMetadata.has(id)).length;
92
+ const unknownCount = pruneToolIds.length - knownCount;
93
+ if (unknownCount > 0) {
94
+ if (simplified) {
95
+ lines.push(`(${unknownCount} tool${unknownCount > 1 ? "s" : ""} with unknown metadata)`);
96
+ }
97
+ else {
98
+ lines.push(`โ†’ (${unknownCount} tool${unknownCount > 1 ? "s" : ""} with unknown metadata)`);
99
+ }
100
+ }
101
+ return lines;
102
+ }
103
+ export function formatPruningResultForTool(prunedIds, toolMetadata, workingDirectory, simplified = false) {
104
+ const lines = [];
105
+ lines.push(`Context pruning complete. Pruned ${prunedIds.length} tool outputs.`);
106
+ lines.push("");
107
+ if (prunedIds.length > 0) {
108
+ lines.push(`Semantically pruned (${prunedIds.length}):`);
109
+ lines.push(...formatPrunedItemsList(prunedIds, toolMetadata, workingDirectory, simplified));
110
+ }
111
+ return lines.join("\n").trim();
112
+ }
113
+ //# sourceMappingURL=utils.js.map