farming-code 2.2.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 (453) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +287 -0
  3. package/README.zh_cn.md +329 -0
  4. package/SECURITY.md +29 -0
  5. package/THIRD_PARTY_NOTICES.md +106 -0
  6. package/backend/acp/client-services.js +312 -0
  7. package/backend/acp/patch-decisions.js +137 -0
  8. package/backend/acp/permission-security.js +108 -0
  9. package/backend/acp-runtime.js +1144 -0
  10. package/backend/acp-session-state.js +448 -0
  11. package/backend/acp-transcript.js +169 -0
  12. package/backend/agent-activity.js +186 -0
  13. package/backend/agent-env.js +250 -0
  14. package/backend/agent-json-stream.js +268 -0
  15. package/backend/agent-manager.js +4259 -0
  16. package/backend/agent-memory-report.js +583 -0
  17. package/backend/agent-order.js +162 -0
  18. package/backend/agent-provider-session.js +287 -0
  19. package/backend/agent-session-history.js +888 -0
  20. package/backend/app-server-api.js +917 -0
  21. package/backend/async-cache.js +94 -0
  22. package/backend/auth.js +178 -0
  23. package/backend/claude-settings.js +121 -0
  24. package/backend/cli-agents.js +484 -0
  25. package/backend/codex-app-server-home.js +39 -0
  26. package/backend/codex-app-server-runtime.js +901 -0
  27. package/backend/codex-context-window.js +189 -0
  28. package/backend/codex-models.js +229 -0
  29. package/backend/codex-rollout-follower.js +243 -0
  30. package/backend/codex-session-history.js +553 -0
  31. package/backend/codex-transcript-sanitizer.js +103 -0
  32. package/backend/codex-transcript.js +2341 -0
  33. package/backend/command-runner-child.js +67 -0
  34. package/backend/config-manager.js +815 -0
  35. package/backend/control-api.js +151 -0
  36. package/backend/data/chinese-poetic-words.json +8223 -0
  37. package/backend/data/poetic-word-sources/china.json +49209 -0
  38. package/backend/data/poetic-word-sources/india.json +9763 -0
  39. package/backend/data/poetic-word-sources/japan.json +8455 -0
  40. package/backend/executable-discovery.js +207 -0
  41. package/backend/farming-app-cli.js +790 -0
  42. package/backend/farming-cli.js +400 -0
  43. package/backend/farming-session-store.js +373 -0
  44. package/backend/haiku-token.js +772 -0
  45. package/backend/index-html.js +49 -0
  46. package/backend/input-parts.js +54 -0
  47. package/backend/input-routing.js +24 -0
  48. package/backend/json-cli-runtime.js +161 -0
  49. package/backend/local-session-engine.js +620 -0
  50. package/backend/main-agent-skills.js +292 -0
  51. package/backend/main-page-session.js +119 -0
  52. package/backend/native-pty-host-client.js +516 -0
  53. package/backend/native-pty-host-path.js +22 -0
  54. package/backend/native-pty-host.js +816 -0
  55. package/backend/native-session-engine.js +196 -0
  56. package/backend/network.js +23 -0
  57. package/backend/npm-update-helper.js +196 -0
  58. package/backend/packaged-node-pty.js +79 -0
  59. package/backend/provider-session-id.js +47 -0
  60. package/backend/qr-share-tickets.js +100 -0
  61. package/backend/review-diff-router.js +180 -0
  62. package/backend/review-diff-service.js +1270 -0
  63. package/backend/review-session-router.js +74 -0
  64. package/backend/review-session-service.js +432 -0
  65. package/backend/review-session-store.js +144 -0
  66. package/backend/review-state-router.js +116 -0
  67. package/backend/review-state-store.js +287 -0
  68. package/backend/run-history-store.js +70 -0
  69. package/backend/server.js +2446 -0
  70. package/backend/session-engine-bridge.js +110 -0
  71. package/backend/session-engine-router.js +66 -0
  72. package/backend/session-engine.js +39 -0
  73. package/backend/shell-busy-integration.js +472 -0
  74. package/backend/slash-command-discovery.js +296 -0
  75. package/backend/storage-layout.js +101 -0
  76. package/backend/system-monitor.js +77 -0
  77. package/backend/terminal-runtime-cleanup.js +80 -0
  78. package/backend/terminal-screen-state.js +240 -0
  79. package/backend/terminal-screen-worker-pool.js +165 -0
  80. package/backend/terminal-screen-worker-thread.js +161 -0
  81. package/backend/terminal-screen-worker.js +255 -0
  82. package/backend/terminal-status.js +356 -0
  83. package/backend/theme-manager.js +145 -0
  84. package/backend/update-service.js +1183 -0
  85. package/backend/usage-forecast.js +86 -0
  86. package/backend/usage-monitor.js +1357 -0
  87. package/backend/workspace-discovery.js +311 -0
  88. package/backend/workspace-file-router.js +431 -0
  89. package/backend/workspace-file-service.js +2765 -0
  90. package/bin/farming +5 -0
  91. package/config/farming.deploy.env.example +13 -0
  92. package/config/farming.install.env.example +17 -0
  93. package/dist/assets/App-BrP-ENHg.css +1 -0
  94. package/dist/assets/App-Dza5yEDe.js +124 -0
  95. package/dist/assets/FileEditorMarkdownPreview-DRDNQ8mX.css +1 -0
  96. package/dist/assets/FileEditorMarkdownPreview-elKWc8Im.js +404 -0
  97. package/dist/assets/FileEditorPane-BQLocXOp.js +5 -0
  98. package/dist/assets/IconGlyphs-RkMAdBXF.js +1 -0
  99. package/dist/assets/KaTeX_AMS-Regular-BQhdFMY1.woff2 +0 -0
  100. package/dist/assets/KaTeX_AMS-Regular-DMm9YOAa.woff +0 -0
  101. package/dist/assets/KaTeX_AMS-Regular-DRggAlZN.ttf +0 -0
  102. package/dist/assets/KaTeX_Caligraphic-Bold-ATXxdsX0.ttf +0 -0
  103. package/dist/assets/KaTeX_Caligraphic-Bold-BEiXGLvX.woff +0 -0
  104. package/dist/assets/KaTeX_Caligraphic-Bold-Dq_IR9rO.woff2 +0 -0
  105. package/dist/assets/KaTeX_Caligraphic-Regular-CTRA-rTL.woff +0 -0
  106. package/dist/assets/KaTeX_Caligraphic-Regular-Di6jR-x-.woff2 +0 -0
  107. package/dist/assets/KaTeX_Caligraphic-Regular-wX97UBjC.ttf +0 -0
  108. package/dist/assets/KaTeX_Fraktur-Bold-BdnERNNW.ttf +0 -0
  109. package/dist/assets/KaTeX_Fraktur-Bold-BsDP51OF.woff +0 -0
  110. package/dist/assets/KaTeX_Fraktur-Bold-CL6g_b3V.woff2 +0 -0
  111. package/dist/assets/KaTeX_Fraktur-Regular-CB_wures.ttf +0 -0
  112. package/dist/assets/KaTeX_Fraktur-Regular-CTYiF6lA.woff2 +0 -0
  113. package/dist/assets/KaTeX_Fraktur-Regular-Dxdc4cR9.woff +0 -0
  114. package/dist/assets/KaTeX_Main-Bold-Cx986IdX.woff2 +0 -0
  115. package/dist/assets/KaTeX_Main-Bold-Jm3AIy58.woff +0 -0
  116. package/dist/assets/KaTeX_Main-Bold-waoOVXN0.ttf +0 -0
  117. package/dist/assets/KaTeX_Main-BoldItalic-DxDJ3AOS.woff2 +0 -0
  118. package/dist/assets/KaTeX_Main-BoldItalic-DzxPMmG6.ttf +0 -0
  119. package/dist/assets/KaTeX_Main-BoldItalic-SpSLRI95.woff +0 -0
  120. package/dist/assets/KaTeX_Main-Italic-3WenGoN9.ttf +0 -0
  121. package/dist/assets/KaTeX_Main-Italic-BMLOBm91.woff +0 -0
  122. package/dist/assets/KaTeX_Main-Italic-NWA7e6Wa.woff2 +0 -0
  123. package/dist/assets/KaTeX_Main-Regular-B22Nviop.woff2 +0 -0
  124. package/dist/assets/KaTeX_Main-Regular-Dr94JaBh.woff +0 -0
  125. package/dist/assets/KaTeX_Main-Regular-ypZvNtVU.ttf +0 -0
  126. package/dist/assets/KaTeX_Math-BoldItalic-B3XSjfu4.ttf +0 -0
  127. package/dist/assets/KaTeX_Math-BoldItalic-CZnvNsCZ.woff2 +0 -0
  128. package/dist/assets/KaTeX_Math-BoldItalic-iY-2wyZ7.woff +0 -0
  129. package/dist/assets/KaTeX_Math-Italic-DA0__PXp.woff +0 -0
  130. package/dist/assets/KaTeX_Math-Italic-flOr_0UB.ttf +0 -0
  131. package/dist/assets/KaTeX_Math-Italic-t53AETM-.woff2 +0 -0
  132. package/dist/assets/KaTeX_SansSerif-Bold-CFMepnvq.ttf +0 -0
  133. package/dist/assets/KaTeX_SansSerif-Bold-D1sUS0GD.woff2 +0 -0
  134. package/dist/assets/KaTeX_SansSerif-Bold-DbIhKOiC.woff +0 -0
  135. package/dist/assets/KaTeX_SansSerif-Italic-C3H0VqGB.woff2 +0 -0
  136. package/dist/assets/KaTeX_SansSerif-Italic-DN2j7dab.woff +0 -0
  137. package/dist/assets/KaTeX_SansSerif-Italic-YYjJ1zSn.ttf +0 -0
  138. package/dist/assets/KaTeX_SansSerif-Regular-BNo7hRIc.ttf +0 -0
  139. package/dist/assets/KaTeX_SansSerif-Regular-CS6fqUqJ.woff +0 -0
  140. package/dist/assets/KaTeX_SansSerif-Regular-DDBCnlJ7.woff2 +0 -0
  141. package/dist/assets/KaTeX_Script-Regular-C5JkGWo-.ttf +0 -0
  142. package/dist/assets/KaTeX_Script-Regular-D3wIWfF6.woff2 +0 -0
  143. package/dist/assets/KaTeX_Script-Regular-D5yQViql.woff +0 -0
  144. package/dist/assets/KaTeX_Size1-Regular-C195tn64.woff +0 -0
  145. package/dist/assets/KaTeX_Size1-Regular-Dbsnue_I.ttf +0 -0
  146. package/dist/assets/KaTeX_Size1-Regular-mCD8mA8B.woff2 +0 -0
  147. package/dist/assets/KaTeX_Size2-Regular-B7gKUWhC.ttf +0 -0
  148. package/dist/assets/KaTeX_Size2-Regular-Dy4dx90m.woff2 +0 -0
  149. package/dist/assets/KaTeX_Size2-Regular-oD1tc_U0.woff +0 -0
  150. package/dist/assets/KaTeX_Size3-Regular-CTq5MqoE.woff +0 -0
  151. package/dist/assets/KaTeX_Size3-Regular-DgpXs0kz.ttf +0 -0
  152. package/dist/assets/KaTeX_Size4-Regular-BF-4gkZK.woff +0 -0
  153. package/dist/assets/KaTeX_Size4-Regular-DWFBv043.ttf +0 -0
  154. package/dist/assets/KaTeX_Size4-Regular-Dl5lxZxV.woff2 +0 -0
  155. package/dist/assets/KaTeX_Typewriter-Regular-C0xS9mPB.woff +0 -0
  156. package/dist/assets/KaTeX_Typewriter-Regular-CO6r4hn1.woff2 +0 -0
  157. package/dist/assets/KaTeX_Typewriter-Regular-D3Ib7_Hf.ttf +0 -0
  158. package/dist/assets/ProjectFilesSection-lS1azbgj.js +12 -0
  159. package/dist/assets/ReviewPage-DgnmgU2T.js +3 -0
  160. package/dist/assets/abap-Cc5D5h5i.js +1 -0
  161. package/dist/assets/abnfDiagram-VRR7QNED-BgawzDQT.js +1 -0
  162. package/dist/assets/apex-BKopwLmx.js +1 -0
  163. package/dist/assets/api-D1lyBYIQ.js +1 -0
  164. package/dist/assets/arc-CWoVlxJw.js +1 -0
  165. package/dist/assets/architecture-TIHT7OUA-CbJBFh3w.js +1 -0
  166. package/dist/assets/architectureDiagram-ZJ3FMSHR-DUShwPg0.js +36 -0
  167. package/dist/assets/array-HeX70jSN.js +1 -0
  168. package/dist/assets/azcli-DI-C34WA.js +1 -0
  169. package/dist/assets/bat-Cbp6u42z.js +1 -0
  170. package/dist/assets/bicep-4QA1jTCM.js +2 -0
  171. package/dist/assets/blockDiagram-677ZJIJ3-CeGZviXR.js +132 -0
  172. package/dist/assets/c4Diagram-LMCZKHZV-CLhYht6S.js +10 -0
  173. package/dist/assets/cameligo-Dda_adPs.js +1 -0
  174. package/dist/assets/channel-Uw90AO0b.js +1 -0
  175. package/dist/assets/chunk-2Q5K7J3B-d5WWh8jo.js +1 -0
  176. package/dist/assets/chunk-32BRIVSS-LFYpT-Cu.js +1 -0
  177. package/dist/assets/chunk-52WLFC77-BH6jDw9J.js +10 -0
  178. package/dist/assets/chunk-5FCAYU7R-C7AmIhYv.js +1 -0
  179. package/dist/assets/chunk-5HE753X5-C8cXaouP.js +1 -0
  180. package/dist/assets/chunk-5JV3BV7I-C1PtimcA.js +1 -0
  181. package/dist/assets/chunk-5TONJI2A-_81zUME8.js +2 -0
  182. package/dist/assets/chunk-5VM5RSS4-Dlw7AXWp.js +15 -0
  183. package/dist/assets/chunk-7BUUIJ7U-ZBRhjLOh.js +1 -0
  184. package/dist/assets/chunk-BIQX33UG-CWmzxeAw.js +1 -0
  185. package/dist/assets/chunk-C7G6YPKG-B_mIUlb7.js +1 -0
  186. package/dist/assets/chunk-CQNSW5MT-CMayolwI.js +1 -0
  187. package/dist/assets/chunk-CYSBUYHQ-lSPbrL3Z.js +1 -0
  188. package/dist/assets/chunk-DECur_0Z.js +1 -0
  189. package/dist/assets/chunk-EMLP6XTP-D9-jtCnM.js +1 -0
  190. package/dist/assets/chunk-EX3LRPZG-C63hVuAJ.js +231 -0
  191. package/dist/assets/chunk-FWX5IMBZ-CboX-WF_.js +2 -0
  192. package/dist/assets/chunk-HOUHSVGY-BOgSd6Un.js +1 -0
  193. package/dist/assets/chunk-ICXQ74PX-C0K-pgZt.js +2 -0
  194. package/dist/assets/chunk-JG7HCLWE-Cib606u_.js +2 -0
  195. package/dist/assets/chunk-JWPE2WC7-DSyBRaRG.js +1 -0
  196. package/dist/assets/chunk-KEIR6QF5-CNOHik0T.js +161 -0
  197. package/dist/assets/chunk-MOJQB5TN-CVMfwN_7.js +88 -0
  198. package/dist/assets/chunk-MOZMSUNE-D6JeZqmE.js +1 -0
  199. package/dist/assets/chunk-OGEWGWER-DLT3pxyw.js +1 -0
  200. package/dist/assets/chunk-OSBZ3O6U-C0W8KSeg.js +1 -0
  201. package/dist/assets/chunk-PUDLZKDR-Cd079yIQ.js +156 -0
  202. package/dist/assets/chunk-Q4XR5HBZ-D0jHa6SO.js +70 -0
  203. package/dist/assets/chunk-QBLGF6JB-p4omp7uO.js +1 -0
  204. package/dist/assets/chunk-R7FJI6CG-CZ_p9hSr.js +1 -0
  205. package/dist/assets/chunk-RYQCIY6F-CZA9pvFX.js +1 -0
  206. package/dist/assets/chunk-U6XO7XAA-CcXKsWxp.js +2 -0
  207. package/dist/assets/chunk-V7JOEXUC-CVDtR75H.js +206 -0
  208. package/dist/assets/chunk-VAUOI2AC-B-W2_9Ot.js +1 -0
  209. package/dist/assets/chunk-VR4S4FIN-FD3kWh32.js +1 -0
  210. package/dist/assets/chunk-WYO6CB5R-C2bGaS5r.js +127 -0
  211. package/dist/assets/chunk-XXDRQBXY-BBXwjhUx.js +1 -0
  212. package/dist/assets/chunk-Y2CYZVJY-Di0sYzi1.js +1 -0
  213. package/dist/assets/chunk-YOTPTUD7-BXHmEk89.js +1 -0
  214. package/dist/assets/chunk-ZGVPDNZ5-ymgts0zo.js +62 -0
  215. package/dist/assets/chunk-ZIRB5QZD-DncwlQQc.js +32 -0
  216. package/dist/assets/classDiagram-OUVF2IWQ-DKW_dtku.js +1 -0
  217. package/dist/assets/classDiagram-v2-EOCWNBFH-C8Fi7-yv.js +1 -0
  218. package/dist/assets/clojure-CvY8A83L.js +1 -0
  219. package/dist/assets/code-dark-Cjb1QGhu.css +1 -0
  220. package/dist/assets/code-mobile-3C2Rr-CN.css +1 -0
  221. package/dist/assets/codicon-ngg6Pgfi.ttf +0 -0
  222. package/dist/assets/coffee-4LX2Sv8A.js +1 -0
  223. package/dist/assets/core-ZlAPicox.js +3 -0
  224. package/dist/assets/cose-bilkent-JH36ORCC-BNIAz0nN.js +1 -0
  225. package/dist/assets/cpp-D4AzSV28.js +1 -0
  226. package/dist/assets/csharp-C4nWN4Yd.js +1 -0
  227. package/dist/assets/csp-CiEaaS5Z.js +1 -0
  228. package/dist/assets/css-DXxBRsbk.js +3 -0
  229. package/dist/assets/css.worker-DyDu5ynT.js +89 -0
  230. package/dist/assets/cssMode-DDWxTPm_.js +1 -0
  231. package/dist/assets/cynefin-VYW2F7L2-DgXGHlRt.js +1 -0
  232. package/dist/assets/cynefinDiagram-TSTJHNR4-CwpobXIl.js +62 -0
  233. package/dist/assets/cypher-DOMzqyFA.js +1 -0
  234. package/dist/assets/cytoscape.esm-Cl8iC3D7.js +321 -0
  235. package/dist/assets/dagre-DXlcHgr3.js +1 -0
  236. package/dist/assets/dagre-VKFMJZFB-Dkhlfjna.js +4 -0
  237. package/dist/assets/dart-BWS7MXt_.js +1 -0
  238. package/dist/assets/defaultLocale-GJwWH1Jr.js +1 -0
  239. package/dist/assets/diagram-FQU43EPY-hA8dicp6.js +3 -0
  240. package/dist/assets/diagram-G47NLZAW-BTY6JTzO.js +24 -0
  241. package/dist/assets/diagram-NH7WQ7WH-xkaHHX9M.js +24 -0
  242. package/dist/assets/diagram-OA4YK3LP-gk_fg9UU.js +30 -0
  243. package/dist/assets/diagram-WEI45ONY-BvC8xd6T.js +41 -0
  244. package/dist/assets/dist-ClAL-Tv5.js +1 -0
  245. package/dist/assets/dockerfile-Baf4U3xT.js +1 -0
  246. package/dist/assets/ebnfDiagram-CCIWWBDH-CR7RaNat.js +1 -0
  247. package/dist/assets/ecl-CT7udlkQ.js +1 -0
  248. package/dist/assets/editor-CtbFZlk0.css +1 -0
  249. package/dist/assets/editor.api2-B9h6iFPK.js +872 -0
  250. package/dist/assets/editor.worker-Dpt_xPrs.js +26 -0
  251. package/dist/assets/elixir-CIbAZw5l.js +1 -0
  252. package/dist/assets/erDiagram-Q63AITRT-_M-JFPbj.js +85 -0
  253. package/dist/assets/eventmodeling-45OFAUF4-DXYTQ2nt.js +1 -0
  254. package/dist/assets/file-icons-EFUGSSwf.js +1 -0
  255. package/dist/assets/flow9-Dqiw45WV.js +1 -0
  256. package/dist/assets/flowDiagram-23GEKE2U-DAiS5Y7G.js +1 -0
  257. package/dist/assets/freemarker2-QBsTERH-.js +3 -0
  258. package/dist/assets/fsharp-E8E2L9jU.js +1 -0
  259. package/dist/assets/ganttDiagram-NO4QXBWP-Bl8P1yf_.js +292 -0
  260. package/dist/assets/gitGraph-TEB2WS4Q-CzTBjEvV.js +1 -0
  261. package/dist/assets/gitGraphDiagram-IHSO6WYX-DoHa5ysz.js +106 -0
  262. package/dist/assets/go-CouVSN4D.js +1 -0
  263. package/dist/assets/graphlib-CbSvZcZU.js +1 -0
  264. package/dist/assets/graphql-a6h6h5-t.js +1 -0
  265. package/dist/assets/handlebars-CuoxPo5A.js +1 -0
  266. package/dist/assets/hcl-vso3e6N-.js +1 -0
  267. package/dist/assets/html-gX5PEu0Q.js +1 -0
  268. package/dist/assets/html.worker-IWNXhnIC.js +502 -0
  269. package/dist/assets/htmlMode-DIWUbUxd.js +1 -0
  270. package/dist/assets/index-BpHPeJf0.js +10 -0
  271. package/dist/assets/info-DKCQHKI2-DznP7j3s.js +1 -0
  272. package/dist/assets/infoDiagram-FWYZ7A6U-DSFcSuUs.js +2 -0
  273. package/dist/assets/ini-SwZZkotR.js +1 -0
  274. package/dist/assets/init-BPLPMQ3Y.js +1 -0
  275. package/dist/assets/ishikawaDiagram-FXEZZL3T-DdkqullI.js +70 -0
  276. package/dist/assets/java-CtRLC4_3.js +1 -0
  277. package/dist/assets/javascript-BYKGIUGs.js +1 -0
  278. package/dist/assets/journeyDiagram-5HDEW3XC-B4hRnQJr.js +139 -0
  279. package/dist/assets/json.worker-c4h5s80L.js +58 -0
  280. package/dist/assets/jsonMode-AFmQQP6u.js +7 -0
  281. package/dist/assets/jsx-runtime-BthL93pI.js +1 -0
  282. package/dist/assets/julia-CuJWFKQH.js +1 -0
  283. package/dist/assets/kanban-definition-HUTT4EX6-tm2FZB2E.js +89 -0
  284. package/dist/assets/katex-C8DPyI6s.js +257 -0
  285. package/dist/assets/kotlin-B_kBhsre.js +1 -0
  286. package/dist/assets/less-CtrHIfz3.js +2 -0
  287. package/dist/assets/lexon-yVt1pJLu.js +1 -0
  288. package/dist/assets/line-CmsjK4kn.js +1 -0
  289. package/dist/assets/linear-Dld3_ERu.js +1 -0
  290. package/dist/assets/liquid-DBIl-f0z.js +1 -0
  291. package/dist/assets/lspLanguageFeatures-DK6tqicV.js +4 -0
  292. package/dist/assets/lua-prOwgJ4U.js +1 -0
  293. package/dist/assets/m3-DhrdTQ84.js +1 -0
  294. package/dist/assets/main-DTJwH51M.css +1 -0
  295. package/dist/assets/map-LZWWoeWa.js +1 -0
  296. package/dist/assets/markdown-DoI5HwSM.js +1 -0
  297. package/dist/assets/mdx-DS-bVtZN.js +1 -0
  298. package/dist/assets/mermaid-parser.core-BQtepoLd.js +4 -0
  299. package/dist/assets/mermaid.core-C7UT_EEL.js +11 -0
  300. package/dist/assets/mindmap-definition-LN4V7U3C-DplfjGms.js +96 -0
  301. package/dist/assets/mips-Dye5jsBU.js +1 -0
  302. package/dist/assets/monaco.contribution-CyLosfZI.js +2 -0
  303. package/dist/assets/msdax-TkNOyIL8.js +1 -0
  304. package/dist/assets/mysql-CEc-RKZF.js +1 -0
  305. package/dist/assets/objective-c-CqqCsQz0.js +1 -0
  306. package/dist/assets/ordinal-BLrOss5K.js +1 -0
  307. package/dist/assets/packet-7NZHBO7P-BDEPOPha.js +1 -0
  308. package/dist/assets/pascal-DO_pj8yg.js +1 -0
  309. package/dist/assets/pascaligo-1cbdZdF3.js +1 -0
  310. package/dist/assets/path-YdFzr2W6.js +1 -0
  311. package/dist/assets/pegDiagram-2B236MQR-lu3SdkQs.js +1 -0
  312. package/dist/assets/perl-B_N3PYfC.js +1 -0
  313. package/dist/assets/pgsql-9iYk1FQ7.js +1 -0
  314. package/dist/assets/php-rO2sgoUM.js +1 -0
  315. package/dist/assets/pie-RZYD4A2V-DWIrwPJQ.js +1 -0
  316. package/dist/assets/pieDiagram-ENE6RG2P-3fHbmDf9.js +39 -0
  317. package/dist/assets/pla-Cbgv60kq.js +1 -0
  318. package/dist/assets/postiats-y6xrhy_M.js +1 -0
  319. package/dist/assets/powerquery-BaD8gWNE.js +1 -0
  320. package/dist/assets/powershell-BMhG4JVe.js +1 -0
  321. package/dist/assets/preload-helper-mJowh_hw.js +1 -0
  322. package/dist/assets/protobuf-CdOP5kN3.js +2 -0
  323. package/dist/assets/pug-Ck60hNF9.js +1 -0
  324. package/dist/assets/python-C93q3xXz.js +1 -0
  325. package/dist/assets/qoder-C9LmmOSf.svg +1 -0
  326. package/dist/assets/qoder-Cf9gl0Y5.svg +1 -0
  327. package/dist/assets/qoder-gHCinseV.svg +1 -0
  328. package/dist/assets/qrcode-DV-_rjU8.js +3 -0
  329. package/dist/assets/qsharp-BcaKFfP-.js +1 -0
  330. package/dist/assets/quadrantDiagram-ABIIQ3AL-a5qoWz-X.js +7 -0
  331. package/dist/assets/r-rFNes0iK.js +1 -0
  332. package/dist/assets/radar-I7S5WNFK-B7OaD8vp.js +1 -0
  333. package/dist/assets/railroad-3IZDKUUU-BXW2nuCA.js +1 -0
  334. package/dist/assets/railroad-abnf-AHOZXSZD-Buw9QG2r.js +1 -0
  335. package/dist/assets/railroad-ebnf-EBAXGLYW-BjSi4sWJ.js +1 -0
  336. package/dist/assets/railroad-peg-LSFZ7HO6-DN1wIVhS.js +1 -0
  337. package/dist/assets/railroadDiagram-RFXS5EU6-D2TOuXW9.js +1 -0
  338. package/dist/assets/razor-CBifNGXO.js +1 -0
  339. package/dist/assets/react-dom-gtU6X-Hj.js +1 -0
  340. package/dist/assets/redis-DkpQ3K6G.js +1 -0
  341. package/dist/assets/redshift-Di9N5TI3.js +1 -0
  342. package/dist/assets/requirementDiagram-TGXJPOKE-LQBWpUvd.js +84 -0
  343. package/dist/assets/restructuredtext-By5ZzLt6.js +1 -0
  344. package/dist/assets/review-BcnwQtJv.css +1 -0
  345. package/dist/assets/rough.esm-c4PR5shF.js +1 -0
  346. package/dist/assets/ruby-fF5zGiLp.js +1 -0
  347. package/dist/assets/rust-C5b3AYY6.js +1 -0
  348. package/dist/assets/sankeyDiagram-HTMAVEWB-B1ohYoyK.js +40 -0
  349. package/dist/assets/sb-CD07UNRs.js +1 -0
  350. package/dist/assets/scala-jtn1ip9G.js +1 -0
  351. package/dist/assets/scheme-C4vqMkn_.js +1 -0
  352. package/dist/assets/scss-I4Glxjbz.js +3 -0
  353. package/dist/assets/sequenceDiagram-DBY2YBRQ-C3vM-hMq.js +162 -0
  354. package/dist/assets/shell-DubUcuns.js +1 -0
  355. package/dist/assets/sizeCapture-X5ZJPWSS-daTB6OcF.js +1 -0
  356. package/dist/assets/solidity-CNy2KSl2.js +1 -0
  357. package/dist/assets/sophia-D9_URt84.js +1 -0
  358. package/dist/assets/sparql-DviXpm4C.js +1 -0
  359. package/dist/assets/sql-vDRbAZgK.js +1 -0
  360. package/dist/assets/src-WBW1QxJt.js +1 -0
  361. package/dist/assets/st-CnpnRqA7.js +1 -0
  362. package/dist/assets/stateDiagram-2N3HPSRC-BvFhOryI.js +1 -0
  363. package/dist/assets/stateDiagram-v2-6OUMAXLB-WMrz4PNo.js +1 -0
  364. package/dist/assets/swift-D_g8Ganz.js +1 -0
  365. package/dist/assets/swimlanes-5IMT3BWC-DKF_b-2s.js +2 -0
  366. package/dist/assets/swimlanesDiagram-G3AALYLV-BGswC9oC.js +8 -0
  367. package/dist/assets/systemverilog-OuZa5h1M.js +1 -0
  368. package/dist/assets/tcl-DBm9ucsV.js +1 -0
  369. package/dist/assets/timeline-definition-FHXFAJF6-vAs11ux_.js +120 -0
  370. package/dist/assets/tokens-BwenNn5Q.css +1 -0
  371. package/dist/assets/treeView-QDETBFTQ-BVfICaZQ.js +1 -0
  372. package/dist/assets/treemap-6X3UGDF4-oWHPqo17.js +1 -0
  373. package/dist/assets/ts.worker-BwM5Ha3L.js +67719 -0
  374. package/dist/assets/tsMode-DGZTlTj8.js +11 -0
  375. package/dist/assets/twig-BRzEqX5Y.js +1 -0
  376. package/dist/assets/typescript-KJKfYO7K.js +1 -0
  377. package/dist/assets/typespec-D4ZgGeX8.js +1 -0
  378. package/dist/assets/useWorkspaceMenuKeyboard-CneKAZUJ.js +1 -0
  379. package/dist/assets/vb-DcP4s6WS.js +1 -0
  380. package/dist/assets/vennDiagram-L72KCM5P-BybTX_9B.js +34 -0
  381. package/dist/assets/wardley-OPB4EBWU-Dg8t5y3s.js +1 -0
  382. package/dist/assets/wardleyDiagram-EHGQE667-CicUmMBR.js +78 -0
  383. package/dist/assets/wgsl-CnRJ_QUf.js +298 -0
  384. package/dist/assets/workers-BSQRIkqa.js +1 -0
  385. package/dist/assets/workspace-view-state-CTyDzk2D.js +1 -0
  386. package/dist/assets/xml-C8FAcN6j.js +1 -0
  387. package/dist/assets/xychartDiagram-FW5EYKEG-BhWDyCX-.js +7 -0
  388. package/dist/assets/yaml-BQ4NrRhG.js +1 -0
  389. package/dist/assets/zsh-CLpveKlF.svg +1 -0
  390. package/dist/assets/zsh-FxSpMPbz.svg +1 -0
  391. package/dist/farming-2/app-icon-v2-180.png +0 -0
  392. package/dist/farming-2/app-icon-v2-192.png +0 -0
  393. package/dist/farming-2/app-icon-v2-512.png +0 -0
  394. package/dist/farming-2/app-icon-v2-maskable-512.png +0 -0
  395. package/dist/farming-2/app-icon-v2-master.png +0 -0
  396. package/dist/farming-2/favicon-v2-16.png +0 -0
  397. package/dist/farming-2/favicon-v2-32.png +0 -0
  398. package/dist/farming-2/favicon-v2-48.png +0 -0
  399. package/dist/farming-2/favicon-v2-64.png +0 -0
  400. package/dist/farming-2/favicon-v2.ico +0 -0
  401. package/dist/farming-2/favicon.ico +0 -0
  402. package/dist/farming-2/github-social-preview.png +0 -0
  403. package/dist/farming-2/images/avatar-watercolor-v1-bee-garden.png +0 -0
  404. package/dist/farming-2/images/avatar-watercolor-v2.png +0 -0
  405. package/dist/farming-2/images/avatar-watercolor-v3.png +0 -0
  406. package/dist/farming-2/legacy-icons-v1/favicon.ico +1 -0
  407. package/dist/farming-2/legacy-icons-v1/logo-16.png +0 -0
  408. package/dist/farming-2/legacy-icons-v1/logo-180.png +0 -0
  409. package/dist/farming-2/legacy-icons-v1/logo-192.png +0 -0
  410. package/dist/farming-2/legacy-icons-v1/logo-32.png +0 -0
  411. package/dist/farming-2/legacy-icons-v1/logo-48.png +0 -0
  412. package/dist/farming-2/legacy-icons-v1/logo-512.png +0 -0
  413. package/dist/farming-2/legacy-icons-v1/logo-64.png +0 -0
  414. package/dist/farming-2/logo-16.png +0 -0
  415. package/dist/farming-2/logo-180.png +0 -0
  416. package/dist/farming-2/logo-192.png +0 -0
  417. package/dist/farming-2/logo-32.png +0 -0
  418. package/dist/farming-2/logo-48.png +0 -0
  419. package/dist/farming-2/logo-512.png +0 -0
  420. package/dist/farming-2/logo-64.png +0 -0
  421. package/dist/farming-2/site.webmanifest +27 -0
  422. package/dist/farming-2/style_capsules/watercolor-pastoral.json +94 -0
  423. package/dist/index.html +27 -0
  424. package/frontend/ghostty-loader.js +24 -0
  425. package/frontend/runtime-paths.js +28 -0
  426. package/frontend/session-bridge.js +82 -0
  427. package/frontend/session-modal-bridge.js +331 -0
  428. package/frontend/skin-bridge.js +25 -0
  429. package/frontend/skins/crt/app.js +6940 -0
  430. package/frontend/skins/crt/assets/branding/farming-crt-icon.svg +11 -0
  431. package/frontend/skins/crt/assets/branding/farming-crt-logo-v1.png +0 -0
  432. package/frontend/skins/crt/assets/effects/phosphor-noise.svg +11 -0
  433. package/frontend/skins/crt/assets/fonts/departure-mono/DepartureMonoNerdFontMono-Regular.otf +0 -0
  434. package/frontend/skins/crt/assets/fonts/departure-mono/LICENSE +93 -0
  435. package/frontend/skins/crt/effects.js +8 -0
  436. package/frontend/skins/crt/index.html +1712 -0
  437. package/frontend/skins/crt/styles/billing.css +1003 -0
  438. package/frontend/skins/crt/styles/effects.css +171 -0
  439. package/frontend/skins/crt/styles/history.css +215 -0
  440. package/frontend/skins/crt/styles/monochrome-green.css +509 -0
  441. package/frontend/skins/crt/styles/search.css +271 -0
  442. package/frontend/terminal-bridge.js +192 -0
  443. package/frontend/theme-loader.js +84 -0
  444. package/frontend/themes/terminal/theme.json +24 -0
  445. package/frontend/vendor/ghostty-web/LICENSE +21 -0
  446. package/frontend/vendor/ghostty-web/__vite-browser-external-2447137e.js +4 -0
  447. package/frontend/vendor/ghostty-web/ghostty-vt.wasm +0 -0
  448. package/frontend/vendor/ghostty-web/ghostty-web.js +2963 -0
  449. package/frontend/vendor/ghostty-web/ghostty-web.umd.cjs +13 -0
  450. package/frontend/vendor/ghostty-web/index.d.ts +1842 -0
  451. package/index.html +23 -0
  452. package/package.json +144 -0
  453. package/scripts/sync-ghostty-vendor.js +66 -0
@@ -0,0 +1,448 @@
1
+ const MAX_ACP_UPDATES = 2_000;
2
+ const MAX_ACP_UPDATE_LOG_VALUE_CHARS = 32 * 1024;
3
+ const {
4
+ isCodexInjectedContextMessage,
5
+ stripCodexInternalContextBlocks,
6
+ } = require('./codex-transcript-sanitizer');
7
+
8
+ function clone(value) {
9
+ return value === undefined ? undefined : JSON.parse(JSON.stringify(value));
10
+ }
11
+
12
+ function compactUpdateForLog(update) {
13
+ let serialized = '';
14
+ try {
15
+ serialized = JSON.stringify(update);
16
+ } catch {
17
+ return { sessionUpdate: String(update?.sessionUpdate || ''), truncated: true };
18
+ }
19
+ if (serialized.length <= MAX_ACP_UPDATE_LOG_VALUE_CHARS) return clone(update);
20
+ return {
21
+ sessionUpdate: String(update?.sessionUpdate || ''),
22
+ toolCallId: String(update?.toolCallId || ''),
23
+ messageId: String(update?.messageId || ''),
24
+ truncated: true,
25
+ originalChars: serialized.length,
26
+ };
27
+ }
28
+
29
+ function appendContent(blocks, content) {
30
+ if (!content || typeof content !== 'object') return;
31
+ const next = clone(content);
32
+ const previous = blocks[blocks.length - 1];
33
+ if (previous?.type === 'text' && next.type === 'text') {
34
+ previous.text = `${previous.text || ''}${next.text || ''}`;
35
+ return;
36
+ }
37
+ blocks.push(next);
38
+ }
39
+
40
+ function contentText(content) {
41
+ return (Array.isArray(content) ? content : [])
42
+ .filter(block => block?.type === 'text')
43
+ .map(block => String(block.text || ''))
44
+ .join('');
45
+ }
46
+
47
+ function isContextCompactionText(content) {
48
+ return /^\*?Context compacted(?: to fit the model's context window)?\.?\*?$/i.test(contentText(content).trim());
49
+ }
50
+
51
+ function canMergeMessageIds(existing, incoming) {
52
+ return !existing || !incoming || existing === incoming;
53
+ }
54
+
55
+ class AcpSessionState {
56
+ constructor(options = {}) {
57
+ this.provider = String(options.provider || '');
58
+ this.sessionId = String(options.sessionId || '');
59
+ this.cwd = String(options.cwd || '');
60
+ this.maxUpdates = Number.isFinite(options.maxUpdates)
61
+ ? Math.max(1, Math.floor(options.maxUpdates))
62
+ : MAX_ACP_UPDATES;
63
+ // ACP history replay and live session/update notifications both reduce
64
+ // into this one ordered entry stream. There is deliberately no synthetic
65
+ // turn model here.
66
+ this.entries = [];
67
+ this.updates = [];
68
+ this.toolEntries = new Map();
69
+ this.compactionEntries = new Map();
70
+ this.activePlanEntry = null;
71
+ this.plan = null;
72
+ this.usage = null;
73
+ this.availableCommands = [];
74
+ this.currentModeId = '';
75
+ this.configOptions = [];
76
+ this.title = '';
77
+ this.updatedAt = '';
78
+ this.truncated = false;
79
+ this.sequence = 0;
80
+ this.revision = Number.isFinite(Number(options.revisionBase))
81
+ ? Math.max(0, Math.floor(Number(options.revisionBase)))
82
+ : 0;
83
+ this.resetBeforeRevision = Number.isFinite(Number(options.resetBeforeRevision))
84
+ ? Math.max(0, Math.floor(Number(options.resetBeforeRevision)))
85
+ : 0;
86
+ }
87
+
88
+ setSessionId(sessionId) {
89
+ this.sessionId = String(sessionId || this.sessionId);
90
+ }
91
+
92
+ nextEntryId(prefix) {
93
+ return `${prefix}-${++this.sequence}`;
94
+ }
95
+
96
+ pushEntry(entry) {
97
+ this.touchEntry(entry);
98
+ this.entries.push(entry);
99
+ return entry;
100
+ }
101
+
102
+ touchEntry(entry) {
103
+ if (!entry) return this.revision;
104
+ entry._revision = ++this.revision;
105
+ return this.revision;
106
+ }
107
+
108
+ touchCurrentTurn() {
109
+ const entry = this.entries[this.entries.length - 1];
110
+ if (entry) this.touchEntry(entry);
111
+ else this.revision += 1;
112
+ return this.revision;
113
+ }
114
+
115
+ beginPrompt(prompt) {
116
+ const content = Array.isArray(prompt)
117
+ ? clone(prompt)
118
+ : [{ type: 'text', text: String(prompt || '') }];
119
+ this.activePlanEntry = null;
120
+ const startedAt = Date.now();
121
+ return this.pushEntry({
122
+ id: this.nextEntryId('user'),
123
+ type: 'message',
124
+ role: 'user',
125
+ messageId: '',
126
+ optimistic: true,
127
+ content,
128
+ turnStartedAt: startedAt,
129
+ turnCompletedAt: null,
130
+ turnDurationMs: null,
131
+ });
132
+ }
133
+
134
+ completePrompt() {
135
+ // Runtime completion changes the visible state of the last turn. Touch the
136
+ // existing entry so delta readers can refresh that turn without inventing
137
+ // a protocol entry boundary.
138
+ const userEntry = this.entries.findLast(entry => entry?.type === 'message' && entry.role === 'user' && entry.turnStartedAt);
139
+ if (userEntry && !userEntry.turnCompletedAt) {
140
+ userEntry.turnCompletedAt = Date.now();
141
+ const startedAt = Number(userEntry.turnStartedAt);
142
+ const completedAt = Number(userEntry.turnCompletedAt);
143
+ userEntry.turnDurationMs = Number.isFinite(startedAt) && Number.isFinite(completedAt)
144
+ ? Math.max(0, completedAt - startedAt)
145
+ : null;
146
+ this.touchEntry(userEntry);
147
+ } else {
148
+ this.touchCurrentTurn();
149
+ }
150
+ }
151
+
152
+ recordError(message, kind = 'unknown') {
153
+ const text = String(message || '').trim();
154
+ if (!text) return null;
155
+ return this.pushEntry({
156
+ id: this.nextEntryId('error'),
157
+ type: 'error',
158
+ message: text,
159
+ kind: String(kind || 'unknown'),
160
+ status: 'failed',
161
+ });
162
+ }
163
+
164
+ finishHistoryReplay() {
165
+ // History replay uses the same reducer as live updates; nothing to close.
166
+ }
167
+
168
+ apply(notification) {
169
+ if (!notification || notification.sessionId !== this.sessionId) return false;
170
+ const update = notification.update;
171
+ if (!update || typeof update !== 'object') return false;
172
+ this.updates.push({
173
+ sequence: this.updates.length + 1,
174
+ at: new Date().toISOString(),
175
+ update: compactUpdateForLog(update),
176
+ });
177
+ if (this.updates.length > this.maxUpdates) {
178
+ this.updates.splice(0, this.updates.length - this.maxUpdates);
179
+ this.truncated = true;
180
+ }
181
+
182
+ const kind = update.sessionUpdate;
183
+ if (kind === 'user_message_chunk' || kind === 'agent_message_chunk' || kind === 'agent_thought_chunk') {
184
+ this.applyMessageChunk(update, kind);
185
+ } else if (kind === 'tool_call') {
186
+ this.applyToolCall(update, false);
187
+ } else if (kind === 'tool_call_update') {
188
+ this.applyToolCall(update, true);
189
+ } else if (kind === 'plan') {
190
+ this.applyPlan({ type: 'items', entries: clone(update.entries || []) });
191
+ } else if (kind === 'plan_update') {
192
+ this.applyPlan(clone(update.plan));
193
+ } else if (kind === 'plan_removed') {
194
+ this.removePlan();
195
+ } else if (kind === 'context_compaction' || kind === 'context_compaction_update') {
196
+ this.applyCompaction(update);
197
+ } else if (kind === 'usage_update') {
198
+ this.usage = clone(update);
199
+ } else if (kind === 'available_commands_update') {
200
+ this.availableCommands = clone(update.availableCommands || []);
201
+ } else if (kind === 'current_mode_update') {
202
+ this.currentModeId = String(update.currentModeId || '');
203
+ } else if (kind === 'config_option_update') {
204
+ this.configOptions = clone(update.configOptions || []);
205
+ } else if (kind === 'session_info_update') {
206
+ if (Object.prototype.hasOwnProperty.call(update, 'title')) this.title = String(update.title || '');
207
+ if (Object.prototype.hasOwnProperty.call(update, 'updatedAt')) this.updatedAt = String(update.updatedAt || '');
208
+ }
209
+ return true;
210
+ }
211
+
212
+ applyMessageChunk(update, kind) {
213
+ const role = kind === 'user_message_chunk' ? 'user' : 'assistant';
214
+ const type = kind === 'agent_thought_chunk' ? 'thought' : 'message';
215
+ const messageId = String(update.messageId || '');
216
+ const last = this.entries[this.entries.length - 1];
217
+
218
+ const compactionMeta = update?._meta?.context_compaction;
219
+ if (kind === 'agent_message_chunk' && (isContextCompactionText([update.content]) || compactionMeta)) {
220
+ this.applyCompaction({
221
+ compactionId: compactionMeta?.id || messageId,
222
+ status: compactionMeta?.status || 'completed',
223
+ summary: compactionMeta?.summary || '',
224
+ });
225
+ return;
226
+ }
227
+
228
+ // Farming inserts the local prompt optimistically. ACP Agents may echo the
229
+ // same prompt during live updates; attach its protocol id without rendering
230
+ // the user message twice.
231
+ if (
232
+ role === 'user'
233
+ && last?.type === 'message'
234
+ && last.role === 'user'
235
+ && last.optimistic
236
+ && (last.content || []).some(content => JSON.stringify(content) === JSON.stringify(update.content))
237
+ ) {
238
+ if (!last.messageId) last.messageId = messageId;
239
+ this.touchEntry(last);
240
+ return;
241
+ }
242
+
243
+ if (
244
+ last?.type === type
245
+ && last.role === role
246
+ && canMergeMessageIds(last.messageId, messageId)
247
+ ) {
248
+ if (!last.messageId) last.messageId = messageId;
249
+ appendContent(last.content, update.content);
250
+ this.touchEntry(last);
251
+ return;
252
+ }
253
+
254
+ if (role === 'user') this.activePlanEntry = null;
255
+ this.pushEntry({
256
+ id: messageId || this.nextEntryId(type),
257
+ type,
258
+ role,
259
+ messageId,
260
+ content: [],
261
+ });
262
+ appendContent(this.entries[this.entries.length - 1].content, update.content);
263
+ }
264
+
265
+ applyToolCall(update, isPatch) {
266
+ const id = String(update.toolCallId || '');
267
+ if (!id) return;
268
+ let entry = this.toolEntries.get(id);
269
+ if (!entry) {
270
+ entry = this.pushEntry({
271
+ id,
272
+ type: 'tool',
273
+ title: '',
274
+ kind: 'other',
275
+ status: 'pending',
276
+ content: [],
277
+ });
278
+ this.toolEntries.set(id, entry);
279
+ }
280
+ for (const field of ['title', 'kind', 'status', 'content', 'locations', 'rawInput', 'rawOutput', '_meta']) {
281
+ if (!isPatch || Object.prototype.hasOwnProperty.call(update, field)) {
282
+ if (update[field] !== undefined) entry[field] = clone(update[field]);
283
+ }
284
+ }
285
+ this.touchEntry(entry);
286
+ }
287
+
288
+ applyCompaction(update) {
289
+ const id = String(update.compactionId || update.id || this.nextEntryId('compaction'));
290
+ let entry = this.compactionEntries.get(id);
291
+ if (!entry) {
292
+ entry = this.pushEntry({ id, type: 'compaction', status: 'in_progress', summary: '' });
293
+ this.compactionEntries.set(id, entry);
294
+ }
295
+ if (Object.prototype.hasOwnProperty.call(update, 'status')) entry.status = String(update.status || 'completed');
296
+ if (Object.prototype.hasOwnProperty.call(update, 'summary')) entry.summary = String(update.summary || '');
297
+ this.touchEntry(entry);
298
+ }
299
+
300
+ applyPlan(plan) {
301
+ this.plan = clone(plan);
302
+ if (!this.activePlanEntry) {
303
+ this.activePlanEntry = this.pushEntry({
304
+ id: this.nextEntryId('plan'),
305
+ type: 'plan',
306
+ plan: clone(plan),
307
+ });
308
+ return;
309
+ }
310
+ this.activePlanEntry.plan = clone(plan);
311
+ this.touchEntry(this.activePlanEntry);
312
+ }
313
+
314
+ removePlan() {
315
+ if (this.activePlanEntry) {
316
+ const index = this.entries.indexOf(this.activePlanEntry);
317
+ if (index >= 0) this.entries.splice(index, 1);
318
+ }
319
+ this.activePlanEntry = null;
320
+ this.plan = null;
321
+ this.touchCurrentTurn();
322
+ }
323
+
324
+ transcriptSlice(options = {}) {
325
+ const maxTurns = Number.isFinite(Number(options.maxTurns))
326
+ ? Math.max(1, Math.floor(Number(options.maxTurns)))
327
+ : 80;
328
+ const requestedRevision = Number(options.sinceRevision);
329
+ const resetRequired = this.resetBeforeRevision > 0
330
+ && Number.isFinite(requestedRevision)
331
+ && requestedRevision <= this.resetBeforeRevision;
332
+ const delta = Number.isFinite(requestedRevision) && requestedRevision >= 0 && !resetRequired;
333
+ let startIndex = 0;
334
+
335
+ if (delta) {
336
+ startIndex = this.entries.findIndex(entry => Number(entry?._revision || 0) > requestedRevision);
337
+ if (startIndex < 0) startIndex = this.entries.length;
338
+ if (startIndex < this.entries.length) {
339
+ while (startIndex > 0) {
340
+ const entry = this.entries[startIndex];
341
+ if (entry?.type === 'message' && entry.role === 'user') break;
342
+ startIndex -= 1;
343
+ }
344
+ }
345
+ } else {
346
+ let remaining = maxTurns;
347
+ startIndex = this.entries.length;
348
+ while (startIndex > 0) {
349
+ startIndex -= 1;
350
+ const entry = this.entries[startIndex];
351
+ if (entry?.type === 'message' && entry.role === 'user') {
352
+ remaining -= 1;
353
+ if (remaining <= 0) break;
354
+ }
355
+ }
356
+ }
357
+
358
+ return {
359
+ entries: this.sanitizedEntries(startIndex, { forTranscript: true }),
360
+ revision: this.revision,
361
+ delta,
362
+ hasMoreBefore: startIndex > 0,
363
+ };
364
+ }
365
+
366
+ sanitizedEntries(startIndex = 0, options = {}) {
367
+ const safeStart = Math.min(this.entries.length, Math.max(0, Math.floor(startIndex)));
368
+ const entries = options.forTranscript === true
369
+ ? this.entries.slice(safeStart).map(entry => {
370
+ const visible = { ...entry };
371
+ delete visible._revision;
372
+ if (entry.type !== 'tool') return clone(visible);
373
+ // Tool details are read synchronously by the transcript projector and
374
+ // never mutated there. Keep their potentially large protocol payloads
375
+ // by reference so an initial page does not deep-clone megabytes merely
376
+ // to produce a compact summary.
377
+ return visible;
378
+ })
379
+ : clone(this.entries.slice(safeStart));
380
+ if (options.forTranscript !== true) {
381
+ for (const entry of entries) delete entry._revision;
382
+ }
383
+ if (this.provider !== 'codex') return entries;
384
+
385
+ let internalSegment = false;
386
+ for (let index = 0; index < safeStart; index += 1) {
387
+ const entry = this.entries[index];
388
+ if (entry?.type !== 'message' || entry.role !== 'user') continue;
389
+ const hasAttachment = (entry.content || []).some(content => content.type !== 'text');
390
+ internalSegment = !hasAttachment && isCodexInjectedContextMessage(contentText(entry.content));
391
+ }
392
+ for (const entry of entries) {
393
+ if (entry.type === 'message' && entry.role === 'user') {
394
+ const hasAttachment = (entry.content || []).some(content => content.type !== 'text');
395
+ const rawText = contentText(entry.content);
396
+ internalSegment = !hasAttachment && isCodexInjectedContextMessage(rawText);
397
+ }
398
+ entry.internal = internalSegment;
399
+ if (!['message', 'thought'].includes(entry.type)) continue;
400
+ for (const content of entry.content || []) {
401
+ if (content.type === 'text') content.text = stripCodexInternalContextBlocks(content.text);
402
+ }
403
+ }
404
+ return entries;
405
+ }
406
+
407
+ isInternalEntry(targetEntry) {
408
+ if (this.provider !== 'codex' || !targetEntry) return false;
409
+ let internalSegment = false;
410
+ for (const entry of this.entries) {
411
+ if (entry.type === 'message' && entry.role === 'user') {
412
+ const hasAttachment = (entry.content || []).some(content => content.type !== 'text');
413
+ internalSegment = !hasAttachment && isCodexInjectedContextMessage(contentText(entry.content));
414
+ }
415
+ if (entry === targetEntry) return internalSegment;
416
+ }
417
+ return false;
418
+ }
419
+
420
+ snapshot(extra = {}, options = {}) {
421
+ const entries = options.includeEntries === false ? [] : this.sanitizedEntries(0);
422
+ const snapshot = {
423
+ version: 2,
424
+ protocol: 'acp',
425
+ provider: this.provider,
426
+ sessionId: this.sessionId,
427
+ cwd: this.cwd,
428
+ title: this.title,
429
+ updatedAt: this.updatedAt || extra.updatedAt || '',
430
+ truncated: this.truncated,
431
+ revision: this.revision,
432
+ entries,
433
+ usage: clone(this.usage),
434
+ availableCommands: clone(this.availableCommands),
435
+ currentModeId: this.currentModeId,
436
+ configOptions: clone(this.configOptions),
437
+ ...clone(extra),
438
+ };
439
+ if (options.includeUpdates === true) snapshot.updates = clone(this.updates);
440
+ return snapshot;
441
+ }
442
+ }
443
+
444
+ module.exports = {
445
+ AcpSessionState,
446
+ MAX_ACP_UPDATES,
447
+ MAX_ACP_UPDATE_LOG_VALUE_CHARS,
448
+ };
@@ -0,0 +1,169 @@
1
+ const { createTwoFilesPatch, diffLines } = require('diff');
2
+
3
+ const MAX_RENDERED_DIFF_CHARS = 64 * 1024;
4
+
5
+ function diffBlocks(content) {
6
+ return (Array.isArray(content) ? content : [])
7
+ .filter(block => block?.type === 'diff' && typeof block.path === 'string' && block.path.trim());
8
+ }
9
+
10
+ function diffAction(block) {
11
+ const kind = String(block?._meta?.kind || '').trim().toLowerCase();
12
+ if (['add', 'added', 'create', 'created'].includes(kind)) return 'Added';
13
+ if (['delete', 'deleted', 'remove', 'removed'].includes(kind)) return 'Deleted';
14
+ if (['move', 'moved'].includes(kind)) return 'Moved';
15
+ if (['rename', 'renamed'].includes(kind)) return 'Renamed';
16
+ return 'Updated';
17
+ }
18
+
19
+ function patchLineStats(oldText, newText) {
20
+ return diffLines(oldText, newText).reduce((stats, part) => {
21
+ const count = Number(part.count || 0);
22
+ if (part.added) stats.added += count;
23
+ if (part.removed) stats.removed += count;
24
+ return stats;
25
+ }, { added: 0, removed: 0 });
26
+ }
27
+
28
+ function patchChanges(content, options = {}) {
29
+ return diffBlocks(content).map(block => {
30
+ const path = String(block.path || '').trim();
31
+ const oldText = block.oldText == null ? '' : String(block.oldText);
32
+ const newText = block.newText == null ? '' : String(block.newText);
33
+ const stats = patchLineStats(oldText, newText);
34
+ return {
35
+ path,
36
+ kind: diffAction(block).toLowerCase(),
37
+ added: stats.added,
38
+ removed: stats.removed,
39
+ ...(options.includeDiff === true
40
+ ? { diff: boundedDiffText(createTwoFilesPatch(path, path, oldText, newText, 'before', 'after', { context: 3 })) }
41
+ : {}),
42
+ };
43
+ });
44
+ }
45
+
46
+ function patchReviewChanges(content) {
47
+ return diffBlocks(content).map(block => ({
48
+ kind: diffAction(block).toLowerCase(),
49
+ newText: block.newText == null ? '' : String(block.newText),
50
+ oldText: block.oldText == null ? '' : String(block.oldText),
51
+ path: String(block.path || '').trim(),
52
+ }));
53
+ }
54
+
55
+ function boundedDiffText(value) {
56
+ const text = String(value || '');
57
+ if (text.length <= MAX_RENDERED_DIFF_CHARS) return text;
58
+ return `${text.slice(0, MAX_RENDERED_DIFF_CHARS)}\n\n[Diff detail truncated]`;
59
+ }
60
+
61
+ function renderedDiffText(block) {
62
+ const path = String(block.path || '').trim();
63
+ const oldText = block.oldText == null ? '' : String(block.oldText);
64
+ const newText = block.newText == null ? '' : String(block.newText);
65
+ const patch = createTwoFilesPatch(path, path, oldText, newText, 'before', 'after', { context: 3 });
66
+ return `File: ${path}\n${boundedDiffText(patch)}`.trim();
67
+ }
68
+
69
+ function jsonText(value) {
70
+ if (value === undefined || value === null) return '';
71
+ if (typeof value === 'string') return value;
72
+ try {
73
+ return JSON.stringify(value, null, 2);
74
+ } catch {
75
+ return String(value);
76
+ }
77
+ }
78
+
79
+ function toolContentText(content) {
80
+ return (Array.isArray(content) ? content : []).map(block => {
81
+ if (!block || typeof block !== 'object') return '';
82
+ if (block.type === 'content') {
83
+ const inner = block.content;
84
+ if (inner?.type === 'text') return String(inner.text || '');
85
+ if (inner?.type === 'resource_link') return [inner.name, inner.uri].filter(Boolean).join(' — ');
86
+ if (inner?.type === 'resource') return jsonText(inner.resource);
87
+ if (inner?.type === 'image') return `[Image: ${inner.mimeType || 'image'}]`;
88
+ if (inner?.type === 'audio') return `[Audio: ${inner.mimeType || 'audio'}]`;
89
+ return jsonText(inner);
90
+ }
91
+ if (block.type === 'diff') {
92
+ return renderedDiffText(block);
93
+ }
94
+ if (block.type === 'terminal') {
95
+ const terminal = block.terminal && typeof block.terminal === 'object' ? block.terminal : null;
96
+ const status = terminal?.exitStatus
97
+ ? `Exited ${terminal.exitStatus.exitCode ?? terminal.exitStatus.signal ?? ''}`.trim()
98
+ : 'Running';
99
+ const output = String(terminal?.output || '').trim();
100
+ return [`Terminal: ${block.terminalId || ''} (${status})`.trim(), output].filter(Boolean).join('\n');
101
+ }
102
+ if (block.type === 'text') return String(block.text || '');
103
+ return jsonText(block);
104
+ }).filter(Boolean).join('\n\n').trim();
105
+ }
106
+
107
+ function equivalentJsonText(text, value) {
108
+ const candidate = String(text || '').trim();
109
+ if (!candidate || value === undefined || value === null) return false;
110
+ if (candidate === jsonText(value).trim()) return true;
111
+ try {
112
+ return JSON.stringify(JSON.parse(candidate)) === JSON.stringify(value);
113
+ } catch {
114
+ return false;
115
+ }
116
+ }
117
+
118
+ function toolOutputText(entry) {
119
+ const output = entry.rawOutput;
120
+ if (
121
+ String(entry.kind || '').toLowerCase() === 'execute'
122
+ && output
123
+ && typeof output === 'object'
124
+ && !Array.isArray(output)
125
+ ) {
126
+ const stdout = typeof output.stdout === 'string' ? output.stdout.trimEnd() : '';
127
+ const stderr = typeof output.stderr === 'string' ? output.stderr.trimEnd() : '';
128
+ const sections = [];
129
+ if (stdout) sections.push(stdout);
130
+ if (stderr) sections.push(`stderr\n${stderr}`);
131
+ if (output.interrupted === true) sections.push('Interrupted');
132
+ if (sections.length > 0) return sections.join('\n\n');
133
+ }
134
+ return jsonText(output).trim();
135
+ }
136
+
137
+ function detailForTool(entry) {
138
+ const sections = [];
139
+ const rawInput = jsonText(entry.rawInput).trim();
140
+ // Terminal blocks have a dedicated, live presentation populated by the ACP
141
+ // client terminal manager. Rendering the same block through generic detail
142
+ // text duplicates its output directly below the terminal card.
143
+ let structuredContent = toolContentText(
144
+ (Array.isArray(entry.content) ? entry.content : []).filter(block => block?.type !== 'terminal')
145
+ );
146
+ const rawOutput = toolOutputText(entry);
147
+ // Some ACP adapters mirror rawOutput as a text content block. Keep the
148
+ // canonical output once instead of presenting the same JSON twice.
149
+ if (equivalentJsonText(structuredContent, entry.rawOutput)) structuredContent = '';
150
+ const locations = (Array.isArray(entry.locations) ? entry.locations : [])
151
+ .map(location => {
152
+ const path = String(location?.path || location?.uri || '');
153
+ const line = location?.line == null ? '' : `:${location.line}`;
154
+ return `${path}${line}`;
155
+ })
156
+ .filter(Boolean)
157
+ .join('\n');
158
+ if (rawInput) sections.push(`Input\n${rawInput}`);
159
+ if (structuredContent) sections.push(structuredContent);
160
+ if (rawOutput) sections.push(`Output\n${rawOutput}`);
161
+ if (locations) sections.push(`Locations\n${locations}`);
162
+ return sections.join('\n\n');
163
+ }
164
+
165
+ module.exports = {
166
+ acpToolChanges: entry => patchChanges(entry?.content, { includeDiff: true }),
167
+ acpToolDetail: detailForTool,
168
+ acpToolReviewChanges: entry => patchReviewChanges(entry?.content),
169
+ };