commandmate 0.34.1 → 0.35.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (311) hide show
  1. package/.next/BUILD_ID +1 -1
  2. package/.next/app-build-manifest.json +176 -163
  3. package/.next/app-path-routes-manifest.json +27 -27
  4. package/.next/build-manifest.json +2 -2
  5. package/.next/prerender-manifest.json +9 -9
  6. package/.next/required-server-files.json +1 -1
  7. package/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  8. package/.next/server/app/api/agents/update/route_client-reference-manifest.js +1 -1
  9. package/.next/server/app/api/agents/versions/route_client-reference-manifest.js +1 -1
  10. package/.next/server/app/api/app/update/route_client-reference-manifest.js +1 -1
  11. package/.next/server/app/api/app/update-check/route.js +1 -1
  12. package/.next/server/app/api/app/update-check/route_client-reference-manifest.js +1 -1
  13. package/.next/server/app/api/assistant/conversation/route.js.nft.json +1 -1
  14. package/.next/server/app/api/assistant/conversation/route_client-reference-manifest.js +1 -1
  15. package/.next/server/app/api/assistant/current-output/route.js.nft.json +1 -1
  16. package/.next/server/app/api/assistant/current-output/route_client-reference-manifest.js +1 -1
  17. package/.next/server/app/api/assistant/messages/route.js +1 -1
  18. package/.next/server/app/api/assistant/messages/route.js.nft.json +1 -1
  19. package/.next/server/app/api/assistant/messages/route_client-reference-manifest.js +1 -1
  20. package/.next/server/app/api/assistant/session/route.js +1 -1
  21. package/.next/server/app/api/assistant/session/route.js.nft.json +1 -1
  22. package/.next/server/app/api/assistant/session/route_client-reference-manifest.js +1 -1
  23. package/.next/server/app/api/assistant/start/route.js +1 -1
  24. package/.next/server/app/api/assistant/start/route.js.nft.json +1 -1
  25. package/.next/server/app/api/assistant/start/route_client-reference-manifest.js +1 -1
  26. package/.next/server/app/api/assistant/terminal/route.js +1 -1
  27. package/.next/server/app/api/assistant/terminal/route.js.nft.json +1 -1
  28. package/.next/server/app/api/assistant/terminal/route_client-reference-manifest.js +1 -1
  29. package/.next/server/app/api/assistant/tools/route.js.nft.json +1 -1
  30. package/.next/server/app/api/assistant/tools/route_client-reference-manifest.js +1 -1
  31. package/.next/server/app/api/auth/login/route_client-reference-manifest.js +1 -1
  32. package/.next/server/app/api/auth/logout/route_client-reference-manifest.js +1 -1
  33. package/.next/server/app/api/auth/status/route_client-reference-manifest.js +1 -1
  34. package/.next/server/app/api/capabilities/route.js +1 -1
  35. package/.next/server/app/api/capabilities/route_client-reference-manifest.js +1 -1
  36. package/.next/server/app/api/daily-summary/route_client-reference-manifest.js +1 -1
  37. package/.next/server/app/api/daily-summary/status/route_client-reference-manifest.js +1 -1
  38. package/.next/server/app/api/external-apps/[id]/health/route_client-reference-manifest.js +1 -1
  39. package/.next/server/app/api/external-apps/[id]/route_client-reference-manifest.js +1 -1
  40. package/.next/server/app/api/external-apps/route_client-reference-manifest.js +1 -1
  41. package/.next/server/app/api/fs/browse/route_client-reference-manifest.js +1 -1
  42. package/.next/server/app/api/fs/recent-paths/route_client-reference-manifest.js +1 -1
  43. package/.next/server/app/api/hooks/agent-event/route.js.nft.json +1 -1
  44. package/.next/server/app/api/hooks/agent-event/route_client-reference-manifest.js +1 -1
  45. package/.next/server/app/api/hooks/claude-done/route.js +1 -1
  46. package/.next/server/app/api/hooks/claude-done/route.js.nft.json +1 -1
  47. package/.next/server/app/api/hooks/claude-done/route_client-reference-manifest.js +1 -1
  48. package/.next/server/app/api/hooks/permission-request/route.js.nft.json +1 -1
  49. package/.next/server/app/api/hooks/permission-request/route_client-reference-manifest.js +1 -1
  50. package/.next/server/app/api/metrics/vibe/route_client-reference-manifest.js +1 -1
  51. package/.next/server/app/api/ollama/models/route_client-reference-manifest.js +1 -1
  52. package/.next/server/app/api/push/escalation/route_client-reference-manifest.js +1 -1
  53. package/.next/server/app/api/push/subscriptions/route_client-reference-manifest.js +1 -1
  54. package/.next/server/app/api/push/vapid/route_client-reference-manifest.js +1 -1
  55. package/.next/server/app/api/relays/[relayId]/cancel/route.js +1 -1
  56. package/.next/server/app/api/relays/[relayId]/cancel/route.js.nft.json +1 -1
  57. package/.next/server/app/api/relays/[relayId]/cancel/route_client-reference-manifest.js +1 -1
  58. package/.next/server/app/api/relays/route.js +1 -1
  59. package/.next/server/app/api/relays/route.js.nft.json +1 -1
  60. package/.next/server/app/api/relays/route_client-reference-manifest.js +1 -1
  61. package/.next/server/app/api/remote/pair/route_client-reference-manifest.js +1 -1
  62. package/.next/server/app/api/repositories/[id]/route_client-reference-manifest.js +1 -1
  63. package/.next/server/app/api/repositories/[id]/todos/[todoId]/route_client-reference-manifest.js +1 -1
  64. package/.next/server/app/api/repositories/[id]/todos/route_client-reference-manifest.js +1 -1
  65. package/.next/server/app/api/repositories/clone/[jobId]/route.js +1 -1
  66. package/.next/server/app/api/repositories/clone/[jobId]/route.js.nft.json +1 -1
  67. package/.next/server/app/api/repositories/clone/[jobId]/route_client-reference-manifest.js +1 -1
  68. package/.next/server/app/api/repositories/clone/route.js +1 -1
  69. package/.next/server/app/api/repositories/clone/route.js.nft.json +1 -1
  70. package/.next/server/app/api/repositories/clone/route_client-reference-manifest.js +1 -1
  71. package/.next/server/app/api/repositories/excluded/route_client-reference-manifest.js +1 -1
  72. package/.next/server/app/api/repositories/restore/route.js +1 -1
  73. package/.next/server/app/api/repositories/restore/route.js.nft.json +1 -1
  74. package/.next/server/app/api/repositories/restore/route_client-reference-manifest.js +1 -1
  75. package/.next/server/app/api/repositories/route.js +1 -1
  76. package/.next/server/app/api/repositories/route.js.nft.json +1 -1
  77. package/.next/server/app/api/repositories/route_client-reference-manifest.js +1 -1
  78. package/.next/server/app/api/repositories/scan/route.js +1 -1
  79. package/.next/server/app/api/repositories/scan/route.js.nft.json +1 -1
  80. package/.next/server/app/api/repositories/scan/route_client-reference-manifest.js +1 -1
  81. package/.next/server/app/api/repositories/sync/route.js +1 -1
  82. package/.next/server/app/api/repositories/sync/route.js.nft.json +1 -1
  83. package/.next/server/app/api/repositories/sync/route_client-reference-manifest.js +1 -1
  84. package/.next/server/app/api/repositories/validate-path/route_client-reference-manifest.js +1 -1
  85. package/.next/server/app/api/settings/default-agents/route.js.nft.json +1 -1
  86. package/.next/server/app/api/settings/default-agents/route_client-reference-manifest.js +1 -1
  87. package/.next/server/app/api/settings/default-surface-mode/route_client-reference-manifest.js +1 -1
  88. package/.next/server/app/api/sidebar/group-order/route_client-reference-manifest.js +1 -1
  89. package/.next/server/app/api/skills/[id]/route_client-reference-manifest.js +1 -1
  90. package/.next/server/app/api/skills/installations/route_client-reference-manifest.js +1 -1
  91. package/.next/server/app/api/skills/operations/route_client-reference-manifest.js +1 -1
  92. package/.next/server/app/api/skills/reindex/route_client-reference-manifest.js +1 -1
  93. package/.next/server/app/api/skills/route_client-reference-manifest.js +1 -1
  94. package/.next/server/app/api/slash-commands/route_client-reference-manifest.js +1 -1
  95. package/.next/server/app/api/tasks/[taskId]/cancel/route_client-reference-manifest.js +1 -1
  96. package/.next/server/app/api/tasks/[taskId]/route_client-reference-manifest.js +1 -1
  97. package/.next/server/app/api/templates/[id]/route_client-reference-manifest.js +1 -1
  98. package/.next/server/app/api/templates/route_client-reference-manifest.js +1 -1
  99. package/.next/server/app/api/todos/route_client-reference-manifest.js +1 -1
  100. package/.next/server/app/api/verification/runs/[runId]/route_client-reference-manifest.js +1 -1
  101. package/.next/server/app/api/verification/runs/route_client-reference-manifest.js +1 -1
  102. package/.next/server/app/api/worktrees/[id]/auto-yes/route.js +1 -1
  103. package/.next/server/app/api/worktrees/[id]/auto-yes/route.js.nft.json +1 -1
  104. package/.next/server/app/api/worktrees/[id]/auto-yes/route_client-reference-manifest.js +1 -1
  105. package/.next/server/app/api/worktrees/[id]/capture/route.js.nft.json +1 -1
  106. package/.next/server/app/api/worktrees/[id]/capture/route_client-reference-manifest.js +1 -1
  107. package/.next/server/app/api/worktrees/[id]/clear-composer/route.js +1 -1
  108. package/.next/server/app/api/worktrees/[id]/clear-composer/route.js.nft.json +1 -1
  109. package/.next/server/app/api/worktrees/[id]/clear-composer/route_client-reference-manifest.js +1 -1
  110. package/.next/server/app/api/worktrees/[id]/cli-reference/route_client-reference-manifest.js +1 -1
  111. package/.next/server/app/api/worktrees/[id]/cli-tool/route_client-reference-manifest.js +1 -1
  112. package/.next/server/app/api/worktrees/[id]/cmate/schedules/route_client-reference-manifest.js +1 -1
  113. package/.next/server/app/api/worktrees/[id]/current-output/route.js +1 -1
  114. package/.next/server/app/api/worktrees/[id]/current-output/route.js.nft.json +1 -1
  115. package/.next/server/app/api/worktrees/[id]/current-output/route_client-reference-manifest.js +1 -1
  116. package/.next/server/app/api/worktrees/[id]/env/route_client-reference-manifest.js +1 -1
  117. package/.next/server/app/api/worktrees/[id]/execution-logs/[logId]/route_client-reference-manifest.js +1 -1
  118. package/.next/server/app/api/worktrees/[id]/execution-logs/route_client-reference-manifest.js +1 -1
  119. package/.next/server/app/api/worktrees/[id]/files/[...path]/route.js +1 -1
  120. package/.next/server/app/api/worktrees/[id]/files/[...path]/route_client-reference-manifest.js +1 -1
  121. package/.next/server/app/api/worktrees/[id]/git/branch/create/route_client-reference-manifest.js +1 -1
  122. package/.next/server/app/api/worktrees/[id]/git/branch/delete/route_client-reference-manifest.js +1 -1
  123. package/.next/server/app/api/worktrees/[id]/git/branches/route_client-reference-manifest.js +1 -1
  124. package/.next/server/app/api/worktrees/[id]/git/checkout/route_client-reference-manifest.js +1 -1
  125. package/.next/server/app/api/worktrees/[id]/git/commit/route_client-reference-manifest.js +1 -1
  126. package/.next/server/app/api/worktrees/[id]/git/diff/route_client-reference-manifest.js +1 -1
  127. package/.next/server/app/api/worktrees/[id]/git/fetch/route_client-reference-manifest.js +1 -1
  128. package/.next/server/app/api/worktrees/[id]/git/log/route_client-reference-manifest.js +1 -1
  129. package/.next/server/app/api/worktrees/[id]/git/pull/route_client-reference-manifest.js +1 -1
  130. package/.next/server/app/api/worktrees/[id]/git/push/route_client-reference-manifest.js +1 -1
  131. package/.next/server/app/api/worktrees/[id]/git/reset/route_client-reference-manifest.js +1 -1
  132. package/.next/server/app/api/worktrees/[id]/git/revert/route_client-reference-manifest.js +1 -1
  133. package/.next/server/app/api/worktrees/[id]/git/show/[commitHash]/route_client-reference-manifest.js +1 -1
  134. package/.next/server/app/api/worktrees/[id]/git/stage/route_client-reference-manifest.js +1 -1
  135. package/.next/server/app/api/worktrees/[id]/git/staged/route_client-reference-manifest.js +1 -1
  136. package/.next/server/app/api/worktrees/[id]/git/stash/[index]/route_client-reference-manifest.js +1 -1
  137. package/.next/server/app/api/worktrees/[id]/git/stash/apply/route_client-reference-manifest.js +1 -1
  138. package/.next/server/app/api/worktrees/[id]/git/stash/pop/route_client-reference-manifest.js +1 -1
  139. package/.next/server/app/api/worktrees/[id]/git/stash/push/route_client-reference-manifest.js +1 -1
  140. package/.next/server/app/api/worktrees/[id]/git/stash/route_client-reference-manifest.js +1 -1
  141. package/.next/server/app/api/worktrees/[id]/git/status/route_client-reference-manifest.js +1 -1
  142. package/.next/server/app/api/worktrees/[id]/git/unstage/route_client-reference-manifest.js +1 -1
  143. package/.next/server/app/api/worktrees/[id]/git/working-diff/route_client-reference-manifest.js +1 -1
  144. package/.next/server/app/api/worktrees/[id]/instances/notes/route_client-reference-manifest.js +1 -1
  145. package/.next/server/app/api/worktrees/[id]/instances/opencode/route.js.nft.json +1 -1
  146. package/.next/server/app/api/worktrees/[id]/instances/opencode/route_client-reference-manifest.js +1 -1
  147. package/.next/server/app/api/worktrees/[id]/interrupt/route.js.nft.json +1 -1
  148. package/.next/server/app/api/worktrees/[id]/interrupt/route_client-reference-manifest.js +1 -1
  149. package/.next/server/app/api/worktrees/[id]/kill-session/route.js +1 -1
  150. package/.next/server/app/api/worktrees/[id]/kill-session/route.js.nft.json +1 -1
  151. package/.next/server/app/api/worktrees/[id]/kill-session/route_client-reference-manifest.js +1 -1
  152. package/.next/server/app/api/worktrees/[id]/logs/[filename]/route_client-reference-manifest.js +1 -1
  153. package/.next/server/app/api/worktrees/[id]/logs/route_client-reference-manifest.js +1 -1
  154. package/.next/server/app/api/worktrees/[id]/marp-render/route_client-reference-manifest.js +1 -1
  155. package/.next/server/app/api/worktrees/[id]/memos/[memoId]/route_client-reference-manifest.js +1 -1
  156. package/.next/server/app/api/worktrees/[id]/memos/route_client-reference-manifest.js +1 -1
  157. package/.next/server/app/api/worktrees/[id]/messages/route_client-reference-manifest.js +1 -1
  158. package/.next/server/app/api/worktrees/[id]/opencode/diff/route_client-reference-manifest.js +1 -1
  159. package/.next/server/app/api/worktrees/[id]/opencode/session/route_client-reference-manifest.js +1 -1
  160. package/.next/server/app/api/worktrees/[id]/opencode/share/route_client-reference-manifest.js +1 -1
  161. package/.next/server/app/api/worktrees/[id]/prompt-response/route.js +1 -1
  162. package/.next/server/app/api/worktrees/[id]/prompt-response/route.js.nft.json +1 -1
  163. package/.next/server/app/api/worktrees/[id]/prompt-response/route_client-reference-manifest.js +1 -1
  164. package/.next/server/app/api/worktrees/[id]/resolve-target/route_client-reference-manifest.js +1 -1
  165. package/.next/server/app/api/worktrees/[id]/respond/route.js +1 -1
  166. package/.next/server/app/api/worktrees/[id]/respond/route.js.nft.json +1 -1
  167. package/.next/server/app/api/worktrees/[id]/respond/route_client-reference-manifest.js +1 -1
  168. package/.next/server/app/api/worktrees/[id]/route.js +1 -1
  169. package/.next/server/app/api/worktrees/[id]/route.js.nft.json +1 -1
  170. package/.next/server/app/api/worktrees/[id]/route_client-reference-manifest.js +1 -1
  171. package/.next/server/app/api/worktrees/[id]/schedules/[scheduleId]/route_client-reference-manifest.js +1 -1
  172. package/.next/server/app/api/worktrees/[id]/schedules/active/route_client-reference-manifest.js +1 -1
  173. package/.next/server/app/api/worktrees/[id]/schedules/route_client-reference-manifest.js +1 -1
  174. package/.next/server/app/api/worktrees/[id]/search/route_client-reference-manifest.js +1 -1
  175. package/.next/server/app/api/worktrees/[id]/send/route.js +1 -1
  176. package/.next/server/app/api/worktrees/[id]/send/route.js.nft.json +1 -1
  177. package/.next/server/app/api/worktrees/[id]/send/route_client-reference-manifest.js +1 -1
  178. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/git-workflow/route.js.nft.json +1 -1
  179. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/git-workflow/route_client-reference-manifest.js +1 -1
  180. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/install/route_client-reference-manifest.js +1 -1
  181. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/plan/route_client-reference-manifest.js +1 -1
  182. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/uninstall/route_client-reference-manifest.js +1 -1
  183. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/uninstall-plan/route_client-reference-manifest.js +1 -1
  184. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/update/route_client-reference-manifest.js +1 -1
  185. package/.next/server/app/api/worktrees/[id]/skills/[skillId]/update-plan/route_client-reference-manifest.js +1 -1
  186. package/.next/server/app/api/worktrees/[id]/skills/route_client-reference-manifest.js +1 -1
  187. package/.next/server/app/api/worktrees/[id]/slash-commands/route_client-reference-manifest.js +1 -1
  188. package/.next/server/app/api/worktrees/[id]/special-keys/route.js +1 -1
  189. package/.next/server/app/api/worktrees/[id]/special-keys/route.js.nft.json +1 -1
  190. package/.next/server/app/api/worktrees/[id]/special-keys/route_client-reference-manifest.js +1 -1
  191. package/.next/server/app/api/worktrees/[id]/tasks/route_client-reference-manifest.js +1 -1
  192. package/.next/server/app/api/worktrees/[id]/terminal/route.js.nft.json +1 -1
  193. package/.next/server/app/api/worktrees/[id]/terminal/route_client-reference-manifest.js +1 -1
  194. package/.next/server/app/api/worktrees/[id]/timers/history/route_client-reference-manifest.js +1 -1
  195. package/.next/server/app/api/worktrees/[id]/timers/route.js +1 -1
  196. package/.next/server/app/api/worktrees/[id]/timers/route.js.nft.json +1 -1
  197. package/.next/server/app/api/worktrees/[id]/timers/route_client-reference-manifest.js +1 -1
  198. package/.next/server/app/api/worktrees/[id]/todos/[todoId]/route_client-reference-manifest.js +1 -1
  199. package/.next/server/app/api/worktrees/[id]/todos/route_client-reference-manifest.js +1 -1
  200. package/.next/server/app/api/worktrees/[id]/tree/[...path]/route_client-reference-manifest.js +1 -1
  201. package/.next/server/app/api/worktrees/[id]/tree/route_client-reference-manifest.js +1 -1
  202. package/.next/server/app/api/worktrees/[id]/upload/[...path]/route_client-reference-manifest.js +1 -1
  203. package/.next/server/app/api/worktrees/[id]/verify/config/route_client-reference-manifest.js +1 -1
  204. package/.next/server/app/api/worktrees/[id]/verify/route_client-reference-manifest.js +1 -1
  205. package/.next/server/app/api/worktrees/[id]/verify/runs/[runId]/cancel/route_client-reference-manifest.js +1 -1
  206. package/.next/server/app/api/worktrees/[id]/verify/runs/[runId]/route_client-reference-manifest.js +1 -1
  207. package/.next/server/app/api/worktrees/[id]/verify/runs/route_client-reference-manifest.js +1 -1
  208. package/.next/server/app/api/worktrees/[id]/viewed/route_client-reference-manifest.js +1 -1
  209. package/.next/server/app/api/worktrees/apply-default-agents/route_client-reference-manifest.js +1 -1
  210. package/.next/server/app/api/worktrees/route.js +1 -1
  211. package/.next/server/app/api/worktrees/route.js.nft.json +1 -1
  212. package/.next/server/app/api/worktrees/route_client-reference-manifest.js +1 -1
  213. package/.next/server/app/chat/page.js +2 -2
  214. package/.next/server/app/chat/page.js.nft.json +1 -1
  215. package/.next/server/app/chat/page_client-reference-manifest.js +1 -1
  216. package/.next/server/app/login/page_client-reference-manifest.js +1 -1
  217. package/.next/server/app/manifest.webmanifest/route_client-reference-manifest.js +1 -1
  218. package/.next/server/app/more/page.js +2 -2
  219. package/.next/server/app/more/page.js.nft.json +1 -1
  220. package/.next/server/app/more/page_client-reference-manifest.js +1 -1
  221. package/.next/server/app/offline/page_client-reference-manifest.js +1 -1
  222. package/.next/server/app/page.js +1 -1
  223. package/.next/server/app/page.js.nft.json +1 -1
  224. package/.next/server/app/page_client-reference-manifest.js +1 -1
  225. package/.next/server/app/proxy/[...path]/route_client-reference-manifest.js +1 -1
  226. package/.next/server/app/repositories/page.js +2 -2
  227. package/.next/server/app/repositories/page.js.nft.json +1 -1
  228. package/.next/server/app/repositories/page_client-reference-manifest.js +1 -1
  229. package/.next/server/app/review/page.js +1 -1
  230. package/.next/server/app/review/page.js.nft.json +1 -1
  231. package/.next/server/app/review/page_client-reference-manifest.js +1 -1
  232. package/.next/server/app/sessions/page.js +1 -1
  233. package/.next/server/app/sessions/page.js.nft.json +1 -1
  234. package/.next/server/app/sessions/page_client-reference-manifest.js +1 -1
  235. package/.next/server/app/skills/[skillId]/page.js +2 -2
  236. package/.next/server/app/skills/[skillId]/page.js.nft.json +1 -1
  237. package/.next/server/app/skills/[skillId]/page_client-reference-manifest.js +1 -1
  238. package/.next/server/app/skills/installed/page.js +2 -2
  239. package/.next/server/app/skills/installed/page.js.nft.json +1 -1
  240. package/.next/server/app/skills/installed/page_client-reference-manifest.js +1 -1
  241. package/.next/server/app/skills/page.js +1 -1
  242. package/.next/server/app/skills/page.js.nft.json +1 -1
  243. package/.next/server/app/skills/page_client-reference-manifest.js +1 -1
  244. package/.next/server/app/worktrees/[id]/files/[...path]/page_client-reference-manifest.js +1 -1
  245. package/.next/server/app/worktrees/[id]/page.js +11 -11
  246. package/.next/server/app/worktrees/[id]/page.js.nft.json +1 -1
  247. package/.next/server/app/worktrees/[id]/page_client-reference-manifest.js +1 -1
  248. package/.next/server/app/worktrees/[id]/terminal/page_client-reference-manifest.js +1 -1
  249. package/.next/server/app-paths-manifest.json +27 -27
  250. package/.next/server/chunks/1210.js +1 -1
  251. package/.next/server/chunks/{6286.js → 1467.js} +6 -6
  252. package/.next/server/chunks/1886.js +1 -1
  253. package/.next/server/chunks/2980.js +1 -1
  254. package/.next/server/chunks/3077.js +1 -1
  255. package/.next/server/chunks/3241.js +1 -1
  256. package/.next/server/chunks/3323.js +1 -1
  257. package/.next/server/chunks/434.js +1 -1
  258. package/.next/server/chunks/4443.js +1 -1
  259. package/.next/server/chunks/450.js +1 -1
  260. package/.next/server/chunks/6130.js +1 -1
  261. package/.next/server/chunks/650.js +1 -1
  262. package/.next/server/chunks/6677.js +3 -3
  263. package/.next/server/chunks/7075.js +1 -1
  264. package/.next/server/chunks/7506.js +1 -1
  265. package/.next/server/chunks/7905.js +1 -1
  266. package/.next/server/chunks/8728.js +8 -0
  267. package/.next/server/chunks/8918.js +5 -5
  268. package/.next/server/chunks/9123.js +2 -2
  269. package/.next/server/middleware-manifest.json +5 -5
  270. package/.next/server/pages/500.html +1 -1
  271. package/.next/server/server-reference-manifest.json +1 -1
  272. package/.next/static/chunks/2407-b9001cc6041876e1.js +1 -0
  273. package/.next/static/chunks/{4322-dfd5a7119b5ba4fc.js → 4322-59a7dbd77a7763cc.js} +1 -1
  274. package/.next/static/chunks/4388-410b1d8ed0d8d98b.js +1 -0
  275. package/.next/static/chunks/4718-56ebb6e55073ed5e.js +1 -0
  276. package/.next/static/chunks/{2652-18b8fea64413467e.js → 4809-145884b958e7d9a6.js} +1 -1
  277. package/.next/static/chunks/app/chat/{page-e60d07c4c79602f0.js → page-609c9a0f5ce44799.js} +1 -1
  278. package/.next/static/chunks/app/error-c1dc1038d0a84a33.js +1 -0
  279. package/.next/static/chunks/app/global-error-49f765ecb7fd6527.js +1 -0
  280. package/.next/static/chunks/app/{layout-4c2f21e3f653ee4c.js → layout-114dc6e93e332392.js} +1 -1
  281. package/.next/static/chunks/app/more/{page-fc94f86aa881489e.js → page-7c5380e4a7561935.js} +1 -1
  282. package/.next/static/chunks/app/{page-26a42881c8648cd3.js → page-a4f03c188610c6c8.js} +1 -1
  283. package/.next/static/chunks/app/repositories/{page-2576158c8420fda0.js → page-a15efb4ce1d1721e.js} +1 -1
  284. package/.next/static/chunks/app/review/{page-35b99baaf3c93b38.js → page-90ac618489676cbc.js} +1 -1
  285. package/.next/static/chunks/app/sessions/{page-a3ab6f122ec60d5a.js → page-6486d9a643c1dc6f.js} +1 -1
  286. package/.next/static/chunks/app/skills/[skillId]/{page-06799157652e8fa9.js → page-844872df04f52943.js} +1 -1
  287. package/.next/static/chunks/app/skills/installed/{page-2f3987e3a131c8d0.js → page-566dfde26d7e63ba.js} +1 -1
  288. package/.next/static/chunks/app/skills/{page-e70bfcf5ed4e4865.js → page-7859540e8092aace.js} +1 -1
  289. package/.next/static/chunks/app/worktrees/[id]/page-3a58ae66e203f935.js +1 -0
  290. package/.next/trace +14 -13
  291. package/dist/lib/detection/tools/verified-against.d.ts +20 -0
  292. package/dist/lib/detection/tools/verified-against.d.ts.map +1 -1
  293. package/dist/lib/detection/tools/verified-against.js +20 -0
  294. package/dist/server/src/config/websocket-config.js +67 -0
  295. package/dist/server/src/lib/auto-yes-poller.js +40 -7
  296. package/dist/server/src/lib/detection/selection-shape.js +361 -3
  297. package/dist/server/src/lib/detection/tools/command-code/detect.js +96 -0
  298. package/dist/server/src/lib/detection/tools/command-code/dialog.js +314 -0
  299. package/dist/server/src/lib/detection/tools/verified-against.js +20 -0
  300. package/dist/server/src/lib/polling/response-checker.js +48 -2
  301. package/dist/server/src/lib/ws-server.js +111 -1
  302. package/package.json +1 -1
  303. package/public/sw.js +12 -0
  304. package/.next/server/chunks/595.js +0 -8
  305. package/.next/static/chunks/4718-29cfcfb806724d9a.js +0 -1
  306. package/.next/static/chunks/8361-0142beb59be2abf3.js +0 -1
  307. package/.next/static/chunks/app/error-27ab04bce6545dae.js +0 -1
  308. package/.next/static/chunks/app/global-error-7b761b8e181ffc1f.js +0 -1
  309. package/.next/static/chunks/app/worktrees/[id]/page-60eab4e24c37cb77.js +0 -1
  310. /package/.next/static/{oDWX0JcwfhUYrMnnqDWVC → 0vChXhzA5YWj3f0D6A-Cn}/_buildManifest.js +0 -0
  311. /package/.next/static/{oDWX0JcwfhUYrMnnqDWVC → 0vChXhzA5YWj3f0D6A-Cn}/_ssgManifest.js +0 -0
@@ -72,6 +72,24 @@
72
72
  * box. Measured live on v1.40.1 at the production 200x1000 geometry; the capture
73
73
  * is `tests/fixtures/chat-dialog-card-2254/command-code-model-1-40-1.txt`.
74
74
  *
75
+ * `beforePrompt` arrived with Issue #2521 as a third `afterPrompt` branch and
76
+ * was moved ahead of the shared parser by Issue #2522. It is the only branch
77
+ * here not read off a footer: `AskUserQuestion` draws none. The screen is a
78
+ * rule, a tab strip (`● Dispatch | ◯ Review`), the question and a strict
79
+ * `1.`…`N.` run with one `❯` on it, and `readCommandCodeQuestionRegion` is what
80
+ * recognises that shape. Before #2521, a wrapped option description took the
81
+ * frame away from the shared parser and the generic composer check answered
82
+ * `ready` off the dialog's own cursor row — so `wait` exited 0 on a pane that
83
+ * was asking a human a question.
84
+ *
85
+ * #2521 answered that with a manual-operation fallback (the selection-list
86
+ * reason, no `promptData`). #2522 added `tools/command-code/dialog.ts`, which
87
+ * READS the same region, and the branch now publishes one of two verdicts:
88
+ * `PROMPT_DETECTED` with the parsed question, options and `❯` default where the
89
+ * reading succeeds, and #2521's fallback where the screen is plainly up and the
90
+ * reading declines. The move to `beforePrompt` is part of that: see the branch
91
+ * for why the generic parser must not get this frame either before or after.
92
+ *
75
93
  * ## What #2304 re-measured, and what it did not change
76
94
  *
77
95
  * Nothing here changed, and that is the finding. Seven frames were captured
@@ -104,6 +122,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
104
122
  exports.commandCodeStatusDetector = exports.VERIFIED_AGAINST = void 0;
105
123
  const cli_patterns_1 = require("../../cli-patterns");
106
124
  const selection_shape_1 = require("../../selection-shape");
125
+ const dialog_1 = require("./dialog");
107
126
  const status_reason_1 = require("../../status-reason");
108
127
  const run_detection_1 = require("../run-detection");
109
128
  const verified_against_1 = require("../verified-against");
@@ -112,6 +131,83 @@ exports.VERIFIED_AGAINST = verified_against_1.COMMAND_CODE_VERIFIED_AGAINST;
112
131
  exports.commandCodeStatusDetector = (0, run_detection_1.createToolStatusDetector)({
113
132
  tool: 'command-code',
114
133
  verifiedAgainst: exports.VERIFIED_AGAINST,
134
+ beforePrompt(frame) {
135
+ // Issue #2521 recognised this screen; Issue #2522 reads it.
136
+ //
137
+ // `AskUserQuestion` draws no footer, so neither `afterPrompt` branch below
138
+ // reads it — and the shared `detectPrompt` at step 1 does not either, because
139
+ // a wrapped option description continues on a row that begins with a SINGLE
140
+ // space (` answer).`) and the generic multiple-choice parser ends its scan
141
+ // there, one row short of option 1. The frame therefore reached step 3, where
142
+ // `COMMAND_CODE_PROMPT_PATTERN` (`^❯(\s*$|\s+\S)`) matched the dialog's own
143
+ // cursor row, `❯ 1. Prepare worktrees + dispatch (Recommended)`, and the pane
144
+ // was published as `ready` / `input_prompt`. A human was being asked a
145
+ // question and `wait` exited 0 on it.
146
+ //
147
+ // ## Why `beforePrompt` and not `afterPrompt` (Issue #2522 確定仕様 A / B)
148
+ //
149
+ // #2521's branch sat at 1.5, after the shared parser, because it only had to
150
+ // catch the frames that parser could not read. This one has to run FIRST, and
151
+ // for two separate reasons:
152
+ //
153
+ // - **the short spelling.** With one-line descriptions the generic parser
154
+ // SUCCEEDS on this screen, and succeeds badly: `extractQuestionText` walks
155
+ // up to five rows above option 1 and takes the tab strip, the rule and the
156
+ // transcript's TODOS row into the question. Placing the reader after it
157
+ // would leave exactly the frames that already look fine — and are wrong;
158
+ // - **the unreadable spelling.** A question screen with a gap in its
159
+ // numbering, or one taller than the reader's cap, must reach #2521's
160
+ // manual-operation fallback and NOT the generic parser's partial list.
161
+ // That is only expressible ahead of the parser.
162
+ //
163
+ // `/usage`, `/model` and the four permission dialogs are unaffected, and not
164
+ // by ordering: `readCommandCodeQuestionRegion` positively declines every one
165
+ // of them (the pickers by their own footers, the permission dialogs by having
166
+ // no tab strip), which is what the fixture sweep in
167
+ // `command-code-askuserquestion-2521.test.ts` pins.
168
+ //
169
+ // Read against `frame.raw` rather than `frame.lastLines` or `frame.clean`:
170
+ // the region runs from the last rule row to the last content row, which is
171
+ // more rows than the 15-row window holds, and the rule row itself is what
172
+ // `stripBoxDrawing` would erase. Every other consumer of this reading keeps
173
+ // the same tick's raw capture for the same reason (確定仕様 C).
174
+ const reading = (0, dialog_1.readCommandCodeQuestionDialog)(frame.raw);
175
+ // Read in full: the question, its options, the `❯` default and the free-text
176
+ // row are all in hand, so the pane is published exactly as an ordinary
177
+ // answerable dialog is. `hasActivePrompt: true` is what puts `promptData` on
178
+ // `/current-output`, raises the answer buttons, lets `respond <id> 2` reach
179
+ // the pane and lets Auto-Yes consider it — every one of them through the
180
+ // SAME payload, which is the point of reading it once here.
181
+ if (reading.kind === 'prompt') {
182
+ return {
183
+ status: 'waiting',
184
+ confidence: 'high',
185
+ reason: status_reason_1.STATUS_REASON.PROMPT_DETECTED,
186
+ hasActivePrompt: true,
187
+ evidence: 'positive',
188
+ promptDetection: reading.prompt,
189
+ };
190
+ }
191
+ // The question UI is plainly up and this reader could not read it. #2521's
192
+ // verdict, unchanged and deliberately kept: `COMMAND_CODE_SELECTION_LIST` is
193
+ // in `SELECTION_LIST_REASONS`, which publishes `isSelectionListActive`,
194
+ // raises the arrow-driven card and makes `wait` exit 10 instead of polling a
195
+ // blocked agent to its `--timeout`.
196
+ //
197
+ // `hasActivePrompt: false` and no `promptDetection`: nothing parsed the
198
+ // options, so there is no payload to answer with and none is invented — and
199
+ // the generic parser is not given a second chance to invent a partial one.
200
+ if (reading.kind === 'unsupported') {
201
+ return {
202
+ status: 'waiting',
203
+ confidence: 'high',
204
+ reason: status_reason_1.STATUS_REASON.COMMAND_CODE_SELECTION_LIST,
205
+ hasActivePrompt: false,
206
+ evidence: 'positive',
207
+ };
208
+ }
209
+ return null;
210
+ },
115
211
  afterPrompt(frame) {
116
212
  // Issue #2369. `/usage` opens a READ-ONLY panel: a plan header, two usage
117
213
  // meters, a breakdown URL, and `Press Esc to close` as its last row. It is
@@ -0,0 +1,314 @@
1
+ "use strict";
2
+ /**
3
+ * Command Code's footer-less `AskUserQuestion`, read as an answerable prompt
4
+ * (Issue #2522).
5
+ *
6
+ * ## What Issue #2521 left here
7
+ *
8
+ * #2521 taught the status chain to RECOGNISE this screen. It draws a 200-column
9
+ * rule, a tab strip (`● Dispatch | ◯ Review`), a question and a strict `1.`…`N.`
10
+ * run with one `❯` on it — and no hint-bar footer at all — and when an option's
11
+ * description wraps, the continuation row begins with a SINGLE space:
12
+ *
13
+ * ────────────────────────────… (200 columns of U+2500)
14
+ * ● Dispatch | ◯ Review
15
+ *
16
+ * Approve proceeding from the plan into worktree creation and dispatch?
17
+ *
18
+ * ❯ 1. Prepare worktrees + dispatch (Recommended)
19
+ * I create the worktrees and pause for you to
20
+ * answer).
21
+ * 2. Worktrees only, then pause
22
+ * …
23
+ *
24
+ * `isContinuationLine` in the shared multiple-choice parser refuses ` answer).`
25
+ * (one leading space, five characters or more, no path shape), so the generic
26
+ * reverse scan stops there one row short of option 1, collects `[2,3,4]`, and
27
+ * rejects the block for not starting at `1`. #2521's answer was a manual-operation
28
+ * fallback: `waiting` / `COMMAND_CODE_SELECTION_LIST` / `hasActivePrompt: false`,
29
+ * which stops `wait` exiting 0 and raises a card a human drives with the arrows.
30
+ *
31
+ * This module is the other half. It reads the SAME region #2521 recognises
32
+ * ({@link readCommandCodeQuestionRegion}) and produces the `multiple_choice`
33
+ * payload that `respond`, the chat surface's answer buttons, the prompt-history
34
+ * rows, the push notification and Auto-Yes all consume — so a frame this reads
35
+ * is published as `PROMPT_DETECTED` and the fallback no longer applies to it.
36
+ *
37
+ * ## Three states, one reading
38
+ *
39
+ * {@link readCommandCodeQuestionDialog} answers a discriminated union rather
40
+ * than `PromptDetectionResult | null`, because "this is not that screen" and
41
+ * "this IS that screen and I cannot read it" need opposite handling and a `null`
42
+ * cannot tell them apart (Issue #2522 確定仕様 B):
43
+ *
44
+ * | `kind` | what it means | what the caller does |
45
+ * |---------------|--------------------------------------------|----------------------|
46
+ * | `none` | not Command Code's question screen | every existing tool-specific / generic path, unchanged |
47
+ * | `prompt` | read in full | use this prompt; do not let the generic parser overwrite it |
48
+ * | `unsupported` | the question UI is plainly up, and a gap / a duplicate / an over-tall region / an unreadable option run stopped the reading | #2521's manual-operation fallback. No `promptData`, no auto-answer, and NOT the generic parser's partial list |
49
+ *
50
+ * ## Why it is not "call the generic parser, fall back to this"
51
+ *
52
+ * Because the generic parser SUCCEEDS on the short spelling of this screen —
53
+ * one-line descriptions, nothing wrapped — and succeeds badly: `extractQuestionText`
54
+ * walks up to {@link QUESTION_CONTEXT_LINES} rows above the options and would
55
+ * take the tab strip, the rule and the transcript's TODOS row into the question.
56
+ * So this reader runs FIRST wherever it runs at all, and the question it produces
57
+ * is bounded by the tab row rather than by a row count.
58
+ *
59
+ * ## Input contract
60
+ *
61
+ * A frame with its BOX DRAWING INTACT — `capture-pane -p -e` output, or that
62
+ * with ANSI removed. The region is anchored on a pure-U+2500 rule row, and
63
+ * `stripBoxDrawing` blanks exactly that row, so a `captureAndCleanOutput`
64
+ * spelling reaches `none` here however plainly the dialog is on screen. That is
65
+ * the trap #2522 確定仕様 C is written against: the three consumers that clean
66
+ * their frames (`detectPromptWithOptions`, the Auto-Yes poller, `/prompt-response`)
67
+ * each keep the RAW capture from the same tick and hand it here, and hand the
68
+ * cleaned string to everything else. ANSI is stripped internally, per row, off
69
+ * the same split the region indices address, so either spelling reads alike.
70
+ *
71
+ * Pure and side-effect free: no status, no poller, no database, no UI.
72
+ */
73
+ Object.defineProperty(exports, "__esModule", { value: true });
74
+ exports.COMMAND_CODE_QUESTION_MAX_REGION_ROWS = void 0;
75
+ exports.readCommandCodeQuestionDialog = readCommandCodeQuestionDialog;
76
+ exports.detectCommandCodeQuestionPrompt = detectCommandCodeQuestionPrompt;
77
+ const ansi_1 = require("../../ansi");
78
+ const prompt_detect_multiple_choice_1 = require("../../prompt-detect-multiple-choice");
79
+ const selection_shape_1 = require("../../selection-shape");
80
+ const dialog_block_1 = require("../dialog-block");
81
+ /**
82
+ * How many rows of dialog this reader will parse.
83
+ *
84
+ * 確定仕様 A forbids truncating to the 15-row detection window or the 40-row
85
+ * selection-shape tail — a wrapped description is exactly what pushes the
86
+ * question out of those — and equally forbids reporting a PARTIAL list as a
87
+ * success when a cap is hit. So the cap is stated here, generously, and hitting
88
+ * it is `unsupported` rather than "the options I managed to see".
89
+ *
90
+ * Sixty rows is the tallest this screen can plausibly be (a tab strip, a blank,
91
+ * a question wrapped over half a dozen rows, and nine options with four rows of
92
+ * description each) and equals {@link findNumberedOptionBlock}'s own
93
+ * `MAX_BLOCK_ROWS`, so the two cannot disagree about which one declined: the
94
+ * region is measured first and the block walk can no longer reach its limit.
95
+ */
96
+ exports.COMMAND_CODE_QUESTION_MAX_REGION_ROWS = 60;
97
+ /**
98
+ * How many non-blank rows under the LAST option may be its own description.
99
+ *
100
+ * The region ends at the last row carrying content, so the rows
101
+ * {@link findNumberedOptionBlock} files as `footer` are not chrome — this screen
102
+ * draws none — they are the wrapped tail of the bottom option, and 確定仕様 A
103
+ * says a description under the last option folds into it exactly as one under
104
+ * any other option does. Same trade agy's reader makes for the same reason.
105
+ */
106
+ const LAST_OPTION_TAIL_ROWS = 12;
107
+ /** The cursor glyph, restated from the region reader's own private constant. */
108
+ const COMMAND_CODE_CURSOR_GLYPH = '❯';
109
+ /**
110
+ * The cursor row's own option number, for the cross-check below.
111
+ *
112
+ * The region reading already proved there is exactly one `❯` in the region and
113
+ * that it sits on an option row; this recovers WHICH option it is, so the
114
+ * default can be pinned against {@link findNumberedOptionBlock}'s own answer
115
+ * instead of trusting a glyph union (`[❯›●>]`) that is wider than this screen's.
116
+ */
117
+ const CURSOR_OPTION_NUMBER_PATTERN = /❯[^\S\n]*(\d{1,2})[.)]/;
118
+ /**
119
+ * The one option on this screen that is NOT answerable by its number
120
+ * (Issue #2522 確定仕様 A / D).
121
+ *
122
+ * Command Code draws `4. Type something...` as the last row of the list, and it
123
+ * is not a fourth choice: the measured `QuestionPrompt` gives the ordinary
124
+ * choices to a `SelectInput` and renders this one as a separate `TextInput`. It
125
+ * is kept as a displayed option — a human has to see that the screen offers free
126
+ * text — and marked `requiresTextInput`, which is what stops `resolveBaseAnswer`
127
+ * auto-selecting it and what makes the answer UIs open a text field instead of
128
+ * sending a bare `4`.
129
+ *
130
+ * Added to the shared builder's result rather than to `TEXT_INPUT_PATTERNS`,
131
+ * because that list is the GENERIC one every CLI is read through and 対象外
132
+ * forbids widening it: `/enter\s+/`-class patterns there already over-match, and
133
+ * one more entry would change what every other tool's options mean.
134
+ *
135
+ * Anchored at the start of the label so the fold-in of a description below the
136
+ * row (`Type something... Write your own answer.`) still matches.
137
+ */
138
+ const COMMAND_CODE_FREE_TEXT_OPTION_PATTERN = /^[^\S\n]*type\s+something\b/i;
139
+ /**
140
+ * A checkbox option — the row shape of a MULTI-select question.
141
+ *
142
+ * The same expression `prompt-answer-sender` and `prompt-answer-semantic` use to
143
+ * recognise one, restated here (both are private to their modules) because this
144
+ * reader has to DECLINE the screen rather than answer it: 対象外 says Review,
145
+ * multi-select and free-text screens are not to be pushed through the
146
+ * single-select parser, and the reason is mechanical. On a checkbox list the
147
+ * digit TOGGLES a box and the confirm is a separate `Next` row, so a payload
148
+ * that claimed "option 2 is the answer" would have `respond 2` tick a box and
149
+ * stop — leaving the question up and the operator told it was answered.
150
+ *
151
+ * `unsupported` rather than `none`: the screen IS a live question and the human
152
+ * has to be sent to the pane for it, which is exactly #2521's fallback.
153
+ */
154
+ const CHECKBOX_OPTION_PATTERN = /^\[[ x]\]\s/i;
155
+ /**
156
+ * The same tail limits `prompt-detector.ts` applies to `rawContent`
157
+ * (`RAW_CONTENT_MAX_LINES` / `RAW_CONTENT_MAX_CHARS`), restated because that
158
+ * helper is private to it. A prompt row stores this text as its message body.
159
+ *
160
+ * In practice neither bound binds here — the region is at most
161
+ * {@link COMMAND_CODE_QUESTION_MAX_REGION_ROWS} rows — which is the point: what
162
+ * used to reach these consumers for this screen was the whole 1000-row pane.
163
+ */
164
+ const RAW_CONTENT_MAX_LINES = 200;
165
+ const RAW_CONTENT_MAX_CHARS = 5000;
166
+ function truncateRawContent(content) {
167
+ const lines = content.split('\n');
168
+ const tail = lines.length > RAW_CONTENT_MAX_LINES ? lines.slice(-RAW_CONTENT_MAX_LINES) : lines;
169
+ const joined = tail.join('\n');
170
+ return joined.length > RAW_CONTENT_MAX_CHARS ? joined.slice(-RAW_CONTENT_MAX_CHARS) : joined;
171
+ }
172
+ function unsupported(reason) {
173
+ return { kind: 'unsupported', reason };
174
+ }
175
+ /**
176
+ * Read Command Code's `AskUserQuestion` off one capture (Issue #2522).
177
+ *
178
+ * @param frame - a capture with its box drawing intact (ANSI optional, CRLF
179
+ * tolerated). A `stripBoxDrawing`-ed string answers `none`; see the module
180
+ * docblock for why that is a contract and not a limitation to work around.
181
+ */
182
+ function readCommandCodeQuestionDialog(frame) {
183
+ if (!frame)
184
+ return { kind: 'none' };
185
+ // The positive recognition is #2521's, unchanged and not re-derived: the last
186
+ // qualifying rule row, a tab strip under it, a question, a strict `1.`…`N.`
187
+ // run and exactly one `❯` on one of its rows, with the pickers and panels the
188
+ // other branches own excluded. Everything below is READING what it recognised.
189
+ const region = (0, selection_shape_1.readCommandCodeQuestionRegion)(frame);
190
+ if (region === null) {
191
+ // The strict reading declined. Two very different frames arrive here, and
192
+ // 確定仕様 B needs them told apart: one is any other screen in the world,
193
+ // the other is THIS screen with a gap in its numbering, a repeated row or a
194
+ // second cursor. `hasCommandCodeQuestionChrome` is the same structural scan
195
+ // with the two list-shaped conditions dropped, so it says which — and a
196
+ // question screen nobody can parse still stops `wait` instead of being
197
+ // handed back to the composer check that publishes `ready` off its own `❯`.
198
+ return (0, selection_shape_1.hasCommandCodeQuestionChrome)(frame)
199
+ ? unsupported('numbering-unreadable')
200
+ : { kind: 'none' };
201
+ }
202
+ const lines = frame.replace(/\r\n/g, '\n').split('\n').map(ansi_1.stripAnsi);
203
+ const regionRows = lines.slice(region.firstLineIndex, region.lastLineIndex + 1);
204
+ if (regionRows.length > exports.COMMAND_CODE_QUESTION_MAX_REGION_ROWS) {
205
+ return unsupported('region-too-tall');
206
+ }
207
+ const tabOffset = region.tabLineIndex - region.firstLineIndex;
208
+ // The shared block reader, on the region alone. Walking UP from the bottom is
209
+ // what folds a wrapped description into the option ABOVE it — which is the
210
+ // rule 確定仕様 A states for indent 0, 1 and 2 alike, and the one the generic
211
+ // parser's `isContinuationLine` could not follow.
212
+ const block = (0, dialog_block_1.findNumberedOptionBlock)(regionRows, regionRows.length, LAST_OPTION_TAIL_ROWS);
213
+ if (block === null)
214
+ return unsupported('option-block-unreadable');
215
+ const labels = [...block.options];
216
+ if (block.footer !== '') {
217
+ // Rows below the bottom option. The region's lower edge is the last row with
218
+ // content and this screen draws no footer, so they are that option's own
219
+ // description.
220
+ const last = labels.length - 1;
221
+ labels[last] = [labels[last], ...block.footer.split('\n')].join(' ').trim();
222
+ }
223
+ if (labels.length !== region.optionCount)
224
+ return unsupported('option-count-mismatch');
225
+ if (labels.some((label) => CHECKBOX_OPTION_PATTERN.test(label)))
226
+ return unsupported('multi-select');
227
+ // The default. Not `selectedGlyph` alone: `findNumberedOptionBlock`'s glyph
228
+ // union is `[❯›●>]` because it serves every CLI, and `●` is this screen's TAB
229
+ // marker — so the answer is cross-checked against the row the region reading
230
+ // actually found the one `❯` on, and a disagreement declines rather than
231
+ // guessing which option a human is about to confirm.
232
+ const cursorRow = regionRows[region.cursorLineIndex - region.firstLineIndex] ?? '';
233
+ const cursorMatch = CURSOR_OPTION_NUMBER_PATTERN.exec(cursorRow);
234
+ if (block.selectedIndex < 0 ||
235
+ block.selectedGlyph !== COMMAND_CODE_CURSOR_GLYPH ||
236
+ cursorMatch === null ||
237
+ Number(cursorMatch[1]) !== block.selectedIndex + 1) {
238
+ return unsupported('default-unresolved');
239
+ }
240
+ // The question: everything between the tab strip and option 1, blanks dropped,
241
+ // wrapped rows joined with ONE space and in draw order. Bounded by the tab row
242
+ // rather than by a row count, so neither the rule, the TODOS row above it nor
243
+ // the tab strip itself can reach it — and not narrowed to "the last row ending
244
+ // in `?`", so a question wrapped over three rows keeps its first two. `?` is
245
+ // usable evidence elsewhere and is deliberately not required here.
246
+ const questionRows = regionRows
247
+ .slice(tabOffset + 1, block.firstRow)
248
+ .map((row) => row.trim())
249
+ .filter((row) => row !== '');
250
+ if (questionRows.length === 0)
251
+ return unsupported('question-missing');
252
+ const question = questionRows.join(' ');
253
+ // The dialog's own rows, and nothing above the rule. Both surfaces are built
254
+ // from the same slice on purpose: `instructionText` is what the answer panels
255
+ // show a human, `approvalTarget` is what the contract's deny patterns are
256
+ // matched against (#1699), and for THIS screen they are the same text — the
257
+ // region already excludes the previous turn, so there is no wider human-facing
258
+ // window to offer and no narrower machine-facing one to carve out. What
259
+ // matters is that the descriptions are inside both: a deny pattern has to see
260
+ // the sentence the option is actually promising.
261
+ const dialogText = (0, prompt_detect_multiple_choice_1.joinApprovalTarget)(regionRows, tabOffset + 1, regionRows.length);
262
+ const built = (0, prompt_detect_multiple_choice_1.buildMultipleChoiceResult)(question, labels.map((label, index) => ({
263
+ number: index + 1,
264
+ label,
265
+ isDefault: index === block.selectedIndex,
266
+ })), { instructionText: dialogText, approvalTarget: dialogText }, regionRows.join('\n'), truncateRawContent,
267
+ // 確定仕様 D. The measured `QuestionPrompt` hands the ordinary choices to a
268
+ // `SelectInput`, which calls `onSelect` on the DIGIT — so a trailing Enter
269
+ // would land on whatever the tool painted next (the following question, or
270
+ // Review), confirming a second operation nobody chose. `answer_only` is also
271
+ // the safe direction if that measurement is ever wrong for a build: a digit
272
+ // that selects nothing leaves the dialog exactly where it was, while the
273
+ // Enter it would otherwise be paired with cannot be taken back.
274
+ 'answer_only',
275
+ // This IS an AskUserQuestion — a tab strip, a question and its own choices,
276
+ // not a permission prompt. It changes no keystroke for this tool (the cursor
277
+ // navigation arm of `sendPromptAnswer` is claude's and agy's), and it is what
278
+ // lets `/prompt-response` tell "the picker is up but unreadable" from "the
279
+ // prompt is gone".
280
+ true);
281
+ const promptData = built.promptData;
282
+ /* c8 ignore next -- buildMultipleChoiceResult always returns multiple_choice */
283
+ if (promptData === undefined || promptData.type !== 'multiple_choice') {
284
+ return unsupported('option-block-unreadable');
285
+ }
286
+ return {
287
+ kind: 'prompt',
288
+ region,
289
+ prompt: {
290
+ ...built,
291
+ promptData: {
292
+ ...promptData,
293
+ options: promptData.options.map((option) => option.requiresTextInput === true ||
294
+ COMMAND_CODE_FREE_TEXT_OPTION_PATTERN.test(option.label)
295
+ ? { ...option, requiresTextInput: true }
296
+ : option),
297
+ },
298
+ },
299
+ };
300
+ }
301
+ /**
302
+ * The same reading as a `PromptDetectionResult | null`, for the call sites whose
303
+ * only question is "is there an answerable prompt here?".
304
+ *
305
+ * `null` for BOTH `none` and `unsupported`, which is safe exactly where the
306
+ * caller has already decided what to do about the second — the detector's
307
+ * `beforePrompt` publishes #2521's fallback for it, and `/prompt-response`
308
+ * refuses it with `unsupported_dialog_layout`. A caller that cannot tell the two
309
+ * apart must use {@link readCommandCodeQuestionDialog} instead.
310
+ */
311
+ function detectCommandCodeQuestionPrompt(frame) {
312
+ const reading = readCommandCodeQuestionDialog(frame);
313
+ return reading.kind === 'prompt' ? reading.prompt : null;
314
+ }
@@ -112,6 +112,26 @@ exports.ANTIGRAVITY_VERIFIED_AGAINST = {
112
112
  * tmux socket at the production geometry — the default pane size does not
113
113
  * reproduce the 200-column rules that fence the composer, and the status row
114
114
  * drops its `esc to interrupt` tail below 72 columns.
115
+ *
116
+ * ## Deliberately NOT advanced by Issues #2521 / #2522
117
+ *
118
+ * Both read the `AskUserQuestion` screen, and both did it from the anonymised
119
+ * capture in `tests/fixtures/command-code-askuserquestion-2521/` — whose rows
120
+ * 410-423 are verbatim from a live pane, but whose version is what the reporting
121
+ * session SAID it was (1.53.0) rather than something re-probed. #2522's own
122
+ * fixture directory is synthetic throughout, and the send mode
123
+ * (`submitMode: 'answer_only'`) was chosen from a STATIC reading of a locally
124
+ * installed 1.53.1 `QuestionPrompt` plus the safe-direction argument in
125
+ * `tools/command-code/dialog.ts` — not from a keystroke sent at a live pane.
126
+ *
127
+ * None of that is the measurement this stamp records. #2304 set the precedent in
128
+ * the other direction: seven frames re-captured live on 1.49.0 changed no rule,
129
+ * and the stamp still says 1.40.1 because that is the build the rules were READ
130
+ * OFF. Advancing it here on a reported version, a synthetic fixture and a
131
+ * package read off disk would make `getDetectorFreshness` claim a measurement
132
+ * nobody took. When a live 1.53.x session is probed — the question screen, the
133
+ * keys it accepts and what one of them advances — bump this to that exact
134
+ * version with its own `capturedAt`.
115
135
  */
116
136
  exports.COMMAND_CODE_VERIFIED_AGAINST = {
117
137
  version: '1.40.1',
@@ -18,6 +18,7 @@ const db_1 = require("../../lib/db");
18
18
  const ws_server_1 = require("../../lib/ws-server");
19
19
  const prompt_detector_1 = require("../../lib/detection/prompt-detector");
20
20
  const dialog_1 = require("../../lib/detection/tools/antigravity/dialog");
21
+ const dialog_2 = require("../../lib/detection/tools/command-code/dialog");
21
22
  const conversation_logger_1 = require("../../lib/conversation-logger");
22
23
  const types_1 = require("../../lib/cli-tools/types");
23
24
  const claude_output_1 = require("../../lib/claude-output");
@@ -205,13 +206,29 @@ function buildPromptExtractionResult(lines, lastCapturedLine, totalLines, buffer
205
206
  * doubly-bordered row loses a second character on the second pass). Taking the
206
207
  * already-clean frame here is what keeps the two callers reading identical text.
207
208
  *
209
+ * ## The raw frame, and why it is a SECOND argument rather than a replacement
210
+ *
211
+ * Issue #2522. Command Code's `AskUserQuestion` is anchored on a 200-column
212
+ * U+2500 rule row, and `stripBoxDrawing` blanks exactly that row — so the
213
+ * reading that recognises the screen answers `null` on the spelling this
214
+ * function takes, however plainly the dialog is on the pane. The frame the
215
+ * cleaning started from is therefore passed alongside it: the caller has it in
216
+ * hand from the same tick, no second capture is taken, and `stripBoxDrawing`
217
+ * (which is not idempotent) still runs exactly once per tick, upstream.
218
+ *
219
+ * Omitting `rawFrame` is not an error and not a silent downgrade for anything
220
+ * else: only Command Code's reader consults it, and a caller that has no raw
221
+ * frame for this tool reaches the same `null` the old code did.
222
+ *
208
223
  * @param cleanOutput - tmux output with ANSI **and** box drawing already removed
209
224
  * @param cliToolId - CLI tool identifier for building detection options
210
225
  * @param precomputedLines - `cleanOutput.split('\n')` when the caller already has it
211
226
  * (Issue #499 Item 4); must be the split of THIS string, not of the raw capture
227
+ * @param rawFrame - the SAME tick's capture with its box drawing intact (ANSI
228
+ * optional), for the tool readers anchored on it (Issue #2522)
212
229
  * @returns PromptDetectionResult with isPrompt, promptData, and cleanContent
213
230
  */
214
- function detectPromptOnCleanFrame(cleanOutput, cliToolId, precomputedLines) {
231
+ function detectPromptOnCleanFrame(cleanOutput, cliToolId, precomputedLines, rawFrame) {
215
232
  // Issue #2364: agy's `↑/↓ Navigate` dialogs are read by agy's own reader
216
233
  // before the generic pass, on the same spelling `tools/antigravity/detect.ts`
217
234
  // reads them on. The generic multiple-choice parser takes one row per option
@@ -232,6 +249,31 @@ function detectPromptOnCleanFrame(cleanOutput, cliToolId, precomputedLines) {
232
249
  if (dialog !== null)
233
250
  return dialog;
234
251
  }
252
+ // Issue #2522: Command Code's footer-less `AskUserQuestion`, read by the same
253
+ // module `tools/command-code/detect.ts` publishes its status from — so the
254
+ // status API, the row this poller stores, the push notification's excerpt and
255
+ // `/prompt-response`'s re-verification all describe ONE screen with one
256
+ // question, one option list and one default.
257
+ //
258
+ // Ahead of the generic pass rather than after it, and both halves matter:
259
+ //
260
+ // - `prompt` — the generic parser SUCCEEDS on the short, unwrapped spelling
261
+ // of this screen and drags the tab strip and the transcript row above it
262
+ // into the question, so "fall back to the reader" would leave the frames
263
+ // that look fine looking wrong;
264
+ // - `unsupported` — the question UI is up and the reading declined (a gap in
265
+ // the numbering, an over-tall region). 確定仕様 B: no `promptData`, and
266
+ // explicitly NOT the generic parser's partial list either. The status path
267
+ // publishes #2521's manual-operation fallback for the same frame, so a
268
+ // human is still told to answer it at the pane.
269
+ if (cliToolId === 'command-code' && rawFrame !== undefined) {
270
+ const reading = (0, dialog_2.readCommandCodeQuestionDialog)(rawFrame);
271
+ if (reading.kind === 'prompt')
272
+ return reading.prompt;
273
+ if (reading.kind === 'unsupported') {
274
+ return { isPrompt: false, cleanContent: cleanOutput.trim() };
275
+ }
276
+ }
235
277
  const promptOptions = (0, cli_patterns_1.buildDetectPromptOptions)(cliToolId);
236
278
  return (0, prompt_detector_1.detectPrompt)(cleanOutput, precomputedLines ? { ...promptOptions, precomputedLines } : promptOptions);
237
279
  }
@@ -295,7 +337,11 @@ function isNumberedDialogVouched(cliToolId, promptDetection, frame) {
295
337
  * @returns PromptDetectionResult with isPrompt, promptData, and cleanContent
296
338
  */
297
339
  function detectPromptWithOptions(output, cliToolId) {
298
- return detectPromptOnCleanFrame((0, cli_patterns_1.stripBoxDrawing)((0, cli_patterns_1.stripAnsi)(output)), cliToolId);
340
+ // Issue #2522: `output` is the capture, so the box-drawing-bearing spelling is
341
+ // right here and is handed on as `rawFrame`. Nothing is captured twice and
342
+ // nothing is cleaned twice — the fourth argument is the string the first one
343
+ // was DERIVED from.
344
+ return detectPromptOnCleanFrame((0, cli_patterns_1.stripBoxDrawing)((0, cli_patterns_1.stripAnsi)(output)), cliToolId, undefined, output);
299
345
  }
300
346
  // ============================================================================
301
347
  // extractResponse (internal)