@cortexkit/opencode-magic-context 0.39.0 → 0.40.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 (58) hide show
  1. package/README.md +20 -0
  2. package/dist/config/index.d.ts.map +1 -1
  3. package/dist/config/profiles.d.ts +22 -0
  4. package/dist/config/profiles.d.ts.map +1 -0
  5. package/dist/config/project-security.d.ts +3 -0
  6. package/dist/config/project-security.d.ts.map +1 -1
  7. package/dist/config/schema/magic-context.d.ts +400 -0
  8. package/dist/config/schema/magic-context.d.ts.map +1 -1
  9. package/dist/features/magic-context/fail-closed-block.d.ts +11 -1
  10. package/dist/features/magic-context/fail-closed-block.d.ts.map +1 -1
  11. package/dist/features/magic-context/memory/embedding-failure.d.ts +11 -0
  12. package/dist/features/magic-context/memory/embedding-failure.d.ts.map +1 -0
  13. package/dist/features/magic-context/memory/embedding-openai.d.ts +5 -0
  14. package/dist/features/magic-context/memory/embedding-openai.d.ts.map +1 -1
  15. package/dist/features/magic-context/memory/embedding-provider.d.ts +3 -0
  16. package/dist/features/magic-context/memory/embedding-provider.d.ts.map +1 -1
  17. package/dist/features/magic-context/project-embedding-registry.d.ts +2 -0
  18. package/dist/features/magic-context/project-embedding-registry.d.ts.map +1 -1
  19. package/dist/features/magic-context/storage-db.d.ts +1 -1
  20. package/dist/features/magic-context/storage-db.d.ts.map +1 -1
  21. package/dist/features/magic-context/transform-decision-log.d.ts.map +1 -1
  22. package/dist/hooks/magic-context/format-embed-failure.d.ts +3 -0
  23. package/dist/hooks/magic-context/format-embed-failure.d.ts.map +1 -0
  24. package/dist/hooks/magic-context/inject-compartments.d.ts +4 -3
  25. package/dist/hooks/magic-context/inject-compartments.d.ts.map +1 -1
  26. package/dist/hooks/magic-context/strip-content.d.ts +6 -0
  27. package/dist/hooks/magic-context/strip-content.d.ts.map +1 -1
  28. package/dist/hooks/magic-context/transform-postprocess-phase.d.ts +1 -0
  29. package/dist/hooks/magic-context/transform-postprocess-phase.d.ts.map +1 -1
  30. package/dist/{index-k2ts0wk1.js → index-axpym70t.js} +395 -66
  31. package/dist/index.js +119 -163
  32. package/dist/plugin/hooks/create-session-hooks.d.ts +2 -0
  33. package/dist/plugin/hooks/create-session-hooks.d.ts.map +1 -1
  34. package/dist/plugin/rpc-handlers.d.ts.map +1 -1
  35. package/dist/{recomp-orchestrator-2pncxee7.js → recomp-orchestrator-dmyvqekw.js} +1 -1
  36. package/dist/shared/rpc-types.d.ts +2 -0
  37. package/dist/shared/rpc-types.d.ts.map +1 -1
  38. package/dist/shared/rpc-utils.d.ts +12 -1
  39. package/dist/shared/rpc-utils.d.ts.map +1 -1
  40. package/dist/shared/status-detail-text.d.ts.map +1 -1
  41. package/dist/tui/data/context-db.d.ts.map +1 -1
  42. package/dist/tui-compiled/data/context-db.d.ts.map +1 -1
  43. package/package.json +1 -1
  44. package/src/config/index.test.ts +361 -2
  45. package/src/config/index.ts +29 -10
  46. package/src/config/profiles.ts +106 -0
  47. package/src/config/project-security.hostile-matrix.test.ts +9 -0
  48. package/src/config/project-security.test.ts +17 -0
  49. package/src/config/project-security.ts +10 -0
  50. package/src/config/schema/magic-context.test.ts +128 -0
  51. package/src/config/schema/magic-context.ts +89 -0
  52. package/src/shared/rpc-types.ts +2 -0
  53. package/src/shared/rpc-utils.test.ts +32 -0
  54. package/src/shared/rpc-utils.ts +38 -13
  55. package/src/shared/status-detail-text.test.ts +2 -0
  56. package/src/shared/status-detail-text.ts +1 -0
  57. package/src/tui/data/context-db.ts +1 -0
  58. package/src/tui-compiled/data/context-db.ts +1 -0
@@ -398,9 +398,163 @@ function buildPrimaryLanguageDirective(language) {
398
398
  return `Use ${target} for your natural-language replies to the user unless the user explicitly asks for another language. Keep code, identifiers, file paths, commands, logs, and quoted text verbatim.`;
399
399
  }
400
400
 
401
+ // src/shared/redaction.ts
402
+ import { homedir, userInfo } from "node:os";
403
+ function escapeRegex(value) {
404
+ return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
405
+ }
406
+ var SECRET_WORDS = [
407
+ "key",
408
+ "token",
409
+ "secret",
410
+ "password",
411
+ "auth",
412
+ "authorization",
413
+ "bearer",
414
+ "credential"
415
+ ];
416
+ var SECRET_SEGMENT_PATTERN = new RegExp(`^(?:${SECRET_WORDS.map((w) => `${w}s?`).join("|")})$`, "i");
417
+ var TRAILING_DESCRIPTORS = new Set(["id", "ids", "value", "values", "header", "headers"]);
418
+ function redactionTypeForKey(key) {
419
+ const normalized = key.trim().toLowerCase().replace(/[^a-z0-9_.-]+/g, "_");
420
+ const suffix = normalized.split(".").filter(Boolean).at(-1) ?? normalized;
421
+ return suffix || "secret";
422
+ }
423
+ function isNonSecretScalarValue(value) {
424
+ const v = value.trim();
425
+ if (v === "true" || v === "false" || v === "null" || v === "undefined")
426
+ return true;
427
+ return /^[+-]?\d+(?:\.\d+)?(?:[eE][+-]?\d+)?$/.test(v);
428
+ }
429
+ var SECRET_QUALIFIERS = new Set([
430
+ "api",
431
+ "access",
432
+ "private",
433
+ "client",
434
+ "auth",
435
+ "authorization",
436
+ "secret",
437
+ "bearer",
438
+ "session",
439
+ "refresh",
440
+ "service",
441
+ "x",
442
+ "openai",
443
+ "anthropic",
444
+ "google",
445
+ "github",
446
+ "huggingface",
447
+ "aws",
448
+ "azure"
449
+ ]);
450
+ function sanitizePathString(value) {
451
+ const home = homedir();
452
+ const username = userInfo().username;
453
+ let sanitized = value;
454
+ if (home) {
455
+ sanitized = sanitized.replace(new RegExp(escapeRegex(home), "g"), "~");
456
+ }
457
+ sanitized = sanitized.replace(/\/Users\/[^/]+\//g, "/Users/<USER>/");
458
+ sanitized = sanitized.replace(/\/home\/[^/]+\//g, "/home/<USER>/");
459
+ sanitized = sanitized.replace(/C:\\Users\\[^\\]+\\/g, "C:\\Users\\<USER>\\");
460
+ if (username) {
461
+ sanitized = sanitized.replace(new RegExp(escapeRegex(username), "g"), "<USER>");
462
+ }
463
+ return sanitized;
464
+ }
465
+ var SECRET_TEXT_PATTERNS = [
466
+ {
467
+ pattern: /\bsk-ant-(?:api03-)?[A-Za-z0-9_-]{32,}/g,
468
+ replacement: "<ANTHROPIC_API_KEY_REDACTED>"
469
+ },
470
+ {
471
+ pattern: /\bsk-(?:proj-)?[A-Za-z0-9_-]{32,}/g,
472
+ replacement: "<OPENAI_API_KEY_REDACTED>"
473
+ },
474
+ {
475
+ pattern: /\bgithub_pat_[A-Za-z0-9_]{20,}/g,
476
+ replacement: "<GITHUB_PAT_REDACTED>"
477
+ },
478
+ {
479
+ pattern: /\b(?:gh[opsu]|ghr)_[A-Za-z0-9]{30,}/g,
480
+ replacement: "<GITHUB_TOKEN_REDACTED>"
481
+ },
482
+ {
483
+ pattern: /\bhf_[A-Za-z0-9]{30,}/g,
484
+ replacement: "<HUGGINGFACE_TOKEN_REDACTED>"
485
+ },
486
+ {
487
+ pattern: /\b(?:AKIA|ASIA)[0-9A-Z]{16}\b/g,
488
+ replacement: "<AWS_ACCESS_KEY_ID_REDACTED>"
489
+ },
490
+ {
491
+ pattern: /\bxox[abprsuvc]-[A-Za-z0-9-]{10,}/g,
492
+ replacement: "<SLACK_TOKEN_REDACTED>"
493
+ },
494
+ {
495
+ pattern: /\bAIza[A-Za-z0-9_-]{35}\b/g,
496
+ replacement: "<GOOGLE_API_KEY_REDACTED>"
497
+ },
498
+ {
499
+ pattern: /\b(Authorization\s*:\s*Bearer\s+)([A-Za-z0-9._~+/=-]{8,})/gi,
500
+ replacement: (_full, prefix) => `${prefix}<REDACTED:bearer>`
501
+ },
502
+ {
503
+ pattern: /\beyJ[A-Za-z0-9_-]+\.[A-Za-z0-9_-]+\.[A-Za-z0-9_-]+/g,
504
+ replacement: "<JWT_REDACTED>"
505
+ },
506
+ {
507
+ pattern: /(["'])([^"']*(?:key|token|secret|password|auth|bearer|credential)[^"']*)\1(\s*:\s*)(["'])([^"']*)\4/gi,
508
+ replacement: (full, quote, key, separator, valueQuote, value) => isNonSecretScalarValue(value) ? full : `${quote}${key}${quote}${separator}${valueQuote}<REDACTED:${redactionTypeForKey(key)}>${valueQuote}`
509
+ },
510
+ {
511
+ pattern: /\b([A-Za-z0-9_.-]*(?:key|token|secret|password|auth|bearer|credential)[A-Za-z0-9_.-]*)\s*=\s*([^\s'"`]+)/gi,
512
+ replacement: (full, key, value) => isNonSecretScalarValue(value) ? full : `${key}=<REDACTED:${redactionTypeForKey(key)}>`
513
+ }
514
+ ];
515
+ function redactSecretText(value) {
516
+ let redacted = value;
517
+ for (const { pattern, replacement } of SECRET_TEXT_PATTERNS) {
518
+ if (typeof replacement === "string") {
519
+ redacted = redacted.replace(pattern, replacement);
520
+ } else {
521
+ redacted = redacted.replace(pattern, replacement);
522
+ }
523
+ }
524
+ return redacted;
525
+ }
526
+ function sanitizeDiagnosticText(value) {
527
+ return redactSecretText(sanitizePathString(value));
528
+ }
529
+ var SHAREABILITY_SENSITIVE_PATTERNS = [
530
+ /\bC:\/Users\/[^/\s]+/i,
531
+ /(?:^|\s)~\/[^\s]+/,
532
+ /\b(?:api[_-]?key|secret|token|password|passwd|pwd|client[_-]?secret|access[_-]?key)\b\s*[:=]\s*\S+/i,
533
+ /\b(?:localhost|127\.0\.0\.1|0\.0\.0\.0|\[::1\])(?::\d+)?\b/i,
534
+ /\b(?:10|127)\.\d{1,3}\.\d{1,3}\.\d{1,3}\b/,
535
+ /\b192\.168\.\d{1,3}\.\d{1,3}\b/,
536
+ /\b172\.(?:1[6-9]|2\d|3[01])\.\d{1,3}\.\d{1,3}\b/
537
+ ];
538
+ function hasShareabilitySensitiveText(text) {
539
+ try {
540
+ if (sanitizeDiagnosticText(text) !== text)
541
+ return true;
542
+ return SHAREABILITY_SENSITIVE_PATTERNS.some((pattern) => pattern.test(text));
543
+ } catch {
544
+ return true;
545
+ }
546
+ }
547
+
401
548
  // src/features/magic-context/fail-closed-block.ts
402
549
  var FAIL_CLOSED_DOCTOR_COMMAND = "npx @cortexkit/magic-context@latest doctor";
403
550
  var FAIL_CLOSED_REPROBE_EVERY_N = 5;
551
+ function attachFailClosedBlockingProcessEvidence(process2, evidence) {
552
+ Object.defineProperties(process2, {
553
+ startTime: { configurable: true, value: evidence.startTime },
554
+ commandLine: { configurable: true, value: evidence.commandLine }
555
+ });
556
+ return process2;
557
+ }
404
558
 
405
559
  class FailClosedBlockingError extends Error {
406
560
  code = "FAIL_CLOSED_BLOCKING";
@@ -423,6 +577,7 @@ function isMagicContextHiddenAgentName(agent) {
423
577
  return false;
424
578
  }
425
579
  var MAX_FORMATTED_BLOCKING_PROCESSES = 8;
580
+ var MAX_FORMATTED_COMMAND_LINE_LENGTH = 80;
426
581
  function normalizeFailClosedProcessKind(process2) {
427
582
  switch (process2.kind) {
428
583
  case "OpenCode server":
@@ -445,13 +600,61 @@ function normalizeFailClosedProcessKind(process2) {
445
600
  return "process";
446
601
  }
447
602
  }
603
+ function formatFailClosedProcessStartTime(startTime) {
604
+ if (!Number.isFinite(startTime) || startTime <= 0)
605
+ return "unverified";
606
+ try {
607
+ const parts = new Intl.DateTimeFormat("en-US", {
608
+ day: "numeric",
609
+ hour: "2-digit",
610
+ minute: "2-digit",
611
+ month: "short",
612
+ hour12: false
613
+ }).formatToParts(new Date(startTime));
614
+ const values = Object.fromEntries(parts.map(({ type, value }) => [type, value]));
615
+ if (!values.month || !values.day || !values.hour || !values.minute)
616
+ return "unverified";
617
+ return `${values.month} ${values.day} ${values.hour}:${values.minute}`;
618
+ } catch {
619
+ return "unverified";
620
+ }
621
+ }
622
+ function formatFailClosedCommandLine(commandLine) {
623
+ if (typeof commandLine !== "string" || commandLine.trim().length === 0)
624
+ return "unverified";
625
+ try {
626
+ const normalized = commandLine.replaceAll("\x00", " ").replace(/\s+/g, " ").trim();
627
+ if (normalized.length === 0)
628
+ return "unverified";
629
+ const sanitized = sanitizeDiagnosticText(normalized).trim();
630
+ if (sanitized.length === 0)
631
+ return "unverified";
632
+ return sanitized.length > MAX_FORMATTED_COMMAND_LINE_LENGTH ? `${sanitized.slice(0, MAX_FORMATTED_COMMAND_LINE_LENGTH - 3)}...` : sanitized;
633
+ } catch {
634
+ return "unverified";
635
+ }
636
+ }
448
637
  function formatFailClosedBlockingProcesses(processes) {
449
638
  const uniqueProcesses = new Map;
450
639
  for (const process2 of processes) {
451
640
  if (!Number.isInteger(process2.pid) || process2.pid <= 0)
452
641
  continue;
453
- const kind = normalizeFailClosedProcessKind(process2);
454
- uniqueProcesses.set(`${kind}\x00${process2.pid}`, { kind, pid: process2.pid });
642
+ const candidate = {
643
+ kind: normalizeFailClosedProcessKind(process2),
644
+ pid: process2.pid,
645
+ startTime: process2.startTime,
646
+ commandLine: process2.commandLine
647
+ };
648
+ const previous = uniqueProcesses.get(process2.pid);
649
+ if (!previous || previous.kind === "process" && candidate.kind !== "process") {
650
+ uniqueProcesses.set(process2.pid, candidate);
651
+ } else {
652
+ uniqueProcesses.set(process2.pid, {
653
+ ...previous,
654
+ startTime: previous.startTime ?? candidate.startTime,
655
+ commandLine: previous.commandLine ?? candidate.commandLine
656
+ });
657
+ }
455
658
  }
456
659
  const entries = [...uniqueProcesses.values()];
457
660
  const visible = entries.slice(0, MAX_FORMATTED_BLOCKING_PROCESSES);
@@ -461,10 +664,12 @@ function formatFailClosedBlockingProcesses(processes) {
461
664
  rendered.push(`${omitted} more blocking process(es)`);
462
665
  if (rendered.length === 0)
463
666
  return "a live process";
464
- if (rendered.length === 1)
465
- return rendered[0];
466
- const last = rendered.pop();
467
- return `${rendered.join(", ")}, and ${last}`;
667
+ const summary = rendered.length === 1 ? rendered[0] : `${rendered.slice(0, -1).join(", ")}, and ${rendered.at(-1)}`;
668
+ const evidence = entries.map(({ kind, pid, startTime, commandLine }) => `- PID ${pid}: ${kind}, started ${formatFailClosedProcessStartTime(startTime)}, cmd: ${formatFailClosedCommandLine(commandLine)}`).join(`
669
+ `);
670
+ return `${summary}
671
+ Blocking process evidence:
672
+ ${evidence}`;
468
673
  }
469
674
  function formatFailClosedBlockingMessage(reason) {
470
675
  if (reason.kind === "migration_guard") {
@@ -687,6 +892,17 @@ function readPsProcessStartTime(pid) {
687
892
  return null;
688
893
  }
689
894
  }
895
+ function readProcessStartTime(pid) {
896
+ if (!Number.isInteger(pid) || pid <= 0)
897
+ return null;
898
+ return rpcIdentityPlatform === "linux" ? readLinuxProcessStartTime(pid) : rpcIdentityPlatform === "win32" ? null : readPsProcessStartTime(pid);
899
+ }
900
+ function readProcessProbeEvidence(pid) {
901
+ return {
902
+ startTime: readProcessStartTime(pid),
903
+ commandLine: readProcessCommand(pid)
904
+ };
905
+ }
690
906
  function parseCsvLine(line) {
691
907
  const fields = [];
692
908
  let field = "";
@@ -819,16 +1035,16 @@ function commandLooksLikeOpenCode(command) {
819
1035
  const normalized = command.toLowerCase();
820
1036
  return OPEN_CODE_COMMAND_MARKERS.some((marker) => normalized.includes(marker));
821
1037
  }
822
- function isPidIdentityPlausible(record) {
1038
+ function isPidIdentityPlausible(record, evidence) {
823
1039
  if (!Number.isInteger(record.pid) || record.pid <= 0)
824
1040
  return "implausible";
825
1041
  if (Number.isFinite(record.started_at) && record.started_at > 0) {
826
- const processStartTime = rpcIdentityPlatform === "linux" ? readLinuxProcessStartTime(record.pid) : rpcIdentityPlatform === "win32" ? null : readPsProcessStartTime(record.pid);
1042
+ const processStartTime = evidence ? evidence.startTime : readProcessStartTime(record.pid);
827
1043
  if (processStartTime === null)
828
1044
  return "inconclusive";
829
1045
  return processStartTime <= record.started_at + RPC_IDENTITY_SKEW_TOLERANCE_MS ? "plausible" : "implausible";
830
1046
  }
831
- const command = rpcIdentityPlatform === "linux" ? readLinuxProcessCommand(record.pid) : rpcIdentityPlatform === "win32" ? readWindowsProcess(record.pid).command ?? null : readPsProcessCommand(record.pid);
1047
+ const command = evidence ? evidence.commandLine : rpcIdentityPlatform === "linux" ? readLinuxProcessCommand(record.pid) : rpcIdentityPlatform === "win32" ? readWindowsProcess(record.pid).command ?? null : readPsProcessCommand(record.pid);
832
1048
  if (command === null)
833
1049
  return "inconclusive";
834
1050
  return commandLooksLikeOpenCode(command) ? "plausible" : "implausible";
@@ -2407,7 +2623,7 @@ var CATEGORY_DEFAULT_TTL = {
2407
2623
  import { execFileSync as execFileSync2 } from "node:child_process";
2408
2624
  import { createHash as createHash3 } from "node:crypto";
2409
2625
  import { existsSync, realpathSync, statSync } from "node:fs";
2410
- import { homedir } from "node:os";
2626
+ import { homedir as homedir2 } from "node:os";
2411
2627
  import path from "node:path";
2412
2628
  var GIT_TIMEOUT_MS = 5000;
2413
2629
  var TRANSIENT_FAILURE_COOLDOWN_MS = 5 * 60 * 1000;
@@ -2421,7 +2637,7 @@ var dubiousOwnershipLoggedDirectories = new Set;
2421
2637
  var dubiousOwnershipWarnedDirectories = new Set;
2422
2638
  var transientGitIdentityReuseLoggedDirectories = new Set;
2423
2639
  var execFileSyncForIdentity = execFileSync2;
2424
- var userHomeDirectoryForIdentity = () => homedir();
2640
+ var userHomeDirectoryForIdentity = () => homedir2();
2425
2641
  var nowMs = () => Date.now();
2426
2642
 
2427
2643
  class ProjectIdentityError extends Error {
@@ -5308,7 +5524,7 @@ import { createHash as createHash5 } from "node:crypto";
5308
5524
  // src/hooks/magic-context/read-session-formatting.ts
5309
5525
  import { existsSync as existsSync2, readFileSync as readFileSync2, realpathSync as realpathSync2 } from "node:fs";
5310
5526
  import { createRequire } from "node:module";
5311
- import { homedir as homedir2 } from "node:os";
5527
+ import { homedir as homedir3 } from "node:os";
5312
5528
  import { dirname, join as join2, resolve } from "node:path";
5313
5529
  import { pathToFileURL } from "node:url";
5314
5530
 
@@ -5425,7 +5641,7 @@ var tokenizerLoadPromise;
5425
5641
  var tokenizerWarningSent = false;
5426
5642
  function tokenizerPackageRoots() {
5427
5643
  const cwd = process.cwd();
5428
- const openCodeCache = join2(process.env.XDG_CACHE_HOME ?? join2(homedir2(), ".cache"), "opencode");
5644
+ const openCodeCache = join2(process.env.XDG_CACHE_HOME ?? join2(homedir3(), ".cache"), "opencode");
5429
5645
  const roots = [cwd, openCodeCache];
5430
5646
  const candidates = [];
5431
5647
  for (const root of roots) {
@@ -6159,8 +6375,8 @@ function classifyDiscoveryRecordKind(record) {
6159
6375
  }
6160
6376
  return null;
6161
6377
  }
6162
- function classifyRpcProcess(record) {
6163
- return classifyDiscoveryRecordKind(record) ?? classifyProcessKind(readProcessCommand(record.pid));
6378
+ function classifyRpcProcess(record, commandLine) {
6379
+ return classifyDiscoveryRecordKind(record) ?? classifyProcessKind(commandLine === undefined ? readProcessProbeEvidence(record.pid).commandLine : commandLine);
6164
6380
  }
6165
6381
  function classifyJunkDiscovery(portFile, raw, staleFiles) {
6166
6382
  let mtimeMs;
@@ -6237,18 +6453,23 @@ function inspectRpcServerDiscovery(storageDir) {
6237
6453
  continue;
6238
6454
  }
6239
6455
  const liveness = isPidAlive(record.pid);
6240
- const identity = liveness === "dead" ? "implausible" : isPidIdentityPlausible(record);
6241
- if (liveness === "alive" && identity === "plausible") {
6456
+ if (liveness === "dead") {
6457
+ staleFiles.push(portFile);
6458
+ continue;
6459
+ }
6460
+ const evidence = readProcessProbeEvidence(record.pid);
6461
+ const identity = isPidIdentityPlausible(record, evidence);
6462
+ if (identity === "plausible") {
6242
6463
  pids.add(record.pid);
6243
- const detected = {
6244
- kind: classifyRpcProcess(record),
6464
+ const detected = attachFailClosedBlockingProcessEvidence({
6465
+ kind: classifyRpcProcess(record, evidence.commandLine),
6245
6466
  pid: record.pid
6246
- };
6467
+ }, evidence);
6247
6468
  const previous = processByPid.get(record.pid);
6248
6469
  if (!previous || previous.kind === "process" && detected.kind !== "process") {
6249
6470
  processByPid.set(record.pid, detected);
6250
6471
  }
6251
- } else if (liveness === "dead" || identity === "implausible") {
6472
+ } else if (identity === "implausible") {
6252
6473
  staleFiles.push(portFile);
6253
6474
  } else {
6254
6475
  inconclusivePids.add(record.pid);
@@ -6281,6 +6502,9 @@ function inspectRpcServerDiscovery(storageDir) {
6281
6502
  }
6282
6503
  return { state: "stale", serverPids: [], staleFiles };
6283
6504
  }
6505
+ function createPiBlockingProcess(pid) {
6506
+ return attachFailClosedBlockingProcessEvidence({ kind: "Pi", pid }, readProcessProbeEvidence(pid));
6507
+ }
6284
6508
  function formatInconclusiveOpenCodeMigrationWarning(dbPath, pids) {
6285
6509
  return `[magic-context] storage warning: continuing migration for ${dbPath}; OpenCode server PID ${pids.join(", ")} was not confirmed because its liveness or identity check could not run. This commonly means an OS sandbox denied kill(0) or ps. No live OpenCode server was confirmed.`;
6286
6510
  }
@@ -6322,10 +6546,7 @@ function enforceMigrationOnOpenGuard(db, dbPath, dbDir, latestSupportedVersion)
6322
6546
  const piDiscovery = inspectLivePiProcesses();
6323
6547
  const piPids = migrationBlockingPiPids(dbPath, discovery, piDiscovery.processIds);
6324
6548
  const serverProcesses = discovery.serverProcesses ?? (discovery.state === "live" ? discovery.serverPids.map((pid) => ({ kind: "process", pid })) : []);
6325
- const blockingProcesses = [
6326
- ...serverProcesses,
6327
- ...piPids.map((pid) => ({ kind: "Pi", pid }))
6328
- ];
6549
+ const blockingProcesses = [...serverProcesses, ...piPids.map(createPiBlockingProcess)];
6329
6550
  if ((discovery.state === "absent" || discovery.state === "stale" || discovery.state === "inconclusive") && piPids.length === 0) {
6330
6551
  lastMigrationOnOpenRefusal = null;
6331
6552
  logInconclusiveMigrationProbes(dbPath, discovery, piDiscovery.state);
@@ -14380,15 +14601,15 @@ import {
14380
14601
  unlinkSync as unlinkSync2,
14381
14602
  writeFileSync
14382
14603
  } from "node:fs";
14383
- import { homedir as homedir3 } from "node:os";
14604
+ import { homedir as homedir4 } from "node:os";
14384
14605
  import { basename as basename2, dirname as dirname3, isAbsolute, join as join5 } from "node:path";
14385
14606
  var CONFIG_FILE_BASENAME = "magic-context";
14386
14607
  var MOVED_MARKER_SUFFIX = ".MOVED_READPLEASE";
14387
14608
  function homeDir() {
14388
14609
  if (process.platform === "win32") {
14389
- return process.env.USERPROFILE || process.env.HOME || homedir3();
14610
+ return process.env.USERPROFILE || process.env.HOME || homedir4();
14390
14611
  }
14391
- return process.env.HOME || homedir3();
14612
+ return process.env.HOME || homedir4();
14392
14613
  }
14393
14614
  function configHome() {
14394
14615
  const xdg = process.env.XDG_CONFIG_HOME;
@@ -16927,7 +17148,7 @@ function countSessionCompartmentEmbedCoverage(db, projectPath, sessionId, modelI
16927
17148
  import { createHash as createHash14, randomUUID as randomUUID2 } from "node:crypto";
16928
17149
 
16929
17150
  // src/config/schema/magic-context.ts
16930
- import { homedir as homedir4 } from "node:os";
17151
+ import { homedir as homedir5 } from "node:os";
16931
17152
 
16932
17153
  // ../../node_modules/.bun/zod@4.4.3/node_modules/zod/v4/classic/external.js
16933
17154
  var exports_external = {};
@@ -17554,7 +17775,7 @@ __export(exports_util, {
17554
17775
  createTransparentProxy: () => createTransparentProxy,
17555
17776
  defineLazy: () => defineLazy,
17556
17777
  esc: () => esc,
17557
- escapeRegex: () => escapeRegex,
17778
+ escapeRegex: () => escapeRegex2,
17558
17779
  explicitlyAborted: () => explicitlyAborted,
17559
17780
  extend: () => extend,
17560
17781
  finalizeIssue: () => finalizeIssue,
@@ -17831,7 +18052,7 @@ var primitiveTypes = /* @__PURE__ */ new Set([
17831
18052
  "symbol",
17832
18053
  "undefined"
17833
18054
  ]);
17834
- function escapeRegex(str) {
18055
+ function escapeRegex2(str) {
17835
18056
  return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
17836
18057
  }
17837
18058
  function clone(inst, def, params) {
@@ -18541,7 +18762,7 @@ function emoji() {
18541
18762
  var ipv4 = /^(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])\.){3}(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])$/;
18542
18763
  var ipv6 = /^(([0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:))$/;
18543
18764
  var mac = (delimiter) => {
18544
- const escapedDelim = escapeRegex(delimiter ?? ":");
18765
+ const escapedDelim = escapeRegex2(delimiter ?? ":");
18545
18766
  return new RegExp(`^(?:[0-9A-F]{2}${escapedDelim}){5}[0-9A-F]{2}$|^(?:[0-9a-f]{2}${escapedDelim}){5}[0-9a-f]{2}$`);
18546
18767
  };
18547
18768
  var cidrv4 = /^((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])\.){3}(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])\/([0-9]|[1-2][0-9]|3[0-2])$/;
@@ -19042,7 +19263,7 @@ var $ZodCheckUpperCase = /* @__PURE__ */ $constructor("$ZodCheckUpperCase", (ins
19042
19263
  });
19043
19264
  var $ZodCheckIncludes = /* @__PURE__ */ $constructor("$ZodCheckIncludes", (inst, def) => {
19044
19265
  $ZodCheck.init(inst, def);
19045
- const escapedRegex = escapeRegex(def.includes);
19266
+ const escapedRegex = escapeRegex2(def.includes);
19046
19267
  const pattern = new RegExp(typeof def.position === "number" ? `^.{${def.position}}${escapedRegex}` : escapedRegex);
19047
19268
  def.pattern = pattern;
19048
19269
  inst._zod.onattach.push((inst2) => {
@@ -19066,7 +19287,7 @@ var $ZodCheckIncludes = /* @__PURE__ */ $constructor("$ZodCheckIncludes", (inst,
19066
19287
  });
19067
19288
  var $ZodCheckStartsWith = /* @__PURE__ */ $constructor("$ZodCheckStartsWith", (inst, def) => {
19068
19289
  $ZodCheck.init(inst, def);
19069
- const pattern = new RegExp(`^${escapeRegex(def.prefix)}.*`);
19290
+ const pattern = new RegExp(`^${escapeRegex2(def.prefix)}.*`);
19070
19291
  def.pattern ?? (def.pattern = pattern);
19071
19292
  inst._zod.onattach.push((inst2) => {
19072
19293
  const bag = inst2._zod.bag;
@@ -19089,7 +19310,7 @@ var $ZodCheckStartsWith = /* @__PURE__ */ $constructor("$ZodCheckStartsWith", (i
19089
19310
  });
19090
19311
  var $ZodCheckEndsWith = /* @__PURE__ */ $constructor("$ZodCheckEndsWith", (inst, def) => {
19091
19312
  $ZodCheck.init(inst, def);
19092
- const pattern = new RegExp(`.*${escapeRegex(def.suffix)}$`);
19313
+ const pattern = new RegExp(`.*${escapeRegex2(def.suffix)}$`);
19093
19314
  def.pattern ?? (def.pattern = pattern);
19094
19315
  inst._zod.onattach.push((inst2) => {
19095
19316
  const bag = inst2._zod.bag;
@@ -20736,7 +20957,7 @@ var $ZodEnum = /* @__PURE__ */ $constructor("$ZodEnum", (inst, def) => {
20736
20957
  const values = getEnumValues(def.entries);
20737
20958
  const valuesSet = new Set(values);
20738
20959
  inst._zod.values = valuesSet;
20739
- inst._zod.pattern = new RegExp(`^(${values.filter((k) => propertyKeyTypes.has(typeof k)).map((o) => typeof o === "string" ? escapeRegex(o) : o.toString()).join("|")})$`);
20960
+ inst._zod.pattern = new RegExp(`^(${values.filter((k) => propertyKeyTypes.has(typeof k)).map((o) => typeof o === "string" ? escapeRegex2(o) : o.toString()).join("|")})$`);
20740
20961
  inst._zod.parse = (payload, _ctx) => {
20741
20962
  const input = payload.value;
20742
20963
  if (valuesSet.has(input)) {
@@ -20758,7 +20979,7 @@ var $ZodLiteral = /* @__PURE__ */ $constructor("$ZodLiteral", (inst, def) => {
20758
20979
  }
20759
20980
  const values = new Set(def.values);
20760
20981
  inst._zod.values = values;
20761
- inst._zod.pattern = new RegExp(`^(${def.values.map((o) => typeof o === "string" ? escapeRegex(o) : o ? escapeRegex(o.toString()) : String(o)).join("|")})$`);
20982
+ inst._zod.pattern = new RegExp(`^(${def.values.map((o) => typeof o === "string" ? escapeRegex2(o) : o ? escapeRegex2(o.toString()) : String(o)).join("|")})$`);
20762
20983
  inst._zod.parse = (payload, _ctx) => {
20763
20984
  const input = payload.value;
20764
20985
  if (values.has(input)) {
@@ -21123,7 +21344,7 @@ var $ZodTemplateLiteral = /* @__PURE__ */ $constructor("$ZodTemplateLiteral", (i
21123
21344
  const end = source.endsWith("$") ? source.length - 1 : source.length;
21124
21345
  regexParts.push(source.slice(start, end));
21125
21346
  } else if (part === null || primitiveTypes.has(typeof part)) {
21126
- regexParts.push(escapeRegex(`${part}`));
21347
+ regexParts.push(escapeRegex2(`${part}`));
21127
21348
  } else {
21128
21349
  throw new Error(`Invalid template literal part: ${part}`);
21129
21350
  }
@@ -31492,6 +31713,37 @@ var DreamerPiHarnessBlockSchema = exports_external.object({
31492
31713
  thinking_level: PiThinkingLevelSchema.describe("Pi thinking level for the primary entry when it declares none. Fallback entries declare thinking levels per-entry."),
31493
31714
  tasks: exports_external.record(exports_external.string(), PiTaskExecutionSchema).optional().describe("Pi task execution overrides. Each named task accepts only model, fallback_models, thinking_level, and timeout_minutes.")
31494
31715
  }).strict().describe("Strict Pi dreamer model-resolution block. It accepts no OpenCode vocabulary.");
31716
+ var ProfileOpenCodeModelBlockSchema = exports_external.object({
31717
+ model: OcEntrySchema.optional().describe("Primary OpenCode model entry."),
31718
+ fallback_models: exports_external.array(OcEntrySchema).optional().describe("Ordered fallback OpenCode model entries."),
31719
+ variant: exports_external.string().optional().describe("OpenCode reasoning variant for the primary model entry.")
31720
+ }).strict().describe("Strict profile-only OpenCode model-selection block.");
31721
+ var ProfilePiModelBlockSchema = exports_external.object({
31722
+ model: PiEntrySchema.optional().describe("Primary Pi model entry."),
31723
+ fallback_models: exports_external.array(PiEntrySchema).optional().describe("Ordered fallback Pi model entries."),
31724
+ thinking_level: PiThinkingLevelSchema.describe("Pi thinking level for the primary model entry.")
31725
+ }).strict().describe("Strict profile-only Pi model-selection block.");
31726
+ var ProfileHistorianSchema = exports_external.object({
31727
+ opencode: ProfileOpenCodeModelBlockSchema.optional(),
31728
+ pi: ProfilePiModelBlockSchema.optional()
31729
+ }).strict();
31730
+ var ProfileDreamerSchema = exports_external.object({
31731
+ opencode: ProfileOpenCodeModelBlockSchema.optional(),
31732
+ pi: ProfilePiModelBlockSchema.optional()
31733
+ }).strict();
31734
+ var ProfileSidekickSchema = AgentOverrideConfigSchema.pick({
31735
+ model: true,
31736
+ fallback_models: true,
31737
+ variant: true
31738
+ }).extend({
31739
+ thinking_level: PiThinkingLevelSchema.describe("Pi thinking level for the sidekick model selection.")
31740
+ }).strict();
31741
+ var ConfigProfileSchema = exports_external.object({
31742
+ historian: ProfileHistorianSchema.optional(),
31743
+ dreamer: ProfileDreamerSchema.optional(),
31744
+ sidekick: ProfileSidekickSchema.optional()
31745
+ }).strict().describe("User-owned model-selection overlay. Only historian/dreamer harness model blocks and sidekick model-selection fields are allowed.");
31746
+ var ConfigProfilesSchema = exports_external.record(exports_external.string().trim().min(1, "Profile names must not be empty or whitespace-only."), ConfigProfileSchema);
31495
31747
  var CronScheduleSchema = exports_external.string().refine((s) => s.trim() === "" || isValidCron(s), {
31496
31748
  message: 'Invalid schedule: use a 5-field cron expression (e.g. "0 3 * * *" for 3am daily, "0 3 * * 0" for Sunday 3am, "0 */6 * * *" every 6h) or "" to disable.'
31497
31749
  }).describe('5-field cron schedule (e.g. "0 3 * * *"), or "" to disable this task.');
@@ -31579,9 +31831,9 @@ var EmbeddingFallbackProviderSchema = exports_external.enum(["local", "openai-co
31579
31831
  function expandConfigPath(value) {
31580
31832
  const trimmed = value.trim();
31581
31833
  if (trimmed === "~")
31582
- return homedir4();
31834
+ return homedir5();
31583
31835
  if (trimmed.startsWith("~/"))
31584
- return `${homedir4()}/${trimmed.slice(2)}`;
31836
+ return `${homedir5()}/${trimmed.slice(2)}`;
31585
31837
  return trimmed;
31586
31838
  }
31587
31839
  var BaseEmbeddingConfigSchema = exports_external.object({
@@ -31682,6 +31934,8 @@ var MagicContextConfigSchema = exports_external.object({
31682
31934
  transform_mode: exports_external.enum(["ts", "rust"]).default("ts").describe('Experimental: routes the entire Magic Context runtime for the project through the ck-mc Rust module over subc (requires user-level `subc` config); "ts" is the current TypeScript pipeline.'),
31683
31935
  auto_update: exports_external.boolean().optional().describe("Enable automatic npm self-update checks for the OpenCode plugin. Security: USER-only in config loader, so hostile project configs cannot suppress updates."),
31684
31936
  language: exports_external.string().trim().toLowerCase().refine((s) => isValidLanguageCode(s), 'language must be a 2-letter ISO 639-1 code (e.g. "tr", "es", "de")').optional().describe("Output language for Magic Context's generated content and guidance, as a " + '2-letter ISO 639-1 code (e.g. "tr", "es", "de", "ja", "pt"). When set, the ' + "historian, dreamer, sidekick, and the agent-guidance block instruct the model to " + "write its PROSE in this language while keeping all structural tokens (XML tags, " + "the five memory category names, code identifiers, file paths) in English. " + "USER-LEVEL ONLY (ignored in project config for security). Unset = today's " + "behavior (model mirrors the conversation; English scaffolding). Changing it " + "triggers one cache re-materialization; existing compartments/memories keep their " + "original language until naturally rewritten."),
31937
+ profile: exports_external.string().trim().min(1).optional().describe("Select a named user-owned model profile. A valid project name overrides this user default; an empty string, null, or other non-string project value is ignored with a warning so the user selection still applies. Unknown names warn and use the base configuration."),
31938
+ profiles: ConfigProfilesSchema.optional().describe("User-level named model profiles. A profile may contain only historian/dreamer model, fallback_models, OpenCode variant, and Pi thinking_level fields plus sidekick model-selection fields; task execution policy (including timeout_minutes) is excluded. Project configs may select a name but cannot define profiles."),
31685
31939
  historian: HistorianConfigSchema.describe("Historian metadata plus independent strict OpenCode and Pi execution blocks. Retained metadata stays at historian; model, fallback_models, variant, and thinking_level belong only in historian.opencode or historian.pi."),
31686
31940
  dreamer: DreamerConfigSchema.optional().describe("Dreamer metadata and scheduling plus independent strict OpenCode and Pi execution blocks. schedule and promotion_threshold stay at dreamer.tasks; model, fallback_models, variant, thinking_level, and timeout_minutes belong only in the matching harness block."),
31687
31941
  smart_notes: exports_external.object({
@@ -32098,6 +32352,25 @@ function releaseGitSweepLease(db, projectPath, holderId) {
32098
32352
  });
32099
32353
  }
32100
32354
 
32355
+ // src/features/magic-context/memory/embedding-failure.ts
32356
+ function dominantEmbeddingFailure(failures) {
32357
+ const counts = new Map;
32358
+ for (const failure of failures) {
32359
+ const key = `${failure.class}\x00${failure.reason}`;
32360
+ const current = counts.get(key);
32361
+ if (current)
32362
+ current.count += 1;
32363
+ else
32364
+ counts.set(key, { failure, count: 1 });
32365
+ }
32366
+ let dominant;
32367
+ for (const candidate of counts.values()) {
32368
+ if (!dominant || candidate.count > dominant.count)
32369
+ dominant = candidate;
32370
+ }
32371
+ return dominant?.failure;
32372
+ }
32373
+
32101
32374
  // src/features/magic-context/memory/embedding-synapse.ts
32102
32375
  import { createHash as createHash13 } from "node:crypto";
32103
32376
 
@@ -34477,6 +34750,7 @@ class OpenAICompatibleEmbeddingProvider {
34477
34750
  circuitOpenUntil = 0;
34478
34751
  openLogged = false;
34479
34752
  modelMismatchLogged = false;
34753
+ lastFailureReason = null;
34480
34754
  halfOpenProbeInFlight = false;
34481
34755
  constructor(options) {
34482
34756
  this.endpoint = normalizeEndpoint2(options.endpoint);
@@ -34566,41 +34840,59 @@ class OpenAICompatibleEmbeddingProvider {
34566
34840
  signal: internalController.signal
34567
34841
  });
34568
34842
  if (!response.ok) {
34569
- log(`[magic-context] openai-compatible embedding request failed: ${response.status} ${response.statusText}`);
34570
- this.recordFailure(isProbe);
34843
+ const excerpt = await response.text().catch(() => "");
34844
+ const failure = this.failure("http_error", `HTTP ${response.status} from endpoint${this.bodyExcerpt(excerpt)}`, response.status >= 500 || response.status === 408 || response.status === 429);
34845
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34846
+ this.recordFailure(isProbe, failure);
34571
34847
  return Array.from({ length: texts.length }, () => null);
34572
34848
  }
34573
34849
  const rawBody = await response.text();
34574
34850
  if (rawBody.trim().length === 0) {
34575
- log(`[magic-context] openai-compatible embedding request returned empty body (status=${response.status}, content-type=${response.headers.get("content-type") ?? "none"})`);
34576
- this.recordFailure(isProbe);
34851
+ const failure = this.failure("invalid_envelope", "response body was empty", false);
34852
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34853
+ this.recordFailure(isProbe, failure);
34577
34854
  return Array.from({ length: texts.length }, () => null);
34578
34855
  }
34579
34856
  let body;
34580
34857
  try {
34581
34858
  body = JSON.parse(rawBody);
34582
- } catch (parseError) {
34583
- const snippet = rawBody.slice(0, 200).replace(/\s+/g, " ");
34584
- log(`[magic-context] openai-compatible embedding response was not JSON (status=${response.status}, ${rawBody.length}B body, snippet="${snippet}"):`, parseError instanceof Error ? parseError.message : parseError);
34585
- this.recordFailure(isProbe);
34859
+ } catch {
34860
+ const failure = this.failure("invalid_envelope", `response body was not valid JSON${this.bodyExcerpt(rawBody)}`, false);
34861
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34862
+ this.recordFailure(isProbe, failure);
34586
34863
  return Array.from({ length: texts.length }, () => null);
34587
34864
  }
34588
34865
  const servedModel = typeof body.model === "string" ? body.model : "";
34589
34866
  if (this.model && servedModel && !embeddingModelsMatch(servedModel, this.model)) {
34590
34867
  if (!this.modelMismatchLogged) {
34591
- log(`[magic-context] embedding endpoint served a DIFFERENT model than requested — refusing the substituted vectors (they have the wrong dimensions/space). requested="${this.model}" served="${servedModel}". Check that the endpoint serves the requested model; variant suffixes and vendor prefixes are matched automatically.`);
34868
+ log(`[magic-context] embedding endpoint served a DIFFERENT model than requested — refusing the substituted vectors (they have the wrong dimensions/space). requested="${sanitizeDiagnosticText(this.model)}" served="${sanitizeDiagnosticText(servedModel)}". Check that the endpoint serves the requested model; variant suffixes and vendor prefixes are matched automatically.`);
34592
34869
  this.modelMismatchLogged = true;
34593
34870
  }
34594
- this.recordFailure(isProbe);
34871
+ this.recordFailure(isProbe, this.failure("substitution_rejected", `served model '${sanitizeDiagnosticText(servedModel)}' does not match requested '${sanitizeDiagnosticText(this.model)}' (substitution guard)`, false));
34595
34872
  return Array.from({ length: texts.length }, () => null);
34596
34873
  }
34597
- const items = Array.isArray(body.data) ? body.data : [];
34874
+ const responseKeys = Object.keys(body).sort();
34875
+ if (!Array.isArray(body.data)) {
34876
+ const failure = this.failure("invalid_envelope", `response had keys [${responseKeys.join(", ")}] but data[] was absent`, false);
34877
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34878
+ this.recordFailure(isProbe, failure);
34879
+ return Array.from({ length: texts.length }, () => null);
34880
+ }
34881
+ if (body.data.length === 0) {
34882
+ const failure = this.failure("empty_result", "response data[] was empty", true);
34883
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34884
+ this.recordFailure(isProbe, failure);
34885
+ return Array.from({ length: texts.length }, () => null);
34886
+ }
34887
+ const items = body.data;
34598
34888
  const results = Array.from({ length: texts.length }, (_, index) => {
34599
34889
  const embedding = items[index]?.embedding;
34600
34890
  return Array.isArray(embedding) ? Float32Array.from(embedding) : null;
34601
34891
  });
34602
34892
  if (results.every((r) => r === null)) {
34603
- this.recordFailure(isProbe);
34893
+ const failure = this.failure("invalid_envelope", `response had keys [${responseKeys.join(", ")}] but data[].embedding was absent`, false);
34894
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34895
+ this.recordFailure(isProbe, failure);
34604
34896
  } else {
34605
34897
  this.recordSuccess();
34606
34898
  }
@@ -34610,11 +34902,14 @@ class OpenAICompatibleEmbeddingProvider {
34610
34902
  if (isAbort) {
34611
34903
  if (signal?.aborted) {} else {
34612
34904
  log(`[magic-context] openai-compatible embedding request timed out after ${FETCH_TIMEOUT_MS}ms`);
34613
- this.recordFailure(isProbe);
34905
+ const failure = this.failure("transport_error", `request timed out after ${FETCH_TIMEOUT_MS}ms`, true);
34906
+ this.recordFailure(isProbe, failure);
34614
34907
  }
34615
34908
  } else {
34616
- log("[magic-context] openai-compatible embedding request failed:", error51);
34617
- this.recordFailure(isProbe);
34909
+ const detail = error51 instanceof Error ? error51.message : String(error51);
34910
+ const failure = this.failure("transport_error", `transport error: ${sanitizeDiagnosticText(detail)}`, true);
34911
+ log(`[magic-context] openai-compatible embedding request failed: ${failure.reason}`);
34912
+ this.recordFailure(isProbe, failure);
34618
34913
  }
34619
34914
  return Array.from({ length: texts.length }, () => null);
34620
34915
  } finally {
@@ -34646,14 +34941,23 @@ class OpenAICompatibleEmbeddingProvider {
34646
34941
  return "short_circuit";
34647
34942
  }
34648
34943
  this.halfOpenProbeInFlight = true;
34649
- log("[magic-context] openai-compatible embedding: circuit half-open, probing endpoint");
34944
+ log(`[magic-context] openai-compatible embedding: circuit half-open, probing endpoint after ${this.lastFailureReason?.reason ?? "unknown failure"}`);
34650
34945
  return "probe";
34651
34946
  }
34652
- recordFailure(isProbe) {
34947
+ failure(failureClass, reason, retryable) {
34948
+ return { class: failureClass, reason, retryable };
34949
+ }
34950
+ bodyExcerpt(body) {
34951
+ const excerpt = sanitizeDiagnosticText(body).replace(/\s+/g, " ").trim().slice(0, 200);
34952
+ return excerpt ? `: ${excerpt}` : "";
34953
+ }
34954
+ recordFailure(isProbe, failure) {
34955
+ if (failure)
34956
+ this.lastFailureReason = failure;
34653
34957
  if (isProbe) {
34654
34958
  this.circuitOpenUntil = Date.now() + OPEN_DURATION_MS;
34655
34959
  if (!this.openLogged) {
34656
- log(`[magic-context] openai-compatible embedding: probe failed, re-opening circuit for ${OPEN_DURATION_MS / 60000}min`);
34960
+ log(`[magic-context] openai-compatible embedding: probe failed (${failure?.reason ?? this.lastFailureReason?.reason ?? "unknown failure"}), re-opening circuit for ${OPEN_DURATION_MS / 60000}min`);
34657
34961
  this.openLogged = true;
34658
34962
  }
34659
34963
  this.failureTimes = [];
@@ -34666,7 +34970,7 @@ class OpenAICompatibleEmbeddingProvider {
34666
34970
  if (this.failureTimes.length >= FAILURE_THRESHOLD) {
34667
34971
  this.circuitOpenUntil = now + OPEN_DURATION_MS;
34668
34972
  if (!this.openLogged) {
34669
- log(`[magic-context] openai-compatible embedding: opening circuit for ${OPEN_DURATION_MS / 60000}min after ${this.failureTimes.length} failures in ${FAILURE_WINDOW_MS / 1000}s`);
34973
+ log(`[magic-context] openai-compatible embedding: opening circuit for ${OPEN_DURATION_MS / 60000}min after ${this.failureTimes.length} failures in ${FAILURE_WINDOW_MS / 1000}s (${failure?.reason ?? this.lastFailureReason?.reason ?? "unknown failure"})`);
34670
34974
  this.openLogged = true;
34671
34975
  }
34672
34976
  this.failureTimes = [];
@@ -34679,6 +34983,10 @@ class OpenAICompatibleEmbeddingProvider {
34679
34983
  this.failureTimes = [];
34680
34984
  this.circuitOpenUntil = 0;
34681
34985
  this.openLogged = false;
34986
+ this.lastFailureReason = null;
34987
+ }
34988
+ getLastFailureReason() {
34989
+ return this.lastFailureReason;
34682
34990
  }
34683
34991
  _getCircuitState() {
34684
34992
  if (this.circuitOpenUntil === 0)
@@ -34696,6 +35004,7 @@ class OpenAICompatibleEmbeddingProvider {
34696
35004
  this.circuitOpenUntil = 0;
34697
35005
  this.openLogged = false;
34698
35006
  this.halfOpenProbeInFlight = false;
35007
+ this.lastFailureReason = null;
34699
35008
  }
34700
35009
  }
34701
35010
 
@@ -35945,11 +36254,16 @@ async function drainCommitBacklogForProject(db, projectIdentity, deadline) {
35945
36254
  }
35946
36255
  return total;
35947
36256
  }
36257
+ function getLastEmbeddingFailureForProject(projectIdentity) {
36258
+ const registration = projectRegistrations.get(projectIdentity);
36259
+ return registration?.provider?.getLastFailureReason?.() ?? null;
36260
+ }
35948
36261
  async function embedCandidateChunkBatch(db, projectIdentity, modelId, candidates, signal) {
35949
36262
  const noWork = [];
35950
36263
  const failed = [];
36264
+ const failureReasons = [];
35951
36265
  if (candidates.length === 0)
35952
- return { embedded: 0, noWork, failed };
36266
+ return { embedded: 0, noWork, failed, failureReasons };
35953
36267
  const maxInputTokens = getProjectEmbeddingMaxInputTokens(projectIdentity);
35954
36268
  const prepared = [];
35955
36269
  for (const candidate of candidates) {
@@ -35966,7 +36280,7 @@ async function embedCandidateChunkBatch(db, projectIdentity, modelId, candidates
35966
36280
  prepared.push({ candidate, windows });
35967
36281
  }
35968
36282
  if (prepared.length === 0)
35969
- return { embedded: 0, noWork, failed };
36283
+ return { embedded: 0, noWork, failed, failureReasons };
35970
36284
  let embedded = 0;
35971
36285
  let i = 0;
35972
36286
  while (i < prepared.length) {
@@ -35998,6 +36312,11 @@ async function embedCandidateChunkBatch(db, projectIdentity, modelId, candidates
35998
36312
  }
35999
36313
  if (signal?.aborted)
36000
36314
  break;
36315
+ if (!result || result.vectors.size === 0) {
36316
+ const failure = getLastEmbeddingFailureForProject(projectIdentity);
36317
+ if (failure)
36318
+ failureReasons.push(failure);
36319
+ }
36001
36320
  if (result) {
36002
36321
  for (const item of slice) {
36003
36322
  if (persistedIds.has(item.candidate.id))
@@ -36039,7 +36358,7 @@ async function embedCandidateChunkBatch(db, projectIdentity, modelId, candidates
36039
36358
  }
36040
36359
  }
36041
36360
  }
36042
- return { embedded, noWork, failed };
36361
+ return { embedded, noWork, failed, failureReasons };
36043
36362
  }
36044
36363
  async function embedSessionCompartmentChunks(db, projectIdentity, sessionId, options) {
36045
36364
  const snapshot2 = getProjectEmbeddingSnapshot(projectIdentity);
@@ -36077,6 +36396,7 @@ async function embedSessionCompartmentChunks(db, projectIdentity, sessionId, opt
36077
36396
  let aborted2 = false;
36078
36397
  let providerDown = false;
36079
36398
  let consecutiveFailedBatches = 0;
36399
+ const failureReasons = [];
36080
36400
  try {
36081
36401
  options?.onProgress?.({ embedded, total });
36082
36402
  for (;; ) {
@@ -36090,7 +36410,8 @@ async function embedSessionCompartmentChunks(db, projectIdentity, sessionId, opt
36090
36410
  const {
36091
36411
  embedded: n,
36092
36412
  noWork,
36093
- failed
36413
+ failed,
36414
+ failureReasons: batchFailureReasons
36094
36415
  } = await embedCandidateChunkBatch(db, projectIdentity, snapshot2.chunkModelId, candidates, drainAbort.signal);
36095
36416
  if (leaseLost || !renewGitSweepLease(db, projectIdentity, holderId)) {
36096
36417
  leaseLost = true;
@@ -36098,6 +36419,7 @@ async function embedSessionCompartmentChunks(db, projectIdentity, sessionId, opt
36098
36419
  aborted2 = true;
36099
36420
  break;
36100
36421
  }
36422
+ failureReasons.push(...batchFailureReasons);
36101
36423
  for (const id of noWork)
36102
36424
  skipIds.push(id);
36103
36425
  for (const id of failed)
@@ -36129,7 +36451,14 @@ async function embedSessionCompartmentChunks(db, projectIdentity, sessionId, opt
36129
36451
  if (providerDown || failedIds.length > 0) {
36130
36452
  const remaining = Math.max(0, countUnembeddedSessionCompartments(db, projectIdentity, sessionId, snapshot2.chunkModelId) - skipIds.length);
36131
36453
  if (remaining > 0) {
36132
- return { status: "stalled", embedded, total, remaining, failed: failedIds.length };
36454
+ return {
36455
+ status: "stalled",
36456
+ embedded,
36457
+ total,
36458
+ remaining,
36459
+ failed: failedIds.length,
36460
+ failure: dominantEmbeddingFailure(failureReasons)
36461
+ };
36133
36462
  }
36134
36463
  }
36135
36464
  return { status: "done", embedded, total, failed: failedIds.length };
@@ -41072,7 +41401,7 @@ function mustMaterialize(args) {
41072
41401
  }
41073
41402
  const liveToolSetHash = hard.toolSetHash ?? "";
41074
41403
  const toolSetHashComparison = liveToolSetHash !== "" ? {
41075
- m0ToolSetHashPrev: args.state.cachedM0ToolSetHash ?? "",
41404
+ m0ToolSetHashPrev: args.state.cachedM0ToolSetHash,
41076
41405
  m0ToolSetHashNew: liveToolSetHash
41077
41406
  } : null;
41078
41407
  const withToolSetHashComparison = (decision) => toolSetHashComparison ? { ...decision, ...toolSetHashComparison } : decision;
@@ -46467,4 +46796,4 @@ async function runUpgradeMemoryMigration(ctx, sessionId, migrationDirectory) {
46467
46796
  }
46468
46797
  }
46469
46798
 
46470
- export { withContentLanguageDirective, buildPrimaryLanguageDirective, cortexKitUserConfigBasePath, cortexKitProjectConfigBasePath, resolveLegacyConfigSources, resolveLegacyConfigSourcesForHarness, migrateMagicContextConfigLocations, exports_external, DEFAULT_PROTECTED_TAGS, parseCron, nextOccurrence, nextDueAtMs, promptSurfaceConfigIdentity, resolvePromptSurface, resolveModelConfigOrDefault, DEFAULT_EXECUTE_THRESHOLD_PERCENTAGE, DEFAULT_HISTORIAN_TIMEOUT_MS, DEFAULT_LOCAL_EMBEDDING_MODEL, PER_HARNESS_MIGRATION_INVENTORY, MagicContextConfigSchema, getOpenCodeDbPath, removeMcOwnedCompactionMarkers, isFailClosedBlockingError, shouldBypassFailClosedBlock, resolveAgentNameFromMessages, createFailClosedController, recordHookInitFailure, clearHookInitFailure, getLastHookInitFailure, ProjectIdentityError, resolveProjectIdentityStrict, takeDubiousOwnershipProjectIdentityWarning, resolveProjectIdentity, resolveProjectIdentityForSession, normalizeStoredProjectPath, storedPathBelongsToIdentity, isLinkedGitWorktree, recordSessionProjectIdentity, beginBootQuietPeriod, bootQuietRemainingMs, scheduleAfterBootQuiet, rpcPortDir, rpcPortFilePath, isPidAlive, parseRpcPortFile, registerModuleNoteEvaluationBridge, getModuleNoteEvaluationBridge, getContextStoreUuid, ensureContextStoreUuid, getAuthorityManagedMarker, reconcileAuthorityProject, checksumAuthoritySeedRows, prepareAuthority, drainAuthority, getMirrorCursor, applyMirroredNoteCompileFields, applyMirrorPage, pullMemoryMirrorOnce, V2_MEMORY_CATEGORIES, CATEGORY_PRIORITY, resolveWorkspaceShareCategories, resolveWorkspaceIdentitySet, expandWorkspaceIdentitySetWithAliases, resolveStoredPathWorkspaceIdentity, storedPathBelongsToWorkspace, sourceNameForMemory, computeWorkspaceEpochFingerprint, textMentionsRecentCommit, hasMeaningfulUserText, extractTexts, extractToolCallSummaries, preloadTokenizer, estimateTokens, normalizeText, getCurrentToolSetHash, recordToolDefinition, getMeasuredToolDefinitionTokens, getSchemaFenceRejection, getMigrationOnOpenRefusal, LATEST_SUPPORTED_VERSION, getDatabasePath, getPersistedSchemaVersion, setSqlitePragmaConfig, runSqliteOptimize, openDatabase, openDatabaseAsync, isDatabasePersisted, getDatabasePersistenceError, COMPARTMENT_LEASE_RENEWAL_MS, acquireCompartmentLease, renewCompartmentLease, releaseCompartmentLease, getCompartments, getLastCompartmentEndMessage, getLastCompartmentEndMessageId, clearRecompStaging, isRawCompactionSummaryInfo, extractInMemoryMessageViews, buildInMemoryTailRawMessages, isRecord, estimateTrueRawMessageTokens, invalidateTrueRawTokenCache, stripPersistedAssistantText, byteSize, stripTagPrefix, prependTag, isThinkingPart, isTextPart, isToolPartWithOutput, isFilePart, buildFileSourceContent, isEditTool, partHasCompletedResult, extractToolCallObservation, ToolMutationBatch, createToolDropTarget, setRawMessageProvider, cleanUserText, withRawSessionMessageCache, readRawSessionMessages, primeTailRawMessageCache, primeInMemoryTailRawMessageCache, readRawSessionMessageOrdinalPage, getRawSessionStoredMessageCount, readRawSessionMessagePartsById, readRawSessionMessageOrdinalById, readRawSessionMessageById, readSessionChunk, getMessageIndexSourceIdentity, isMessageIndexSourceCurrent, getLastIndexedOrdinal, getIndexedMessageCorpusSize, getMessageIndexReconciliationStartOrdinal, isMessageIndexReconciledThrough, deleteIndexedMessage, clearIndexedMessages, indexSingleMessage, indexMessagesAfterOrdinal, sweepOrphanedOpenCodeMessageIndexes, recordEmbeddingMeasurement, getMaxM0MutationId, queueMemoryMutation, getMemoryMutationsForRenderByProjects, getMaxMemoryMutationIdForProjects, MAX_EXECUTE_THRESHOLD, escalationBands, isEmergencyRecoveryArmed, isProviderOverflowReconfirmed, getEmergencyRecoveryArmedAt, loadPersistedUsage, loadProtectedTailMeta, resetProtectedTailNoEligibleHead, getWrapupInProgressState, acquireWrapupInProgress, updateWrapupInProgress, releaseWrapupInProgress, resolveCompactionModeRecord, getCompactionModeRecord, setCompactionModeRecord, getPersistedReasoningWatermark, setPersistedReasoningWatermark, clearPersistedReasoningWatermark, getEmergencyInputSample, setEmergencyDropSample, clearEmergencyDropSample, getLastNudgeUndropped, setLastNudgeUndropped, getChannel1NudgeState, setChannel1NudgeState, resetLastNudgeCycle, resetLastNudgeCycleIfTailShrank, getChannel2NudgeState, getChannel2NudgeClaim, setChannel2NudgeState, casChannel2NudgeState, claimChannel2NudgeState, casChannel2NudgeClaim, getPersistedNoteNudge, getNoteNudgeAnchors, getAutoSearchHintDecisions, appendAutoSearchHintDecision, pruneNoteNudgeAnchors, pruneAutoSearchHintDecisions, removeNoteNudgeAnchorByMessageId, removeAutoSearchHintDecisionByMessageId, getPersistedTodoPermissionDenied, setPersistedTodoPermissionDenied, getPersistedTodoSyntheticAnchor, setPersistedTodoSyntheticAnchor, clearPersistedTodoSyntheticAnchor, setNoteLastReadAt, getHistorianFailureState, clearHistorianFailureState, getOverflowState, recordOverflowDetected, recordDetectedContextLimit, clearEmergencyRecovery, clearDetectedContextLimit, getPersistedCompactionMarkerState, setPersistedCompactionMarkerState, getStrippedPlaceholderIds, applyStrippedPlaceholderDelta, removeStrippedPlaceholderId, getMergedReasoningStrippedIds, addMergedReasoningStrippedIds, getTrailingBlankDecisions, addTrailingBlankDecisions, getStaleReduceStrippedIds, addStaleReduceStrippedIds, getProcessedImageStrippedIds, addProcessedImageStrippedIds, getPendingCompactionMarkerState, clearPendingCompactionMarkerStateIf, peekDeferredExecutePending, setDeferredExecutePendingIfAbsent, clearDeferredExecutePendingIfMatches, getSessionsWithPendingMarker, setSessionWorkMetrics, getNotes, addNote, getSessionNotes, getPendingSmartNotes, getReadySmartNotes, updateNote, dismissNote, markNoteReady, markNoteChecked, queuePendingOp, getPendingOps, clearPendingOps, removePendingOp, PRIMER_CANDIDATE_TTL_MS, PRIMER_CANDIDATE_MAX_AGE_MS, primerOccurrenceKey, primerOccurrenceUtcDay, updatePrimerCandidateEmbedding, getPrimerCandidatesByIds, getPrimerCandidatesForPromotion, countPrimerCandidatesForProject, getActivePrimers, createPrimer, updatePrimerSupport, updatePrimerAnswer, GLOBAL_USER_PROFILE_PROJECT_PATH, getProjectState, bumpProjectMemoryEpoch, bumpProjectUserProfileVersion, saveSourceContent, replaceSourceContent, getSourceContents, CTX_REDUCE_KEEP, estimateImageTokensFromDataUrl, normalizeTodoStateJson, buildSyntheticTodoPart, computeSyntheticCallId, isSyntheticTodoPart, countRealUserMessages, tailHygieneStructuralSignature, sameTailHygieneStructuralSignature, refreshTailHygieneBaseline, effectiveTailHygiene, assertTailHygieneContentUnchanged, CHANNEL1_SENTINEL, CHANNEL1_FLOOR_TOKENS, toolOutputTokens, decideChannel1, evaluateChannel2, buildChannel2Reminder, shouldUseStickyChannel1Reminder, buildChannel1Reminder, estimateEmergencyDropReclaimTokens, planEmergencyDrop, AGE_RECLAIM_MIN_TOKENS, getOldestActiveUnprotectedToolTags, getActiveToolTagsForAgeReclaim, getTriggerTagTokenUpperBound, getActiveTagTokenTotalsByMessage, tagTokenCountIsNull, backfillTagTokenCounts, insertTag, updateTagStatus, updateTagDropMode, updateCavemanDepth, updateTagMessageId, deleteTagsByMessageId, getMaxTagNumberBySession, getTagNumberByMessageId, deriveTagLoadFloor, getTagsBySession, getActiveTagsBySession, getTailHygieneTags, getDroppedTagsBySession, getTagsByNumbers, getMaxDroppedTagNumber, getToolTagNumberByOwner, getNullOwnerToolTag, adoptNullOwnerToolTag, getCandidateToolOwners, pickNearestPriorOwner, createChildSessionWithFence, detectOverflow, resolveFallbackChain, modelBodyField, promptSyncWithValidatedOutputRetry, normalizeSDKResponse, promptSurfaceHashMaterial, createPromptSurfaceRuntime, createPromptSurfaceGuidanceEpochCache, extractLatestAssistantText, hasLengthCappedOutput, setKeepSubagents, shouldKeepSubagents, recordChildInvocation, COMPARTMENT_AGENT_SYSTEM_PROMPT, HISTORIAN_EDITOR_SYSTEM_PROMPT, COMPARTMENT_STRUCTURAL_SYSTEM_PROMPT, Priority, AdmissionClass, StaleRouteHandleError, SocketClosedError, SocketTimeoutError, SubcClient, isConsumerReconnectTransient, connectionFileExists, getCompartmentEvents, loadCompartmentChunkEmbeddingsForSearch, cosineSimilarity, SYNAPSE_DEFAULT_MODEL, SynapseEmbeddingProvider, computeNormalizedHash, saveCommitEmbedding, loadProjectCommitEmbeddings, loadUnembeddedCommits, countEmbeddedCommits, upsertCommits, getLatestIndexedCommitTimeMs, enforceProjectCap, GIT_SWEEP_LEASE_RENEWAL_MS, acquireGitSweepLease, renewGitSweepLease, markGitSweepSuccessAndRelease, parkGitSweepNonIndexable, releaseGitSweepLease, saveEmbeddingIfHashMatches, getProjectEmbeddings, peekProjectEmbeddings, invalidateProject, invalidateMemory, markProjectLoadUntrusted, contentSha256, sweepStaleEmbeddingIdentitiesForProject, registerProjectEmbedding, registerProjectShadowEmbedding, getShadowEmbeddingMeasurementCohort, getPrimaryEmbeddingMeasurementCohort, embedShadowTextForProject, enqueueShadowEmbeddingItems, registerProjectInObservationMode, getProjectEmbeddingSnapshot, embedTextForProject, embedBatchForProject, embedItemsForProject, embedUnembeddedMemoriesForProject, drainCommitBacklogForProject, embedSessionCompartmentChunks, getEmbeddingCoverageStatus, isEmbeddingEnabled, embedText, ensureMemoryEmbeddings, computeCueContentHash, hasMuralCueColumns, getMuralCueState, memoryNeedsCue, setMuralCue, recordMuralCueRejection, hasMemoryShareableColumn, hasMemoryClassifiedAtColumn, getUnclassifiedMemoryIds, ModuleMemoryAuthorityError, insertMemory, insertMemoryIdempotent, getMemoryByHash, getMemoriesByProject, buildWorkspaceMemorySqlFilter, getMemoriesByProjects, getMaxMemoryIdForProjects, readNewMemoriesForM1Union, getMemoryById, getMemoriesByIds, updateMemorySeenCount, updateMemoryRetrievalCount, setMemoryClassification, supersededMemory, mergeMemoryStats, archiveMemory, getMemoryCountsByStatus, sanitizeFtsQuery, searchMemoriesFTS, searchMemoriesFTSUnion, recordMemoryMapping, recordMemoryVerifications, getUnmappedMemoryIds, clearMemoryVerifications, getMemoryVerifications, resolveGitTopLevel, readGitHead, readGitChangedFilesSince, readGitFileChangeTimesSince, verificationFileExists, normalizeVerificationFiles, USER_MEMORY_CANDIDATE_TTL_MS, insertUserMemoryCandidates, getUserMemoryCandidates, deleteUserMemoryCandidates, pruneExpiredUserMemoryCandidates, insertUserMemory, getActiveUserMemories, updateUserMemoryContent, dismissUserMemory, getMural, BoundedSessionMap, registerLkgPersistence, LKG_SNAPSHOT_ARRAY, LKG_SNAPSHOT_OBJECT, LKG_SNAPSHOT_KEY, LKG_SNAPSHOT_STRING, LKG_SNAPSHOT_NUMBER, LKG_SNAPSHOT_BOOLEAN, LKG_SNAPSHOT_NULL, LKG_SNAPSHOT_UNDEFINED, incrementalLkgContentDigests, lkgContentDigest, captureSlot, getSlot, dropSlot, noteEntry, onNoteTrigger, peekNoteNudgeText, markNoteNudgeDelivered, clearNoteNudgeTriggerAndCooldown, resetNoteNudgeCooldownOnly, clearNoteNudgeTriggerOnly, extractM0Block, resolveMuralWire, MARKER_SUMMARY_TEXT, applyDeferredCompactionMarker, removeCompactionMarkerForSession, checkCompactionMarkerConsistency, formatDate, injectTemporalMarkers, clearInjectionCache, getVisibleMemoryIds, prepareCompartmentInjection, renderCompartmentInjection, mustMaterialize, trimMemoriesToBudgetV2, renderMemoryBlockV2, injectM0M1, RECOVERY_NO_HEAD_LIMIT, resolveOpenCodeProtectedTailBoundary, resolveWrapupProtectedTailBoundary, getRawHistoryEligibility, hasRunnableCompartmentWindow, recordHighPressureNoEligibleHead, runCompartmentAgent, snapRangeToCompartments, getActiveCompartmentRun, markActiveCompartmentRunPublished, registerActiveCompartmentRun, startCompartmentAgent, isRecompFailure, isRecompSkip, isRecompComplete, extractRecompReason, contextualizeUpgradeReason, setRecompStarting, setRecompNote, setRecompTerminal, runManagedRecomp, runManagedUpgrade };
46799
+ export { withContentLanguageDirective, buildPrimaryLanguageDirective, cortexKitUserConfigBasePath, cortexKitProjectConfigBasePath, resolveLegacyConfigSources, resolveLegacyConfigSourcesForHarness, migrateMagicContextConfigLocations, exports_external, DEFAULT_PROTECTED_TAGS, parseCron, nextOccurrence, nextDueAtMs, promptSurfaceConfigIdentity, resolvePromptSurface, resolveModelConfigOrDefault, DEFAULT_EXECUTE_THRESHOLD_PERCENTAGE, DEFAULT_HISTORIAN_TIMEOUT_MS, DEFAULT_LOCAL_EMBEDDING_MODEL, PER_HARNESS_MIGRATION_INVENTORY, ConfigProfilesSchema, MagicContextConfigSchema, getOpenCodeDbPath, removeMcOwnedCompactionMarkers, hasShareabilitySensitiveText, isFailClosedBlockingError, shouldBypassFailClosedBlock, resolveAgentNameFromMessages, createFailClosedController, recordHookInitFailure, clearHookInitFailure, getLastHookInitFailure, ProjectIdentityError, resolveProjectIdentityStrict, takeDubiousOwnershipProjectIdentityWarning, resolveProjectIdentity, resolveProjectIdentityForSession, normalizeStoredProjectPath, storedPathBelongsToIdentity, isLinkedGitWorktree, recordSessionProjectIdentity, beginBootQuietPeriod, bootQuietRemainingMs, scheduleAfterBootQuiet, rpcPortDir, rpcPortFilePath, isPidAlive, parseRpcPortFile, registerModuleNoteEvaluationBridge, getModuleNoteEvaluationBridge, getContextStoreUuid, ensureContextStoreUuid, getAuthorityManagedMarker, reconcileAuthorityProject, checksumAuthoritySeedRows, prepareAuthority, drainAuthority, getMirrorCursor, applyMirroredNoteCompileFields, applyMirrorPage, pullMemoryMirrorOnce, V2_MEMORY_CATEGORIES, CATEGORY_PRIORITY, resolveWorkspaceShareCategories, resolveWorkspaceIdentitySet, expandWorkspaceIdentitySetWithAliases, resolveStoredPathWorkspaceIdentity, storedPathBelongsToWorkspace, sourceNameForMemory, computeWorkspaceEpochFingerprint, textMentionsRecentCommit, hasMeaningfulUserText, extractTexts, extractToolCallSummaries, preloadTokenizer, estimateTokens, normalizeText, getCurrentToolSetHash, recordToolDefinition, getMeasuredToolDefinitionTokens, getSchemaFenceRejection, getMigrationOnOpenRefusal, LATEST_SUPPORTED_VERSION, getDatabasePath, getPersistedSchemaVersion, setSqlitePragmaConfig, runSqliteOptimize, openDatabase, openDatabaseAsync, isDatabasePersisted, getDatabasePersistenceError, COMPARTMENT_LEASE_RENEWAL_MS, acquireCompartmentLease, renewCompartmentLease, releaseCompartmentLease, getCompartments, getLastCompartmentEndMessage, getLastCompartmentEndMessageId, clearRecompStaging, isRawCompactionSummaryInfo, extractInMemoryMessageViews, buildInMemoryTailRawMessages, isRecord, estimateTrueRawMessageTokens, invalidateTrueRawTokenCache, stripPersistedAssistantText, byteSize, stripTagPrefix, prependTag, isThinkingPart, isTextPart, isToolPartWithOutput, isFilePart, buildFileSourceContent, isEditTool, partHasCompletedResult, extractToolCallObservation, ToolMutationBatch, createToolDropTarget, setRawMessageProvider, cleanUserText, withRawSessionMessageCache, readRawSessionMessages, primeTailRawMessageCache, primeInMemoryTailRawMessageCache, readRawSessionMessageOrdinalPage, getRawSessionStoredMessageCount, readRawSessionMessagePartsById, readRawSessionMessageOrdinalById, readRawSessionMessageById, readSessionChunk, getMessageIndexSourceIdentity, isMessageIndexSourceCurrent, getLastIndexedOrdinal, getIndexedMessageCorpusSize, getMessageIndexReconciliationStartOrdinal, isMessageIndexReconciledThrough, deleteIndexedMessage, clearIndexedMessages, indexSingleMessage, indexMessagesAfterOrdinal, sweepOrphanedOpenCodeMessageIndexes, recordEmbeddingMeasurement, getMaxM0MutationId, queueMemoryMutation, getMemoryMutationsForRenderByProjects, getMaxMemoryMutationIdForProjects, MAX_EXECUTE_THRESHOLD, escalationBands, isEmergencyRecoveryArmed, isProviderOverflowReconfirmed, getEmergencyRecoveryArmedAt, loadPersistedUsage, loadProtectedTailMeta, resetProtectedTailNoEligibleHead, getWrapupInProgressState, acquireWrapupInProgress, updateWrapupInProgress, releaseWrapupInProgress, resolveCompactionModeRecord, getCompactionModeRecord, setCompactionModeRecord, getPersistedReasoningWatermark, setPersistedReasoningWatermark, clearPersistedReasoningWatermark, getEmergencyInputSample, setEmergencyDropSample, clearEmergencyDropSample, getLastNudgeUndropped, setLastNudgeUndropped, getChannel1NudgeState, setChannel1NudgeState, resetLastNudgeCycle, resetLastNudgeCycleIfTailShrank, getChannel2NudgeState, getChannel2NudgeClaim, setChannel2NudgeState, casChannel2NudgeState, claimChannel2NudgeState, casChannel2NudgeClaim, getPersistedNoteNudge, getNoteNudgeAnchors, getAutoSearchHintDecisions, appendAutoSearchHintDecision, pruneNoteNudgeAnchors, pruneAutoSearchHintDecisions, removeNoteNudgeAnchorByMessageId, removeAutoSearchHintDecisionByMessageId, getPersistedTodoPermissionDenied, setPersistedTodoPermissionDenied, getPersistedTodoSyntheticAnchor, setPersistedTodoSyntheticAnchor, clearPersistedTodoSyntheticAnchor, setNoteLastReadAt, getHistorianFailureState, clearHistorianFailureState, getOverflowState, recordOverflowDetected, recordDetectedContextLimit, clearEmergencyRecovery, clearDetectedContextLimit, getPersistedCompactionMarkerState, setPersistedCompactionMarkerState, getStrippedPlaceholderIds, applyStrippedPlaceholderDelta, removeStrippedPlaceholderId, getMergedReasoningStrippedIds, addMergedReasoningStrippedIds, getTrailingBlankDecisions, addTrailingBlankDecisions, getStaleReduceStrippedIds, addStaleReduceStrippedIds, getProcessedImageStrippedIds, addProcessedImageStrippedIds, getPendingCompactionMarkerState, clearPendingCompactionMarkerStateIf, peekDeferredExecutePending, setDeferredExecutePendingIfAbsent, clearDeferredExecutePendingIfMatches, getSessionsWithPendingMarker, setSessionWorkMetrics, getNotes, addNote, getSessionNotes, getPendingSmartNotes, getReadySmartNotes, updateNote, dismissNote, markNoteReady, markNoteChecked, queuePendingOp, getPendingOps, clearPendingOps, removePendingOp, PRIMER_CANDIDATE_TTL_MS, PRIMER_CANDIDATE_MAX_AGE_MS, primerOccurrenceKey, primerOccurrenceUtcDay, updatePrimerCandidateEmbedding, getPrimerCandidatesByIds, getPrimerCandidatesForPromotion, countPrimerCandidatesForProject, getActivePrimers, createPrimer, updatePrimerSupport, updatePrimerAnswer, GLOBAL_USER_PROFILE_PROJECT_PATH, getProjectState, bumpProjectMemoryEpoch, bumpProjectUserProfileVersion, saveSourceContent, replaceSourceContent, getSourceContents, CTX_REDUCE_KEEP, estimateImageTokensFromDataUrl, normalizeTodoStateJson, buildSyntheticTodoPart, computeSyntheticCallId, isSyntheticTodoPart, countRealUserMessages, tailHygieneStructuralSignature, sameTailHygieneStructuralSignature, refreshTailHygieneBaseline, effectiveTailHygiene, assertTailHygieneContentUnchanged, CHANNEL1_SENTINEL, CHANNEL1_FLOOR_TOKENS, toolOutputTokens, decideChannel1, evaluateChannel2, buildChannel2Reminder, shouldUseStickyChannel1Reminder, buildChannel1Reminder, estimateEmergencyDropReclaimTokens, planEmergencyDrop, AGE_RECLAIM_MIN_TOKENS, getOldestActiveUnprotectedToolTags, getActiveToolTagsForAgeReclaim, getTriggerTagTokenUpperBound, getActiveTagTokenTotalsByMessage, tagTokenCountIsNull, backfillTagTokenCounts, insertTag, updateTagStatus, updateTagDropMode, updateCavemanDepth, updateTagMessageId, deleteTagsByMessageId, getMaxTagNumberBySession, getTagNumberByMessageId, deriveTagLoadFloor, getTagsBySession, getActiveTagsBySession, getTailHygieneTags, getDroppedTagsBySession, getTagsByNumbers, getMaxDroppedTagNumber, getToolTagNumberByOwner, getNullOwnerToolTag, adoptNullOwnerToolTag, getCandidateToolOwners, pickNearestPriorOwner, createChildSessionWithFence, detectOverflow, resolveFallbackChain, modelBodyField, promptSyncWithValidatedOutputRetry, normalizeSDKResponse, promptSurfaceHashMaterial, createPromptSurfaceRuntime, createPromptSurfaceGuidanceEpochCache, extractLatestAssistantText, hasLengthCappedOutput, setKeepSubagents, shouldKeepSubagents, recordChildInvocation, COMPARTMENT_AGENT_SYSTEM_PROMPT, HISTORIAN_EDITOR_SYSTEM_PROMPT, COMPARTMENT_STRUCTURAL_SYSTEM_PROMPT, Priority, AdmissionClass, StaleRouteHandleError, SocketClosedError, SocketTimeoutError, SubcClient, isConsumerReconnectTransient, connectionFileExists, getCompartmentEvents, loadCompartmentChunkEmbeddingsForSearch, cosineSimilarity, SYNAPSE_DEFAULT_MODEL, SynapseEmbeddingProvider, computeNormalizedHash, saveCommitEmbedding, loadProjectCommitEmbeddings, loadUnembeddedCommits, countEmbeddedCommits, upsertCommits, getLatestIndexedCommitTimeMs, enforceProjectCap, GIT_SWEEP_LEASE_RENEWAL_MS, acquireGitSweepLease, renewGitSweepLease, markGitSweepSuccessAndRelease, parkGitSweepNonIndexable, releaseGitSweepLease, saveEmbeddingIfHashMatches, getProjectEmbeddings, peekProjectEmbeddings, invalidateProject, invalidateMemory, markProjectLoadUntrusted, contentSha256, sweepStaleEmbeddingIdentitiesForProject, registerProjectEmbedding, registerProjectShadowEmbedding, getShadowEmbeddingMeasurementCohort, getPrimaryEmbeddingMeasurementCohort, embedShadowTextForProject, enqueueShadowEmbeddingItems, registerProjectInObservationMode, getProjectEmbeddingSnapshot, embedTextForProject, embedBatchForProject, embedItemsForProject, embedUnembeddedMemoriesForProject, drainCommitBacklogForProject, embedSessionCompartmentChunks, getEmbeddingCoverageStatus, isEmbeddingEnabled, embedText, ensureMemoryEmbeddings, computeCueContentHash, hasMuralCueColumns, getMuralCueState, memoryNeedsCue, setMuralCue, recordMuralCueRejection, hasMemoryShareableColumn, hasMemoryClassifiedAtColumn, getUnclassifiedMemoryIds, ModuleMemoryAuthorityError, insertMemory, insertMemoryIdempotent, getMemoryByHash, getMemoriesByProject, buildWorkspaceMemorySqlFilter, getMemoriesByProjects, getMaxMemoryIdForProjects, readNewMemoriesForM1Union, getMemoryById, getMemoriesByIds, updateMemorySeenCount, updateMemoryRetrievalCount, setMemoryClassification, supersededMemory, mergeMemoryStats, archiveMemory, getMemoryCountsByStatus, sanitizeFtsQuery, searchMemoriesFTS, searchMemoriesFTSUnion, recordMemoryMapping, recordMemoryVerifications, getUnmappedMemoryIds, clearMemoryVerifications, getMemoryVerifications, resolveGitTopLevel, readGitHead, readGitChangedFilesSince, readGitFileChangeTimesSince, verificationFileExists, normalizeVerificationFiles, USER_MEMORY_CANDIDATE_TTL_MS, insertUserMemoryCandidates, getUserMemoryCandidates, deleteUserMemoryCandidates, pruneExpiredUserMemoryCandidates, insertUserMemory, getActiveUserMemories, updateUserMemoryContent, dismissUserMemory, getMural, BoundedSessionMap, registerLkgPersistence, LKG_SNAPSHOT_ARRAY, LKG_SNAPSHOT_OBJECT, LKG_SNAPSHOT_KEY, LKG_SNAPSHOT_STRING, LKG_SNAPSHOT_NUMBER, LKG_SNAPSHOT_BOOLEAN, LKG_SNAPSHOT_NULL, LKG_SNAPSHOT_UNDEFINED, incrementalLkgContentDigests, lkgContentDigest, captureSlot, getSlot, dropSlot, noteEntry, onNoteTrigger, peekNoteNudgeText, markNoteNudgeDelivered, clearNoteNudgeTriggerAndCooldown, resetNoteNudgeCooldownOnly, clearNoteNudgeTriggerOnly, extractM0Block, resolveMuralWire, MARKER_SUMMARY_TEXT, applyDeferredCompactionMarker, removeCompactionMarkerForSession, checkCompactionMarkerConsistency, formatDate, injectTemporalMarkers, clearInjectionCache, getVisibleMemoryIds, prepareCompartmentInjection, renderCompartmentInjection, mustMaterialize, trimMemoriesToBudgetV2, renderMemoryBlockV2, injectM0M1, RECOVERY_NO_HEAD_LIMIT, resolveOpenCodeProtectedTailBoundary, resolveWrapupProtectedTailBoundary, getRawHistoryEligibility, hasRunnableCompartmentWindow, recordHighPressureNoEligibleHead, runCompartmentAgent, snapRangeToCompartments, getActiveCompartmentRun, markActiveCompartmentRunPublished, registerActiveCompartmentRun, startCompartmentAgent, isRecompFailure, isRecompSkip, isRecompComplete, extractRecompReason, contextualizeUpgradeReason, setRecompStarting, setRecompNote, setRecompTerminal, runManagedRecomp, runManagedUpgrade };