attention-manifest-protocol 0.4.2 → 0.4.3

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 (827) hide show
  1. package/CHANGELOG.md +341 -293
  2. package/CHANGELOG.zh-CN.md +41 -8
  3. package/README.md +250 -171
  4. package/README.zh-CN.md +251 -171
  5. package/lib/assignment/assign.d.ts +102 -0
  6. package/lib/assignment/assign.js +556 -0
  7. package/lib/assignment/binding.d.ts +103 -0
  8. package/lib/assignment/binding.js +575 -0
  9. package/lib/assignment/errors.d.ts +14 -0
  10. package/lib/assignment/errors.js +16 -0
  11. package/lib/assignment/guards.d.ts +18 -0
  12. package/lib/assignment/guards.js +28 -0
  13. package/lib/assignment/index.d.ts +10 -0
  14. package/lib/assignment/index.js +10 -0
  15. package/lib/assignment/types.d.ts +169 -0
  16. package/lib/assignment/types.js +1 -0
  17. package/lib/attention/budget.d.ts +1 -1
  18. package/lib/attention/budget.js +31 -9
  19. package/lib/bayes/engine.js +2 -1
  20. package/lib/bayes/reliability.js +25 -10
  21. package/lib/boundary/frame.d.ts +10 -4
  22. package/lib/boundary/frame.js +346 -109
  23. package/lib/boundary/kinds.d.ts +11 -0
  24. package/lib/boundary/kinds.js +33 -0
  25. package/lib/boundary/refTable.d.ts +19 -9
  26. package/lib/boundary/refTable.js +128 -30
  27. package/lib/boundary/toolCall.d.ts +22 -10
  28. package/lib/boundary/toolCall.js +798 -97
  29. package/lib/concept/conceptBudget.js +10 -1
  30. package/lib/concurrency/idempotency.d.ts +4 -3
  31. package/lib/concurrency/idempotency.js +57 -13
  32. package/lib/concurrency/retry.js +18 -3
  33. package/lib/context/agentContext.d.ts +13 -0
  34. package/lib/context/agentContext.js +14 -1
  35. package/lib/context/ast.d.ts +4 -1
  36. package/lib/context/ast.js +13 -3
  37. package/lib/context/contentStore.js +22 -9
  38. package/lib/context/contextBuilder.d.ts +457 -0
  39. package/lib/context/contextBuilder.js +1395 -0
  40. package/lib/context/contextPackage.d.ts +214 -0
  41. package/lib/context/contextPackage.js +191 -0
  42. package/lib/context/index.d.ts +14 -3
  43. package/lib/context/index.js +9 -1
  44. package/lib/context/relevance.d.ts +171 -0
  45. package/lib/context/relevance.js +250 -0
  46. package/lib/context/workspaceDiff.d.ts +105 -0
  47. package/lib/context/workspaceDiff.js +238 -0
  48. package/lib/context/workspaceService.d.ts +236 -1
  49. package/lib/context/workspaceService.js +1501 -73
  50. package/lib/cooperation/collaboration.d.ts +9 -0
  51. package/lib/cooperation/session.d.ts +4 -4
  52. package/lib/cooperation/session.js +3 -3
  53. package/lib/database/adapter/filesystemStore.d.ts +145 -0
  54. package/lib/database/adapter/filesystemStore.js +321 -0
  55. package/lib/database/adapter/index.d.ts +2 -0
  56. package/lib/database/adapter/index.js +2 -0
  57. package/lib/database/adapter/workspaceSessionStore.d.ts +118 -0
  58. package/lib/database/adapter/workspaceSessionStore.js +120 -0
  59. package/lib/database/entity/fileGraph.d.ts +53 -0
  60. package/lib/database/entity/fileGraph.js +15 -0
  61. package/lib/database/entity/fileTree.d.ts +76 -0
  62. package/lib/database/entity/fileTree.js +39 -0
  63. package/lib/database/entity/hook.d.ts +29 -0
  64. package/lib/database/entity/hook.js +18 -0
  65. package/lib/database/entity/index.d.ts +4 -0
  66. package/lib/database/entity/index.js +4 -0
  67. package/lib/database/entity/workspaceSession.d.ts +53 -0
  68. package/lib/database/entity/workspaceSession.js +28 -0
  69. package/lib/database/repository/fileAnnotationRepository.d.ts +75 -0
  70. package/lib/database/repository/fileAnnotationRepository.js +109 -0
  71. package/lib/database/repository/fileGraphRepository.d.ts +188 -0
  72. package/lib/database/repository/fileGraphRepository.js +648 -0
  73. package/lib/database/repository/fileNodeRepository.d.ts +116 -0
  74. package/lib/database/repository/fileNodeRepository.js +263 -0
  75. package/lib/database/repository/fileOutlineRepository.d.ts +40 -0
  76. package/lib/database/repository/fileOutlineRepository.js +104 -0
  77. package/lib/database/repository/fileWriteRepository.d.ts +41 -0
  78. package/lib/database/repository/fileWriteRepository.js +93 -0
  79. package/lib/database/repository/hookRepository.d.ts +67 -0
  80. package/lib/database/repository/hookRepository.js +150 -0
  81. package/lib/database/repository/index.d.ts +7 -0
  82. package/lib/database/repository/index.js +7 -0
  83. package/lib/database/repository/workspaceSessionRepository.d.ts +134 -0
  84. package/lib/database/repository/workspaceSessionRepository.js +327 -0
  85. package/lib/database/service/database.d.ts +14 -0
  86. package/lib/database/service/database.js +21 -0
  87. package/lib/database/sql/schema.js +187 -0
  88. package/lib/database/store/database.js +6 -1
  89. package/lib/delegate/team.d.ts +5 -0
  90. package/lib/delegate/team.js +83 -20
  91. package/lib/discover/classify.d.ts +20 -0
  92. package/lib/discover/classify.js +85 -0
  93. package/lib/discover/host.d.ts +20 -0
  94. package/lib/discover/host.js +89 -0
  95. package/lib/discover/index.d.ts +11 -0
  96. package/lib/discover/index.js +11 -0
  97. package/lib/discover/kinds.d.ts +14 -0
  98. package/lib/discover/kinds.js +23 -0
  99. package/lib/discover/tree.d.ts +7 -0
  100. package/lib/discover/tree.js +432 -0
  101. package/lib/discover/types.d.ts +115 -0
  102. package/lib/discover/types.js +1 -0
  103. package/lib/error/boundaryRejection.d.ts +1 -1
  104. package/lib/evaluation/agreement.js +2 -2
  105. package/lib/execution/handles.js +6 -0
  106. package/lib/execution/pin.js +2 -2
  107. package/lib/file/cfb.d.ts +56 -0
  108. package/lib/file/cfb.js +396 -0
  109. package/lib/file/dependency.d.ts +151 -0
  110. package/lib/file/dependency.js +568 -0
  111. package/lib/file/directory.d.ts +34 -0
  112. package/lib/file/directory.js +141 -0
  113. package/lib/file/errors.d.ts +20 -0
  114. package/lib/file/errors.js +18 -0
  115. package/lib/file/exportGraph.d.ts +31 -0
  116. package/lib/file/exportGraph.js +554 -0
  117. package/lib/file/file.d.ts +40 -0
  118. package/lib/file/file.js +339 -0
  119. package/lib/file/importGraph.d.ts +121 -0
  120. package/lib/file/importGraph.js +1022 -0
  121. package/lib/file/index.d.ts +45 -0
  122. package/lib/file/index.js +30 -0
  123. package/lib/file/metadata.d.ts +66 -0
  124. package/lib/file/metadata.js +470 -0
  125. package/lib/file/path.d.ts +60 -0
  126. package/lib/file/path.js +259 -0
  127. package/lib/file/read.d.ts +168 -0
  128. package/lib/file/read.js +541 -0
  129. package/lib/file/runtime.d.ts +95 -0
  130. package/lib/file/runtime.js +150 -0
  131. package/lib/file/service.d.ts +227 -0
  132. package/lib/file/service.js +663 -0
  133. package/lib/file/syntaxTree.d.ts +7 -0
  134. package/lib/file/syntaxTree.js +38 -0
  135. package/lib/file/time.d.ts +38 -0
  136. package/lib/file/time.js +44 -0
  137. package/lib/file/tree.d.ts +53 -0
  138. package/lib/file/tree.js +417 -0
  139. package/lib/file/types.d.ts +371 -0
  140. package/lib/file/types.js +1 -0
  141. package/lib/file/write.d.ts +159 -0
  142. package/lib/file/write.js +1028 -0
  143. package/lib/file/zip.d.ts +35 -0
  144. package/lib/file/zip.js +349 -0
  145. package/lib/fingerprint/algorithm.d.ts +97 -0
  146. package/lib/fingerprint/algorithm.js +271 -0
  147. package/lib/fingerprint/bytes.d.ts +18 -0
  148. package/lib/fingerprint/bytes.js +31 -0
  149. package/lib/fingerprint/error.d.ts +73 -0
  150. package/lib/fingerprint/error.js +86 -0
  151. package/lib/fingerprint/file.d.ts +71 -0
  152. package/lib/fingerprint/file.js +254 -0
  153. package/lib/fingerprint/index.d.ts +37 -0
  154. package/lib/fingerprint/index.js +12 -0
  155. package/lib/fingerprint/json.d.ts +41 -0
  156. package/lib/fingerprint/json.js +94 -0
  157. package/lib/fingerprint/number.d.ts +32 -0
  158. package/lib/fingerprint/number.js +95 -0
  159. package/lib/fingerprint/policy.d.ts +54 -0
  160. package/lib/fingerprint/policy.js +50 -0
  161. package/lib/fingerprint/preimage.d.ts +84 -0
  162. package/lib/fingerprint/preimage.js +133 -0
  163. package/lib/fingerprint/raw.d.ts +26 -0
  164. package/lib/fingerprint/raw.js +45 -0
  165. package/lib/fingerprint/ref.d.ts +39 -0
  166. package/lib/fingerprint/ref.js +178 -0
  167. package/lib/fingerprint/text.d.ts +42 -0
  168. package/lib/fingerprint/text.js +155 -0
  169. package/lib/fingerprint/tree.d.ts +56 -0
  170. package/lib/fingerprint/tree.js +288 -0
  171. package/lib/fingerprint/verify.d.ts +20 -0
  172. package/lib/fingerprint/verify.js +99 -0
  173. package/lib/global/filesystem.d.ts +43 -0
  174. package/lib/global/filesystem.js +75 -0
  175. package/lib/global/index.d.ts +8 -0
  176. package/lib/global/index.js +8 -0
  177. package/lib/global/service.d.ts +51 -0
  178. package/lib/global/service.js +98 -0
  179. package/lib/governance/transport.js +18 -6
  180. package/lib/hook/ast.d.ts +29 -0
  181. package/lib/hook/ast.js +22 -0
  182. package/lib/hook/code.d.ts +55 -0
  183. package/lib/hook/code.js +47 -0
  184. package/lib/hook/dependency.d.ts +45 -0
  185. package/lib/hook/dependency.js +28 -0
  186. package/lib/hook/diff.d.ts +114 -0
  187. package/lib/hook/diff.js +327 -0
  188. package/lib/hook/exportation.d.ts +31 -0
  189. package/lib/hook/exportation.js +24 -0
  190. package/lib/hook/file.d.ts +44 -0
  191. package/lib/hook/file.js +154 -0
  192. package/lib/hook/importation.d.ts +33 -0
  193. package/lib/hook/importation.js +22 -0
  194. package/lib/hook/index.d.ts +30 -0
  195. package/lib/hook/index.js +23 -0
  196. package/lib/hook/outline.d.ts +35 -0
  197. package/lib/hook/outline.js +27 -0
  198. package/lib/hook/project.d.ts +65 -0
  199. package/lib/hook/project.js +217 -0
  200. package/lib/hook/types.d.ts +114 -0
  201. package/lib/hook/types.js +407 -0
  202. package/lib/index.d.ts +9 -0
  203. package/lib/index.js +9 -0
  204. package/lib/lock/lease.js +28 -3
  205. package/lib/manifest/cardSign.d.ts +1 -1
  206. package/lib/manifest/cardSign.js +37 -7
  207. package/lib/manifest/federation.js +13 -6
  208. package/lib/manifest/trust.d.ts +2 -0
  209. package/lib/manifest/trust.js +27 -6
  210. package/lib/module/index.d.ts +4 -0
  211. package/lib/module/index.js +4 -0
  212. package/lib/module/mcp/client.js +21 -2
  213. package/lib/module/mcp/filesystemServer.d.ts +24 -0
  214. package/lib/module/mcp/filesystemServer.js +102 -0
  215. package/lib/module/mcp/http.js +32 -19
  216. package/lib/module/mcp/workspaceServer.js +20 -3
  217. package/lib/module/tool/filesystemExecutor.d.ts +18 -0
  218. package/lib/module/tool/filesystemExecutor.js +49 -0
  219. package/lib/module/tool/globalExecutor.d.ts +17 -0
  220. package/lib/module/tool/globalExecutor.js +39 -0
  221. package/lib/module/tool/globalFilesystemExecutor.d.ts +18 -0
  222. package/lib/module/tool/globalFilesystemExecutor.js +49 -0
  223. package/lib/module/tool/workspaceExecutor.d.ts +9 -0
  224. package/lib/module/tool/workspaceExecutor.js +16 -3
  225. package/lib/naming/aliases.d.ts +48 -0
  226. package/lib/naming/aliases.js +79 -0
  227. package/lib/naming/catalog.d.ts +117 -0
  228. package/lib/naming/catalog.js +108 -0
  229. package/lib/naming/grammar.d.ts +67 -0
  230. package/lib/naming/grammar.js +212 -0
  231. package/lib/naming/ids.d.ts +157 -0
  232. package/lib/naming/ids.js +119 -0
  233. package/lib/naming/index.d.ts +13 -0
  234. package/lib/naming/index.js +13 -0
  235. package/lib/outline/index.d.ts +9 -0
  236. package/lib/outline/index.js +8 -0
  237. package/lib/outline/office.d.ts +160 -0
  238. package/lib/outline/office.js +2375 -0
  239. package/lib/outline/officeBridge.d.ts +32 -0
  240. package/lib/outline/officeBridge.js +27 -0
  241. package/lib/outline/outline.d.ts +159 -0
  242. package/lib/outline/outline.js +837 -0
  243. package/lib/outline/outlineIndex.d.ts +97 -0
  244. package/lib/outline/outlineIndex.js +325 -0
  245. package/lib/outline/outlineKeywords.d.ts +59 -0
  246. package/lib/outline/outlineKeywords.js +143 -0
  247. package/lib/outline/outlineStrategies.d.ts +414 -0
  248. package/lib/outline/outlineStrategies.js +8324 -0
  249. package/lib/outline/reactOutline.d.ts +37 -0
  250. package/lib/outline/reactOutline.js +1070 -0
  251. package/lib/outline/shellOutline.d.ts +65 -0
  252. package/lib/outline/shellOutline.js +873 -0
  253. package/lib/outline/sqlOutline.d.ts +170 -0
  254. package/lib/outline/sqlOutline.js +1536 -0
  255. package/lib/outline/strategy.d.ts +46 -0
  256. package/lib/outline/strategy.js +1 -0
  257. package/lib/outline/types.d.ts +95 -0
  258. package/lib/outline/types.js +1 -0
  259. package/lib/outline/visualBasicOutline.d.ts +27 -0
  260. package/lib/outline/visualBasicOutline.js +750 -0
  261. package/lib/protocol/filesystem.d.ts +55 -0
  262. package/lib/protocol/filesystem.js +105 -0
  263. package/lib/protocol/global.d.ts +42 -0
  264. package/lib/protocol/global.js +63 -0
  265. package/lib/protocol/globalFilesystem.d.ts +40 -0
  266. package/lib/protocol/globalFilesystem.js +59 -0
  267. package/lib/protocol/index.d.ts +4 -0
  268. package/lib/protocol/index.js +4 -0
  269. package/lib/protocol/protocol.d.ts +4 -0
  270. package/lib/protocol/wire.js +5 -2
  271. package/lib/protocol/workspace.d.ts +305 -0
  272. package/lib/protocol/workspace.js +258 -0
  273. package/lib/receipt/receipt.d.ts +8 -0
  274. package/lib/registry/content.js +9 -3
  275. package/lib/runtime/kernelRuntime.js +9 -1
  276. package/lib/scenario/scenario.js +5 -4
  277. package/lib/semantic/canonical.d.ts +61 -0
  278. package/lib/semantic/canonical.js +135 -8
  279. package/lib/semantic/jsonValue.d.ts +31 -0
  280. package/lib/semantic/jsonValue.js +122 -0
  281. package/lib/semantic/sha256.js +3 -0
  282. package/lib/semantic/time.d.ts +14 -0
  283. package/lib/semantic/time.js +56 -0
  284. package/lib/session/context.d.ts +76 -0
  285. package/lib/session/context.js +419 -0
  286. package/lib/session/errors.d.ts +24 -0
  287. package/lib/session/errors.js +22 -0
  288. package/lib/session/identity.d.ts +24 -0
  289. package/lib/session/identity.js +56 -0
  290. package/lib/session/index.d.ts +14 -0
  291. package/lib/session/index.js +12 -0
  292. package/lib/session/registry.d.ts +130 -0
  293. package/lib/session/registry.js +908 -0
  294. package/lib/session/types.d.ts +227 -0
  295. package/lib/session/types.js +14 -0
  296. package/lib/structure/index.d.ts +1 -0
  297. package/lib/structure/index.js +1 -0
  298. package/lib/structure/trie.d.ts +88 -0
  299. package/lib/structure/trie.js +183 -0
  300. package/lib/syntax/byteIndex.d.ts +44 -0
  301. package/lib/syntax/byteIndex.js +148 -0
  302. package/lib/syntax/charset.d.ts +88 -0
  303. package/lib/syntax/charset.js +276 -0
  304. package/lib/syntax/index.d.ts +6 -0
  305. package/lib/syntax/index.js +5 -0
  306. package/lib/syntax/syntaxRegistry.d.ts +150 -0
  307. package/lib/syntax/syntaxRegistry.js +314 -0
  308. package/lib/syntax/syntaxTree.d.ts +106 -0
  309. package/lib/syntax/syntaxTree.js +668 -0
  310. package/lib/syntax/types.d.ts +15 -0
  311. package/lib/syntax/types.js +1 -0
  312. package/lib/types/common.d.ts +1 -1
  313. package/package.json +72 -193
  314. package/.editorconfig +0 -12
  315. package/.prettierignore +0 -17
  316. package/MCP-Token/347/250/216/344/270/216/344/270/213/344/270/200/344/273/243/345/267/245/345/205/267/345/215/217/350/256/256.html +0 -1763
  317. package/docs/annotation-campaign-A.csv +0 -54
  318. package/docs/annotation-campaign-B.csv +0 -54
  319. package/docs/annotation-campaign.csv +0 -54
  320. package/docs/eval/annotations-A.jsonl +0 -16
  321. package/docs/eval/annotations.json +0 -122
  322. package/docs/eval/recorded-labels.json +0 -12
  323. package/docs/eval/replay-cases.json +0 -14
  324. package/docs/eval/replay-labels-b.json +0 -14
  325. package/docs/examples/attention-request.json +0 -16
  326. package/docs/examples/checkpoint.json +0 -15
  327. package/docs/examples/claim.json +0 -66
  328. package/docs/examples/collaboration.json +0 -66
  329. package/docs/examples/concept-checkpoint.json +0 -15
  330. package/docs/examples/concept-prune-plan.json +0 -45
  331. package/docs/examples/federation.json +0 -126
  332. package/docs/examples/frame-chain.json +0 -77
  333. package/docs/examples/ledger-snapshot.json +0 -108
  334. package/docs/examples/manifest.json +0 -77
  335. package/docs/examples/message.json +0 -19
  336. package/docs/examples/other-model.json +0 -45
  337. package/docs/examples/plan.json +0 -50
  338. package/docs/examples/prune-plan.json +0 -48
  339. package/docs/examples/receipt.json +0 -22
  340. package/docs/examples/runtime-run.json +0 -573
  341. package/docs/examples/team.json +0 -66
  342. package/docs/examples/verb-note.json +0 -11
  343. package/docs/probes/bayes-scores.json +0 -1452
  344. package/docs/probes/calibration-imported.json +0 -141
  345. package/docs/probes/context-ast-deepseek.json +0 -1577
  346. package/docs/probes/deepseek-probe.json +0 -917
  347. package/docs/probes/eval-recorded-replay.json +0 -597
  348. package/docs/probes/eval-replay.json +0 -124
  349. package/docs/probes/eval-summary.json +0 -42
  350. package/docs/probes/runtime-eval.json +0 -4230
  351. package/docs/schemas/collaboration.schema.json +0 -73
  352. package/docs/schemas/common.schema.json +0 -125
  353. package/docs/schemas/compaction.schema.json +0 -121
  354. package/docs/schemas/concept-compaction.schema.json +0 -73
  355. package/docs/schemas/concept.schema.json +0 -97
  356. package/docs/schemas/epistemic.schema.json +0 -178
  357. package/docs/schemas/federation.schema.json +0 -66
  358. package/docs/schemas/frame.schema.json +0 -86
  359. package/docs/schemas/ledger-snapshot.schema.json +0 -30
  360. package/docs/schemas/manifest.schema.json +0 -169
  361. package/docs/schemas/message.schema.json +0 -41
  362. package/docs/schemas/plan.schema.json +0 -189
  363. package/docs/schemas/receipt.schema.json +0 -45
  364. package/docs/schemas/social.schema.json +0 -153
  365. package/docs/schemas/team.schema.json +0 -56
  366. package/docs/schemas/verb.schema.json +0 -120
  367. package/eslint.config.mts +0 -96
  368. package/index.html +0 -13
  369. package/lib/context/workspaceProtocol.d.ts +0 -30
  370. package/lib/context/workspaceProtocol.js +0 -49
  371. package/prettier.config.mts +0 -37
  372. package/public/favicon.svg +0 -1
  373. package/public/icons.svg +0 -24
  374. package/src/attention/attention.ts +0 -347
  375. package/src/attention/budget.ts +0 -72
  376. package/src/attention/cognition.ts +0 -519
  377. package/src/attention/index.ts +0 -8
  378. package/src/attention/interrupts.ts +0 -228
  379. package/src/attention/resource.ts +0 -316
  380. package/src/attention/social.ts +0 -217
  381. package/src/attention/socialTypes.ts +0 -115
  382. package/src/authz/authz.ts +0 -305
  383. package/src/authz/index.ts +0 -1
  384. package/src/bayes/calibration.ts +0 -204
  385. package/src/bayes/calibrationRegistry.ts +0 -111
  386. package/src/bayes/calibrationSelection.ts +0 -154
  387. package/src/bayes/engine.ts +0 -532
  388. package/src/bayes/index.ts +0 -6
  389. package/src/bayes/reliability.ts +0 -62
  390. package/src/bayes/scopedPriors.ts +0 -88
  391. package/src/boundary/frame.ts +0 -322
  392. package/src/boundary/ids.ts +0 -14
  393. package/src/boundary/index.ts +0 -12
  394. package/src/boundary/refTable.ts +0 -125
  395. package/src/boundary/toolCall.ts +0 -212
  396. package/src/concept/concept.ts +0 -75
  397. package/src/concept/conceptBudget.ts +0 -346
  398. package/src/concept/conceptBudgetTypes.ts +0 -79
  399. package/src/concept/index.ts +0 -3
  400. package/src/concurrency/idempotency.ts +0 -41
  401. package/src/concurrency/index.ts +0 -5
  402. package/src/concurrency/mutex.ts +0 -26
  403. package/src/concurrency/namedLocks.ts +0 -35
  404. package/src/concurrency/retry.ts +0 -50
  405. package/src/concurrency/worker.ts +0 -128
  406. package/src/context/agentContext.ts +0 -308
  407. package/src/context/ast.ts +0 -499
  408. package/src/context/contentStore.ts +0 -75
  409. package/src/context/context.ts +0 -65
  410. package/src/context/contextIndex.ts +0 -85
  411. package/src/context/document.ts +0 -137
  412. package/src/context/fileStorePath.ts +0 -14
  413. package/src/context/index.ts +0 -43
  414. package/src/context/lifecycle.ts +0 -221
  415. package/src/context/projections.ts +0 -151
  416. package/src/context/workspace.ts +0 -422
  417. package/src/context/workspaceProtocol.ts +0 -112
  418. package/src/context/workspaceService.ts +0 -423
  419. package/src/cooperation/board.ts +0 -104
  420. package/src/cooperation/collaboration.ts +0 -60
  421. package/src/cooperation/index.ts +0 -6
  422. package/src/cooperation/merge.ts +0 -190
  423. package/src/cooperation/metrics.ts +0 -57
  424. package/src/cooperation/session.ts +0 -131
  425. package/src/cooperation/unified.ts +0 -56
  426. package/src/counter.ts +0 -9
  427. package/src/database/adapter/adapters.ts +0 -35
  428. package/src/database/adapter/index.ts +0 -4
  429. package/src/database/adapter/runtimeSink.ts +0 -74
  430. package/src/database/adapter/sessionStore.ts +0 -32
  431. package/src/database/adapter/turnStore.ts +0 -23
  432. package/src/database/entity/agent.ts +0 -199
  433. package/src/database/entity/entity.ts +0 -1046
  434. package/src/database/entity/handle.ts +0 -79
  435. package/src/database/entity/index.ts +0 -32
  436. package/src/database/entity/message.ts +0 -74
  437. package/src/database/entity/meta.ts +0 -11
  438. package/src/database/entity/object.ts +0 -42
  439. package/src/database/entity/outbox.ts +0 -15
  440. package/src/database/entity/process.ts +0 -65
  441. package/src/database/entity/registry.ts +0 -155
  442. package/src/database/entity/runtimeApproval.ts +0 -30
  443. package/src/database/entity/runtimeSession.ts +0 -13
  444. package/src/database/entity/runtimeTurn.ts +0 -15
  445. package/src/database/entity/thread.ts +0 -85
  446. package/src/database/entity/window.ts +0 -85
  447. package/src/database/entity/worker.ts +0 -90
  448. package/src/database/index.ts +0 -6
  449. package/src/database/repository/addressSpaceRepository.ts +0 -72
  450. package/src/database/repository/agentRepository.ts +0 -460
  451. package/src/database/repository/base.ts +0 -41
  452. package/src/database/repository/executionRepository.ts +0 -477
  453. package/src/database/repository/handleRepository.ts +0 -64
  454. package/src/database/repository/index.ts +0 -20
  455. package/src/database/repository/messageRepository.ts +0 -52
  456. package/src/database/repository/objectRepository.ts +0 -69
  457. package/src/database/repository/outboxRepository.ts +0 -63
  458. package/src/database/repository/processRepository.ts +0 -58
  459. package/src/database/repository/registryRepository.ts +0 -119
  460. package/src/database/repository/repository.ts +0 -491
  461. package/src/database/repository/runtimeApprovalRepository.ts +0 -44
  462. package/src/database/repository/runtimeSessionRepository.ts +0 -27
  463. package/src/database/repository/runtimeTurnRepository.ts +0 -39
  464. package/src/database/repository/socialRepository.ts +0 -185
  465. package/src/database/repository/threadRepository.ts +0 -57
  466. package/src/database/repository/windowRepository.ts +0 -88
  467. package/src/database/repository/workerRepository.ts +0 -69
  468. package/src/database/service/database.ts +0 -90
  469. package/src/database/service/handleService.ts +0 -48
  470. package/src/database/service/index.ts +0 -16
  471. package/src/database/service/messageService.ts +0 -61
  472. package/src/database/service/objectService.ts +0 -59
  473. package/src/database/service/processService.ts +0 -61
  474. package/src/database/service/registryServices.ts +0 -88
  475. package/src/database/service/service.ts +0 -183
  476. package/src/database/service/stepService.ts +0 -53
  477. package/src/database/service/threadService.ts +0 -65
  478. package/src/database/service/windowService.ts +0 -30
  479. package/src/database/service/workerService.ts +0 -57
  480. package/src/database/sql/index.ts +0 -3
  481. package/src/database/sql/schema.ts +0 -418
  482. package/src/database/sql/sql.ts +0 -543
  483. package/src/database/store/database.ts +0 -210
  484. package/src/database/store/index.ts +0 -3
  485. package/src/database/store/store.ts +0 -266
  486. package/src/delegate/index.ts +0 -2
  487. package/src/delegate/team.ts +0 -268
  488. package/src/delegate/teamTypes.ts +0 -47
  489. package/src/diagnosis/checklist.ts +0 -74
  490. package/src/diagnosis/context.ts +0 -93
  491. package/src/diagnosis/frame.ts +0 -256
  492. package/src/diagnosis/index.ts +0 -5
  493. package/src/diagnosis/router.ts +0 -72
  494. package/src/diagnosis/types.ts +0 -89
  495. package/src/error/agentError.ts +0 -16
  496. package/src/error/ampError.ts +0 -20
  497. package/src/error/authzError.ts +0 -14
  498. package/src/error/boundaryRejection.ts +0 -20
  499. package/src/error/index.ts +0 -7
  500. package/src/error/kernelError.ts +0 -27
  501. package/src/error/mailboxError.ts +0 -9
  502. package/src/error/windowError.ts +0 -12
  503. package/src/evaluation/agreement.ts +0 -96
  504. package/src/evaluation/index.ts +0 -2
  505. package/src/evaluation/labels.ts +0 -241
  506. package/src/evidence/evidenceGraph.ts +0 -205
  507. package/src/evidence/index.ts +0 -4
  508. package/src/evidence/revalidation.ts +0 -191
  509. package/src/execution/exec.ts +0 -408
  510. package/src/execution/handles.ts +0 -65
  511. package/src/execution/index.ts +0 -3
  512. package/src/execution/pin.ts +0 -154
  513. package/src/frame/frame.ts +0 -70
  514. package/src/frame/index.ts +0 -1
  515. package/src/goal/goal.ts +0 -43
  516. package/src/goal/index.ts +0 -2
  517. package/src/goal/plan.ts +0 -196
  518. package/src/governance/attentionManifest.ts +0 -802
  519. package/src/governance/audit.ts +0 -362
  520. package/src/governance/budget.ts +0 -628
  521. package/src/governance/context.ts +0 -356
  522. package/src/governance/control.ts +0 -159
  523. package/src/governance/cooperation.ts +0 -479
  524. package/src/governance/credential.ts +0 -359
  525. package/src/governance/httpServer.ts +0 -99
  526. package/src/governance/index.ts +0 -32
  527. package/src/governance/legal.ts +0 -574
  528. package/src/governance/matrix.ts +0 -460
  529. package/src/governance/perspectives.ts +0 -406
  530. package/src/governance/signing.ts +0 -407
  531. package/src/governance/store.ts +0 -125
  532. package/src/governance/switching.ts +0 -459
  533. package/src/governance/toolPolicy.ts +0 -80
  534. package/src/governance/transport.ts +0 -204
  535. package/src/governance/types.ts +0 -380
  536. package/src/governance/workflow.ts +0 -743
  537. package/src/index.ts +0 -11
  538. package/src/interaction/index.ts +0 -1
  539. package/src/interaction/interaction.ts +0 -391
  540. package/src/ipc/index.ts +0 -4
  541. package/src/ipc/mailbox.ts +0 -132
  542. package/src/ipc/memorySocialStore.ts +0 -93
  543. package/src/ipc/social.ts +0 -93
  544. package/src/kernel/index.ts +0 -14
  545. package/src/kernel/scheduler.ts +0 -498
  546. package/src/ledger/checkpoint.ts +0 -304
  547. package/src/ledger/index.ts +0 -4
  548. package/src/ledger/ledger.ts +0 -31
  549. package/src/ledger/persistence.ts +0 -159
  550. package/src/ledger/share.ts +0 -80
  551. package/src/lock/index.ts +0 -2
  552. package/src/lock/lease.ts +0 -74
  553. package/src/main.ts +0 -199
  554. package/src/manifest/agentCard.ts +0 -72
  555. package/src/manifest/cardSign.ts +0 -87
  556. package/src/manifest/federation.ts +0 -237
  557. package/src/manifest/federationTypes.ts +0 -55
  558. package/src/manifest/index.ts +0 -8
  559. package/src/manifest/keys.ts +0 -643
  560. package/src/manifest/manifest.ts +0 -114
  561. package/src/manifest/sign.ts +0 -134
  562. package/src/manifest/trust.ts +0 -146
  563. package/src/mission/index.ts +0 -2
  564. package/src/mission/missionQueue.ts +0 -75
  565. package/src/module/index.ts +0 -9
  566. package/src/module/llm/deepseek.ts +0 -214
  567. package/src/module/llm/llm.ts +0 -84
  568. package/src/module/mcp/client.ts +0 -110
  569. package/src/module/mcp/http.ts +0 -102
  570. package/src/module/mcp/protocol.ts +0 -77
  571. package/src/module/mcp/server.ts +0 -148
  572. package/src/module/mcp/transport.ts +0 -30
  573. package/src/module/mcp/workspaceServer.ts +0 -111
  574. package/src/module/sandbox/sandbox.ts +0 -29
  575. package/src/module/tool/mcpExecutor.ts +0 -54
  576. package/src/module/tool/policy.ts +0 -52
  577. package/src/module/tool/redact.ts +0 -29
  578. package/src/module/tool/tool.ts +0 -53
  579. package/src/module/tool/workspaceExecutor.ts +0 -35
  580. package/src/policy/guard.ts +0 -240
  581. package/src/policy/index.ts +0 -2
  582. package/src/policy/policy.ts +0 -561
  583. package/src/process/agent.ts +0 -341
  584. package/src/process/agentService.ts +0 -236
  585. package/src/process/agentStore.ts +0 -378
  586. package/src/process/executionStore.ts +0 -151
  587. package/src/process/index.ts +0 -5
  588. package/src/process/process.ts +0 -240
  589. package/src/process/transitions.ts +0 -19
  590. package/src/progress/index.ts +0 -2
  591. package/src/progress/progress.ts +0 -85
  592. package/src/protocol/a2a.ts +0 -120
  593. package/src/protocol/channel.ts +0 -44
  594. package/src/protocol/envelope.ts +0 -655
  595. package/src/protocol/httpChannel.ts +0 -87
  596. package/src/protocol/index.ts +0 -6
  597. package/src/protocol/protocol.ts +0 -138
  598. package/src/protocol/wire.ts +0 -60
  599. package/src/receipt/index.ts +0 -1
  600. package/src/receipt/receipt.ts +0 -47
  601. package/src/registry/content.ts +0 -69
  602. package/src/registry/index.ts +0 -23
  603. package/src/registry/registry.ts +0 -599
  604. package/src/runtime/action.ts +0 -87
  605. package/src/runtime/behavior.ts +0 -330
  606. package/src/runtime/behaviorTuning.ts +0 -163
  607. package/src/runtime/cognitiveRuntime.ts +0 -703
  608. package/src/runtime/escalation.ts +0 -35
  609. package/src/runtime/governedTask.ts +0 -233
  610. package/src/runtime/index.ts +0 -15
  611. package/src/runtime/kernelRuntime.ts +0 -144
  612. package/src/runtime/operation.ts +0 -35
  613. package/src/runtime/replay.ts +0 -71
  614. package/src/runtime/routing.ts +0 -58
  615. package/src/runtime/safety.ts +0 -48
  616. package/src/runtime/session.ts +0 -341
  617. package/src/runtime/sessionStore.ts +0 -43
  618. package/src/runtime/telemetry.ts +0 -55
  619. package/src/runtime/turnStore.ts +0 -30
  620. package/src/scenario/index.ts +0 -1
  621. package/src/scenario/scenario.ts +0 -299
  622. package/src/semantic/canonical.ts +0 -24
  623. package/src/semantic/index.ts +0 -2
  624. package/src/semantic/sha256.ts +0 -82
  625. package/src/storage/appendLog.ts +0 -372
  626. package/src/storage/fileAppendSink.ts +0 -40
  627. package/src/storage/index.ts +0 -2
  628. package/src/store/bindCache.ts +0 -22
  629. package/src/store/cache.ts +0 -191
  630. package/src/store/context.ts +0 -31
  631. package/src/store/handleStore.ts +0 -31
  632. package/src/store/index.ts +0 -9
  633. package/src/store/messageStore.ts +0 -31
  634. package/src/store/objectStore.ts +0 -31
  635. package/src/store/processStore.ts +0 -31
  636. package/src/store/threadStore.ts +0 -31
  637. package/src/store/windowStore.ts +0 -31
  638. package/src/structure/abstractSyntaxTree.ts +0 -493
  639. package/src/structure/avlTree.ts +0 -408
  640. package/src/structure/binarySearchTree.ts +0 -352
  641. package/src/structure/binaryTree.ts +0 -525
  642. package/src/structure/bloomFilter.ts +0 -231
  643. package/src/structure/compare.ts +0 -110
  644. package/src/structure/cuckooFilter.ts +0 -337
  645. package/src/structure/deque.ts +0 -223
  646. package/src/structure/filterKey.ts +0 -36
  647. package/src/structure/hash.ts +0 -279
  648. package/src/structure/heap.ts +0 -268
  649. package/src/structure/index.ts +0 -20
  650. package/src/structure/iterator.ts +0 -22
  651. package/src/structure/lru.ts +0 -619
  652. package/src/structure/ordered.ts +0 -399
  653. package/src/structure/priority.ts +0 -915
  654. package/src/structure/queue.ts +0 -168
  655. package/src/structure/redBlackTree.ts +0 -680
  656. package/src/structure/segmentTree.ts +0 -248
  657. package/src/structure/stack.ts +0 -118
  658. package/src/structure/unordered.ts +0 -407
  659. package/src/style.css +0 -278
  660. package/src/thread/index.ts +0 -2
  661. package/src/thread/thread.ts +0 -176
  662. package/src/thread/transitions.ts +0 -17
  663. package/src/types/common.ts +0 -119
  664. package/src/types/index.ts +0 -23
  665. package/src/warrant/epistemic.ts +0 -154
  666. package/src/warrant/index.ts +0 -3
  667. package/src/warrant/inquiry.ts +0 -166
  668. package/src/warrant/warrant.ts +0 -179
  669. package/src/window/compaction.ts +0 -403
  670. package/src/window/compactionTypes.ts +0 -119
  671. package/src/window/index.ts +0 -7
  672. package/src/window/page.ts +0 -18
  673. package/src/window/window.ts +0 -244
  674. package/tools/_helpers.ts +0 -34
  675. package/tools/a2a-check.ts +0 -110
  676. package/tools/a2a-flow-check.ts +0 -78
  677. package/tools/agent-card-check.ts +0 -76
  678. package/tools/agent-check.ts +0 -236
  679. package/tools/agent-store-check.ts +0 -153
  680. package/tools/agreement-check.ts +0 -27
  681. package/tools/annotation-server-check.ts +0 -48
  682. package/tools/annotation-server.ts +0 -230
  683. package/tools/annotation-status.ts +0 -65
  684. package/tools/approval-access-check.ts +0 -66
  685. package/tools/arch-check.ts +0 -72
  686. package/tools/attention-core-check.ts +0 -48
  687. package/tools/attention-resource-check.ts +0 -169
  688. package/tools/audit-check.ts +0 -207
  689. package/tools/authority-check.ts +0 -124
  690. package/tools/authz-check.ts +0 -138
  691. package/tools/bayes-check.ts +0 -162
  692. package/tools/bayes-probe.ts +0 -154
  693. package/tools/behavior-tuning-check.ts +0 -53
  694. package/tools/board-check.ts +0 -87
  695. package/tools/boundary-check.ts +0 -199
  696. package/tools/bundle-trust-check.ts +0 -96
  697. package/tools/calibrate-imported.ts +0 -108
  698. package/tools/calibration-check.ts +0 -44
  699. package/tools/calibration-registry-check.ts +0 -40
  700. package/tools/calibration-sim.ts +0 -40
  701. package/tools/card-sign-check.ts +0 -71
  702. package/tools/card-trust-check.ts +0 -78
  703. package/tools/channel-check.ts +0 -86
  704. package/tools/checkpoint-check.ts +0 -620
  705. package/tools/cleanup-style-configs.ts +0 -29
  706. package/tools/cognition-check.ts +0 -648
  707. package/tools/cognitive-runtime-check.ts +0 -609
  708. package/tools/collaboration-demo.ts +0 -78
  709. package/tools/compaction-check.ts +0 -266
  710. package/tools/concept-check.ts +0 -260
  711. package/tools/concurrency-check.ts +0 -242
  712. package/tools/conformance-runtime.ts +0 -389
  713. package/tools/conformance.ts +0 -651
  714. package/tools/context-ast-check.ts +0 -90
  715. package/tools/context-ast-deepseek.ts +0 -242
  716. package/tools/context-graph-bench.ts +0 -50
  717. package/tools/context-graph-check.ts +0 -229
  718. package/tools/context-index-check.ts +0 -48
  719. package/tools/context-lifecycle-check.ts +0 -69
  720. package/tools/context-projection-check.ts +0 -73
  721. package/tools/context-scope-check.ts +0 -134
  722. package/tools/context-storage-check.ts +0 -113
  723. package/tools/cooperation-check.ts +0 -517
  724. package/tools/cooperation-http-check.ts +0 -125
  725. package/tools/deepseek-llm-check.ts +0 -147
  726. package/tools/deepseek-probe.ts +0 -494
  727. package/tools/diagnosis-check.ts +0 -109
  728. package/tools/diagnosis-router-check.ts +0 -50
  729. package/tools/document-context-check.ts +0 -237
  730. package/tools/envelope-check.ts +0 -659
  731. package/tools/eslint-rules/index.ts +0 -26
  732. package/tools/eslint-rules/rules/jsdoc-comment-format.ts +0 -105
  733. package/tools/eslint-rules/rules/no-function-keyword.ts +0 -60
  734. package/tools/eslint-rules/rules/no-multiline-parameters.ts +0 -71
  735. package/tools/eslint-rules/rules/no-multiline-type-parameters.ts +0 -57
  736. package/tools/eslint-rules/rules/no-undefined-comparison.ts +0 -115
  737. package/tools/eslint-rules/rules/prefer-template-for-string-conversion.ts +0 -97
  738. package/tools/eslint-rules/rules/require-typeof-parentheses.ts +0 -49
  739. package/tools/eslint-rules/rules/require-variable-type.ts +0 -36
  740. package/tools/eslint-rules/rules/variable-naming.ts +0 -175
  741. package/tools/eval-recorded-replay.ts +0 -215
  742. package/tools/eval-replay.ts +0 -139
  743. package/tools/eval-summary.ts +0 -136
  744. package/tools/evidence-revalidation-check.ts +0 -235
  745. package/tools/exec-check.ts +0 -217
  746. package/tools/federation-check.ts +0 -166
  747. package/tools/federation-demo.ts +0 -45
  748. package/tools/filter-check.ts +0 -243
  749. package/tools/governance-check.ts +0 -680
  750. package/tools/governance-store-check.ts +0 -131
  751. package/tools/governed-task-check.ts +0 -227
  752. package/tools/guard-check.ts +0 -122
  753. package/tools/http-channel-check.ts +0 -125
  754. package/tools/import-campaign.ts +0 -28
  755. package/tools/inquiry-check.ts +0 -126
  756. package/tools/interaction-check.ts +0 -171
  757. package/tools/interrupts-check.ts +0 -173
  758. package/tools/ipc-check.ts +0 -170
  759. package/tools/kernel-async-check.ts +0 -136
  760. package/tools/kernel-check.ts +0 -369
  761. package/tools/kernel-runtime-check.ts +0 -276
  762. package/tools/keys-check.ts +0 -559
  763. package/tools/label-audit.ts +0 -70
  764. package/tools/labels-workflow-check.ts +0 -49
  765. package/tools/linear-structure-check.ts +0 -524
  766. package/tools/live-exec.ts +0 -62
  767. package/tools/live-governance-eval.ts +0 -813
  768. package/tools/live-legacy.ts +0 -50
  769. package/tools/lru-check.ts +0 -182
  770. package/tools/make-annotation-campaign.ts +0 -57
  771. package/tools/mcp-executor-check.ts +0 -33
  772. package/tools/merge-annotations.ts +0 -32
  773. package/tools/merge-check.ts +0 -98
  774. package/tools/metrics-check.ts +0 -84
  775. package/tools/net-probe.ts +0 -107
  776. package/tools/oauth-probe.ts +0 -117
  777. package/tools/outbox-check.ts +0 -50
  778. package/tools/persistence-check.ts +0 -144
  779. package/tools/pin-check.ts +0 -116
  780. package/tools/platform-check.ts +0 -281
  781. package/tools/policy-check.ts +0 -514
  782. package/tools/prettier-plugin/index.mts +0 -84
  783. package/tools/priority-check.ts +0 -627
  784. package/tools/probe-context7.ts +0 -63
  785. package/tools/registry-check.ts +0 -252
  786. package/tools/reliability-check.ts +0 -25
  787. package/tools/retry-check.ts +0 -85
  788. package/tools/rewrite-declaration-extensions.ts +0 -98
  789. package/tools/runtime-check.ts +0 -165
  790. package/tools/runtime-deepseek-check.ts +0 -85
  791. package/tools/runtime-eval.ts +0 -358
  792. package/tools/scenario-check.ts +0 -161
  793. package/tools/scenario-incident.ts +0 -162
  794. package/tools/scoped-priors-check.ts +0 -35
  795. package/tools/scoped-priors-pooling.ts +0 -34
  796. package/tools/segment-ast-check.ts +0 -649
  797. package/tools/session-check.ts +0 -196
  798. package/tools/session-store-check.ts +0 -73
  799. package/tools/share-check.ts +0 -88
  800. package/tools/sign-check.ts +0 -95
  801. package/tools/signing-check.ts +0 -275
  802. package/tools/snapshot-demo.ts +0 -65
  803. package/tools/social-check.ts +0 -146
  804. package/tools/structure-compare-check.ts +0 -95
  805. package/tools/support/documentScanner.ts +0 -577
  806. package/tools/support/texScanner.ts +0 -631
  807. package/tools/support/workspaceScanner.ts +0 -476
  808. package/tools/team-check.ts +0 -163
  809. package/tools/team-demo.ts +0 -36
  810. package/tools/telemetry-check.ts +0 -44
  811. package/tools/tex-context-check.ts +0 -263
  812. package/tools/tool-gate-check.ts +0 -98
  813. package/tools/tree-structure-check.ts +0 -786
  814. package/tools/trust-flow-check.ts +0 -158
  815. package/tools/turn-store-check.ts +0 -57
  816. package/tools/unified-check.ts +0 -83
  817. package/tools/validate.ts +0 -309
  818. package/tools/wire-check.ts +0 -96
  819. package/tools/workspace-agent-check.ts +0 -486
  820. package/tools/workspace-agent-demo.ts +0 -62
  821. package/tools/workspace-agent-server.ts +0 -101
  822. package/tools/workspace-context-check.ts +0 -331
  823. package/tools/workspace-context.ts +0 -131
  824. package/tsconfig.build.json +0 -14
  825. package/tsconfig.json +0 -24
  826. package/tsconfig.tools.json +0 -31
  827. package/viz/context-ast.json +0 -1577
@@ -0,0 +1,1028 @@
1
+ /**
2
+ * Atomic workspace writes with compare-and-swap guards and a write journal.
3
+ *
4
+ * The write path is intentionally conservative:
5
+ *
6
+ * - the target is resolved through the session sandbox before any I/O;
7
+ * - the current fingerprint is computed from the bytes that are actually
8
+ * present, so `expectFingerprint` is a real CAS rather than a cached guess;
9
+ * - the new bytes go to a same-directory `.amp-*.tmp` file that is `fsync`ed
10
+ * and renamed over the target, so a reader never observes a half-written
11
+ * file;
12
+ * - the parent chain is created only when `createParents` is set, and every
13
+ * created level is re-checked against the sandbox;
14
+ * - `dryRun` performs every check and builds a projected node without touching
15
+ * the disk.
16
+ *
17
+ * In-process writers serialize on `(sessionId, rootId, relativePath)`. That is
18
+ * not a cross-process lock: a second process is caught by the CAS fingerprint,
19
+ * which is why the journal records both the previous and the next fingerprint.
20
+ */
21
+ import { createHash, randomBytes } from "node:crypto";
22
+ import { closeSync, fsyncSync, lstatSync, mkdirSync, openSync, readFileSync, readSync, renameSync, rmSync, writeFileSync } from "node:fs";
23
+ import { dirname, join } from "node:path";
24
+ import { NamedLocks } from "../concurrency/namedLocks.js";
25
+ import { rawDigest } from "../fingerprint/raw.js";
26
+ import { countLines, decodeText, detectCharset, encodeText } from "../syntax/charset.js";
27
+ import { fail, isFilesystemError } from "./errors.js";
28
+ import { buildFileNode } from "./file.js";
29
+ import { describeFile, extensionOfPath, nameOfPath } from "./metadata.js";
30
+ import { byteRangeFingerprint, locateLineSpan } from "./read.js";
31
+ import { creationTime, formatIsoTime, formatNodeTime } from "./time.js";
32
+ /**
33
+ * Default ceiling for the resulting file size, in bytes.
34
+ */
35
+ const DefaultWriteBytes = 4 * 1024 * 1024;
36
+ /**
37
+ * Hard ceiling for the resulting file size, regardless of host configuration.
38
+ */
39
+ const MaxWriteBytes = 64 * 1024 * 1024;
40
+ /**
41
+ * Chunk size used when fingerprinting an existing file without loading it.
42
+ */
43
+ const HashChunkBytes = 64 * 1024;
44
+ /**
45
+ * Extract an `errno` code from an unknown thrown value without trusting it.
46
+ */
47
+ const errorCode = (error) => {
48
+ if (typeof (error) !== "object" || error === null) {
49
+ return "";
50
+ }
51
+ const code = error.code;
52
+ return typeof (code) === "string" ? code : "";
53
+ };
54
+ /**
55
+ * Translate a host filesystem failure into the closed domain taxonomy. The
56
+ * original message is dropped on purpose: it embeds absolute paths.
57
+ */
58
+ const mapFsError = (error) => {
59
+ if (isFilesystemError(error)) {
60
+ throw error;
61
+ }
62
+ switch (errorCode(error)) {
63
+ case "ENOENT": {
64
+ return fail("not_found");
65
+ }
66
+ case "EEXIST": {
67
+ return fail("already_exists");
68
+ }
69
+ case "EACCES":
70
+ case "EPERM":
71
+ case "EROFS": {
72
+ return fail("permission_denied");
73
+ }
74
+ case "EISDIR": {
75
+ return fail("not_file");
76
+ }
77
+ case "ENOTDIR": {
78
+ return fail("not_directory");
79
+ }
80
+ case "ENAMETOOLONG": {
81
+ return fail("invalid_path");
82
+ }
83
+ case "ELOOP": {
84
+ return fail("symlink_denied");
85
+ }
86
+ case "ENOSPC":
87
+ case "EDQUOT": {
88
+ return fail("quota_exceeded");
89
+ }
90
+ default: {
91
+ return fail("internal_error");
92
+ }
93
+ }
94
+ };
95
+ /**
96
+ * Run a best-effort cleanup without masking the failure that caused it.
97
+ */
98
+ const quietly = (action) => {
99
+ try {
100
+ action();
101
+ }
102
+ catch {
103
+ return;
104
+ }
105
+ };
106
+ /**
107
+ * Resolve a positive safe integer option, clamping it to `maximum`.
108
+ *
109
+ * @param value - Caller value, or `undefined` for the default.
110
+ * @param fallback - Default when the value is absent.
111
+ * @param maximum - Inclusive upper bound.
112
+ * @returns The effective value.
113
+ */
114
+ const positiveInteger = (value, fallback, maximum) => {
115
+ if (value === (void 0)) {
116
+ return fallback;
117
+ }
118
+ if (!Number.isSafeInteger(value) || value < 1) {
119
+ return fail("invalid_arguments");
120
+ }
121
+ return Math.min(value, maximum);
122
+ };
123
+ /**
124
+ * `lstat` a path that may legitimately be absent.
125
+ */
126
+ const statIfExists = (absolute) => {
127
+ try {
128
+ return lstatSync(absolute);
129
+ }
130
+ catch (error) {
131
+ if (errorCode(error) === "ENOENT") {
132
+ return undefined;
133
+ }
134
+ return mapFsError(error);
135
+ }
136
+ };
137
+ /**
138
+ * `lstat` a path that must exist.
139
+ */
140
+ const statOrFail = (absolute) => {
141
+ try {
142
+ return lstatSync(absolute);
143
+ }
144
+ catch (error) {
145
+ return mapFsError(error);
146
+ }
147
+ };
148
+ /**
149
+ * Read a file as bytes, translating a failure instead of leaking it.
150
+ */
151
+ const readRegularFile = (absolute) => {
152
+ try {
153
+ return readFileSync(absolute);
154
+ }
155
+ catch (error) {
156
+ return mapFsError(error);
157
+ }
158
+ };
159
+ /**
160
+ * Hash a file through a fixed-size buffer. Used for the previous fingerprint so
161
+ * overwriting a large file does not require loading it into memory.
162
+ */
163
+ const hashRegularFile = (absolute) => {
164
+ const hash = createHash("sha256");
165
+ const buffer = Buffer.allocUnsafe(HashChunkBytes);
166
+ let descriptor = (void 0);
167
+ try {
168
+ descriptor = openSync(absolute, "r");
169
+ let count = readSync(descriptor, buffer, 0, buffer.byteLength, null);
170
+ while (count > 0) {
171
+ hash.update(buffer.subarray(0, count));
172
+ count = readSync(descriptor, buffer, 0, buffer.byteLength, null);
173
+ }
174
+ }
175
+ catch (error) {
176
+ return mapFsError(error);
177
+ }
178
+ finally {
179
+ if (descriptor !== (void 0)) {
180
+ const openDescriptor = descriptor;
181
+ quietly(() => closeSync(openDescriptor));
182
+ }
183
+ }
184
+ return `sha256:${hash.digest("hex")}`;
185
+ };
186
+ /**
187
+ * Decode with a detected charset. A decoder failure is reported as
188
+ * `charset_unsupported`; a classified domain error passes through unchanged.
189
+ */
190
+ const decodePreviewText = (bytes, charset) => {
191
+ try {
192
+ return decodeText(bytes, charset);
193
+ }
194
+ catch (error) {
195
+ if (isFilesystemError(error)) {
196
+ throw error;
197
+ }
198
+ return fail("charset_unsupported");
199
+ }
200
+ };
201
+ /**
202
+ * Build the node a successful write would produce, without writing.
203
+ *
204
+ * When the target exists its current node is the base, so descriptions and
205
+ * timestamps survive; only the content-derived fields are projected from the
206
+ * new bytes. A new target gets a minimal node whose timestamps are "now",
207
+ * because there is no file to inspect yet; its descriptive fields are still
208
+ * derived from the new bytes instead of being left empty.
209
+ */
210
+ const previewFileNode = (rooted, bytes, timeZone) => {
211
+ const detected = detectCharset(bytes);
212
+ const charset = detected.binary ? "binary" : detected.charset;
213
+ const lines = detected.binary ? 0n : countLines(decodePreviewText(bytes, charset));
214
+ const fingerprint = rawDigest(bytes);
215
+ const byteCount = BigInt(bytes.byteLength);
216
+ const current = statIfExists(rooted.absolute);
217
+ if (current !== (void 0) && current.isFile()) {
218
+ const existing = buildFileNode(rooted.root, rooted.relative, { timeZone });
219
+ return { ...existing, charset, lines, bytes: byteCount, fingerprint };
220
+ }
221
+ const described = describeFile(rooted.absolute, rooted.relative, charset, bytes);
222
+ const now = new Date();
223
+ return {
224
+ type: "File",
225
+ path: rooted.relative,
226
+ name: nameOfPath(rooted.relative),
227
+ extension: extensionOfPath(rooted.relative),
228
+ children: [],
229
+ fingerprint,
230
+ charset,
231
+ lines,
232
+ bytes: byteCount,
233
+ create: formatNodeTime(now, timeZone),
234
+ modify: formatNodeTime(now, timeZone),
235
+ description: described.description,
236
+ summary: described.summary,
237
+ purpose: described.purpose,
238
+ };
239
+ };
240
+ /**
241
+ * Normalize and validate a write mode. `upsert` is the default because a write
242
+ * is an assignment: it should not fail merely because the file is new.
243
+ */
244
+ const normalizeMode = (mode) => {
245
+ if (mode === (void 0)) {
246
+ return "upsert";
247
+ }
248
+ switch (mode) {
249
+ case "create":
250
+ case "overwrite":
251
+ case "upsert":
252
+ case "append": {
253
+ return mode;
254
+ }
255
+ default: {
256
+ return fail("invalid_arguments");
257
+ }
258
+ }
259
+ };
260
+ /**
261
+ * Validate a text encoding name.
262
+ */
263
+ const normalizeEncoding = (encoding) => {
264
+ if (encoding === (void 0)) {
265
+ return "utf-8";
266
+ }
267
+ switch (encoding) {
268
+ case "utf-8":
269
+ case "utf-8-bom":
270
+ case "utf-16le":
271
+ case "utf-16be":
272
+ case "latin1": {
273
+ return encoding;
274
+ }
275
+ default: {
276
+ return fail("invalid_arguments");
277
+ }
278
+ }
279
+ };
280
+ /**
281
+ * Encode the request content. Raw bytes may only be written as UTF-8 (the
282
+ * default); declaring another encoding for already-encoded bytes is a caller
283
+ * bug, not something to guess about.
284
+ */
285
+ const encodeContent = (content, encoding) => {
286
+ if (typeof (content) === "string") {
287
+ return encodeText(content, normalizeEncoding(encoding));
288
+ }
289
+ if (content instanceof Uint8Array) {
290
+ if (encoding !== (void 0) && encoding !== "utf-8") {
291
+ return fail("invalid_arguments");
292
+ }
293
+ return content;
294
+ }
295
+ return fail("invalid_arguments");
296
+ };
297
+ /**
298
+ * Enforce the compare-and-swap precondition. `undefined` skips the check,
299
+ * `null` requires an absent file and a string must match exactly.
300
+ */
301
+ const checkCas = (expected, previous) => {
302
+ if (expected === (void 0)) {
303
+ return;
304
+ }
305
+ if (expected !== null && typeof (expected) !== "string") {
306
+ return fail("invalid_arguments");
307
+ }
308
+ if (expected === null) {
309
+ if (previous !== null) {
310
+ return fail("fingerprint_mismatch");
311
+ }
312
+ return;
313
+ }
314
+ if (previous !== expected) {
315
+ return fail("fingerprint_mismatch");
316
+ }
317
+ };
318
+ /**
319
+ * Enforce the mode precondition against the observed file state.
320
+ */
321
+ const checkMode = (mode, exists) => {
322
+ if (mode === "create" && exists) {
323
+ return fail("already_exists");
324
+ }
325
+ if (mode === "overwrite" && !exists) {
326
+ return fail("not_found");
327
+ }
328
+ };
329
+ /**
330
+ * Assemble the bytes that end up on disk. Append reads the previous bytes and
331
+ * concatenates; every other mode writes exactly the encoded fragment. The
332
+ * size ceiling applies to the result, so an append cannot grow past it.
333
+ */
334
+ const finalContent = (absolute, encoded, mode, current, maxBytes) => {
335
+ if (mode === "append" && current !== (void 0)) {
336
+ if (current.size + encoded.byteLength > maxBytes) {
337
+ return fail("quota_exceeded");
338
+ }
339
+ const previous = readRegularFile(absolute);
340
+ const combined = new Uint8Array(previous.byteLength + encoded.byteLength);
341
+ combined.set(previous, 0);
342
+ combined.set(encoded, previous.byteLength);
343
+ return combined;
344
+ }
345
+ if (encoded.byteLength > maxBytes) {
346
+ return fail("quota_exceeded");
347
+ }
348
+ return encoded;
349
+ };
350
+ /**
351
+ * Create one missing directory level after checking it against the sandbox.
352
+ */
353
+ const makeDirectoryChain = (sandbox, root, relative) => {
354
+ const segments = relative.split("/");
355
+ for (let index = 1; index <= segments.length; index += 1) {
356
+ const current = segments.slice(0, index).join("/");
357
+ const absolute = join(root.path, current);
358
+ if (!sandbox.contains(root.path, absolute)) {
359
+ return fail("path_escape");
360
+ }
361
+ sandbox.revalidate({ root, relative: current, absolute });
362
+ const stat = statIfExists(absolute);
363
+ if (stat !== (void 0)) {
364
+ if (!stat.isDirectory()) {
365
+ return fail("not_directory");
366
+ }
367
+ continue;
368
+ }
369
+ try {
370
+ mkdirSync(absolute);
371
+ }
372
+ catch (error) {
373
+ if (errorCode(error) !== "EEXIST") {
374
+ return mapFsError(error);
375
+ }
376
+ }
377
+ }
378
+ };
379
+ /**
380
+ * Validate the existing prefix of a directory chain without creating anything.
381
+ * Used by `dryRun`, which must reject a non-directory ancestor but must not
382
+ * mutate the disk.
383
+ */
384
+ const validateDirectoryChain = (sandbox, root, relative) => {
385
+ const segments = relative.split("/");
386
+ for (let index = 1; index <= segments.length; index += 1) {
387
+ const current = segments.slice(0, index).join("/");
388
+ const absolute = join(root.path, current);
389
+ if (!sandbox.contains(root.path, absolute)) {
390
+ return fail("path_escape");
391
+ }
392
+ sandbox.revalidate({ root, relative: current, absolute });
393
+ const stat = statIfExists(absolute);
394
+ if (stat === (void 0)) {
395
+ return;
396
+ }
397
+ if (!stat.isDirectory()) {
398
+ return fail("not_directory");
399
+ }
400
+ }
401
+ };
402
+ /**
403
+ * Ensure the target's parent directory exists (or would be creatable).
404
+ */
405
+ const prepareParent = (sandbox, rooted, createParents, materialize) => {
406
+ const segments = rooted.relative.split("/");
407
+ if (segments.length <= 1) {
408
+ return;
409
+ }
410
+ const parent = segments.slice(0, -1).join("/");
411
+ if (createParents) {
412
+ if (materialize) {
413
+ makeDirectoryChain(sandbox, rooted.root, parent);
414
+ }
415
+ else {
416
+ validateDirectoryChain(sandbox, rooted.root, parent);
417
+ }
418
+ return;
419
+ }
420
+ const absolute = join(rooted.root.path, parent);
421
+ if (!sandbox.contains(rooted.root.path, absolute)) {
422
+ return fail("path_escape");
423
+ }
424
+ sandbox.revalidate({ root: rooted.root, relative: parent, absolute });
425
+ const stat = statIfExists(absolute);
426
+ if (stat === (void 0)) {
427
+ return fail("not_found");
428
+ }
429
+ if (!stat.isDirectory()) {
430
+ return fail("not_directory");
431
+ }
432
+ };
433
+ /**
434
+ * Write bytes through a same-directory temporary file: write, `fsync`, close,
435
+ * then `rename` over the target. A failure before the rename removes the
436
+ * temporary file; the target is never truncated in place.
437
+ */
438
+ const atomicWrite = (absolute, bytes, modeBits) => {
439
+ const temp = join(dirname(absolute), `.amp-${randomBytes(8).toString("hex")}.tmp`);
440
+ let descriptor = (void 0);
441
+ let renamed = false;
442
+ try {
443
+ descriptor = openSync(temp, "wx", modeBits === (void 0) ? 0o666 : modeBits);
444
+ writeFileSync(descriptor, bytes);
445
+ fsyncSync(descriptor);
446
+ closeSync(descriptor);
447
+ descriptor = (void 0);
448
+ renameSync(temp, absolute);
449
+ renamed = true;
450
+ }
451
+ finally {
452
+ if (descriptor !== (void 0)) {
453
+ const openDescriptor = descriptor;
454
+ quietly(() => closeSync(openDescriptor));
455
+ }
456
+ if (!renamed) {
457
+ quietly(() => rmSync(temp, { force: true }));
458
+ }
459
+ }
460
+ };
461
+ /**
462
+ * Write locks keyed by `(sessionId, rootId, relativePath)`.
463
+ *
464
+ * The class is exported so a host can own one registry and share it with other
465
+ * workspace components; {@link writeFile} uses a process-wide registry because
466
+ * its frozen signature carries no lock parameter.
467
+ */
468
+ export class WriteLocks {
469
+ locks = new NamedLocks();
470
+ async run(name, fn) {
471
+ return this.locks.run(name, fn);
472
+ }
473
+ /**
474
+ * Number of distinct lock names seen so far.
475
+ */
476
+ get size() {
477
+ return this.locks.size;
478
+ }
479
+ }
480
+ /**
481
+ * Process-wide lock registry used by {@link writeFile}.
482
+ */
483
+ const WriteLockRegistry = new WriteLocks();
484
+ /**
485
+ * Run the checks and the write while holding the path lock. Journal creation is
486
+ * metadata only; the callback and the tree refresh run after the lock is
487
+ * released so a callback can safely write the same path again.
488
+ */
489
+ const writeLocked = (context) => {
490
+ context.sandbox.revalidate(context.rooted);
491
+ const current = statIfExists(context.rooted.absolute);
492
+ if (current !== (void 0)) {
493
+ if (current.isSymbolicLink()) {
494
+ return fail("symlink_denied");
495
+ }
496
+ if (!current.isFile()) {
497
+ return fail("not_file");
498
+ }
499
+ }
500
+ const previousFingerprint = current === (void 0) ? null : hashRegularFile(context.rooted.absolute);
501
+ checkCas(context.request.expectFingerprint, previousFingerprint);
502
+ checkMode(context.mode, current !== (void 0));
503
+ const encoded = encodeContent(context.content, context.request.encoding);
504
+ const bytes = finalContent(context.rooted.absolute, encoded, context.mode, current, context.maxBytes);
505
+ prepareParent(context.sandbox, context.rooted, context.createParents, !context.dryRun);
506
+ const created = current === (void 0);
507
+ context.sandbox.revalidate(context.rooted);
508
+ if (context.dryRun) {
509
+ const preview = previewFileNode(context.rooted, bytes, context.timeZone);
510
+ return {
511
+ result: {
512
+ node: preview,
513
+ previousFingerprint,
514
+ created,
515
+ dryRun: true,
516
+ bytesWritten: BigInt(bytes.byteLength),
517
+ revision: preview.fingerprint,
518
+ },
519
+ journal: (void 0),
520
+ relative: context.rooted.relative,
521
+ };
522
+ }
523
+ atomicWrite(context.rooted.absolute, bytes, current === (void 0) ? (void 0) : current.mode & 0o777);
524
+ context.sandbox.revalidate(context.rooted);
525
+ const nextStat = statOrFail(context.rooted.absolute);
526
+ const node = fileNodeFromBytes(context.rooted, bytes, nextStat, context.timeZone);
527
+ let journal = (void 0);
528
+ if (context.options.journal !== (void 0)) {
529
+ journal = {
530
+ id: `w.${randomBytes(8).toString("hex")}`,
531
+ sessionId: context.sessionId,
532
+ rootId: context.rooted.root.id,
533
+ path: context.rooted.relative,
534
+ mode: context.mode,
535
+ previousFingerprint,
536
+ nextFingerprint: rawDigest(bytes),
537
+ bytes: BigInt(bytes.byteLength),
538
+ at: formatIsoTime(new Date()),
539
+ };
540
+ }
541
+ return {
542
+ result: {
543
+ node,
544
+ previousFingerprint,
545
+ created,
546
+ dryRun: false,
547
+ bytesWritten: BigInt(bytes.byteLength),
548
+ revision: node.fingerprint,
549
+ },
550
+ journal,
551
+ relative: context.rooted.relative,
552
+ };
553
+ };
554
+ /**
555
+ * Publish the journal record and refresh the tree after the lock is released.
556
+ */
557
+ const publishWrite = (commit, options) => {
558
+ if (commit.result.dryRun) {
559
+ return commit.result;
560
+ }
561
+ if (options.journal !== (void 0) && commit.journal !== (void 0)) {
562
+ options.journal(commit.journal);
563
+ }
564
+ const tree = options.tree;
565
+ if (tree === (void 0)) {
566
+ return commit.result;
567
+ }
568
+ return { ...commit.result, revision: tree.refresh(commit.relative).revision };
569
+ };
570
+ /**
571
+ * Write one workspace file atomically.
572
+ *
573
+ * Order of checks matches the contract: resolve, lock, read the current file
574
+ * and its fingerprint, CAS, mode, content encoding, size ceiling, parent
575
+ * directory, then the atomic rename. A `dryRun` stops right after the parent
576
+ * check and returns the projected node instead of writing.
577
+ *
578
+ * @param sandbox - Session sandbox that owns path resolution.
579
+ * @param sessionId - Public session handle used for the lock and the journal.
580
+ * @param request - Path, content, mode, CAS precondition and dry-run flag.
581
+ * @param options - Size ceiling, journal sink, tree and timestamp mode.
582
+ * @returns The new node, previous fingerprint and write metadata.
583
+ */
584
+ export const writeFile = async (sandbox, sessionId, request, options = {}) => {
585
+ if (typeof (sessionId) !== "string" || sessionId.length === 0 || sessionId.includes("\u0000")) {
586
+ return fail("invalid_arguments");
587
+ }
588
+ if (typeof (request) !== "object" || request === null) {
589
+ return fail("invalid_arguments");
590
+ }
591
+ const settings = options === (void 0) || options === null ? {} : options;
592
+ const mode = normalizeMode(request.mode);
593
+ const maxBytes = positiveInteger(settings.maxBytes, DefaultWriteBytes, MaxWriteBytes);
594
+ const rooted = sandbox.resolve(request.path, mode === "create" ? "create" : "write");
595
+ if (rooted.relative === ".") {
596
+ return fail("not_file");
597
+ }
598
+ const content = request.content;
599
+ const snapshotContent = typeof (content) === "string" ? content : content instanceof Uint8Array ? new Uint8Array(content) : content;
600
+ const timeZone = settings.timeZone === "utc" ? "utc" : "local";
601
+ const context = {
602
+ sandbox,
603
+ sessionId,
604
+ rooted,
605
+ mode,
606
+ request,
607
+ content: snapshotContent,
608
+ options: settings,
609
+ maxBytes,
610
+ dryRun: request.dryRun === true,
611
+ createParents: request.createParents === true,
612
+ timeZone,
613
+ };
614
+ const lockName = `${sessionId}\u0000${rooted.root.id}\u0000${rooted.relative}`;
615
+ const commit = await WriteLockRegistry.run(lockName, () => writeLocked(context)).catch((error) => mapFsError(error));
616
+ try {
617
+ return publishWrite(commit, settings);
618
+ }
619
+ catch (error) {
620
+ return mapFsError(error);
621
+ }
622
+ };
623
+ /**
624
+ * Validate a raw byte offset.
625
+ */
626
+ const patchByteOffset = (value) => {
627
+ if (!Number.isSafeInteger(value) || value < 0) {
628
+ return fail("invalid_arguments");
629
+ }
630
+ return value;
631
+ };
632
+ /**
633
+ * Validate a 1-based start line.
634
+ */
635
+ const patchStartLine = (value) => {
636
+ if (!Number.isSafeInteger(value) || value < 1) {
637
+ return fail("invalid_arguments");
638
+ }
639
+ return value;
640
+ };
641
+ /**
642
+ * Validate an inclusive end line; `0` is the insertion point before line 1.
643
+ */
644
+ const patchEndLine = (value) => {
645
+ if (!Number.isSafeInteger(value) || value < 0) {
646
+ return fail("invalid_arguments");
647
+ }
648
+ return value;
649
+ };
650
+ /**
651
+ * A range patch cannot be unsafe: the whole-file fingerprint is mandatory.
652
+ */
653
+ const requiredFingerprint = (value) => typeof (value) === "string" && value.length > 0 ? value : fail("invalid_arguments");
654
+ /**
655
+ * Optional secondary range fingerprint.
656
+ */
657
+ const optionalFingerprint = (value) => value === (void 0) ? (void 0) : requiredFingerprint(value);
658
+ /**
659
+ * Encode line replacement content in the file's own charset without a BOM. A
660
+ * BOM belongs to the file, never to an inserted fragment.
661
+ */
662
+ const encodeLineBody = (text, charset) => {
663
+ switch (charset) {
664
+ case "utf-8":
665
+ case "utf-8-bom": {
666
+ return new TextEncoder().encode(text);
667
+ }
668
+ case "utf-16le": {
669
+ return new Uint8Array(Buffer.from(text, "utf16le"));
670
+ }
671
+ case "utf-16be": {
672
+ const body = Buffer.from(text, "utf16le");
673
+ body.swap16();
674
+ return new Uint8Array(body);
675
+ }
676
+ case "latin1": {
677
+ return encodeText(text, "latin1");
678
+ }
679
+ default: {
680
+ return fail("charset_unsupported");
681
+ }
682
+ }
683
+ };
684
+ /**
685
+ * Replace one validated raw byte span in memory.
686
+ */
687
+ const spliceBytes = (bytes, startByte, endByte, replacement) => {
688
+ const result = new Uint8Array(bytes.byteLength - (endByte - startByte) + replacement.byteLength);
689
+ result.set(bytes.subarray(0, startByte), 0);
690
+ result.set(replacement, startByte);
691
+ result.set(bytes.subarray(endByte), startByte + replacement.byteLength);
692
+ return result;
693
+ };
694
+ /**
695
+ * Build the node for already-known bytes plus a stat. Used by range patches so
696
+ * a committed write does not have to read and hash the file a third time.
697
+ */
698
+ const fileNodeFromBytes = (rooted, bytes, stat, timeZone) => {
699
+ const detected = detectCharset(bytes);
700
+ let charset = detected.binary ? "binary" : detected.charset;
701
+ let lines = 0n;
702
+ if (charset !== "binary") {
703
+ try {
704
+ lines = countLines(decodeText(bytes, charset));
705
+ }
706
+ catch {
707
+ charset = "binary";
708
+ lines = 0n;
709
+ }
710
+ }
711
+ const described = describeFile(rooted.absolute, rooted.relative, charset, bytes);
712
+ return {
713
+ type: "File",
714
+ path: rooted.relative,
715
+ name: nameOfPath(rooted.relative),
716
+ extension: extensionOfPath(rooted.relative),
717
+ children: [],
718
+ fingerprint: rawDigest(bytes),
719
+ charset,
720
+ lines,
721
+ bytes: BigInt(bytes.byteLength),
722
+ create: formatNodeTime(creationTime(stat), timeZone),
723
+ modify: formatNodeTime(new Date(stat.mtimeMs), timeZone),
724
+ description: described.description,
725
+ summary: described.summary,
726
+ purpose: described.purpose,
727
+ };
728
+ };
729
+ /**
730
+ * Execute one patch while the path lock is held. The file must already exist;
731
+ * the whole-file fingerprint is checked first, then the optional range
732
+ * fingerprint, then the in-memory splice and the atomic rename.
733
+ */
734
+ const patchLocked = (context, planner) => {
735
+ context.sandbox.revalidate(context.rooted);
736
+ const current = statIfExists(context.rooted.absolute);
737
+ if (current === (void 0)) {
738
+ return fail("not_found");
739
+ }
740
+ if (current.isSymbolicLink()) {
741
+ return fail("symlink_denied");
742
+ }
743
+ if (!current.isFile()) {
744
+ return fail("not_file");
745
+ }
746
+ if (current.size > MaxWriteBytes) {
747
+ return fail("quota_exceeded");
748
+ }
749
+ const bytes = readRegularFile(context.rooted.absolute);
750
+ if (bytes.byteLength > MaxWriteBytes) {
751
+ return fail("quota_exceeded");
752
+ }
753
+ const previousFingerprint = rawDigest(bytes);
754
+ if (previousFingerprint !== context.expectFingerprint) {
755
+ return fail("fingerprint_mismatch");
756
+ }
757
+ const plan = planner(bytes);
758
+ if (!Number.isSafeInteger(plan.startByte) || plan.startByte < 0 || !Number.isSafeInteger(plan.endByte) || plan.endByte < plan.startByte || plan.endByte > bytes.byteLength) {
759
+ return fail("invalid_arguments");
760
+ }
761
+ const previousRangeFingerprint = byteRangeFingerprint(plan.startByte, plan.endByte, bytes.subarray(plan.startByte, plan.endByte));
762
+ if (context.expectRangeFingerprint !== (void 0) && previousRangeFingerprint !== context.expectRangeFingerprint) {
763
+ return fail("fingerprint_mismatch");
764
+ }
765
+ const nextBytes = spliceBytes(bytes, plan.startByte, plan.endByte, plan.replacement);
766
+ if (nextBytes.byteLength > context.maxBytes) {
767
+ return fail("quota_exceeded");
768
+ }
769
+ const nextFingerprint = rawDigest(nextBytes);
770
+ const nextStartByte = plan.startByte;
771
+ const nextEndByte = plan.startByte + plan.replacement.byteLength;
772
+ const nextRangeFingerprint = byteRangeFingerprint(nextStartByte, nextEndByte, nextBytes.subarray(nextStartByte, nextEndByte));
773
+ const previousTotalBytes = BigInt(bytes.byteLength);
774
+ const nextTotalBytes = BigInt(nextBytes.byteLength);
775
+ const baseResult = {
776
+ node: fileNodeFromBytes(context.rooted, nextBytes, current, context.timeZone),
777
+ previousFingerprint,
778
+ created: false,
779
+ dryRun: context.dryRun,
780
+ bytesWritten: nextTotalBytes,
781
+ revision: nextFingerprint,
782
+ kind: context.kind,
783
+ startByte: plan.startByte,
784
+ endByte: plan.endByte,
785
+ startLine: plan.startLine,
786
+ endLine: plan.endLine,
787
+ previousRangeFingerprint,
788
+ nextRangeFingerprint,
789
+ nextStartByte,
790
+ nextEndByte,
791
+ previousTotalBytes,
792
+ nextTotalBytes,
793
+ };
794
+ if (context.dryRun) {
795
+ return { result: baseResult, journal: (void 0), patchJournal: (void 0), relative: context.rooted.relative };
796
+ }
797
+ context.sandbox.revalidate(context.rooted);
798
+ atomicWrite(context.rooted.absolute, nextBytes, current.mode & 0o777);
799
+ context.sandbox.revalidate(context.rooted);
800
+ const nextStat = statOrFail(context.rooted.absolute);
801
+ const node = fileNodeFromBytes(context.rooted, nextBytes, nextStat, context.timeZone);
802
+ const id = `w.${randomBytes(8).toString("hex")}`;
803
+ const at = formatIsoTime(new Date());
804
+ const journal = {
805
+ id,
806
+ sessionId: context.sessionId,
807
+ rootId: context.rooted.root.id,
808
+ path: context.rooted.relative,
809
+ mode: "overwrite",
810
+ previousFingerprint,
811
+ nextFingerprint,
812
+ bytes: nextTotalBytes,
813
+ at,
814
+ };
815
+ const patchJournal = {
816
+ ...journal,
817
+ kind: context.kind,
818
+ startByte: plan.startByte,
819
+ endByte: plan.endByte,
820
+ startLine: plan.startLine,
821
+ endLine: plan.endLine,
822
+ previousRangeFingerprint,
823
+ nextRangeFingerprint,
824
+ nextStartByte,
825
+ nextEndByte,
826
+ previousTotalBytes,
827
+ nextTotalBytes,
828
+ };
829
+ return { result: { ...baseResult, node, revision: node.fingerprint }, journal, patchJournal, relative: context.rooted.relative };
830
+ };
831
+ /**
832
+ * Publish the journal entries and refresh the tree after the lock is released.
833
+ * Journal callbacks must not run under the non-reentrant write lock: a callback
834
+ * that writes the same path would otherwise deadlock.
835
+ */
836
+ const publishPatch = (commit, options) => {
837
+ if (commit.result.dryRun) {
838
+ return commit.result;
839
+ }
840
+ if (options.journal !== (void 0) && commit.journal !== (void 0)) {
841
+ options.journal(commit.journal);
842
+ }
843
+ if (options.patchJournal !== (void 0) && commit.patchJournal !== (void 0)) {
844
+ options.patchJournal(commit.patchJournal);
845
+ }
846
+ const tree = options.tree;
847
+ if (tree === (void 0)) {
848
+ return commit.result;
849
+ }
850
+ return { ...commit.result, revision: tree.refresh(commit.relative).revision };
851
+ };
852
+ /**
853
+ * Replace a raw byte range of an existing file.
854
+ *
855
+ * The whole-file `expectFingerprint` is mandatory and is verified from the bytes
856
+ * read under the lock; `expectRangeFingerprint` is a secondary check. The new
857
+ * file is assembled in memory, written through a same-directory temporary file,
858
+ * `fsync`ed and renamed, so a reader never observes a partial file.
859
+ *
860
+ * @param sandbox - Session sandbox that owns path resolution.
861
+ * @param sessionId - Public session handle used for the lock and journal.
862
+ * @param request - Path, half-open byte range, replacement bytes and CAS guards.
863
+ * @param options - Size ceiling, journal sinks, tree and timestamp mode.
864
+ * @returns Patch result with both fingerprint pairs and the new node.
865
+ */
866
+ export const useByte = async (sandbox, sessionId, request, options = {}) => {
867
+ if (typeof (sessionId) !== "string" || sessionId.length === 0 || sessionId.includes("\u0000")) {
868
+ return fail("invalid_arguments");
869
+ }
870
+ if (typeof (request) !== "object" || request === null) {
871
+ return fail("invalid_arguments");
872
+ }
873
+ const settings = options === (void 0) || options === null ? {} : options;
874
+ const expectFingerprint = requiredFingerprint(request.expectFingerprint);
875
+ const expectRangeFingerprint = optionalFingerprint(request.expectRangeFingerprint);
876
+ if (!(request.content instanceof Uint8Array)) {
877
+ return fail("invalid_arguments");
878
+ }
879
+ const replacement = new Uint8Array(request.content);
880
+ const startByte = patchByteOffset(request.startByte);
881
+ const endByte = patchByteOffset(request.endByte);
882
+ if (endByte < startByte) {
883
+ return fail("invalid_arguments");
884
+ }
885
+ const maxBytes = positiveInteger(settings.maxBytes, DefaultWriteBytes, MaxWriteBytes);
886
+ const rooted = sandbox.resolve(request.path, "write");
887
+ if (rooted.relative === ".") {
888
+ return fail("not_file");
889
+ }
890
+ const context = {
891
+ sandbox,
892
+ sessionId,
893
+ rooted,
894
+ kind: "byte",
895
+ expectFingerprint,
896
+ expectRangeFingerprint,
897
+ dryRun: request.dryRun === true,
898
+ maxBytes,
899
+ timeZone: settings.timeZone === "utc" ? "utc" : "local",
900
+ };
901
+ const planner = (bytes) => {
902
+ if (endByte > bytes.byteLength) {
903
+ return fail("invalid_arguments");
904
+ }
905
+ return { kind: "byte", startByte, endByte, replacement };
906
+ };
907
+ const lockName = `${sessionId}\u0000${rooted.root.id}\u0000${rooted.relative}`;
908
+ const commit = await WriteLockRegistry.run(lockName, () => patchLocked(context, planner)).catch((error) => mapFsError(error));
909
+ try {
910
+ return publishPatch(commit, settings);
911
+ }
912
+ catch (error) {
913
+ return mapFsError(error);
914
+ }
915
+ };
916
+ /**
917
+ * Replace a line range of an existing text file.
918
+ *
919
+ * Line numbers are 1-based and inclusive. The replaced span starts at the first
920
+ * character of `startLine` and includes the terminator of `endLine` when one
921
+ * exists, which means `content` is inserted verbatim: include the desired
922
+ * newline when more lines follow. Use `endLine = startLine - 1` to insert.
923
+ *
924
+ * @param sandbox - Session sandbox that owns path resolution.
925
+ * @param sessionId - Public session handle used for the lock and journal.
926
+ * @param request - Path, inclusive line range, replacement text and CAS guards.
927
+ * @param options - Size ceiling, journal sinks, tree and timestamp mode.
928
+ * @returns Patch result with both fingerprint pairs and the new node.
929
+ */
930
+ export const useLine = async (sandbox, sessionId, request, options = {}) => {
931
+ if (typeof (sessionId) !== "string" || sessionId.length === 0 || sessionId.includes("\u0000")) {
932
+ return fail("invalid_arguments");
933
+ }
934
+ if (typeof (request) !== "object" || request === null) {
935
+ return fail("invalid_arguments");
936
+ }
937
+ const settings = options === (void 0) || options === null ? {} : options;
938
+ const expectFingerprint = requiredFingerprint(request.expectFingerprint);
939
+ const expectRangeFingerprint = optionalFingerprint(request.expectRangeFingerprint);
940
+ if (typeof (request.content) !== "string") {
941
+ return fail("invalid_arguments");
942
+ }
943
+ const content = request.content;
944
+ const startLine = patchStartLine(request.startLine);
945
+ const endLine = patchEndLine(request.endLine);
946
+ if (endLine < startLine - 1) {
947
+ return fail("invalid_arguments");
948
+ }
949
+ const maxBytes = positiveInteger(settings.maxBytes, DefaultWriteBytes, MaxWriteBytes);
950
+ const rooted = sandbox.resolve(request.path, "write");
951
+ if (rooted.relative === ".") {
952
+ return fail("not_file");
953
+ }
954
+ const context = {
955
+ sandbox,
956
+ sessionId,
957
+ rooted,
958
+ kind: "line",
959
+ expectFingerprint,
960
+ expectRangeFingerprint,
961
+ dryRun: request.dryRun === true,
962
+ maxBytes,
963
+ timeZone: settings.timeZone === "utc" ? "utc" : "local",
964
+ };
965
+ const planner = (bytes) => {
966
+ const span = locateLineSpan(bytes, startLine, endLine);
967
+ return {
968
+ kind: "line",
969
+ startByte: span.startByte,
970
+ endByte: span.endByte,
971
+ replacement: encodeLineBody(content, span.charset),
972
+ startLine,
973
+ endLine,
974
+ };
975
+ };
976
+ const lockName = `${sessionId}\u0000${rooted.root.id}\u0000${rooted.relative}`;
977
+ const commit = await WriteLockRegistry.run(lockName, () => patchLocked(context, planner)).catch((error) => mapFsError(error));
978
+ try {
979
+ return publishPatch(commit, settings);
980
+ }
981
+ catch (error) {
982
+ return mapFsError(error);
983
+ }
984
+ };
985
+ /**
986
+ * Create a directory inside a root. `create` requires the parent to exist and
987
+ * fails when the target is already present; `ensure` creates the whole chain
988
+ * and treats an existing directory as success. The root itself is always a
989
+ * valid target for `ensure` and never for `create`.
990
+ *
991
+ * @param sandbox - Session sandbox that owns path resolution.
992
+ * @param path - Root-relative POSIX directory path.
993
+ * @param mode - `create` or `ensure`; defaults to `ensure`.
994
+ * @returns The resolved path of the directory.
995
+ */
996
+ export const ensureDirectory = (sandbox, path, mode = "ensure") => {
997
+ if (mode !== "create" && mode !== "ensure") {
998
+ return fail("invalid_arguments");
999
+ }
1000
+ const rooted = sandbox.resolve(path, "create");
1001
+ if (rooted.relative === ".") {
1002
+ return rooted;
1003
+ }
1004
+ if (mode === "ensure") {
1005
+ makeDirectoryChain(sandbox, rooted.root, rooted.relative);
1006
+ sandbox.revalidate(rooted);
1007
+ return rooted;
1008
+ }
1009
+ if (statIfExists(rooted.absolute) !== (void 0)) {
1010
+ return fail("already_exists");
1011
+ }
1012
+ const parent = dirname(rooted.absolute);
1013
+ if (!sandbox.contains(rooted.root.path, parent)) {
1014
+ return fail("path_escape");
1015
+ }
1016
+ const parentStat = statOrFail(parent);
1017
+ if (!parentStat.isDirectory()) {
1018
+ return fail("not_directory");
1019
+ }
1020
+ try {
1021
+ mkdirSync(rooted.absolute);
1022
+ }
1023
+ catch (error) {
1024
+ return mapFsError(error);
1025
+ }
1026
+ sandbox.revalidate(rooted);
1027
+ return rooted;
1028
+ };