@surething/cockpit 1.0.232 → 1.0.234

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 (220) hide show
  1. package/.next-prod/BUILD_ID +1 -1
  2. package/.next-prod/build-manifest.json +3 -3
  3. package/.next-prod/prerender-manifest.json +3 -3
  4. package/.next-prod/react-loadable-manifest.json +7 -0
  5. package/.next-prod/server/app/_global-error/page.js.nft.json +1 -1
  6. package/.next-prod/server/app/_global-error/page_client-reference-manifest.js +1 -1
  7. package/.next-prod/server/app/_global-error.html +1 -1
  8. package/.next-prod/server/app/_global-error.rsc +1 -1
  9. package/.next-prod/server/app/_global-error.segments/_full.segment.rsc +1 -1
  10. package/.next-prod/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
  11. package/.next-prod/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
  12. package/.next-prod/server/app/_global-error.segments/_head.segment.rsc +1 -1
  13. package/.next-prod/server/app/_global-error.segments/_index.segment.rsc +1 -1
  14. package/.next-prod/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  15. package/.next-prod/server/app/_not-found/page.js.nft.json +1 -1
  16. package/.next-prod/server/app/_not-found/page_client-reference-manifest.js +1 -1
  17. package/.next-prod/server/app/_not-found.html +2 -2
  18. package/.next-prod/server/app/_not-found.rsc +3 -3
  19. package/.next-prod/server/app/_not-found.segments/_full.segment.rsc +3 -3
  20. package/.next-prod/server/app/_not-found.segments/_head.segment.rsc +1 -1
  21. package/.next-prod/server/app/_not-found.segments/_index.segment.rsc +3 -3
  22. package/.next-prod/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  23. package/.next-prod/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  24. package/.next-prod/server/app/_not-found.segments/_tree.segment.rsc +2 -2
  25. package/.next-prod/server/app/api/agent/test/route.js.nft.json +1 -1
  26. package/.next-prod/server/app/api/bash/route.js.nft.json +1 -1
  27. package/.next-prod/server/app/api/chat/codex/route.js +1 -1
  28. package/.next-prod/server/app/api/chat/codex/route.js.nft.json +1 -1
  29. package/.next-prod/server/app/api/chat/deepseek/route.js +1 -1
  30. package/.next-prod/server/app/api/chat/deepseek/route.js.nft.json +1 -1
  31. package/.next-prod/server/app/api/chat/kimi/route.js +1 -1
  32. package/.next-prod/server/app/api/chat/kimi/route.js.nft.json +1 -1
  33. package/.next-prod/server/app/api/chat/ollama/route.js +1 -1
  34. package/.next-prod/server/app/api/chat/ollama/route.js.nft.json +1 -1
  35. package/.next-prod/server/app/api/chat/pty-input/route.js.nft.json +1 -1
  36. package/.next-prod/server/app/api/chat/route.js +1 -1
  37. package/.next-prod/server/app/api/chat/route.js.nft.json +1 -1
  38. package/.next-prod/server/app/api/chat/stop/route.js.nft.json +1 -1
  39. package/.next-prod/server/app/api/claude-stats/route.js.nft.json +1 -1
  40. package/.next-prod/server/app/api/commands/route.js +1 -1
  41. package/.next-prod/server/app/api/commands/route.js.nft.json +1 -1
  42. package/.next-prod/server/app/api/comments/route.js.nft.json +1 -1
  43. package/.next-prod/server/app/api/db/columns/route.js.nft.json +1 -1
  44. package/.next-prod/server/app/api/db/connect/route.js.nft.json +1 -1
  45. package/.next-prod/server/app/api/db/disconnect/route.js.nft.json +1 -1
  46. package/.next-prod/server/app/api/db/export/route.js.nft.json +1 -1
  47. package/.next-prod/server/app/api/db/query/route.js.nft.json +1 -1
  48. package/.next-prod/server/app/api/db/schemas/route.js.nft.json +1 -1
  49. package/.next-prod/server/app/api/dev/spans/route.js.nft.json +1 -1
  50. package/.next-prod/server/app/api/extension/version/route.js.nft.json +1 -1
  51. package/.next-prod/server/app/api/file/route.js.nft.json +1 -1
  52. package/.next-prod/server/app/api/files/blame/route.js.nft.json +1 -1
  53. package/.next-prod/server/app/api/files/clipboard/route.js.nft.json +1 -1
  54. package/.next-prod/server/app/api/files/copy/route.js.nft.json +1 -1
  55. package/.next-prod/server/app/api/files/delete/route.js.nft.json +1 -1
  56. package/.next-prod/server/app/api/files/expanded/route.js.nft.json +1 -1
  57. package/.next-prod/server/app/api/files/index/route.js.nft.json +1 -1
  58. package/.next-prod/server/app/api/files/init/route.js.nft.json +1 -1
  59. package/.next-prod/server/app/api/files/paste/route.js.nft.json +1 -1
  60. package/.next-prod/server/app/api/files/read/route.js.nft.json +1 -1
  61. package/.next-prod/server/app/api/files/readdir/route.js.nft.json +1 -1
  62. package/.next-prod/server/app/api/files/recent/route.js.nft.json +1 -1
  63. package/.next-prod/server/app/api/files/save/route.js.nft.json +1 -1
  64. package/.next-prod/server/app/api/files/search/route.js.nft.json +1 -1
  65. package/.next-prod/server/app/api/files/stat/route.js.nft.json +1 -1
  66. package/.next-prod/server/app/api/files/text/route.js.nft.json +1 -1
  67. package/.next-prod/server/app/api/git/branch-diff/route.js.nft.json +1 -1
  68. package/.next-prod/server/app/api/git/branches/route.js.nft.json +1 -1
  69. package/.next-prod/server/app/api/git/commit-diff/route.js.nft.json +1 -1
  70. package/.next-prod/server/app/api/git/commits/route.js.nft.json +1 -1
  71. package/.next-prod/server/app/api/git/current-branch/route.js.nft.json +1 -1
  72. package/.next-prod/server/app/api/git/diff/route.js.nft.json +1 -1
  73. package/.next-prod/server/app/api/git/discard/route.js.nft.json +1 -1
  74. package/.next-prod/server/app/api/git/stage/route.js.nft.json +1 -1
  75. package/.next-prod/server/app/api/git/status/route.js.nft.json +1 -1
  76. package/.next-prod/server/app/api/git/unstage/route.js.nft.json +1 -1
  77. package/.next-prod/server/app/api/git/worktree/route.js.nft.json +1 -1
  78. package/.next-prod/server/app/api/global-state/route.js +1 -1
  79. package/.next-prod/server/app/api/global-state/route.js.nft.json +1 -1
  80. package/.next-prod/server/app/api/health/route.js.nft.json +1 -1
  81. package/.next-prod/server/app/api/jupyter/load/route.js.nft.json +1 -1
  82. package/.next-prod/server/app/api/jupyter/save/route.js.nft.json +1 -1
  83. package/.next-prod/server/app/api/jupyter/shutdown/route.js.nft.json +1 -1
  84. package/.next-prod/server/app/api/lsp/definition/route.js.nft.json +1 -1
  85. package/.next-prod/server/app/api/lsp/hover/route.js.nft.json +1 -1
  86. package/.next-prod/server/app/api/lsp/references/route.js.nft.json +1 -1
  87. package/.next-prod/server/app/api/lsp/status/route.js.nft.json +1 -1
  88. package/.next-prod/server/app/api/lsp/warmup/route.js.nft.json +1 -1
  89. package/.next-prod/server/app/api/mysql/columns/route.js.nft.json +1 -1
  90. package/.next-prod/server/app/api/mysql/connect/route.js.nft.json +1 -1
  91. package/.next-prod/server/app/api/mysql/disconnect/route.js.nft.json +1 -1
  92. package/.next-prod/server/app/api/mysql/export/route.js.nft.json +1 -1
  93. package/.next-prod/server/app/api/mysql/query/route.js.nft.json +1 -1
  94. package/.next-prod/server/app/api/mysql/schemas/route.js.nft.json +1 -1
  95. package/.next-prod/server/app/api/neo4j/connect/route.js.nft.json +1 -1
  96. package/.next-prod/server/app/api/neo4j/disconnect/route.js.nft.json +1 -1
  97. package/.next-prod/server/app/api/neo4j/query/route.js.nft.json +1 -1
  98. package/.next-prod/server/app/api/neo4j/schema/route.js.nft.json +1 -1
  99. package/.next-prod/server/app/api/note/route.js.nft.json +1 -1
  100. package/.next-prod/server/app/api/ollama/models/route.js.nft.json +1 -1
  101. package/.next-prod/server/app/api/ollama/start/route.js.nft.json +1 -1
  102. package/.next-prod/server/app/api/open-cursor/route.js.nft.json +1 -1
  103. package/.next-prod/server/app/api/open-vscode/route.js.nft.json +1 -1
  104. package/.next-prod/server/app/api/pick-folder/route.js.nft.json +1 -1
  105. package/.next-prod/server/app/api/pinned-sessions/route.js.nft.json +1 -1
  106. package/.next-prod/server/app/api/project-settings/route.js.nft.json +1 -1
  107. package/.next-prod/server/app/api/project-state/route.js.nft.json +1 -1
  108. package/.next-prod/server/app/api/projectGraph/affected/route.js.nft.json +1 -1
  109. package/.next-prod/server/app/api/projectGraph/callees/route.js.nft.json +1 -1
  110. package/.next-prod/server/app/api/projectGraph/callers/route.js.nft.json +1 -1
  111. package/.next-prod/server/app/api/projectGraph/coedit/route.js.nft.json +1 -1
  112. package/.next-prod/server/app/api/projectGraph/context/route.js.nft.json +1 -1
  113. package/.next-prod/server/app/api/projectGraph/file/route.js.nft.json +1 -1
  114. package/.next-prod/server/app/api/projectGraph/file-functions/route.js.nft.json +1 -1
  115. package/.next-prod/server/app/api/projectGraph/impact/route.js.nft.json +1 -1
  116. package/.next-prod/server/app/api/projectGraph/related/route.js.nft.json +1 -1
  117. package/.next-prod/server/app/api/projectGraph/risk/route.js.nft.json +1 -1
  118. package/.next-prod/server/app/api/projectGraph/search/route.js.nft.json +1 -1
  119. package/.next-prod/server/app/api/projects/route.js.nft.json +1 -1
  120. package/.next-prod/server/app/api/push/public-key/route.js +1 -1
  121. package/.next-prod/server/app/api/push/public-key/route.js.nft.json +1 -1
  122. package/.next-prod/server/app/api/push/subscribe/route.js +1 -1
  123. package/.next-prod/server/app/api/push/subscribe/route.js.nft.json +1 -1
  124. package/.next-prod/server/app/api/push/unsubscribe/route.js +1 -1
  125. package/.next-prod/server/app/api/push/unsubscribe/route.js.nft.json +1 -1
  126. package/.next-prod/server/app/api/redis/command/route.js.nft.json +1 -1
  127. package/.next-prod/server/app/api/redis/connect/route.js.nft.json +1 -1
  128. package/.next-prod/server/app/api/redis/delete/route.js.nft.json +1 -1
  129. package/.next-prod/server/app/api/redis/disconnect/route.js.nft.json +1 -1
  130. package/.next-prod/server/app/api/redis/get/route.js.nft.json +1 -1
  131. package/.next-prod/server/app/api/redis/keys/route.js.nft.json +1 -1
  132. package/.next-prod/server/app/api/redis/set/route.js.nft.json +1 -1
  133. package/.next-prod/server/app/api/review/[id]/comments/route.js.nft.json +1 -1
  134. package/.next-prod/server/app/api/review/[id]/replies/route.js.nft.json +1 -1
  135. package/.next-prod/server/app/api/review/[id]/route.js.nft.json +1 -1
  136. package/.next-prod/server/app/api/review/identify/route.js.nft.json +1 -1
  137. package/.next-prod/server/app/api/review/order/route.js.nft.json +1 -1
  138. package/.next-prod/server/app/api/review/route.js.nft.json +1 -1
  139. package/.next-prod/server/app/api/review/share-info/route.js.nft.json +1 -1
  140. package/.next-prod/server/app/api/review/users/route.js.nft.json +1 -1
  141. package/.next-prod/server/app/api/scheduled-tasks/route.js +2 -2
  142. package/.next-prod/server/app/api/scheduled-tasks/route.js.nft.json +1 -1
  143. package/.next-prod/server/app/api/services/config/route.js.nft.json +1 -1
  144. package/.next-prod/server/app/api/services/scripts/route.js.nft.json +1 -1
  145. package/.next-prod/server/app/api/session/[sessionId]/fork/route.js.nft.json +1 -1
  146. package/.next-prod/server/app/api/session/[sessionId]/history/route.js +1 -1
  147. package/.next-prod/server/app/api/session/[sessionId]/history/route.js.nft.json +1 -1
  148. package/.next-prod/server/app/api/session-by-path/route.js +1 -1
  149. package/.next-prod/server/app/api/session-by-path/route.js.nft.json +1 -1
  150. package/.next-prod/server/app/api/sessions/projects/[encodedPath]/route.js.nft.json +1 -1
  151. package/.next-prod/server/app/api/sessions/projects/route.js.nft.json +1 -1
  152. package/.next-prod/server/app/api/sessions/route.js.nft.json +1 -1
  153. package/.next-prod/server/app/api/settings/route.js.nft.json +1 -1
  154. package/.next-prod/server/app/api/skills/[id]/route.js.nft.json +1 -1
  155. package/.next-prod/server/app/api/skills/content/route.js.nft.json +1 -1
  156. package/.next-prod/server/app/api/skills/route.js.nft.json +1 -1
  157. package/.next-prod/server/app/api/terminal/aliases/route.js.nft.json +1 -1
  158. package/.next-prod/server/app/api/terminal/autocomplete/route.js.nft.json +1 -1
  159. package/.next-prod/server/app/api/terminal/bubble-order/route.js.nft.json +1 -1
  160. package/.next-prod/server/app/api/terminal/env/route.js.nft.json +1 -1
  161. package/.next-prod/server/app/api/terminal/history/route.js.nft.json +1 -1
  162. package/.next-prod/server/app/api/version/route.js.nft.json +1 -1
  163. package/.next-prod/server/app/favicon.ico/route.js.nft.json +1 -1
  164. package/.next-prod/server/app/m/page.js +2 -2
  165. package/.next-prod/server/app/m/page.js.nft.json +1 -1
  166. package/.next-prod/server/app/m/page_client-reference-manifest.js +1 -1
  167. package/.next-prod/server/app/manifest.webmanifest/route.js.nft.json +1 -1
  168. package/.next-prod/server/app/page.js +1 -1
  169. package/.next-prod/server/app/page.js.nft.json +1 -1
  170. package/.next-prod/server/app/page_client-reference-manifest.js +1 -1
  171. package/.next-prod/server/app/project/page.js +1 -1
  172. package/.next-prod/server/app/project/page.js.nft.json +1 -1
  173. package/.next-prod/server/app/project/page_client-reference-manifest.js +1 -1
  174. package/.next-prod/server/app/review/[id]/page.js +2 -2
  175. package/.next-prod/server/app/review/[id]/page.js.nft.json +1 -1
  176. package/.next-prod/server/app/review/[id]/page_client-reference-manifest.js +1 -1
  177. package/.next-prod/server/chunks/3863.js +2 -2
  178. package/.next-prod/server/chunks/{3633.js → 5897.js} +373 -3
  179. package/.next-prod/server/chunks/9658.js +26 -26
  180. package/.next-prod/server/chunks/9830.js +1 -1
  181. package/.next-prod/server/middleware-build-manifest.js +1 -1
  182. package/.next-prod/server/middleware-react-loadable-manifest.js +1 -1
  183. package/.next-prod/server/pages/404.html +2 -2
  184. package/.next-prod/server/pages/500.html +1 -1
  185. package/.next-prod/server/server-reference-manifest.json +1 -1
  186. package/.next-prod/static/chunks/{2625-bc4748f0cd7db618.js → 1332-5e141e2acf28015a.js} +10 -10
  187. package/.next-prod/static/chunks/{217-4f8250a204080159.js → 217-e929c46c0bd599a7.js} +4 -4
  188. package/.next-prod/static/chunks/2502-fb8682bc7a61e04d.js +4 -0
  189. package/.next-prod/static/chunks/{2576-6420f6bad0b8ffb3.js → 2576-11e41242c7dd98f1.js} +2 -2
  190. package/.next-prod/static/chunks/4523.3f277a24fbcfde6d.js +138 -0
  191. package/.next-prod/static/chunks/9304-ddde9008da31b2ce.js +1 -0
  192. package/.next-prod/static/chunks/app/{layout-ac2f1f67df01cc89.js → layout-d202f8e0bcc90661.js} +1 -1
  193. package/.next-prod/static/chunks/app/m/page-71570a066f3eacf8.js +1 -0
  194. package/.next-prod/static/chunks/app/{page-1f0a6f49656a4c52.js → page-814b50b5b440249d.js} +1 -1
  195. package/.next-prod/static/chunks/app/project/{page-1f0a6f49656a4c52.js → page-814b50b5b440249d.js} +1 -1
  196. package/.next-prod/static/chunks/app/review/[id]/{page-39fa3a843adf617e.js → page-0c5d03d65758c7dc.js} +1 -1
  197. package/.next-prod/static/chunks/webpack-2c71a79c277961bc.js +1 -0
  198. package/.next-prod/static/css/fa7218e60ff464b5.css +1 -0
  199. package/.next-prod/trace +13 -13
  200. package/.next-prod/trace-build +1 -1
  201. package/bin/cock-browser.mjs +12 -9
  202. package/bin/cock.mjs +5 -5
  203. package/bin/postinstall.mjs +6 -6
  204. package/chrome-extension/automation.js +45 -40
  205. package/chrome-extension/background.js +70 -67
  206. package/chrome-extension/content.js +38 -38
  207. package/chrome-extension/disguise.js +4 -4
  208. package/chrome-extension/network-capture.js +16 -16
  209. package/dist/{chunk-VHFWPI2X.mjs → chunk-3M3JSZ5R.mjs} +28 -1
  210. package/dist/scheduledTasks.mjs +437 -3
  211. package/dist/wsServer.mjs +6 -31
  212. package/package.json +1 -1
  213. package/server.mjs +122 -26
  214. package/.next-prod/server/chunks/7003.js +0 -1
  215. package/.next-prod/static/chunks/471-504b396c8302f4f2.js +0 -4
  216. package/.next-prod/static/chunks/app/m/page-8b1af6f31b60c485.js +0 -1
  217. package/.next-prod/static/chunks/webpack-dbba7fa77ee1faa4.js +0 -1
  218. package/.next-prod/static/css/2a854655f4108c3a.css +0 -1
  219. /package/.next-prod/static/{Z3Em1C_kM7x4RjcH7E7v2 → JfwcuC5YjyhQWeQD-4Gvn}/_buildManifest.js +0 -0
  220. /package/.next-prod/static/{Z3Em1C_kM7x4RjcH7E7v2 → JfwcuC5YjyhQWeQD-4Gvn}/_ssgManifest.js +0 -0
@@ -1 +1 @@
1
- [{"name":"run-webpack","duration":21093023,"timestamp":158697893,"id":14,"parentId":1,"tags":{},"startTime":1782900947547,"traceId":"dcd58a4bd7b49062"},{"name":"run-typescript","duration":18807400,"timestamp":179794924,"id":1603,"parentId":1,"tags":{},"startTime":1782900968644,"traceId":"dcd58a4bd7b49062"},{"name":"static-check","duration":1213527,"timestamp":198644615,"id":1606,"parentId":1,"tags":{},"startTime":1782900987494,"traceId":"dcd58a4bd7b49062"},{"name":"static-generation","duration":6335613,"timestamp":200113230,"id":1878,"parentId":1,"tags":{},"startTime":1782900988963,"traceId":"dcd58a4bd7b49062"},{"name":"collect-build-traces","duration":21023731,"timestamp":199858733,"id":1875,"parentId":1,"tags":{},"startTime":1782900988708,"traceId":"dcd58a4bd7b49062"},{"name":"telemetry-flush","duration":92,"timestamp":220886988,"id":1887,"parentId":1,"tags":{},"startTime":1782901009736,"traceId":"dcd58a4bd7b49062"},{"name":"next-build","duration":62368455,"timestamp":158518639,"id":1,"tags":{"buildMode":"default","version":"16.2.6","bundler":"webpack","has-custom-webpack-config":"true","use-build-worker":"false"},"startTime":1782900947368,"traceId":"dcd58a4bd7b49062"}]
1
+ [{"name":"run-webpack","duration":20216814,"timestamp":210001581,"id":14,"parentId":1,"tags":{},"startTime":1782998700158,"traceId":"01c8448817b155b6"},{"name":"run-typescript","duration":18380914,"timestamp":230222194,"id":1604,"parentId":1,"tags":{},"startTime":1782998720378,"traceId":"01c8448817b155b6"},{"name":"static-check","duration":1181334,"timestamp":248649550,"id":1607,"parentId":1,"tags":{},"startTime":1782998738806,"traceId":"01c8448817b155b6"},{"name":"static-generation","duration":6411700,"timestamp":249973703,"id":1879,"parentId":1,"tags":{},"startTime":1782998740130,"traceId":"01c8448817b155b6"},{"name":"collect-build-traces","duration":20480963,"timestamp":249831652,"id":1876,"parentId":1,"tags":{},"startTime":1782998739988,"traceId":"01c8448817b155b6"},{"name":"telemetry-flush","duration":72,"timestamp":270317441,"id":1888,"parentId":1,"tags":{},"startTime":1782998760474,"traceId":"01c8448817b155b6"},{"name":"next-build","duration":60489593,"timestamp":209827934,"id":1,"tags":{"buildMode":"default","version":"16.2.6","bundler":"webpack","has-custom-webpack-config":"true","use-build-worker":"false"},"startTime":1782998699984,"traceId":"01c8448817b155b6"}]
@@ -332,12 +332,13 @@ async function fetchBrowserInfo(shortId) {
332
332
 
333
333
  // Chunked evaluate result resolver
334
334
  //
335
- // Chrome extension runtime messaging sendResponse 边界有一个 ~8 KiB
336
- // 隐性 structured-clone 截断点;为了避免 evaluate 大结果被默默截掉,
337
- // extension 侧会把 >6 KiB 的结果暂存到 page window 上的一个 Map,
338
- // 返回一个 { __cockpit_chunked: true, token, totalBytes, isString }
339
- // descriptor。这里遇到 descriptor 就自动走 evaluate_chunk action 把完整
340
- // payload 拉回来,对上层 formatOutput 完全透明。
335
+ // Chrome extension runtime messaging has an implicit ~8 KiB structured-clone
336
+ // truncation point at the sendResponse boundary. To keep large evaluate
337
+ // results from being silently cut off, the extension side stashes any result
338
+ // >6 KiB in a Map on the page window and returns a
339
+ // { __cockpit_chunked: true, token, totalBytes, isString } descriptor.
340
+ // Whenever we see that descriptor here, we pull the full payload back via
341
+ // the evaluate_chunk action — fully transparent to formatOutput above.
341
342
  async function fetchOneChunk(baseUrl, id, token, offset, cmdTimeout) {
342
343
  const resp = await fetch(`${baseUrl}/api/browser/evaluate_chunk`, {
343
344
  method: 'POST',
@@ -382,7 +383,8 @@ async function autoResolveChunked(baseUrl, id, data, cmdTimeout) {
382
383
  if (data.__cockpit_chunked === true && typeof data.token === 'string') {
383
384
  return await resolveChunkedDescriptor(baseUrl, id, data, cmdTimeout);
384
385
  }
385
- // allFrames=true 聚合时可能得到数组,每一项都可能是独立 chunked
386
+ // With allFrames=true the aggregate may be an array, and each element
387
+ // may be independently chunked
386
388
  if (Array.isArray(data)) {
387
389
  return Promise.all(data.map(item => autoResolveChunked(baseUrl, id, item, cmdTimeout)));
388
390
  }
@@ -491,8 +493,9 @@ async function run() {
491
493
  process.exit(1);
492
494
  }
493
495
 
494
- // 大结果由 extension 端自动 stash 并返回 chunked descriptor;
495
- // 这里透明地把完整内容拉回来,调用方看不到 chunking 细节。
496
+ // Large results are auto-stashed by the extension side, which returns a
497
+ // chunked descriptor; we transparently pull the full content back here —
498
+ // callers never see the chunking.
496
499
  const resolved = await autoResolveChunked(baseUrl, id, data.data, timeout);
497
500
 
498
501
  // Post-`type` verification — `type` via CDP dispatchKeyEvent silently no-ops
package/bin/cock.mjs CHANGED
@@ -143,12 +143,12 @@ const knownCommands = new Set(['browser', 'terminal', 'update', 'help', 'codegra
143
143
  const arg = process.argv[2];
144
144
  let projectDir = null;
145
145
 
146
- // 第一个参数不是 flag 且不是已知子命令视为目录路径
146
+ // First arg is neither a flag nor a known subcommand treat it as a directory path
147
147
  if (arg && !arg.startsWith('-') && !knownCommands.has(arg)) {
148
- // 展开 ~ home 目录
148
+ // Expand ~ to the home directory
149
149
  const raw = arg.startsWith('~') ? arg.replace(/^~/, homedir()) : arg;
150
150
  projectDir = resolve(raw);
151
- // 目录不存在则创建
151
+ // Create the directory if it doesn't exist
152
152
  if (!existsSync(projectDir)) {
153
153
  mkdirSync(projectDir, { recursive: true });
154
154
  console.log(`Created ${projectDir}`);
@@ -173,7 +173,7 @@ const { exec } = await import('child_process');
173
173
  const running = await isServerRunning();
174
174
 
175
175
  if (running) {
176
- // 服务已运行打开浏览器,立即退出
176
+ // Server already running open the browser and exit immediately
177
177
  const base = `http://localhost:${port}`;
178
178
  const url = projectDir ? `${base}/?cwd=${encodeURIComponent(projectDir)}` : base;
179
179
  if (!process.env.COCKPIT_NO_OPEN) {
@@ -194,7 +194,7 @@ if (!isDev && !existsSync(resolve(PROJECT_ROOT, '.next-prod', 'BUILD_ID'))) {
194
194
  process.exit(1);
195
195
  }
196
196
 
197
- // 传递项目目录给 server.mjs,让它打开正确的 URL
197
+ // Hand the project directory to server.mjs so it opens the right URL
198
198
  if (projectDir) {
199
199
  process.env.COCKPIT_OPEN_PROJECT = projectDir;
200
200
  }
@@ -21,7 +21,7 @@ try {
21
21
  }
22
22
 
23
23
  if (process.platform !== 'win32') {
24
- // node-pty: spawn-helper 需要可执行权限
24
+ // node-pty: spawn-helper needs the executable bit
25
25
  try {
26
26
  const spawnHelper = join(
27
27
  projectRoot,
@@ -33,8 +33,8 @@ if (process.platform !== 'win32') {
33
33
  }
34
34
 
35
35
  // chrome-extension → ~/.cockpit/chrome-extension/
36
- // npm 安装时 projectRoot node_modules 下(无 src/ 目录),需要复制到用户目录
37
- // npm link projectRoot 是源码目录(有 src/),不需要复制
36
+ // Installed via npm: projectRoot sits under node_modules (no src/ dir) → copy into the user dir.
37
+ // Via npm link: projectRoot is the source checkout (has src/) → no copy needed.
38
38
  const isNpmInstall = !existsSync(join(projectRoot, 'src'));
39
39
  if (isNpmInstall) {
40
40
  try {
@@ -46,13 +46,13 @@ if (isNpmInstall) {
46
46
  cpSync(src, dest, { recursive: true, force: true });
47
47
 
48
48
  if (process.platform !== 'win32') {
49
- // sudo 安装时文件 owner rootChrome 无法写入 _metadata/
50
- // SUDO_USER 还原为真实用户
49
+ // Under a sudo install the files end up owned by root and Chrome can't
50
+ // write _metadata/ — restore ownership to the real user via SUDO_USER
51
51
  const realUser = process.env.SUDO_USER;
52
52
  if (realUser) {
53
53
  try { execSync(`chown -R "${realUser}" "${cockpitDir}"`); } catch {}
54
54
  }
55
- // macOS: 清除 com.apple.provenance 等扩展属性
55
+ // macOS: strip extended attributes like com.apple.provenance
56
56
  if (process.platform === 'darwin') {
57
57
  try { execSync(`xattr -cr "${dest}"`); } catch {}
58
58
  }
@@ -1,11 +1,12 @@
1
1
  /**
2
2
  * Cockpit Browser Automation Layer (ES Module)
3
3
  *
4
- * 注入到 Cockpit iframe 中,接收来自 BrowserBubble 的自动化命令,
5
- * 构建 a11y tree、执行 DOM 操作、返回结果。
4
+ * Injected into the Cockpit iframe; receives automation commands from
5
+ * BrowserBubble, builds the a11y tree, performs DOM operations, and
6
+ * returns results.
6
7
  *
7
- * 通过 content.js activateCockpitBridge() 动态 import()。
8
- * 运行在 content script isolated world 中(保留 chrome.runtime 访问权)。
8
+ * Dynamically import()-ed by activateCockpitBridge() in content.js.
9
+ * Runs in the content script isolated world (retains chrome.runtime access).
9
10
  */
10
11
 
11
12
  let _realParent = null;
@@ -14,7 +15,7 @@ let _chrome = null;
14
15
  const LOG_PREFIX = '[Cockpit Automation]';
15
16
 
16
17
  // ============================================================================
17
- // Ref 系统:为 a11y tree 中的元素分配稳定的 ref ID
18
+ // Ref system: assigns stable ref IDs to elements in the a11y tree
18
19
  // ============================================================================
19
20
 
20
21
  let refCounter = 0;
@@ -91,7 +92,7 @@ function findByRef(ref) {
91
92
  }
92
93
 
93
94
  // ============================================================================
94
- // A11y Tree 构建
95
+ // A11y Tree construction
95
96
  // ============================================================================
96
97
 
97
98
  const IMPLICIT_ROLES = {
@@ -284,7 +285,7 @@ function safeRegex(src) {
284
285
  }
285
286
 
286
287
  // ============================================================================
287
- // Console 拦截
288
+ // Console interception
288
289
  // ============================================================================
289
290
 
290
291
  const consoleBuffer = [];
@@ -312,24 +313,26 @@ function initConsoleCapture() {
312
313
  }
313
314
 
314
315
  // ============================================================================
315
- // Network 捕获(接收 Main World network-capture.js 通过 CustomEvent 发来的条目)
316
+ // Network capture (receives entries sent via CustomEvent from the Main
317
+ // World's network-capture.js)
316
318
  //
317
- // fetch / XHR 拦截在 Main World 执行(network-capture.js),
318
- // 本层只负责:存储 buffer、管理录制状态、处理 CLI 命令。
319
+ // fetch / XHR interception runs in the Main World (network-capture.js);
320
+ // this layer is only responsible for: storing the buffer, managing
321
+ // recording state, and handling CLI commands.
319
322
  // ============================================================================
320
323
 
321
324
  const networkBuffer = [];
322
325
  const MAX_NETWORK_BUFFER = 500;
323
326
 
324
- // 录制状态:由本层管理,通过 CustomEvent 同步给 Main World
327
+ // Recording state: managed by this layer, synced to the Main World via CustomEvent
325
328
  const networkRecording = {
326
329
  active: false,
327
330
  filters: {}, // { url, method, status }
328
- timer: null, // 自动过期定时器
331
+ timer: null, // auto-expiry timer
329
332
  startedAt: 0,
330
333
  };
331
334
 
332
- // 清除所有 entry body 数据(过期时调用)
335
+ // Clear body data from all entries (called on expiry)
333
336
  function clearAllBodies() {
334
337
  for (const entry of networkBuffer) {
335
338
  entry.requestHeaders = null;
@@ -339,32 +342,32 @@ function clearAllBodies() {
339
342
  }
340
343
  }
341
344
 
342
- // 同步录制状态到 Main World network-capture.js
345
+ // Sync recording state to the Main World's network-capture.js
343
346
  function syncRecordingToMainWorld() {
344
347
  window.dispatchEvent(new CustomEvent('cockpit:network-recording', {
345
348
  detail: { active: networkRecording.active, filters: networkRecording.filters },
346
349
  }));
347
350
  }
348
351
 
349
- // 监听 Main World 发来的网络条目
352
+ // Listen for network entries sent from the Main World
350
353
  function initNetworkListener() {
351
- // 请求发起时收到占位条目(保持发起顺序)
354
+ // Placeholder entry received when a request starts (preserves initiation order)
352
355
  window.addEventListener('cockpit:network-entry', (e) => {
353
356
  networkBuffer.push(e.detail);
354
357
  if (networkBuffer.length > MAX_NETWORK_BUFFER) networkBuffer.splice(0, 1);
355
358
  });
356
- // 响应完成时收到更新(补全 status / duration / body 等字段)
359
+ // Update received when the response completes (fills in status / duration / body etc.)
357
360
  window.addEventListener('cockpit:network-update', (e) => {
358
361
  const update = e.detail;
359
362
  const entry = networkBuffer.find(r => r.id === update.id);
360
363
  if (entry) Object.assign(entry, update);
361
364
  });
362
- // 通知 Main WorldIsolated World 已就绪,可以 flush 缓存的条目
365
+ // Notify the Main World: the Isolated World is ready, cached entries can be flushed
363
366
  window.dispatchEvent(new CustomEvent('cockpit:network-bridge-ready'));
364
367
  }
365
368
 
366
369
  // ============================================================================
367
- // 命令处理器
370
+ // Command handlers
368
371
  // ============================================================================
369
372
 
370
373
  const handlers = {
@@ -382,7 +385,7 @@ const handlers = {
382
385
  buildA11yTree(document.body, { filter, includeHiddenText, maxDepth }),
383
386
 
384
387
  screenshot: async () => {
385
- // 1) 通知父页面(项目 iframe):切到 console view + 切到本项目 + 返回 iframe bounds
388
+ // 1) Notify the parent page (project iframe): switch to console view + switch to this project + return the iframe bounds
386
389
  const boundsReqId = 'ss-' + Date.now();
387
390
  const bounds = await new Promise((resolve, reject) => {
388
391
  const timeout = setTimeout(() => reject(new Error('Timeout preparing screenshot')), 5000);
@@ -397,7 +400,7 @@ const handlers = {
397
400
  _realParent.postMessage({ type: 'cockpit:prepare-screenshot', reqId: boundsReqId }, '*');
398
401
  });
399
402
 
400
- // 2) captureVisibleTab 截取整个浏览器标签页
403
+ // 2) captureVisibleTab captures the entire browser tab
401
404
  const dataUrl = await new Promise((resolve, reject) => {
402
405
  _chrome.runtime.sendMessage({ type: 'cockpit:capture-tab' }, (response) => {
403
406
  if (_chrome.runtime.lastError) { reject(new Error(_chrome.runtime.lastError.message)); return; }
@@ -406,7 +409,7 @@ const handlers = {
406
409
  });
407
410
  });
408
411
 
409
- // 3) 裁切到 iframe 区域
412
+ // 3) Crop to the iframe area
410
413
  const img = new Image();
411
414
  await new Promise((resolve, reject) => { img.onload = resolve; img.onerror = reject; img.src = dataUrl; });
412
415
  const cropCanvas = document.createElement('canvas');
@@ -416,7 +419,7 @@ const handlers = {
416
419
  cropCtx.drawImage(img, bounds.x, bounds.y, bounds.width, bounds.height, 0, 0, bounds.width, bounds.height);
417
420
  const result = cropCanvas.toDataURL('image/png');
418
421
 
419
- // 4) 通知父页面截图完成,恢复界面
422
+ // 4) Notify the parent page the screenshot is done, restore the UI
420
423
  _realParent.postMessage({ type: 'cockpit:screenshot-done' }, '*');
421
424
 
422
425
  return { image: result, format: 'png' };
@@ -659,11 +662,11 @@ const handlers = {
659
662
  },
660
663
 
661
664
  evaluate: async ({ js, allFrames }) => {
662
- // 通过 background.js chrome.scripting.executeScript 在 main world 执行
663
- // 不受页面 CSP 限制,可访问页面 JS 变量(React state 等)
664
- // allFrames: true → 在所有 frame 中执行(解决跨域 iframe 访问问题)
665
- // 大结果 (>6 KiB) 会在 MAIN world auto-stash 并以 descriptor 形式返回;
666
- // cock-browser CLI 识别 descriptor 后会通过 evaluate_chunk 回填内容。
665
+ // Executed in the main world via background.js's chrome.scripting.executeScript.
666
+ // Not restricted by the page's CSP; can access page JS variables (React state, etc.).
667
+ // allFrames: true → execute in all frames (solves cross-origin iframe access).
668
+ // Large results (>6 KiB) are auto-stashed in the MAIN world and returned as a descriptor;
669
+ // the cock-browser CLI recognizes the descriptor and backfills the content via evaluate_chunk.
667
670
  return new Promise((resolve) => {
668
671
  _chrome.runtime.sendMessage({ type: 'cockpit:evaluate', js, allFrames: !!allFrames }, (response) => {
669
672
  if (_chrome.runtime.lastError) {
@@ -677,13 +680,15 @@ const handlers = {
677
680
  },
678
681
 
679
682
  evaluate_chunk: async ({ token, offset = 0, size = 5000 }) => {
680
- // 读取 MAIN-world stash 里某个 token 的一段内容。token 由上一次 evaluate
681
- // 返回的 descriptor 提供。注意 stash page window 上,页面导航/刷新会丢;
682
- // 必须同一个浏览器 session、同一个页面上下文。
683
+ // Reads a slice of a token's content from the MAIN-world stash. The token
684
+ // comes from the descriptor returned by the previous evaluate. Note the
685
+ // stash lives on the page window, so page navigation/reload loses it;
686
+ // must be the same browser session and the same page context.
683
687
  //
684
- // 返回 { chunk, done, nextOffset, totalBytes, isString }
685
- // size 默认 5000 以确保每次返回对象 JSON 序列化 < 6000,远低于 Chrome
686
- // chrome.runtime 消息边界的 ~8192 字节隐性截断阈值。
688
+ // Returns { chunk, done, nextOffset, totalBytes, isString };
689
+ // size defaults to 5000 to keep each returned object's JSON serialization
690
+ // < 6000, well below Chrome's ~8192-byte implicit truncation threshold at
691
+ // the chrome.runtime message boundary.
687
692
  const offNum = Number(offset) || 0;
688
693
  const szNum = Math.min(Math.max(1, Number(size) || 5000), 7000);
689
694
  const tokStr = String(token);
@@ -755,10 +760,10 @@ const handlers = {
755
760
  };
756
761
  },
757
762
 
758
- // 录制控制:start 开始捕获 bodystop 停止,status 查看状态
763
+ // Recording control: start begins body capture, stop ends it, status shows state
759
764
  network_record: async ({ action = 'status', url, method, status, ttl = 600 }) => {
760
765
  if (action === 'start') {
761
- // 清除旧的过期定时器
766
+ // Clear the old expiry timer
762
767
  if (networkRecording.timer) clearTimeout(networkRecording.timer);
763
768
  networkRecording.active = true;
764
769
  networkRecording.filters = {};
@@ -767,7 +772,7 @@ const handlers = {
767
772
  if (status) networkRecording.filters.status = status;
768
773
  networkRecording.startedAt = Date.now();
769
774
  syncRecordingToMainWorld();
770
- // ttl 秒后自动过期(默认 10 分钟)
775
+ // Auto-expire after ttl seconds (default 10 minutes)
771
776
  networkRecording.timer = setTimeout(() => {
772
777
  networkRecording.active = false;
773
778
  clearAllBodies();
@@ -784,7 +789,7 @@ const handlers = {
784
789
  networkRecording.active = false;
785
790
  if (networkRecording.timer) { clearTimeout(networkRecording.timer); networkRecording.timer = null; }
786
791
  syncRecordingToMainWorld();
787
- // 停止后不立即清 body,允许查询已录制的数据
792
+ // Don't clear bodies immediately after stopping; allow querying the recorded data
788
793
  return { recording: false, recordedCount: networkBuffer.filter(r => r.recorded).length };
789
794
  }
790
795
  // status
@@ -1299,7 +1304,7 @@ function simpleJsonPath(data, path) {
1299
1304
  }
1300
1305
 
1301
1306
  // ============================================================================
1302
- // 命令分发
1307
+ // Command dispatch
1303
1308
  // ============================================================================
1304
1309
 
1305
1310
  function handleCommand(event) {
@@ -1357,7 +1362,7 @@ function bagCounts(s) {
1357
1362
  }
1358
1363
 
1359
1364
  // ============================================================================
1360
- // 导出初始化函数
1365
+ // Exported initialization function
1361
1366
  // ============================================================================
1362
1367
 
1363
1368
  export function initAutomation(realParent, chromeApi) {