@wrongstack/core 0.141.0 → 0.155.0

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 (51) hide show
  1. package/dist/{agent-bridge-r9y6gdn4.d.ts → agent-bridge-BbZU5TPN.d.ts} +1 -1
  2. package/dist/{agent-subagent-runner-1GeQE_L0.d.ts → agent-subagent-runner-Bsueu0J2.d.ts} +2 -2
  3. package/dist/{brain-Cp_3GIS2.d.ts → brain-CS_B0vIE.d.ts} +2 -0
  4. package/dist/coordination/index.d.ts +7 -7
  5. package/dist/coordination/index.js +147 -10
  6. package/dist/coordination/index.js.map +1 -1
  7. package/dist/defaults/index.d.ts +13 -13
  8. package/dist/defaults/index.js +360 -78
  9. package/dist/defaults/index.js.map +1 -1
  10. package/dist/execution/index.d.ts +6 -6
  11. package/dist/execution/index.js +277 -16
  12. package/dist/execution/index.js.map +1 -1
  13. package/dist/extension/index.d.ts +2 -2
  14. package/dist/{goal-preamble-iuIUTQwk.d.ts → goal-preamble-CbV8pXLD.d.ts} +11 -3
  15. package/dist/{index-CPweVoFM.d.ts → index-B5wz-GXm.d.ts} +1 -1
  16. package/dist/{index-BZdezm3g.d.ts → index-CI1hRfPt.d.ts} +2 -2
  17. package/dist/index.d.ts +23 -23
  18. package/dist/index.js +396 -86
  19. package/dist/index.js.map +1 -1
  20. package/dist/infrastructure/index.d.ts +3 -3
  21. package/dist/infrastructure/index.js +11 -2
  22. package/dist/infrastructure/index.js.map +1 -1
  23. package/dist/kernel/index.d.ts +3 -3
  24. package/dist/kernel/index.js.map +1 -1
  25. package/dist/{mcp-servers-Bl5LTvQg.d.ts → mcp-servers-CPERR2De.d.ts} +8 -1
  26. package/dist/{multi-agent-coordinator-QWEzJDlm.d.ts → multi-agent-coordinator-BSKSFNhv.d.ts} +1 -1
  27. package/dist/{null-fleet-bus-BUyfqh23.d.ts → null-fleet-bus-CGOez8Le.d.ts} +4 -4
  28. package/dist/observability/index.d.ts +1 -1
  29. package/dist/{parallel-eternal-engine-Dj2SYzha.d.ts → parallel-eternal-engine-CYoTKjsz.d.ts} +13 -4
  30. package/dist/{path-resolver-DRjQBkoO.d.ts → path-resolver-DuhlmPil.d.ts} +1 -1
  31. package/dist/{plan-templates-CkKNPU3I.d.ts → plan-templates-DbH7lg-t.d.ts} +2 -2
  32. package/dist/{provider-runner-BNpuIyOL.d.ts → provider-runner-Cocq0O9E.d.ts} +1 -1
  33. package/dist/sdd/index.d.ts +3 -3
  34. package/dist/sdd/index.js +143 -6
  35. package/dist/sdd/index.js.map +1 -1
  36. package/dist/{secret-vault-DoISxaKO.d.ts → secret-vault-BJDY28ev.d.ts} +7 -1
  37. package/dist/{secret-vault-BTcC_T5v.d.ts → secret-vault-w8MbUe2Q.d.ts} +1 -1
  38. package/dist/security/index.d.ts +2 -2
  39. package/dist/security/index.js +60 -23
  40. package/dist/security/index.js.map +1 -1
  41. package/dist/storage/index.d.ts +5 -5
  42. package/dist/storage/index.js +78 -44
  43. package/dist/storage/index.js.map +1 -1
  44. package/dist/types/index.d.ts +11 -11
  45. package/dist/types/index.js +186 -26
  46. package/dist/types/index.js.map +1 -1
  47. package/dist/utils/index.d.ts +65 -1
  48. package/dist/utils/index.js +64 -5
  49. package/dist/utils/index.js.map +1 -1
  50. package/package.json +1 -1
  51. package/skills/tech-stack/SKILL.md +253 -97
@@ -1,34 +1,34 @@
1
1
  export { A as AgentError, k as Capabilities, u as ConfigError, g as ContentBlock, E as ERROR_CODES, w as ErrorCode, x as ErrorSeverity, y as ErrorSubsystem, F as FileSnapshot, z as FsError, I as ImageBlock, J as JSONSchema, M as Message, B as MessageRole, f as Permission, D as PluginError, P as Provider, e as ProviderError, G as ProviderErrorBody, R as Request, b as Response, p as ResumedSession, K as RiskTier, q as SessionData, N as SessionError, S as SessionEvent, h as SessionMetadata, i as SessionStore, r as SessionSummary, a as SessionWriter, V as StopReason, W as StreamEvent, X as StreamHangError, l as TextBlock, Y as ThinkingBlock, T as Tool, Z as ToolCallContext, _ as ToolError, $ as ToolFinalEvent, j as ToolProgressEvent, n as ToolResultBlock, a0 as ToolStreamEvent, m as ToolUseBlock, U as Usage, a1 as WrongStackError, a2 as asBlocks, a3 as asText, a5 as isAgentError, a6 as isConfigError, a7 as isFsError, a8 as isImageBlock, a9 as isPluginError, aa as isSessionError, ab as isTextBlock, ac as isThinkingBlock, ad as isToolError, ae as isToolResultBlock, af as isToolUseBlock, ag as isWrongStackError, ah as toWrongStackError } from '../context-C7G_MtLV.js';
2
- export { P as ProviderRunner, R as RunProviderOptions } from '../provider-runner-BNpuIyOL.js';
2
+ export { P as ProviderRunner, R as RunProviderOptions } from '../provider-runner-Cocq0O9E.js';
3
3
  export { A as AutonomyConfig, n as CONTEXT_WINDOW_MODES, h as Config, j as ConfigLoader, i as ConfigStore, o as ContextConfig, C as ContextWindowAggressiveOn, p as ContextWindowConfigLike, q as ContextWindowMode, r as ContextWindowModeId, g as ContextWindowPolicy, s as ContextWindowThresholds, t as CustomModelDefinition, D as DEFAULT_CONTEXT_WINDOW_MODE_ID, F as FeaturesConfig, f as HookEntry, H as HookEvent, l as HookInput, e as HookMatcher, m as HookOutcome, I as InProcessHook, u as IndexingConfig, L as LaunchConfig, v as LogConfig, c as MCPServerConfig, d as ModelMatrixEntry, x as PluginConfig, y as ProviderApiKey, P as ProviderConfig, z as SessionLoggingConfig, S as ShellHook, B as SyncCategory, k as SyncConfig, T as ToolsConfig, E as formatContextWindowModeList, G as getContextWindowMode, J as isContextWindowModeId, K as listContextWindowModes, N as resolveContextWindowPolicy } from '../config-BaVThgnT.js';
4
4
  export { a as CompactReport, C as Compactor } from '../compactor-BueGt7LG.js';
5
5
  export { a as PermissionDecision, P as PermissionPolicy, T as TrustPolicy } from '../permission-B7nKnEvQ.js';
6
6
  export { C as CheckpointInfo, R as RewindResult, a as RewindResultExtended, S as SessionRewinder } from '../session-rewinder-C9HnMkhP.js';
7
7
  export { a as AddAttachmentInput, c as Attachment, d as AttachmentKind, e as AttachmentMeta, b as AttachmentRef, A as AttachmentStore, D as DefaultSessionReader } from '../session-reader-BAtCxdaw.js';
8
8
  export { D as DEFAULT_AUTONOMY_CONFIG, a as DEFAULT_CONTEXT_CONFIG, b as DEFAULT_SESSION_LOGGING_CONFIG, c as DEFAULT_SESSION_PRUNE_DAYS, d as DEFAULT_TOOLS_CONFIG } from '../default-config-CXsDvOmP.js';
9
- export { D as DefaultSecretScrubber, a as DefaultSecretVault, S as SecretVaultOptions, d as decryptConfigSecrets, e as encryptConfigSecrets, i as isSecretField, m as migratePlaintextSecrets, r as rewriteConfigEncrypted } from '../secret-vault-BTcC_T5v.js';
9
+ export { D as DefaultSecretScrubber, a as DefaultSecretVault, S as SecretVaultOptions, d as decryptConfigSecrets, e as encryptConfigSecrets, i as isSecretField, m as migratePlaintextSecrets, r as rewriteConfigEncrypted } from '../secret-vault-w8MbUe2Q.js';
10
10
  export { D as DefaultLogger, a as DefaultLoggerOptions } from '../logger-B9J5puGM.js';
11
- export { D as DefaultPathResolver, a as DefaultTokenCounter } from '../path-resolver-DRjQBkoO.js';
12
- export { p as MEMORY_TYPE_LABELS, q as MemoryClearedPayload, r as MemoryConsolidatedPayload, k as MemoryEntry, s as MemoryForgottenPayload, t as MemoryPriority, m as MemoryRelevanceContext, u as MemoryRememberedPayload, M as MemoryScope, l as MemoryStore, v as MemoryType, S as ScoredEntry } from '../brain-Cp_3GIS2.js';
13
- import { I as IterationStage, f as ParallelIterationStage } from '../parallel-eternal-engine-Dj2SYzha.js';
14
- export { C as CompactorOptions, g as DEFAULT_RECOVERY_STRATEGIES, D as DefaultErrorHandler, a as DefaultRetryPolicy, H as HybridCompactor, R as RecoveryStrategy, T as ToolExecutor, h as buildRecoveryStrategies } from '../parallel-eternal-engine-Dj2SYzha.js';
11
+ export { D as DefaultPathResolver, a as DefaultTokenCounter } from '../path-resolver-DuhlmPil.js';
12
+ export { p as MEMORY_TYPE_LABELS, q as MemoryClearedPayload, r as MemoryConsolidatedPayload, k as MemoryEntry, s as MemoryForgottenPayload, t as MemoryPriority, m as MemoryRelevanceContext, u as MemoryRememberedPayload, M as MemoryScope, l as MemoryStore, v as MemoryType, S as ScoredEntry } from '../brain-CS_B0vIE.js';
13
+ import { I as IterationStage, f as ParallelIterationStage } from '../parallel-eternal-engine-CYoTKjsz.js';
14
+ export { C as CompactorOptions, g as DEFAULT_RECOVERY_STRATEGIES, D as DefaultErrorHandler, a as DefaultRetryPolicy, H as HybridCompactor, R as RecoveryStrategy, T as ToolExecutor, h as buildRecoveryStrategies } from '../parallel-eternal-engine-CYoTKjsz.js';
15
15
  export { b as SkillEntry, S as SkillLoader, a as SkillManifest } from '../skill-Bj6Ezqb8.js';
16
16
  export { B as BuildContext, b as ModelCapabilities, a as Renderer, S as SystemPromptBuilder } from '../pipeline-BG7UgbDc.js';
17
17
  export { I as InputReader, P as PromptOption } from '../input-reader-E-ffP2ee.js';
18
- export { O as CoordinatorEvents, C as CoordinatorStatus, D as DoneCondition, I as MCPRegistryView, L as MetricsSinkView, c as MultiAgentConfig, M as MultiAgentCoordinator, N as Plugin, P as PluginAPI, Q as PluginCapabilities, R as PluginDependency, E as PluginPipelines, _ as ProviderFactory, H as ProviderRegistryView, K as SessionWriterView, z as SlashCommand, J as SlashCommandRegistryView, e as SpawnResult, S as SubagentConfig, U as SubagentContext, V as SubagentError, W as SubagentErrorKind, X as SubagentRunContext, Y as SubagentRunOutcome, d as SubagentRunner, Z as TaskDelegation, f as TaskResult, T as TaskSpec, G as ToolRegistryView } from '../agent-subagent-runner-1GeQE_L0.js';
18
+ export { O as CoordinatorEvents, C as CoordinatorStatus, D as DoneCondition, I as MCPRegistryView, L as MetricsSinkView, c as MultiAgentConfig, M as MultiAgentCoordinator, N as Plugin, P as PluginAPI, Q as PluginCapabilities, R as PluginDependency, E as PluginPipelines, _ as ProviderFactory, H as ProviderRegistryView, K as SessionWriterView, z as SlashCommand, J as SlashCommandRegistryView, e as SpawnResult, S as SubagentConfig, U as SubagentContext, V as SubagentError, W as SubagentErrorKind, X as SubagentRunContext, Y as SubagentRunOutcome, d as SubagentRunner, Z as TaskDelegation, f as TaskResult, T as TaskSpec, G as ToolRegistryView } from '../agent-subagent-runner-Bsueu0J2.js';
19
19
  export { D as DefaultModelsRegistry, a as DefaultModelsRegistryOptions, c as classifyFamily } from '../models-registry-D90K9UnM.js';
20
20
  export { D as DEFAULT_MODES, b as Mode, a as ModeConfig, c as ModeManifest, M as ModeStore } from '../mode-CZlO9iU1.js';
21
- export { I as InMemoryAgentBridge, a as InMemoryBridgeTransport, c as createMessage } from '../agent-bridge-r9y6gdn4.js';
21
+ export { I as InMemoryAgentBridge, a as InMemoryBridgeTransport, c as createMessage } from '../agent-bridge-BbZU5TPN.js';
22
22
  export { D as DEFAULT_SPEC_TEMPLATE, S as SpecAnalysis, a as SpecApiEndpoint, b as SpecRequirement, c as SpecSection, d as SpecSectionType, e as SpecStatus, f as SpecTemplate, g as SpecValidationResult, h as Specification } from '../spec-TBi3Jr6T.js';
23
23
  export { C as CriticalPathResult, f as TaskAssignment, g as TaskDependency, h as TaskEdge, i as TaskFilter, d as TaskGraph, e as TaskNode, a as TaskPriority, c as TaskProgress, j as TaskSort, b as TaskStatus, T as TaskType, k as computeTaskProgress, l as findCriticalPath, t as topologicalSort } from '../task-graph-u1q9Jkyk.js';
24
24
  export { A as AggregateHealth, a as HealthCheck, b as HealthCheckResult, H as HealthRegistry, c as HealthStatus, d as MetricLabels, e as MetricSeries, M as MetricsSink, f as MetricsSnapshot, S as Span, T as Tracer } from '../observability-D-HZN_mF.js';
25
- export { S as SystemPromptContributor } from '../index-CPweVoFM.js';
25
+ export { S as SystemPromptContributor } from '../index-B5wz-GXm.js';
26
26
  import '../logger-B63L5bTg.js';
27
27
  import '../retry-policy-rutAfVeR.js';
28
- import '../secret-vault-DoISxaKO.js';
28
+ import '../secret-vault-BJDY28ev.js';
29
29
  import '../path-resolver-CPRj4bFY.js';
30
30
  import '../goal-store-CV9Yz2X_.js';
31
- import '../multi-agent-coordinator-QWEzJDlm.js';
31
+ import '../multi-agent-coordinator-BSKSFNhv.js';
32
32
  import 'node:events';
33
33
 
34
34
  /** Union of serial and parallel autonomy engine stage types (from EternalAutonomyEngine / ParallelEternalEngine). */
@@ -425,6 +425,65 @@ async function renameWithRetry(from, to) {
425
425
  throw lastErr;
426
426
  }
427
427
 
428
+ // src/utils/deep-merge.ts
429
+ var FORBIDDEN_PROTO_KEYS = /* @__PURE__ */ new Set([
430
+ "__proto__",
431
+ "constructor",
432
+ "prototype",
433
+ "__defineGetter__",
434
+ "__defineSetter__",
435
+ "__lookupGetter__",
436
+ "__lookupSetter__"
437
+ ]);
438
+ function isPrimitiveArray(a) {
439
+ return a.every((v) => v === null || typeof v !== "object" && typeof v !== "function");
440
+ }
441
+ function deepMerge(base, patch, options = {}) {
442
+ const {
443
+ conflictResolution = "prefer-patch",
444
+ arrayMode = "replace",
445
+ protectProto = true,
446
+ onNonPrimitiveArrayReplace
447
+ } = options;
448
+ if (typeof base !== "object" || base === null) {
449
+ return conflictResolution === "prefer-patch" ? patch : base;
450
+ }
451
+ if (typeof patch !== "object" || patch === null) {
452
+ return conflictResolution === "prefer-patch" ? patch : base;
453
+ }
454
+ if (Array.isArray(base) && Array.isArray(patch)) {
455
+ if (arrayMode === "concat-primitives" && isPrimitiveArray(base) && isPrimitiveArray(patch)) {
456
+ return [.../* @__PURE__ */ new Set([...base, ...patch])];
457
+ }
458
+ return conflictResolution === "prefer-patch" ? patch : base;
459
+ }
460
+ if (Array.isArray(base) || Array.isArray(patch)) {
461
+ return conflictResolution === "prefer-patch" ? patch : base;
462
+ }
463
+ const baseObj = base;
464
+ const patchObj = patch;
465
+ const out = { ...baseObj };
466
+ for (const [k, v] of Object.entries(patchObj)) {
467
+ if (protectProto && FORBIDDEN_PROTO_KEYS.has(k)) continue;
468
+ const existing = out[k];
469
+ if (v !== null && typeof v === "object" && !Array.isArray(v) && existing !== null && typeof existing === "object" && !Array.isArray(existing)) {
470
+ out[k] = deepMerge(existing, v, options);
471
+ } else if (Array.isArray(v) && Array.isArray(existing)) {
472
+ if (onNonPrimitiveArrayReplace && !isPrimitiveArray(v)) {
473
+ onNonPrimitiveArrayReplace(k, existing.length, v.length);
474
+ }
475
+ out[k] = deepMerge(existing, v, options);
476
+ } else if (v !== void 0) {
477
+ if (onNonPrimitiveArrayReplace && Array.isArray(v) && !isPrimitiveArray(v)) {
478
+ const existingLen = Array.isArray(existing) ? existing.length : 0;
479
+ onNonPrimitiveArrayReplace(k, existingLen, v.length);
480
+ }
481
+ out[k] = v;
482
+ }
483
+ }
484
+ return out;
485
+ }
486
+
428
487
  // src/security/secret-vault.ts
429
488
  var KEY_BYTES = 32;
430
489
  var IV_BYTES = 12;
@@ -627,28 +686,6 @@ function walkCount(node, vault, counter) {
627
686
  }
628
687
  return out;
629
688
  }
630
- var FORBIDDEN_PROTO_KEYS = /* @__PURE__ */ new Set([
631
- "__proto__",
632
- "constructor",
633
- "prototype",
634
- "__defineGetter__",
635
- "__defineSetter__",
636
- "__lookupGetter__",
637
- "__lookupSetter__"
638
- ]);
639
- function deepMerge(a, b) {
640
- const out = { ...a };
641
- for (const [k, v] of Object.entries(b)) {
642
- if (FORBIDDEN_PROTO_KEYS.has(k)) continue;
643
- const existing = out[k];
644
- if (v !== null && typeof v === "object" && !Array.isArray(v) && existing !== null && typeof existing === "object" && !Array.isArray(existing)) {
645
- out[k] = deepMerge(existing, v);
646
- } else {
647
- out[k] = v;
648
- }
649
- }
650
- return out;
651
- }
652
689
 
653
690
  // src/utils/term.ts
654
691
  var hasStdout = () => typeof process !== "undefined" && !!process.stdout;
@@ -1164,8 +1201,8 @@ function findPreserveStart(messages, preserveK) {
1164
1201
  for (let i = preserveStart; i < messages.length; i++) {
1165
1202
  const m = messages[i];
1166
1203
  if (!m || typeof m.content === "string" || !Array.isArray(m.content)) continue;
1167
- const hasToolUse2 = m.content.some((b) => b.type === "tool_use");
1168
- if (hasToolUse2 && i + 1 < messages.length) {
1204
+ const hasToolUse3 = m.content.some((b) => b.type === "tool_use");
1205
+ if (hasToolUse3 && i + 1 < messages.length) {
1169
1206
  const next = messages[i + 1];
1170
1207
  if (next && next.role === "user" && typeof next.content !== "string" && Array.isArray(next.content) && next.content.some((b) => b.type === "tool_result")) {
1171
1208
  preserveStart = i + 1;
@@ -1229,14 +1266,137 @@ function buildLosslessDigest(messages) {
1229
1266
  }
1230
1267
  return lines.join("\n");
1231
1268
  }
1269
+ function extractText(m) {
1270
+ if (typeof m.content === "string") return m.content;
1271
+ return m.content.filter(isTextBlock).map((b) => b.text).join(" ");
1272
+ }
1273
+ function hasToolUse2(m) {
1274
+ if (typeof m.content === "string") return false;
1275
+ return m.content.some((b) => b.type === "tool_use");
1276
+ }
1277
+ function hasLargeToolResult(m, threshold = 3e3) {
1278
+ if (typeof m.content === "string") return false;
1279
+ return m.content.some(
1280
+ (b) => b.type === "tool_result" && b.content && (typeof b.content === "string" ? b.content.length : JSON.stringify(b.content).length) > threshold
1281
+ );
1282
+ }
1283
+ function scoreMessage(m, context) {
1284
+ const text = extractText(m).toLowerCase();
1285
+ if (text.trim().length === 0 && (hasToolUse2(m) || typeof m.content !== "string")) {
1286
+ const hasResult = typeof m.content !== "string" && m.content.some((b) => b.type === "tool_result");
1287
+ if (hasToolUse2(m) || hasResult) return 0;
1288
+ }
1289
+ if (context?.failureCounts && m.role === "user" && hasToolUse2(m) === false) {
1290
+ const isFailure = /error|fail|exception|timeout|enonet|eacces|eperm|enoent|abort/i.test(text);
1291
+ if (isFailure) {
1292
+ const errKey = /(error|fail|exception|timeout|enonet|eacces|eperm|enoent|abort)/i.exec(text)?.[0]?.toLowerCase() ?? "error";
1293
+ const count = (context.failureCounts.get(errKey) ?? 0) + 1;
1294
+ context.failureCounts.set(errKey, count);
1295
+ if (count >= 5) return 0;
1296
+ if (count >= 3) return 1;
1297
+ }
1298
+ }
1299
+ if (m.role === "user") {
1300
+ if (/\b(wrong|no\b|stop\b|don'?t\b|actually|fix that|undo|revert|forget|ignore|skip)\b/i.test(
1301
+ text
1302
+ )) {
1303
+ return 5;
1304
+ }
1305
+ }
1306
+ if (/\b(error|exception|fatal|critical|crash|panic|abort|segfault|core dump|undefined is not|null pointer|typeerror|referenceerror|syntaxerror)\b/i.test(
1307
+ text
1308
+ )) {
1309
+ return 5;
1310
+ }
1311
+ if (/\b(security|vulnerability|injection|xss|csrf|secret|apikey|api.key|hardcoded|leak|exploit|cve)\b/i.test(
1312
+ text
1313
+ )) {
1314
+ return 5;
1315
+ }
1316
+ if (m.role === "assistant" && /\b(architecture|design|approach|strategy|pattern|refactor|migrate|restructure|decision|trade.?off)\b/i.test(
1317
+ text
1318
+ )) {
1319
+ return 5;
1320
+ }
1321
+ if (hasLargeToolResult(m)) return 1;
1322
+ if (m.role === "user" && !hasToolUse2(m) && /\b(files_with_matches|count|found \d+ match|directory tree|\.\.\. and \d+ more)\b/i.test(text)) {
1323
+ return 1;
1324
+ }
1325
+ return 3;
1326
+ }
1327
+ function buildSmartDigest(messages) {
1328
+ const lines = [];
1329
+ const failureCounts = /* @__PURE__ */ new Map();
1330
+ let noiseCount = 0;
1331
+ for (const m of messages) {
1332
+ const score = scoreMessage(m, { failureCounts });
1333
+ const text = extractText(m);
1334
+ const toolCount = countToolBlocks(m);
1335
+ if (score === 0) {
1336
+ noiseCount++;
1337
+ continue;
1338
+ }
1339
+ const marker = toolCount > 0 ? ` [${toolCount} tool call(s)]` : "";
1340
+ let display;
1341
+ switch (score) {
1342
+ case 5:
1343
+ display = text.trim();
1344
+ break;
1345
+ case 3:
1346
+ display = firstSentence(text);
1347
+ break;
1348
+ case 1:
1349
+ display = oneLineSummary(m, text);
1350
+ break;
1351
+ default:
1352
+ display = firstSentence(text);
1353
+ }
1354
+ if (display.length === 0 && toolCount === 0) continue;
1355
+ lines.push(`[${m.role}]: ${display}${marker}`);
1356
+ }
1357
+ if (noiseCount > 0) {
1358
+ lines.push(`[system]: ${noiseCount} low-importance turn(s) collapsed (repeated failures / pure tool I/O)`);
1359
+ }
1360
+ return lines.join("\n");
1361
+ }
1362
+ function countToolBlocks(m) {
1363
+ if (typeof m.content === "string") return 0;
1364
+ return m.content.filter(
1365
+ (b) => b.type === "tool_use" || b.type === "tool_result"
1366
+ ).length;
1367
+ }
1368
+ function firstSentence(text) {
1369
+ const trimmed = text.trim();
1370
+ if (trimmed.length === 0) return "";
1371
+ const dot = trimmed.indexOf(". ");
1372
+ if (dot === -1) return trimmed.length > 150 ? `${trimmed.slice(0, 147)}\u2026` : trimmed;
1373
+ const sentence = trimmed.slice(0, dot + 1);
1374
+ return sentence.length > 150 ? `${sentence.slice(0, 147)}\u2026` : sentence;
1375
+ }
1376
+ function oneLineSummary(m, text) {
1377
+ const trimmed = text.trim();
1378
+ if (trimmed.length === 0) {
1379
+ if (typeof m.content !== "string") {
1380
+ const results = m.content.filter((b) => b.type === "tool_result");
1381
+ if (results.length > 0) {
1382
+ return `[${results.length} tool result(s) \u2014 see session log]`;
1383
+ }
1384
+ }
1385
+ return "[no text content]";
1386
+ }
1387
+ const firstLine = trimmed.split("\n")[0] ?? "";
1388
+ return firstLine.length > 100 ? `${firstLine.slice(0, 97)}\u2026` : firstLine;
1389
+ }
1232
1390
 
1233
1391
  // src/execution/compactor.ts
1234
1392
  var HybridCompactor = class {
1235
1393
  preserveK;
1236
1394
  eliseThreshold;
1395
+ smart;
1237
1396
  constructor(opts = {}) {
1238
1397
  this.preserveK = opts.preserveK ?? 5;
1239
1398
  this.eliseThreshold = opts.eliseThreshold ?? 2e3;
1399
+ this.smart = opts.smart ?? false;
1240
1400
  }
1241
1401
  async compact(ctx, opts = {}) {
1242
1402
  const beforeTokens = estimateMessages(ctx.messages);
@@ -1308,7 +1468,7 @@ var HybridCompactor = class {
1308
1468
  if (boundary <= 0) return { saved: 0 };
1309
1469
  const removed = messages.slice(0, boundary);
1310
1470
  const removedTokens = estimateMessages(removed);
1311
- const digest = buildLosslessDigest(removed) || `${removed.length} earlier turns (no textual content; tool I/O omitted \u2014 see session log)`;
1471
+ const digest = this.smart ? buildSmartDigest(removed) || `${removed.length} earlier turns (no textual content; tool I/O omitted \u2014 see session log)` : buildLosslessDigest(removed) || `${removed.length} earlier turns (no textual content; tool I/O omitted \u2014 see session log)`;
1312
1472
  const summaryMsg = {
1313
1473
  role: "system",
1314
1474
  content: `[prior_turns_digest: ${digest}]`
@@ -3118,7 +3278,7 @@ ${excerpt}`;
3118
3278
  subjectFor(toolName, input, subjectKey) {
3119
3279
  if (!input || typeof input !== "object") return void 0;
3120
3280
  const obj = input;
3121
- const globChars = /[*?\[\]]/g;
3281
+ const globChars = /[*?[\]]/g;
3122
3282
  const escapeGlob = (s) => s.replace(globChars, (c) => `\\${c}`);
3123
3283
  const normalizePath = (s) => escapeGlob(s.replace(/\\/g, "/"));
3124
3284
  if (subjectKey) {