@unbrained/pm-cli 2026.9.4 → 2026.9.6

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 (277) hide show
  1. package/.agents/skills/HARNESS_COMPATIBILITY.md +1 -1
  2. package/.agents/skills/README.md +2 -2
  3. package/.agents/skills/pm-developer/SKILL.md +4 -1
  4. package/.agents/skills/pm-developer/references/COMMAND_PLAYBOOK.md +10 -0
  5. package/.agents/skills/pm-developer/references/GRAPH_AND_RELATIONSHIPS.md +3 -1
  6. package/.agents/skills/pm-extensions/SKILL.md +2 -2
  7. package/.agents/skills/pm-extensions/references/LIFECYCLE.md +3 -3
  8. package/.agents/skills/pm-extensions/references/TROUBLESHOOTING.md +3 -3
  9. package/.agents/skills/pm-user/SKILL.md +2 -0
  10. package/.agents/skills/pm-user/references/BACKLOG_SHAPING.md +5 -0
  11. package/.agents/skills/pm-user/references/WORKFLOWS.md +20 -5
  12. package/.claude-plugin/marketplace.json +2 -2
  13. package/CHANGELOG.md +58 -3
  14. package/dist/cli/commander-usage.d.ts +2 -0
  15. package/dist/cli/commander-usage.js +15 -12
  16. package/dist/cli/help-json-payload.js +12 -7
  17. package/dist/cli/main.js +22 -11
  18. package/dist/cli/register-list-query.js +4 -2
  19. package/dist/cli/register-mutation.js +4 -2
  20. package/dist/cli/register-operations.js +17 -8
  21. package/dist/cli-bundle/bundle-manifest.json +153 -161
  22. package/dist/cli-bundle/chunks/chunk-AZDFJGH6.js +9 -0
  23. package/dist/cli-bundle/chunks/{chunk-V72UV7QS.js → chunk-BAX2BYUW.js} +73 -73
  24. package/dist/cli-bundle/chunks/{chunk-HI6BHPCU.js → chunk-CKOL5U7J.js} +51 -51
  25. package/dist/cli-bundle/chunks/{chunk-A24WAVE6.js → chunk-JT6XF6GE.js} +2 -2
  26. package/dist/cli-bundle/chunks/{chunk-I2AS367G.js → chunk-JX4DH4WC.js} +2 -2
  27. package/dist/cli-bundle/chunks/{chunk-YW4QK2G7.js → chunk-NPN5I67J.js} +2 -2
  28. package/dist/cli-bundle/chunks/chunk-OF76PSDQ.js +5 -0
  29. package/dist/cli-bundle/chunks/chunk-QUWFABDM.js +232 -0
  30. package/dist/cli-bundle/chunks/{chunk-RI4XNOYS.js → chunk-RWWBOWJ5.js} +2 -2
  31. package/dist/cli-bundle/chunks/chunk-WGAOYSYH.js +40 -0
  32. package/dist/cli-bundle/chunks/{chunk-X6CMGV6L.js → chunk-WI2AYPA7.js} +2 -2
  33. package/dist/cli-bundle/chunks/{register-list-query-Z5YYSJJG.js → register-list-query-5JL52D33.js} +3 -3
  34. package/dist/cli-bundle/chunks/{register-mutation-ELSP6I4I.js → register-mutation-ZPG7KMVP.js} +4 -4
  35. package/dist/cli-bundle/chunks/register-operations-I5W3KMGB.js +2 -0
  36. package/dist/cli-bundle/chunks/{register-setup-E2AE72QG.js → register-setup-H4SVAVX7.js} +2 -2
  37. package/dist/cli-bundle/focused-chunks/{chunk-3646BZ4W.js → chunk-3BZEOXLT.js} +2 -2
  38. package/dist/cli-bundle/focused-chunks/chunk-AL5ON6K6.js +2 -0
  39. package/dist/cli-bundle/focused-chunks/chunk-CHC2IDXA.js +6 -0
  40. package/dist/cli-bundle/focused-chunks/chunk-CK6QFAPZ.js +20 -0
  41. package/dist/cli-bundle/focused-chunks/{chunk-NBMJD6MK.js → chunk-EZR3GHFE.js} +2 -2
  42. package/dist/cli-bundle/focused-chunks/chunk-H2WJWK7L.js +56 -0
  43. package/dist/cli-bundle/focused-chunks/{chunk-53IHPICX.js → chunk-LIJIA4TY.js} +2 -2
  44. package/dist/cli-bundle/focused-chunks/{chunk-25UJBH4M.js → chunk-M6PBRFSH.js} +2 -2
  45. package/dist/cli-bundle/focused-chunks/{chunk-AJR3OP2E.js → chunk-NTPY5GSO.js} +2 -2
  46. package/dist/cli-bundle/focused-chunks/chunk-P5O7MP5Y.js +2 -0
  47. package/dist/cli-bundle/focused-chunks/chunk-PDMW2E36.js +177 -0
  48. package/dist/cli-bundle/focused-chunks/{chunk-MHKUIPJW.js → chunk-PEFABF7E.js} +2 -2
  49. package/dist/cli-bundle/focused-chunks/{chunk-6PWPQKDN.js → chunk-QTVCLMSZ.js} +2 -2
  50. package/dist/cli-bundle/focused-chunks/{chunk-7N2TV7WZ.js → chunk-QTZRBUYA.js} +2 -2
  51. package/dist/cli-bundle/focused-chunks/chunk-SGQST3PQ.js +12 -0
  52. package/dist/cli-bundle/focused-chunks/chunk-UKHASMMP.js +10 -0
  53. package/dist/cli-bundle/focused-chunks/chunk-ZPEKQHOC.js +2 -0
  54. package/dist/cli-bundle/main.js +22 -15
  55. package/dist/cli-bundle/sdk-authoring.js +1 -1
  56. package/dist/cli-bundle/sdk-contracts.js +2 -2
  57. package/dist/cli-bundle/sdk-core.js +37 -37
  58. package/dist/cli-bundle/sdk-governance.js +1 -1
  59. package/dist/cli-bundle/sdk-graph.js +1 -1
  60. package/dist/cli-bundle/sdk-merge.js +42 -39
  61. package/dist/cli-bundle/sdk-query.js +1 -1
  62. package/dist/cli-bundle/sdk-runtime.js +1 -1
  63. package/dist/cli-bundle/sdk-testing.js +1 -1
  64. package/dist/cli-bundle/sdk.js +9 -9
  65. package/dist/core/extensions/extension-types.d.ts +2 -0
  66. package/dist/core/extensions/extension-types.js +2 -2
  67. package/dist/core/extensions/module-graph-snapshot.js +5 -4
  68. package/dist/core/fs/host-environment-errors.d.ts +27 -0
  69. package/dist/core/fs/host-environment-errors.js +142 -0
  70. package/dist/core/history/drift-scan.d.ts +5 -0
  71. package/dist/core/history/drift-scan.js +16 -6
  72. package/dist/core/history/event-classification.d.ts +1 -1
  73. package/dist/core/history/event-classification.js +3 -2
  74. package/dist/core/history/history.js +37 -5
  75. package/dist/core/history/identity.d.ts +15 -0
  76. package/dist/core/history/identity.js +31 -0
  77. package/dist/core/history/projection.js +50 -17
  78. package/dist/core/history/read.js +6 -3
  79. package/dist/core/history/replay.d.ts +1 -2
  80. package/dist/core/history/replay.js +4 -4
  81. package/dist/core/history/version-address.d.ts +13 -0
  82. package/dist/core/history/version-address.js +33 -0
  83. package/dist/core/item/actionability.d.ts +21 -1
  84. package/dist/core/item/actionability.js +45 -10
  85. package/dist/core/item/id.js +8 -4
  86. package/dist/core/item/item-type-definition.d.ts +2 -0
  87. package/dist/core/item/item-type-definition.js +9 -2
  88. package/dist/core/item/type-registry.d.ts +5 -1
  89. package/dist/core/item/type-registry.js +9 -4
  90. package/dist/core/output/mutation-projection.js +12 -5
  91. package/dist/core/shared/errors.d.ts +8 -0
  92. package/dist/core/shared/errors.js +2 -2
  93. package/dist/core/store/item-metadata-query-index.js +13 -10
  94. package/dist/core/store/item-metadata-read-work.d.ts +19 -0
  95. package/dist/core/store/item-metadata-read-work.js +44 -0
  96. package/dist/core/store/item-store.d.ts +14 -0
  97. package/dist/core/store/item-store.js +52 -10
  98. package/dist/core/store/settings-validator.js +3 -2
  99. package/dist/core/validate/fix-planning.d.ts +1 -1
  100. package/dist/core/validate/fix-planning.js +2 -2
  101. package/dist/core/validate/missing-link-owners.d.ts +1 -1
  102. package/dist/core/validate/missing-link-owners.js +5 -3
  103. package/dist/core/validate/stale-file-classification.d.ts +6 -4
  104. package/dist/core/validate/stale-file-classification.js +20 -5
  105. package/dist/mcp/server.js +12 -5
  106. package/dist/sdk/actionability.d.ts +1 -1
  107. package/dist/sdk/actionability.js +3 -3
  108. package/dist/sdk/cli-contracts/command-aliases.js +11 -2
  109. package/dist/sdk/cli-contracts/completeness.js +4 -3
  110. package/dist/sdk/cli-contracts/flag-contracts.d.ts +2 -0
  111. package/dist/sdk/cli-contracts/flag-contracts.js +31 -5
  112. package/dist/sdk/cli-contracts/flag-lexicon-contracts.js +21 -13
  113. package/dist/sdk/cli-contracts/grammar-contracts.js +11 -2
  114. package/dist/sdk/cli-contracts/runtime-contracts.js +5 -2
  115. package/dist/sdk/cli-contracts/schemas/assurance-definition.d.ts +254 -5
  116. package/dist/sdk/cli-contracts/schemas/assurance-definition.js +52 -2
  117. package/dist/sdk/cli-contracts/tool-parameter-tables.js +30 -6
  118. package/dist/sdk/cli-contracts/tool-schema.d.ts +2 -2
  119. package/dist/sdk/cli-contracts/tool-schema.js +32 -7
  120. package/dist/sdk/context/usage-ledger.d.ts +41 -0
  121. package/dist/sdk/context/usage-ledger.js +186 -0
  122. package/dist/sdk/context-intent-contracts.js +3 -3
  123. package/dist/sdk/context-usage.d.ts +18 -9
  124. package/dist/sdk/context-usage.js +44 -121
  125. package/dist/sdk/define.d.ts +1 -1
  126. package/dist/sdk/define.js +2 -2
  127. package/dist/sdk/dependency-provenance.d.ts +7 -0
  128. package/dist/sdk/dependency-provenance.js +14 -4
  129. package/dist/sdk/duplicates.d.ts +2 -0
  130. package/dist/sdk/duplicates.js +3 -2
  131. package/dist/sdk/environment/host-environment-errors.d.ts +5 -27
  132. package/dist/sdk/environment/host-environment-errors.js +4 -137
  133. package/dist/sdk/extension/install-runtime.js +9 -6
  134. package/dist/sdk/extension/install-snapshot.js +7 -6
  135. package/dist/sdk/generated/generated-error-code-catalog-part-1.js +104 -56
  136. package/dist/sdk/generated/generated-error-code-catalog-part-2.js +50 -2
  137. package/dist/sdk/governance/assurance-action.d.ts +3 -2
  138. package/dist/sdk/governance/assurance-action.js +23 -11
  139. package/dist/sdk/governance/assurance-runtime.d.ts +2 -0
  140. package/dist/sdk/governance/assurance-runtime.js +6 -3
  141. package/dist/sdk/governance/defect-recurrence-coverage.d.ts +93 -0
  142. package/dist/sdk/governance/defect-recurrence-coverage.js +189 -0
  143. package/dist/sdk/governance/defect-recurrence-graph.d.ts +33 -0
  144. package/dist/sdk/governance/defect-recurrence-graph.js +121 -0
  145. package/dist/sdk/governance/defect-recurrence.d.ts +8 -0
  146. package/dist/sdk/governance/defect-recurrence.js +118 -17
  147. package/dist/sdk/governance/health.d.ts +17 -2
  148. package/dist/sdk/governance/health.js +31 -10
  149. package/dist/sdk/governance/linked-file-report.d.ts +41 -0
  150. package/dist/sdk/governance/linked-file-report.js +72 -0
  151. package/dist/sdk/governance/validate-history-drift.js +16 -5
  152. package/dist/sdk/governance/validate.d.ts +5 -2
  153. package/dist/sdk/governance/validate.js +21 -37
  154. package/dist/sdk/governance.d.ts +2 -0
  155. package/dist/sdk/governance.js +4 -2
  156. package/dist/sdk/guide-topics.js +116 -2
  157. package/dist/sdk/history/salvage.d.ts +35 -0
  158. package/dist/sdk/history/salvage.js +248 -0
  159. package/dist/sdk/history-compact.js +32 -37
  160. package/dist/sdk/history-read.d.ts +3 -2
  161. package/dist/sdk/history-read.js +6 -3
  162. package/dist/sdk/history-repair.d.ts +12 -0
  163. package/dist/sdk/history-repair.js +60 -13
  164. package/dist/sdk/lifecycle/claim.d.ts +4 -0
  165. package/dist/sdk/lifecycle/claim.js +9 -3
  166. package/dist/sdk/lifecycle/close.d.ts +8 -0
  167. package/dist/sdk/lifecycle/close.js +16 -8
  168. package/dist/sdk/lifecycle/create.js +9 -12
  169. package/dist/sdk/lifecycle/restore.d.ts +1 -0
  170. package/dist/sdk/lifecycle/restore.js +19 -7
  171. package/dist/sdk/lifecycle/update.js +12 -12
  172. package/dist/sdk/lifecycle-policy.d.ts +3 -0
  173. package/dist/sdk/lifecycle-policy.js +2 -2
  174. package/dist/sdk/merge/abandoned-receipts.d.ts +15 -0
  175. package/dist/sdk/merge/abandoned-receipts.js +47 -0
  176. package/dist/sdk/merge/driver.js +4 -2
  177. package/dist/sdk/merge/index.d.ts +1 -0
  178. package/dist/sdk/merge/index.js +2 -2
  179. package/dist/sdk/merge/receipt-operation.d.ts +15 -0
  180. package/dist/sdk/merge/receipt-operation.js +97 -0
  181. package/dist/sdk/merge/receipt-schema.d.ts +20 -0
  182. package/dist/sdk/merge/receipt-schema.js +398 -0
  183. package/dist/sdk/merge/receipts.d.ts +16 -7
  184. package/dist/sdk/merge/receipts.js +54 -340
  185. package/dist/sdk/merge/reconcile.d.ts +2 -0
  186. package/dist/sdk/merge/reconcile.js +11 -4
  187. package/dist/sdk/output-projection.d.ts +3 -1
  188. package/dist/sdk/output-projection.js +11 -3
  189. package/dist/sdk/public-surface.json +1 -0
  190. package/dist/sdk/query/context.d.ts +9 -0
  191. package/dist/sdk/query/context.js +33 -21
  192. package/dist/sdk/query/duplicate-candidates.d.ts +7 -0
  193. package/dist/sdk/query/duplicate-candidates.js +71 -0
  194. package/dist/sdk/query/get.d.ts +2 -2
  195. package/dist/sdk/query/get.js +9 -8
  196. package/dist/sdk/query/history.d.ts +11 -0
  197. package/dist/sdk/query/history.js +34 -10
  198. package/dist/sdk/query/next.d.ts +15 -1
  199. package/dist/sdk/query/next.js +43 -20
  200. package/dist/sdk/query.d.ts +3 -0
  201. package/dist/sdk/query.js +5 -2
  202. package/dist/sdk/read-output-session.js +5 -3
  203. package/dist/sdk/runtime-primitives.d.ts +1 -1
  204. package/dist/sdk/runtime-primitives.js +3 -3
  205. package/dist/sdk/runtime.js +4 -2
  206. package/dist/sdk/similarity.d.ts +24 -3
  207. package/dist/sdk/similarity.js +50 -55
  208. package/dist/types.d.ts +2 -0
  209. package/dist/types.js +2 -2
  210. package/docs/AGENT_GUIDE.md +58 -1
  211. package/docs/BOUNDED_CONTEXT_READS.md +185 -0
  212. package/docs/CLOSE_EVIDENCE_RECOVERY.md +35 -0
  213. package/docs/COMMANDS.md +30 -8
  214. package/docs/CONTEXT_RELEVANCE.md +16 -4
  215. package/docs/DEFECT_RECURRENCE.md +80 -6
  216. package/docs/EXTENSIONS.md +18 -19
  217. package/docs/HISTORY_RECOVERY.md +146 -0
  218. package/docs/MERGE_SAFETY.md +50 -0
  219. package/docs/OUTPUT_PROJECTION_CONTRACTS.md +66 -0
  220. package/docs/PR_REVIEW_LOOP.md +18 -3
  221. package/docs/README.md +19 -1
  222. package/docs/RELEASING.md +31 -13
  223. package/docs/SDK_CONTEXT_TRUTH_CONTRACTS.md +24 -1
  224. package/docs/SDK_EXECUTION_CONTRACTS.md +105 -0
  225. package/docs/SDK_LIFECYCLE.md +27 -0
  226. package/docs/SDK_RUNTIME_BOUNDARIES.md +11 -0
  227. package/docs/TESTING.md +5 -0
  228. package/docs/agent-task-token-baseline.json +17 -17
  229. package/docs/agent-task-transcripts.json +2 -1
  230. package/docs/generated/FLAG_LEXICON_BUDGETS.md +11 -11
  231. package/docs/generated/REFUSAL_CLOSURE_CENSUS.md +11 -3
  232. package/marketplace.json +2 -2
  233. package/package.json +8 -6
  234. package/packages/pm-beads/package.json +1 -1
  235. package/packages/pm-calendar/package.json +1 -1
  236. package/packages/pm-command-kit/package.json +1 -1
  237. package/packages/pm-digital-twin/package.json +1 -1
  238. package/packages/pm-governance-audit/README.md +10 -1
  239. package/packages/pm-governance-audit/extensions/governance-audit/dedupe-audit.ts +50 -65
  240. package/packages/pm-governance-audit/extensions/governance-audit/index.ts +2 -2
  241. package/packages/pm-governance-audit/extensions/governance-audit/sdk.ts +1 -0
  242. package/packages/pm-governance-audit/package.json +1 -1
  243. package/packages/pm-guide-shell/package.json +1 -1
  244. package/packages/pm-kanban/package.json +1 -1
  245. package/packages/pm-lifecycle-hooks/package.json +1 -1
  246. package/packages/pm-linked-test-adapters/package.json +1 -1
  247. package/packages/pm-search-advanced/package.json +1 -1
  248. package/packages/pm-templates/package.json +1 -1
  249. package/packages/pm-todos/package.json +1 -1
  250. package/packages/pm-vcs/package.json +1 -1
  251. package/plugins/pm-claude/.claude-plugin/plugin.json +1 -1
  252. package/plugins/pm-claude/skills/pm-audit/SKILL.md +2 -2
  253. package/plugins/pm-claude/skills/pm-developer/SKILL.md +2 -2
  254. package/plugins/pm-claude/skills/pm-planner/SKILL.md +2 -2
  255. package/plugins/pm-claude/skills/pm-release/SKILL.md +2 -2
  256. package/plugins/pm-claude/skills/pm-workflow/SKILL.md +3 -3
  257. package/plugins/pm-codex/.codex-plugin/plugin.json +1 -1
  258. package/plugins/pm-codex/skills/pm-auditor/SKILL.md +2 -2
  259. package/plugins/pm-codex/skills/pm-native/SKILL.md +3 -4
  260. package/plugins/pm-codex/skills/pm-release/SKILL.md +2 -2
  261. package/scripts/finalize-build.mjs +13 -1
  262. package/dist/cli-bundle/chunks/chunk-6XSKPNCF.js +0 -230
  263. package/dist/cli-bundle/chunks/chunk-OGBVU67G.js +0 -5
  264. package/dist/cli-bundle/chunks/chunk-TXW6VL33.js +0 -38
  265. package/dist/cli-bundle/chunks/chunk-VGLHECAP.js +0 -9
  266. package/dist/cli-bundle/chunks/register-operations-OH7R3ZT4.js +0 -2
  267. package/dist/cli-bundle/focused-chunks/chunk-4YRAVI43.js +0 -12
  268. package/dist/cli-bundle/focused-chunks/chunk-5P4HVOWG.js +0 -176
  269. package/dist/cli-bundle/focused-chunks/chunk-636VVQ7F.js +0 -54
  270. package/dist/cli-bundle/focused-chunks/chunk-B3A6MJYE.js +0 -2
  271. package/dist/cli-bundle/focused-chunks/chunk-BFDDJ2T2.js +0 -2
  272. package/dist/cli-bundle/focused-chunks/chunk-BHUIRZWQ.js +0 -9
  273. package/dist/cli-bundle/focused-chunks/chunk-JADHHPY6.js +0 -6
  274. package/dist/cli-bundle/focused-chunks/chunk-NSKBLHVI.js +0 -20
  275. package/dist/cli-bundle/focused-chunks/chunk-P2GOAOQN.js +0 -2
  276. package/dist/cli-bundle/focused-chunks/chunk-YARWJM2B.js +0 -2
  277. package/sdk/public-surface.json +0 -33034
@@ -4,18 +4,16 @@
4
4
  * Privacy-minimal, derived context-usage feedback primitives. The JSONL ledger
5
5
  * contains only item ids, timestamps, authors, ranks, profiles, and command
6
6
  * intents; it never enters item history and is safe to delete or rebuild.
7
+ * Persistence requires trusted, stable workspace directory entries and
8
+ * ancestors. For a workspace writable by an untrusted concurrent actor, set
9
+ * PM_CONTEXT_USAGE_DISABLED=1 or use an isolated copy owned by the caller.
7
10
  */
8
11
 
9
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="997a09a2-cf0c-5384-b457-d9627d465b71")}catch(e){}}();
12
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="b1b1aa19-b1de-5140-8aea-ee1994ee9ecd")}catch(e){}}();
10
13
  import { randomUUID } from "node:crypto";
11
- import { appendFile, mkdir, readFile, rename, stat, writeFile, } from "node:fs/promises";
12
- import path from "node:path";
13
- import { acquireLock } from "../core/lock/lock.js";
14
- const DEFAULT_MAX_EVENTS = 2_048;
15
- const DEFAULT_RETENTION_DAYS = 30;
14
+ import { appendEvents, readEvents, resolveNow, ContextUsageValidationError, CONTEXT_USAGE_LIMITS, } from "./context/usage-ledger.js";
15
+ export { ContextUsageValidationError, CONTEXT_USAGE_LIMITS } from "./context/usage-ledger.js";
16
16
  const DAY_MS = 86_400_000;
17
- const DEFAULT_COMPACTION_BYTES = 262_144;
18
- const CONTEXT_USAGE_LOCK_ID = "context-usage-ledger";
19
17
  const CONTEXT_USAGE_SERVING_RECEIPT = Symbol.for("@unbrained/pm-cli/context-usage-serving-receipt");
20
18
  function asObjectRecord(value) {
21
19
  return typeof value === "object" && value !== null && !Array.isArray(value)
@@ -69,15 +67,13 @@ function addContextUsageIdList(ids, value) {
69
67
  addContextUsageId(ids, itemId);
70
68
  }
71
69
  function collectNextResultItemIds(record, ids) {
72
- const rows = [
73
- ...(asObjectRecord(record.recommended) === null
74
- ? []
75
- : [record.recommended]),
76
- ...(Array.isArray(record.ready) ? record.ready : []),
77
- ...(Array.isArray(record.decision_needed) ? record.decision_needed : []),
78
- ...(Array.isArray(record.blocked) ? record.blocked : []),
79
- ...(Array.isArray(record.held_by_others) ? record.held_by_others : []),
80
- ];
70
+ const rows = asObjectRecord(record.recommended) === null
71
+ ? []
72
+ : [record.recommended];
73
+ for (const key of ["ready", "decision_needed", "gate_needed", "containers", "blocked", "held_by_others"]) {
74
+ if (Array.isArray(record[key]))
75
+ rows.push(...record[key]);
76
+ }
81
77
  for (const value of rows) {
82
78
  const row = asObjectRecord(value);
83
79
  addContextUsageId(ids, row?.id);
@@ -164,86 +160,7 @@ export async function finalizeContextUsageDelivery(options) {
164
160
  });
165
161
  return true;
166
162
  }
167
- /** Named validation failure emitted by context-usage SDK inputs. */
168
- export class ContextUsageValidationError extends TypeError {
169
- /** Stable machine-readable error code for package and CLI hosts. */
170
- code = "context_usage_validation_failed";
171
- /** Creates a typed validation error without exposing derived ledger contents. */
172
- constructor(message) {
173
- super(message);
174
- this.name = "ContextUsageValidationError";
175
- }
176
- }
177
- function ledgerPath(pmRoot) {
178
- return path.join(pmRoot, "runtime", "context-usage.jsonl");
179
- }
180
- function resolveNow(options) {
181
- const iso = options.now ?? new Date().toISOString();
182
- const ms = Date.parse(iso);
183
- if (!Number.isFinite(ms))
184
- throw new ContextUsageValidationError("Context usage now must be a valid timestamp");
185
- return { iso: new Date(ms).toISOString(), ms };
186
- }
187
- async function readEvents(options) {
188
- try {
189
- const text = await readFile(ledgerPath(options.pmRoot), "utf8");
190
- const events = text
191
- .split("\n")
192
- .filter(Boolean)
193
- .flatMap((line) => {
194
- try {
195
- return [JSON.parse(line)];
196
- }
197
- catch {
198
- return [];
199
- }
200
- });
201
- const maxEvents = options.maxEvents ?? DEFAULT_MAX_EVENTS;
202
- const retentionDays = options.retentionDays ?? DEFAULT_RETENTION_DAYS;
203
- const cutoff = resolveNow(options).ms - retentionDays * DAY_MS;
204
- return events
205
- .filter((entry) => Date.parse(entry.at) >= cutoff)
206
- .slice(-maxEvents);
207
- }
208
- catch {
209
- return [];
210
- }
211
- }
212
- async function appendEvents(options, events, deliveryServeId) {
213
- const maxEvents = options.maxEvents ?? DEFAULT_MAX_EVENTS;
214
- const retentionDays = options.retentionDays ?? DEFAULT_RETENTION_DAYS;
215
- if (!Number.isInteger(maxEvents) ||
216
- maxEvents < 1 ||
217
- !Number.isFinite(retentionDays) ||
218
- retentionDays <= 0) {
219
- throw new ContextUsageValidationError("Context usage retention requires positive maxEvents and retentionDays");
220
- }
221
- const target = ledgerPath(options.pmRoot);
222
- const runtimeDirectory = path.dirname(target);
223
- const releaseLock = await acquireLock(options.pmRoot, CONTEXT_USAGE_LOCK_ID, 30, `context-usage:${process.pid}`, false, false, 3_000);
224
- try {
225
- await mkdir(runtimeDirectory, { recursive: true });
226
- if (deliveryServeId !== undefined &&
227
- (await readEvents(options)).some((event) => event.kind === "delivery" && event.serve_id === deliveryServeId)) {
228
- return;
229
- }
230
- await appendFile(target, events.map((event) => `${JSON.stringify(event)}\n`).join(""), "utf8");
231
- const customBounds = options.maxEvents !== undefined || options.retentionDays !== undefined;
232
- if (!customBounds && (await stat(target)).size <= DEFAULT_COMPACTION_BYTES)
233
- return;
234
- const retained = await readEvents(options);
235
- const temporary = `${target}.${process.pid}.${randomUUID()}.tmp`;
236
- await writeFile(temporary, `${retained.map((entry) => JSON.stringify(entry)).join("\n")}\n`, "utf8");
237
- await rename(temporary, target);
238
- }
239
- finally {
240
- await releaseLock();
241
- }
242
- }
243
- async function appendEvent(options, event) {
244
- await appendEvents(options, [event]);
245
- }
246
- /** Records a propensity-complete context/next serving event. */
163
+ /** Records a bounded prefix of ranked context candidates with explicit sampling counts. */
247
164
  export async function recordContextUsageServing(options) {
248
165
  if ([
249
166
  process.env.PM_CONTEXT_USAGE_DISABLED === "1",
@@ -255,32 +172,37 @@ export async function recordContextUsageServing(options) {
255
172
  throw new ContextUsageValidationError("Context usage serving requires an author and valid ranked rows");
256
173
  }
257
174
  const normalizedRows = options.rows.map((row) => ({
258
- ...row,
259
175
  id: row.id.trim(),
176
+ rank: row.rank,
177
+ included: row.included,
260
178
  }));
261
179
  if (new Set(normalizedRows.map((row) => row.id)).size !== normalizedRows.length) {
262
180
  throw new ContextUsageValidationError("Context usage serving requires unique normalized row ids");
263
181
  }
182
+ const recordedRows = normalizedRows.slice(0, CONTEXT_USAGE_LIMITS.max_serving_rows);
264
183
  const receipt = {
265
184
  serve_id: randomUUID(),
266
185
  author: options.author.trim(),
267
186
  surface: options.surface,
268
187
  rows: normalizedRows,
188
+ recorded_item_ids: recordedRows.map((row) => row.id),
269
189
  };
270
- await appendEvent(options, {
271
- kind: "serve",
272
- schema_version: 2,
273
- serve_id: receipt.serve_id,
274
- at: resolveNow(options).iso,
275
- author: options.author.trim(),
276
- surface: options.surface,
277
- profile: options.profile.trim() || "balanced",
278
- rows: receipt.rows.map((row) => ({ ...row })),
279
- result_omitted: false,
280
- packed_item_ids: receipt.rows
281
- .filter((row) => row.included)
282
- .map((row) => row.id),
283
- });
190
+ receipt.storage = await appendEvents(options, [{
191
+ kind: "serve",
192
+ schema_version: 2,
193
+ serve_id: receipt.serve_id,
194
+ at: resolveNow(options).iso,
195
+ author: options.author.trim(),
196
+ surface: options.surface,
197
+ profile: options.profile.trim() || "balanced",
198
+ rows: recordedRows,
199
+ candidate_count: normalizedRows.length,
200
+ omitted_row_count: normalizedRows.length - recordedRows.length,
201
+ result_omitted: false,
202
+ packed_item_ids: recordedRows
203
+ .filter((row) => row.included)
204
+ .map((row) => row.id),
205
+ }]);
284
206
  return receipt;
285
207
  }
286
208
  /** Append the exact post-egress delivery decision for one serving receipt. */
@@ -298,6 +220,7 @@ export async function recordContextUsageDelivery(options) {
298
220
  (options.resultOmitted && deliveredItemIds.length > 0)) {
299
221
  throw new ContextUsageValidationError("Context usage delivery requires emitted ranked ids and zero ids for an omitted result");
300
222
  }
223
+ const recordedIds = new Set(options.receipt.recorded_item_ids ?? options.receipt.rows.map((row) => row.id));
301
224
  const delivery = {
302
225
  kind: "delivery",
303
226
  schema_version: 2,
@@ -306,7 +229,7 @@ export async function recordContextUsageDelivery(options) {
306
229
  author: options.receipt.author,
307
230
  surface: options.receipt.surface,
308
231
  result_omitted: options.resultOmitted,
309
- delivered_item_ids: deliveredItemIds,
232
+ delivered_item_ids: deliveredItemIds.filter((id) => recordedIds.has(id)),
310
233
  };
311
234
  await appendEvents(options, [delivery], delivery.serve_id);
312
235
  }
@@ -320,13 +243,13 @@ export async function recordContextUsageTouch(options) {
320
243
  !options.intent.trim()) {
321
244
  throw new ContextUsageValidationError("Context usage touch requires author, itemId, and intent");
322
245
  }
323
- await appendEvent(options, {
324
- kind: "touch",
325
- at: resolveNow(options).iso,
326
- author: options.author.trim(),
327
- item_id: options.itemId.trim(),
328
- intent: options.intent.trim(),
329
- });
246
+ await appendEvents(options, [{
247
+ kind: "touch",
248
+ at: resolveNow(options).iso,
249
+ author: options.author.trim(),
250
+ item_id: options.itemId.trim(),
251
+ intent: options.intent.trim(),
252
+ }]);
330
253
  }
331
254
  /**
332
255
  * Records mutation outcomes as one append and one optional compaction pass.
@@ -442,4 +365,4 @@ export async function readContextUsageAffinity(options) {
442
365
  };
443
366
  }
444
367
  //# sourceMappingURL=context-usage.js.map
445
- //# debugId=997a09a2-cf0c-5384-b457-d9627d465b71
368
+ //# debugId=b1b1aa19-b1de-5140-8aea-ee1994ee9ecd
@@ -37,7 +37,7 @@ import type { ProjectProfileDefinition } from "../core/profile/profile-presets.j
37
37
  type ExactDefinition<TDefinition, TContract> = TDefinition & Record<Exclude<keyof TDefinition, keyof TContract>, never>;
38
38
  type FlagAuthoringDefinition = Pick<FlagDefinition, "long" | "short" | "value_name" | "description" | "required" | "enabled" | "visible" | "value_type" | "type" | "list" | "default">;
39
39
  type ItemFieldAuthoringDefinition = Pick<SchemaFieldDefinition, "name" | "type" | "optional" | "default" | "values">;
40
- type ItemTypeAuthoringDefinition = Pick<SchemaItemTypeDefinition, "name" | "folder" | "aliases" | "required_create_fields" | "required_create_repeatables" | "command_option_policies" | "options" | "description" | "default_status">;
40
+ type ItemTypeAuthoringDefinition = Pick<SchemaItemTypeDefinition, "name" | "folder" | "aliases" | "required_create_fields" | "required_create_repeatables" | "command_option_policies" | "options" | "description" | "default_status" | "execution_role">;
41
41
  type MigrationAuthoringDefinition = Pick<SchemaMigrationDefinition, "id" | "description" | "status" | "mandatory" | "run">;
42
42
  type SearchProviderAuthoringDefinition = Pick<SearchProviderDefinition, "name" | "query" | "queryExpansion" | "query_expansion" | "rerank" | "embedBatch" | "embed_batch" | "embed">;
43
43
  type VectorStoreAdapterAuthoringDefinition = Pick<VectorStoreAdapterDefinition, "name" | "query" | "upsert" | "delete">;
@@ -9,7 +9,7 @@
9
9
  * to keep `capabilities` matched to the surfaces the extension actually registers.
10
10
  */
11
11
 
12
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="7fc669d4-1db2-5636-8304-2c111a684726")}catch(e){}}();
12
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="e37a2da9-966f-5044-bc5e-d27ddb07e65b")}catch(e){}}();
13
13
  export function defineExtensionManifest(manifest) {
14
14
  return manifest;
15
15
  }
@@ -218,4 +218,4 @@ export function defineOnIndexHook(hook) {
218
218
  return hook;
219
219
  }
220
220
  //# sourceMappingURL=define.js.map
221
- //# debugId=7fc669d4-1db2-5636-8304-2c111a684726
221
+ //# debugId=e37a2da9-966f-5044-bc5e-d27ddb07e65b
@@ -61,3 +61,10 @@ export declare function normalizeDependencySourceKind(sourceKind: string | undef
61
61
  * global seeds preserve the caller-provided id verbatim (apart from trimming).
62
62
  */
63
63
  export declare function normalizeDependencySeedId(id: string, prefix: string, sourceKind: string | undefined): string;
64
+ /**
65
+ * Canonicalize a local relationship target using the workspace prefix. Explicit
66
+ * provider locators and externally sourced identities retain case and spelling;
67
+ * only surrounding whitespace is removed. Resolution and parent policy remain
68
+ * the caller's responsibility, so dangling local ids are never guessed remote.
69
+ */
70
+ export declare function normalizeItemReference(reference: string, prefix: string, sourceKind?: string): string;
@@ -5,7 +5,7 @@
5
5
  * items outside the current workspace.
6
6
  */
7
7
 
8
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="f3f3beb2-1d60-52fe-88ce-1ab3cb9dba0d")}catch(e){}}();
8
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="ee17fdea-aeac-55b0-8302-a8740ba8428e")}catch(e){}}();
9
9
  import { normalizeItemId } from "../core/item/id.js";
10
10
  import { isExternalDependencyReference, isExternalDependencySourceKind, } from "../core/item/dependency-reference.js";
11
11
  export { isExternalDependencyReference, isExternalDependencySourceKind, } from "../core/item/dependency-reference.js";
@@ -117,10 +117,20 @@ export function normalizeDependencySourceKind(sourceKind) {
117
117
  * global seeds preserve the caller-provided id verbatim (apart from trimming).
118
118
  */
119
119
  export function normalizeDependencySeedId(id, prefix, sourceKind) {
120
- const trimmed = id.trim();
121
- return isExternalDependencySourceKind(sourceKind)
120
+ return normalizeItemReference(id, prefix, sourceKind);
121
+ }
122
+ /**
123
+ * Canonicalize a local relationship target using the workspace prefix. Explicit
124
+ * provider locators and externally sourced identities retain case and spelling;
125
+ * only surrounding whitespace is removed. Resolution and parent policy remain
126
+ * the caller's responsibility, so dangling local ids are never guessed remote.
127
+ */
128
+ export function normalizeItemReference(reference, prefix, sourceKind) {
129
+ const trimmed = reference.trim();
130
+ return isExternalDependencySourceKind(sourceKind) ||
131
+ isExternalDependencyReference(trimmed)
122
132
  ? trimmed
123
133
  : normalizeItemId(trimmed, prefix);
124
134
  }
125
135
  //# sourceMappingURL=dependency-provenance.js.map
126
- //# debugId=f3f3beb2-1d60-52fe-88ce-1ab3cb9dba0d
136
+ //# debugId=ee17fdea-aeac-55b0-8302-a8740ba8428e
@@ -8,6 +8,8 @@ import type { GlobalOptions } from "../core/shared/command-types.js";
8
8
  import { type DuplicateCluster, type DuplicateClustersResult } from "./similarity.js";
9
9
  /** Options shared by the `pm duplicates` command and SDK action. */
10
10
  export interface DuplicatesCommandOptions {
11
+ /** Compare all pairs instead of using lossless prefix filtering. */
12
+ exhaustive?: boolean;
11
13
  /** Lifecycle statuses to include; omitted means every status. */
12
14
  status?: readonly string[];
13
15
  /** Inclusive creation timestamp lower bound. */
@@ -1,11 +1,12 @@
1
1
 
2
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="6152efa9-8338-57f0-b3de-5707befed019")}catch(e){}}();
2
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="51a84d98-6b3c-55ad-81f8-81928aa6e537")}catch(e){}}();
3
3
  import { resolvePmRoot } from "../core/store/paths.js";
4
4
  import { findDuplicateClusters, } from "./similarity.js";
5
5
  /** Discover existing duplicate clusters without creating or mutating an item. */
6
6
  export async function runDuplicates(global, options = {}) {
7
7
  const result = await findDuplicateClusters({
8
8
  pmRoot: resolvePmRoot(process.cwd(), global.path),
9
+ exhaustive: options.exhaustive,
9
10
  ...(options.status === undefined
10
11
  ? {}
11
12
  : {
@@ -37,4 +38,4 @@ export async function runDuplicates(global, options = {}) {
37
38
  };
38
39
  }
39
40
  //# sourceMappingURL=duplicates.js.map
40
- //# debugId=6152efa9-8338-57f0-b3de-5707befed019
41
+ //# debugId=51a84d98-6b3c-55ad-81f8-81928aa6e537
@@ -1,27 +1,5 @@
1
- import { PmCliError } from "../../core/shared/errors.js";
2
- /** Optional stable codes used by an existing SDK surface for each fault class. */
3
- export interface HostEnvironmentFaultCodeOverrides {
4
- /** Code used for quota and storage exhaustion. */
5
- capacity?: string;
6
- /** Code used for access policy and read-only filesystems. */
7
- permission?: string;
8
- /** Code used for file-descriptor and memory exhaustion. */
9
- resource?: string;
10
- }
11
- /** Context and compatibility controls for a host-environment boundary. */
12
- export interface HostEnvironmentBoundaryOptions {
13
- /** Existing surface-specific codes that must remain compatible. */
14
- codes?: HostEnvironmentFaultCodeOverrides;
15
- /** Human explanation of why the operation needs host resources. */
16
- why?: string;
17
- /** Additional ordered recovery guidance. */
18
- nextSteps?: readonly string[];
19
- /** Copyable retry command when one is safe. */
20
- suggestedRetry?: string;
21
- }
22
- /** Return a declared host errno only when it represents recoverable environment state. */
23
- export declare function classifyHostEnvironmentFault(error: unknown): string | null;
24
- /** Translate one known host fault into a stable path-redacted SDK refusal. */
25
- export declare function translateHostEnvironmentFault(error: unknown, operation: string, options?: HostEnvironmentBoundaryOptions): PmCliError | null;
26
- /** Run one SDK filesystem stage and translate only declared host faults. */
27
- export declare function withHostEnvironmentBoundary<T>(operation: string, run: () => Promise<T>, options?: HostEnvironmentBoundaryOptions): Promise<T>;
1
+ /**
2
+ * @module sdk/host-environment-errors
3
+ * Public SDK compatibility surface for path-redacted host filesystem refusals.
4
+ */
5
+ export { classifyHostEnvironmentFault, translateHostEnvironmentFault, withHostEnvironmentBoundary, type HostEnvironmentBoundaryOptions, type HostEnvironmentFaultCodeOverrides, } from "../../core/fs/host-environment-errors.js";
@@ -1,142 +1,9 @@
1
1
  /**
2
2
  * @module sdk/host-environment-errors
3
- *
4
- * Classifies host filesystem/resource failures at SDK boundaries without
5
- * leaking local paths or swallowing genuine implementation defects.
3
+ * Public SDK compatibility surface for path-redacted host filesystem refusals.
6
4
  */
7
5
 
8
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="1c74b5a9-67b8-597c-98de-a4487691081f")}catch(e){}}();
9
- import { constants as osConstants } from "node:os";
10
- import { EXIT_CODE } from "../../core/shared/constants.js";
11
- import { PmCliError } from "../../core/shared/errors.js";
12
- const HOST_ENVIRONMENT_FAULTS = new Map([
13
- [
14
- "EACCES",
15
- {
16
- summary: "was denied filesystem permission",
17
- recovery: "Grant the required filesystem access, then retry.",
18
- category: "permission",
19
- },
20
- ],
21
- [
22
- "EDQUOT",
23
- {
24
- summary: "exceeded the filesystem quota",
25
- recovery: "Raise or reclaim the filesystem quota, then retry.",
26
- category: "capacity",
27
- },
28
- ],
29
- [
30
- "EMFILE",
31
- {
32
- summary: "exhausted the process file-descriptor limit",
33
- recovery: "Close unused file handles or raise the process limit, then retry.",
34
- category: "resource",
35
- },
36
- ],
37
- [
38
- "ENFILE",
39
- {
40
- summary: "exhausted the host file-descriptor limit",
41
- recovery: "Free host file descriptors or raise the host limit, then retry.",
42
- category: "resource",
43
- },
44
- ],
45
- [
46
- "ENOMEM",
47
- {
48
- summary: "ran out of available memory",
49
- recovery: "Free memory or reduce concurrent work, then retry.",
50
- category: "resource",
51
- },
52
- ],
53
- [
54
- "ENOSPC",
55
- {
56
- summary: "ran out of storage space",
57
- recovery: "Free storage on the filesystem holding the project, then retry.",
58
- category: "capacity",
59
- },
60
- ],
61
- [
62
- "EPERM",
63
- {
64
- summary: "was denied by the host permission policy",
65
- recovery: "Grant the required filesystem permission, then retry.",
66
- category: "permission",
67
- },
68
- ],
69
- [
70
- "EROFS",
71
- {
72
- summary: "targeted a read-only filesystem",
73
- recovery: "Use a writable project filesystem or remount it read-write, then retry.",
74
- category: "permission",
75
- },
76
- ],
77
- ]);
78
- const OPERATION_PATTERN = /^[a-z][a-z0-9_]{0,63}$/u;
79
- const HOST_ENVIRONMENT_ERRNO_NAMES = new Map([
80
- [osConstants.errno.EACCES, "EACCES"],
81
- [osConstants.errno.EDQUOT, "EDQUOT"],
82
- [osConstants.errno.EMFILE, "EMFILE"],
83
- [osConstants.errno.ENFILE, "ENFILE"],
84
- [osConstants.errno.ENOMEM, "ENOMEM"],
85
- [osConstants.errno.ENOSPC, "ENOSPC"],
86
- [osConstants.errno.EPERM, "EPERM"],
87
- [osConstants.errno.EROFS, "EROFS"],
88
- ].filter(([errno]) => Number.isInteger(errno)));
89
- const HOST_ENVIRONMENT_FAULT_CODES = {
90
- capacity: { code: "host_environment_capacity_fault" },
91
- permission: { code: "host_environment_permission_fault" },
92
- resource: { code: "host_environment_resource_fault" },
93
- };
94
- /** Return a declared host errno only when it represents recoverable environment state. */
95
- export function classifyHostEnvironmentFault(error) {
96
- if (typeof error !== "object" || error === null) {
97
- return null;
98
- }
99
- const errorRecord = error;
100
- if (typeof errorRecord.code === "string" &&
101
- HOST_ENVIRONMENT_FAULTS.has(errorRecord.code)) {
102
- return errorRecord.code;
103
- }
104
- if (typeof errorRecord.errno !== "number" ||
105
- !Number.isInteger(errorRecord.errno)) {
106
- return null;
107
- }
108
- return HOST_ENVIRONMENT_ERRNO_NAMES.get(Math.abs(errorRecord.errno)) ?? null;
109
- }
110
- /** Translate one known host fault into a stable path-redacted SDK refusal. */
111
- export function translateHostEnvironmentFault(error, operation, options = {}) {
112
- const errno = classifyHostEnvironmentFault(error);
113
- if (errno === null)
114
- return null;
115
- if (!OPERATION_PATTERN.test(operation)) {
116
- throw new PmCliError("Host environment operation labels must be bounded identifiers.", EXIT_CODE.USAGE, { code: "host_environment_operation_invalid", field: "operation" });
117
- }
118
- const fault = HOST_ENVIRONMENT_FAULTS.get(errno);
119
- return new PmCliError(`Host filesystem operation ${operation} ${fault.summary}.`, EXIT_CODE.GENERIC_FAILURE, {
120
- code: options.codes?.[fault.category] ??
121
- HOST_ENVIRONMENT_FAULT_CODES[fault.category].code,
122
- reason: errno,
123
- required: fault.recovery,
124
- why: options.why ??
125
- "The operating system refused a required project filesystem operation.",
126
- nextSteps: [fault.recovery, ...(options.nextSteps ?? [])],
127
- ...(options.suggestedRetry
128
- ? { recovery: { suggested_retry: options.suggestedRetry } }
129
- : {}),
130
- });
131
- }
132
- /** Run one SDK filesystem stage and translate only declared host faults. */
133
- export async function withHostEnvironmentBoundary(operation, run, options = {}) {
134
- try {
135
- return await run();
136
- }
137
- catch (error) {
138
- throw translateHostEnvironmentFault(error, operation, options) ?? error;
139
- }
140
- }
6
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="8a0d8f6e-f4ff-5a0c-9205-d28e03df72b9")}catch(e){}}();
7
+ export { classifyHostEnvironmentFault, translateHostEnvironmentFault, withHostEnvironmentBoundary, } from "../../core/fs/host-environment-errors.js";
141
8
  //# sourceMappingURL=host-environment-errors.js.map
142
- //# debugId=1c74b5a9-67b8-597c-98de-a4487691081f
9
+ //# debugId=8a0d8f6e-f4ff-5a0c-9205-d28e03df72b9
@@ -4,7 +4,8 @@
4
4
  * Provides cross-platform extension copy safety and owner-bound install locks.
5
5
  */
6
6
 
7
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="263602a2-c000-5df7-80d2-6f095985496f")}catch(e){}}();
7
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="b100fde9-412b-587b-85ac-532117e2253f")}catch(e){}}();
8
+ import { withHostEnvironmentBoundary } from "../../core/fs/host-environment-errors.js";
8
9
  import { randomUUID } from "node:crypto";
9
10
  import fs from "node:fs/promises";
10
11
  import os from "node:os";
@@ -88,7 +89,7 @@ export const resolveCanonicalExtensionInstallDestination = async (destinationDir
88
89
  return path.join(canonicalDestinationParent, path.basename(resolvedDestination));
89
90
  };
90
91
  /** Copy an extension without recursively copying a destination nested below its source. */
91
- export const copyExtensionDirectoryWithoutSelfNesting = async (sourceDirectory, destinationDirectory, copyDirectory, temporaryDirectory = os.tmpdir()) => {
92
+ export const copyExtensionDirectoryWithoutSelfNesting = async (sourceDirectory, destinationDirectory, copyDirectory, temporaryDirectory = os.tmpdir()) => withHostEnvironmentBoundary("extension_install_copy", async () => {
92
93
  const resolvedSource = path.resolve(sourceDirectory);
93
94
  const canonicalSource = await fs
94
95
  .realpath(resolvedSource)
@@ -148,13 +149,15 @@ export const copyExtensionDirectoryWithoutSelfNesting = async (sourceDirectory,
148
149
  finally {
149
150
  await fs.rm(stagingRoot, { recursive: true, force: true });
150
151
  }
151
- };
152
+ });
152
153
  /** Copy one extension directory with bounded transient-race retries. */
153
154
  export const copyExtensionDirectoryForInstall = async (sourceDirectory, destinationDirectory, copyDirectory = fs.cp) => {
154
155
  for (let attempt = 1; attempt <= EXTENSION_INSTALL_COPY_ATTEMPTS; attempt += 1) {
155
156
  try {
156
- await fs.rm(destinationDirectory, { recursive: true, force: true });
157
- await copyExtensionDirectoryWithoutSelfNesting(sourceDirectory, destinationDirectory, copyDirectory);
157
+ await withHostEnvironmentBoundary("extension_install_copy", async () => {
158
+ await fs.rm(destinationDirectory, { recursive: true, force: true });
159
+ await copyExtensionDirectoryWithoutSelfNesting(sourceDirectory, destinationDirectory, copyDirectory);
160
+ });
158
161
  return;
159
162
  }
160
163
  catch (error) {
@@ -308,4 +311,4 @@ export const withExtensionInstallLock = async (settingsRoot, destinationDirector
308
311
  }
309
312
  };
310
313
  //# sourceMappingURL=install-runtime.js.map
311
- //# debugId=263602a2-c000-5df7-80d2-6f095985496f
314
+ //# debugId=b100fde9-412b-587b-85ac-532117e2253f
@@ -4,7 +4,8 @@
4
4
  * Captures and restores extension files and metadata around install persistence.
5
5
  */
6
6
 
7
- !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="98b47a2f-d48a-5c90-8b88-3f33bdd1c826")}catch(e){}}();
7
+ !function(){try{var e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof globalThis?globalThis:"undefined"!=typeof self?self:{},n=(new e.Error).stack;n&&(e._sentryDebugIds=e._sentryDebugIds||{},e._sentryDebugIds[n]="58ec3f16-267a-5a31-abd2-df46bb82b716")}catch(e){}}();
8
+ import { withHostEnvironmentBoundary } from "../../core/fs/host-environment-errors.js";
8
9
  import fs from "node:fs/promises";
9
10
  import path from "node:path";
10
11
  import { getSettingsPath } from "../../core/store/paths.js";
@@ -17,7 +18,7 @@ export const readOptionalMetadataFile = async (filePath) => fs.readFile(filePath
17
18
  throw error;
18
19
  });
19
20
  /** Capture extension files and metadata before applying an install mutation. */
20
- export const captureExtensionInstallSnapshot = async (selectedRoot, settingsRoot, destinationDirectory, destinationExists, backupDirectory) => {
21
+ export const captureExtensionInstallSnapshot = async (selectedRoot, settingsRoot, destinationDirectory, destinationExists, backupDirectory) => withHostEnvironmentBoundary("extension_install_backup", async () => {
21
22
  const managedStatePath = resolveManagedExtensionStatePath(selectedRoot);
22
23
  const settingsPath = getSettingsPath(settingsRoot);
23
24
  const [managedStateContents, settingsContents] = await Promise.all([
@@ -39,9 +40,9 @@ export const captureExtensionInstallSnapshot = async (selectedRoot, settingsRoot
39
40
  settingsPath,
40
41
  settingsContents,
41
42
  };
42
- };
43
+ });
43
44
  /** Restore directory and metadata snapshots after a partially persisted install. */
44
- export const restoreExtensionInstallSnapshot = async (snapshot) => {
45
+ export const restoreExtensionInstallSnapshot = async (snapshot) => withHostEnvironmentBoundary("extension_install_rollback", async () => {
45
46
  await fs.rm(snapshot.destinationDirectory, { recursive: true, force: true });
46
47
  if (snapshot.destinationExists) {
47
48
  await fs.cp(snapshot.backupDirectory, snapshot.destinationDirectory, {
@@ -61,6 +62,6 @@ export const restoreExtensionInstallSnapshot = async (snapshot) => {
61
62
  await fs.writeFile(filePath, contents);
62
63
  }
63
64
  }
64
- };
65
+ });
65
66
  //# sourceMappingURL=install-snapshot.js.map
66
- //# debugId=98b47a2f-d48a-5c90-8b88-3f33bdd1c826
67
+ //# debugId=58ec3f16-267a-5a31-abd2-df46bb82b716