@proletariat/cli 0.3.16 → 0.3.18

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 (338) hide show
  1. package/dist/commands/action/create.d.ts +1 -0
  2. package/dist/commands/action/create.js +74 -38
  3. package/dist/commands/action/delete.d.ts +1 -0
  4. package/dist/commands/action/delete.js +23 -24
  5. package/dist/commands/action/index.d.ts +1 -0
  6. package/dist/commands/action/index.js +5 -10
  7. package/dist/commands/action/list.d.ts +1 -0
  8. package/dist/commands/action/list.js +3 -1
  9. package/dist/commands/action/run.d.ts +1 -0
  10. package/dist/commands/action/run.js +44 -32
  11. package/dist/commands/action/show.d.ts +2 -0
  12. package/dist/commands/action/update.d.ts +1 -0
  13. package/dist/commands/action/update.js +80 -39
  14. package/dist/commands/agent/auth.d.ts +2 -0
  15. package/dist/commands/agent/auth.js +44 -3
  16. package/dist/commands/agent/discover.d.ts +2 -0
  17. package/dist/commands/agent/discover.js +35 -3
  18. package/dist/commands/agent/index.d.ts +1 -0
  19. package/dist/commands/agent/index.js +25 -45
  20. package/dist/commands/agent/list.d.ts +8 -3
  21. package/dist/commands/agent/list.js +16 -29
  22. package/dist/commands/agent/login.d.ts +1 -0
  23. package/dist/commands/agent/login.js +14 -32
  24. package/dist/commands/agent/rebuild.d.ts +1 -0
  25. package/dist/commands/agent/rebuild.js +2 -2
  26. package/dist/commands/agent/remove.d.ts +17 -0
  27. package/dist/commands/agent/remove.js +144 -0
  28. package/dist/commands/agent/restart.d.ts +1 -0
  29. package/dist/commands/agent/restart.js +2 -2
  30. package/dist/commands/agent/shell.d.ts +1 -0
  31. package/dist/commands/agent/shell.js +63 -76
  32. package/dist/commands/agent/staff/add.d.ts +1 -0
  33. package/dist/commands/agent/staff/add.js +7 -1
  34. package/dist/commands/agent/staff/index.d.ts +1 -0
  35. package/dist/commands/agent/staff/index.js +5 -4
  36. package/dist/commands/agent/staff/remove.d.ts +1 -0
  37. package/dist/commands/agent/status.d.ts +1 -0
  38. package/dist/commands/agent/status.js +11 -23
  39. package/dist/commands/agent/temp/cleanup.d.ts +1 -0
  40. package/dist/commands/agent/temp/index.d.ts +1 -0
  41. package/dist/commands/agent/temp/index.js +4 -3
  42. package/dist/commands/agent/themes/index.d.ts +1 -0
  43. package/dist/commands/agent/themes/index.js +9 -3
  44. package/dist/commands/agent/themes/set.d.ts +1 -0
  45. package/dist/commands/agent/themes/set.js +7 -1
  46. package/dist/commands/agent/visit.d.ts +1 -0
  47. package/dist/commands/agent/visit.js +11 -23
  48. package/dist/commands/autocomplete/setup.d.ts +11 -0
  49. package/dist/commands/autocomplete/setup.js +113 -8
  50. package/dist/commands/board/index.d.ts +4 -0
  51. package/dist/commands/board/index.js +32 -30
  52. package/dist/commands/board/watch.d.ts +2 -0
  53. package/dist/commands/branch/create.d.ts +1 -0
  54. package/dist/commands/branch/create.js +33 -41
  55. package/dist/commands/branch/index.d.ts +1 -0
  56. package/dist/commands/branch/list.d.ts +2 -0
  57. package/dist/commands/branch/validate.d.ts +2 -0
  58. package/dist/commands/branch/where.d.ts +1 -0
  59. package/dist/commands/claude.d.ts +6 -0
  60. package/dist/commands/claude.js +166 -116
  61. package/dist/commands/commit.d.ts +6 -0
  62. package/dist/commands/commit.js +68 -73
  63. package/dist/commands/config/index.d.ts +13 -0
  64. package/dist/commands/config/index.js +142 -98
  65. package/dist/commands/docker/clean.d.ts +2 -1
  66. package/dist/commands/docker/clean.js +20 -29
  67. package/dist/commands/docker/index.d.ts +1 -0
  68. package/dist/commands/docker/index.js +37 -41
  69. package/dist/commands/docker/prune.d.ts +2 -1
  70. package/dist/commands/docker/prune.js +20 -27
  71. package/dist/commands/docker/restart.d.ts +2 -1
  72. package/dist/commands/docker/restart.js +20 -29
  73. package/dist/commands/docker/stop.d.ts +2 -1
  74. package/dist/commands/docker/stop.js +20 -29
  75. package/dist/commands/epic/activate.d.ts +1 -0
  76. package/dist/commands/epic/archive.d.ts +1 -0
  77. package/dist/commands/epic/create.d.ts +1 -0
  78. package/dist/commands/epic/index.d.ts +1 -0
  79. package/dist/commands/epic/link/block.d.ts +1 -0
  80. package/dist/commands/epic/link/duplicates.d.ts +1 -0
  81. package/dist/commands/epic/link/index.d.ts +1 -0
  82. package/dist/commands/epic/link/relates.d.ts +1 -0
  83. package/dist/commands/epic/link/remove.d.ts +1 -0
  84. package/dist/commands/epic/list.d.ts +2 -0
  85. package/dist/commands/epic/move.d.ts +1 -0
  86. package/dist/commands/epic/progress.d.ts +1 -0
  87. package/dist/commands/epic/project.d.ts +1 -0
  88. package/dist/commands/epic/reorder.d.ts +1 -0
  89. package/dist/commands/epic/spec.d.ts +1 -0
  90. package/dist/commands/epic/ticket.d.ts +1 -0
  91. package/dist/commands/epic/view.d.ts +1 -0
  92. package/dist/commands/execution/index.d.ts +1 -0
  93. package/dist/commands/execution/index.js +9 -25
  94. package/dist/commands/execution/list.d.ts +2 -0
  95. package/dist/commands/execution/logs.d.ts +1 -0
  96. package/dist/commands/execution/logs.js +6 -16
  97. package/dist/commands/execution/stop.d.ts +1 -0
  98. package/dist/commands/execution/stop.js +4 -15
  99. package/dist/commands/gh/index.d.ts +1 -0
  100. package/dist/commands/gh/index.js +27 -27
  101. package/dist/commands/gh/login.d.ts +4 -0
  102. package/dist/commands/gh/login.js +31 -0
  103. package/dist/commands/gh/status.d.ts +4 -0
  104. package/dist/commands/gh/status.js +27 -4
  105. package/dist/commands/gh/token.d.ts +4 -0
  106. package/dist/commands/gh/token.js +49 -5
  107. package/dist/commands/phase/create.d.ts +1 -1
  108. package/dist/commands/phase/create.js +116 -74
  109. package/dist/commands/phase/delete.d.ts +1 -0
  110. package/dist/commands/phase/delete.js +23 -22
  111. package/dist/commands/phase/list.d.ts +1 -0
  112. package/dist/commands/phase/list.js +3 -5
  113. package/dist/commands/phase/move.d.ts +1 -0
  114. package/dist/commands/phase/move.js +39 -39
  115. package/dist/commands/phase/template/apply.d.ts +1 -0
  116. package/dist/commands/phase/template/create.d.ts +2 -0
  117. package/dist/commands/phase/template/delete.d.ts +1 -0
  118. package/dist/commands/phase/template/index.d.ts +1 -0
  119. package/dist/commands/phase/template/list.d.ts +1 -0
  120. package/dist/commands/phase/template/update.d.ts +2 -0
  121. package/dist/commands/phase/update.d.ts +1 -1
  122. package/dist/commands/phase/update.js +89 -55
  123. package/dist/commands/pmo/init.d.ts +2 -0
  124. package/dist/commands/pmo/init.js +84 -22
  125. package/dist/commands/pr/create.d.ts +12 -3
  126. package/dist/commands/pr/create.js +130 -147
  127. package/dist/commands/pr/index.d.ts +6 -3
  128. package/dist/commands/pr/index.js +41 -39
  129. package/dist/commands/pr/link.d.ts +7 -3
  130. package/dist/commands/pr/link.js +126 -150
  131. package/dist/commands/pr/status.d.ts +6 -3
  132. package/dist/commands/pr/status.js +101 -126
  133. package/dist/commands/project/archive.d.ts +1 -0
  134. package/dist/commands/project/archive.js +15 -20
  135. package/dist/commands/project/create.d.ts +1 -0
  136. package/dist/commands/project/create.js +13 -5
  137. package/dist/commands/project/delete.d.ts +1 -0
  138. package/dist/commands/project/delete.js +14 -28
  139. package/dist/commands/project/index.d.ts +1 -0
  140. package/dist/commands/project/index.js +0 -5
  141. package/dist/commands/project/list.d.ts +2 -0
  142. package/dist/commands/project/list.js +21 -3
  143. package/dist/commands/project/spec.d.ts +1 -0
  144. package/dist/commands/project/spec.js +17 -23
  145. package/dist/commands/project/unarchive.d.ts +2 -0
  146. package/dist/commands/project/unarchive.js +21 -2
  147. package/dist/commands/project/view.d.ts +1 -0
  148. package/dist/commands/project/view.js +34 -22
  149. package/dist/commands/repo/add.d.ts +2 -0
  150. package/dist/commands/repo/add.js +44 -1
  151. package/dist/commands/repo/index.d.ts +1 -0
  152. package/dist/commands/repo/index.js +20 -38
  153. package/dist/commands/repo/list.d.ts +2 -0
  154. package/dist/commands/repo/remove.d.ts +1 -0
  155. package/dist/commands/repo/remove.js +45 -63
  156. package/dist/commands/repo/view.d.ts +2 -0
  157. package/dist/commands/repo/view.js +30 -5
  158. package/dist/commands/roadmap/add-project.d.ts +1 -0
  159. package/dist/commands/roadmap/create.d.ts +1 -0
  160. package/dist/commands/roadmap/delete.d.ts +1 -0
  161. package/dist/commands/roadmap/generate.d.ts +1 -0
  162. package/dist/commands/roadmap/index.d.ts +1 -0
  163. package/dist/commands/roadmap/list.d.ts +2 -0
  164. package/dist/commands/roadmap/remove-project.d.ts +1 -0
  165. package/dist/commands/roadmap/reorder.d.ts +1 -0
  166. package/dist/commands/roadmap/update.d.ts +1 -0
  167. package/dist/commands/roadmap/view.d.ts +1 -0
  168. package/dist/commands/session/attach.d.ts +1 -0
  169. package/dist/commands/session/index.d.ts +1 -0
  170. package/dist/commands/session/index.js +8 -25
  171. package/dist/commands/session/list.d.ts +2 -0
  172. package/dist/commands/spec/create.d.ts +1 -1
  173. package/dist/commands/spec/create.js +64 -65
  174. package/dist/commands/spec/index.d.ts +1 -0
  175. package/dist/commands/spec/index.js +36 -22
  176. package/dist/commands/spec/link/depends.d.ts +1 -0
  177. package/dist/commands/spec/link/depends.js +6 -6
  178. package/dist/commands/spec/link/duplicates.d.ts +1 -0
  179. package/dist/commands/spec/link/duplicates.js +6 -6
  180. package/dist/commands/spec/link/index.d.ts +2 -1
  181. package/dist/commands/spec/link/index.js +0 -4
  182. package/dist/commands/spec/link/relates.d.ts +1 -0
  183. package/dist/commands/spec/link/relates.js +6 -6
  184. package/dist/commands/spec/link/remove.d.ts +2 -1
  185. package/dist/commands/spec/link/remove.js +6 -6
  186. package/dist/commands/spec/list.d.ts +2 -0
  187. package/dist/commands/spec/list.js +25 -0
  188. package/dist/commands/spec/plan.d.ts +2 -1
  189. package/dist/commands/spec/plan.js +19 -26
  190. package/dist/commands/spec/ticket.d.ts +2 -1
  191. package/dist/commands/spec/ticket.js +48 -34
  192. package/dist/commands/spec/view.d.ts +2 -1
  193. package/dist/commands/spec/view.js +25 -16
  194. package/dist/commands/status/create.d.ts +1 -1
  195. package/dist/commands/status/create.js +80 -64
  196. package/dist/commands/status/delete.d.ts +2 -1
  197. package/dist/commands/status/delete.js +26 -22
  198. package/dist/commands/status/index.d.ts +1 -0
  199. package/dist/commands/status/index.js +26 -19
  200. package/dist/commands/status/list.d.ts +1 -0
  201. package/dist/commands/status/list.js +12 -7
  202. package/dist/commands/status/move.d.ts +2 -1
  203. package/dist/commands/status/move.js +62 -61
  204. package/dist/commands/status/update.d.ts +2 -2
  205. package/dist/commands/status/update.js +110 -77
  206. package/dist/commands/template/delete.d.ts +1 -0
  207. package/dist/commands/template/delete.js +47 -48
  208. package/dist/commands/template/index.d.ts +1 -0
  209. package/dist/commands/template/index.js +26 -33
  210. package/dist/commands/template/list.d.ts +1 -0
  211. package/dist/commands/template/phase/create.d.ts +1 -0
  212. package/dist/commands/template/phase/create.js +6 -0
  213. package/dist/commands/template/phase/index.d.ts +1 -0
  214. package/dist/commands/template/phase/index.js +27 -26
  215. package/dist/commands/template/phase/update.d.ts +1 -0
  216. package/dist/commands/template/phase/update.js +6 -0
  217. package/dist/commands/template/ticket/index.d.ts +1 -0
  218. package/dist/commands/template/ticket/index.js +27 -26
  219. package/dist/commands/template/ticket/save.d.ts +1 -0
  220. package/dist/commands/template/ticket/save.js +6 -0
  221. package/dist/commands/terminal/title.d.ts +26 -0
  222. package/dist/commands/terminal/title.js +37 -3
  223. package/dist/commands/ticket/bulk.d.ts +1 -0
  224. package/dist/commands/ticket/complete.d.ts +1 -0
  225. package/dist/commands/ticket/complete.js +18 -14
  226. package/dist/commands/ticket/create.d.ts +1 -0
  227. package/dist/commands/ticket/create.js +45 -41
  228. package/dist/commands/ticket/delete.d.ts +1 -0
  229. package/dist/commands/ticket/delete.js +1 -1
  230. package/dist/commands/ticket/edit.d.ts +1 -0
  231. package/dist/commands/ticket/edit.js +1 -1
  232. package/dist/commands/ticket/epic.d.ts +1 -0
  233. package/dist/commands/ticket/epic.js +2 -2
  234. package/dist/commands/ticket/index.d.ts +1 -0
  235. package/dist/commands/ticket/link/block.d.ts +1 -0
  236. package/dist/commands/ticket/link/block.js +1 -1
  237. package/dist/commands/ticket/link/duplicates.d.ts +1 -0
  238. package/dist/commands/ticket/link/duplicates.js +1 -1
  239. package/dist/commands/ticket/link/index.d.ts +1 -0
  240. package/dist/commands/ticket/link/index.js +9 -8
  241. package/dist/commands/ticket/link/relates.d.ts +1 -0
  242. package/dist/commands/ticket/link/relates.js +1 -1
  243. package/dist/commands/ticket/link/remove.d.ts +1 -0
  244. package/dist/commands/ticket/link/remove.js +1 -1
  245. package/dist/commands/ticket/list.d.ts +2 -0
  246. package/dist/commands/ticket/move.d.ts +1 -0
  247. package/dist/commands/ticket/move.js +27 -19
  248. package/dist/commands/ticket/project.d.ts +1 -0
  249. package/dist/commands/ticket/project.js +3 -3
  250. package/dist/commands/ticket/reassign.d.ts +1 -0
  251. package/dist/commands/ticket/reassign.js +1 -1
  252. package/dist/commands/ticket/spec.d.ts +1 -0
  253. package/dist/commands/ticket/spec.js +3 -3
  254. package/dist/commands/ticket/status.d.ts +1 -0
  255. package/dist/commands/ticket/status.js +1 -1
  256. package/dist/commands/ticket/template/apply.d.ts +1 -0
  257. package/dist/commands/ticket/template/create.d.ts +2 -0
  258. package/dist/commands/ticket/template/delete.d.ts +1 -0
  259. package/dist/commands/ticket/template/index.d.ts +1 -0
  260. package/dist/commands/ticket/template/list.d.ts +1 -0
  261. package/dist/commands/ticket/template/save.d.ts +2 -0
  262. package/dist/commands/ticket/update.d.ts +1 -0
  263. package/dist/commands/ticket/update.js +1 -1
  264. package/dist/commands/ticket/view.d.ts +1 -0
  265. package/dist/commands/ticket/view.js +1 -1
  266. package/dist/commands/work/complete.d.ts +1 -0
  267. package/dist/commands/work/index.d.ts +1 -0
  268. package/dist/commands/work/ready.d.ts +1 -0
  269. package/dist/commands/work/revise.d.ts +1 -0
  270. package/dist/commands/work/spawn-all.d.ts +2 -0
  271. package/dist/commands/work/spawn-all.js +11 -4
  272. package/dist/commands/work/spawn.d.ts +1 -0
  273. package/dist/commands/work/spawn.js +261 -166
  274. package/dist/commands/work/start.d.ts +1 -0
  275. package/dist/commands/work/start.js +270 -189
  276. package/dist/commands/work/watch.d.ts +1 -0
  277. package/dist/commands/work/watch.js +63 -58
  278. package/dist/commands/workflow/create.d.ts +1 -0
  279. package/dist/commands/workflow/create.js +2 -4
  280. package/dist/commands/workflow/delete.d.ts +1 -0
  281. package/dist/commands/workflow/delete.js +21 -33
  282. package/dist/commands/workflow/index.d.ts +1 -0
  283. package/dist/commands/workflow/list.d.ts +1 -0
  284. package/dist/commands/workflow/list.js +3 -6
  285. package/dist/commands/workflow/switch.d.ts +2 -0
  286. package/dist/commands/workflow/switch.js +46 -21
  287. package/dist/commands/workflow/view.d.ts +1 -0
  288. package/dist/commands/workflow/view.js +18 -27
  289. package/dist/commands/workspace/remove.d.ts +2 -2
  290. package/dist/commands/workspace/remove.js +16 -21
  291. package/dist/commands/workspace/use.d.ts +2 -2
  292. package/dist/commands/workspace/use.js +12 -18
  293. package/dist/lib/agents/commands.d.ts +1 -1
  294. package/dist/lib/agents/commands.js +4 -4
  295. package/dist/lib/database/drizzle-schema.d.ts +5009 -0
  296. package/dist/lib/database/drizzle-schema.js +699 -0
  297. package/dist/lib/database/drizzle.d.ts +29 -0
  298. package/dist/lib/database/drizzle.js +37 -0
  299. package/dist/lib/database/index.d.ts +1 -0
  300. package/dist/lib/database/index.js +1 -1
  301. package/dist/lib/execution/config.d.ts +6 -0
  302. package/dist/lib/execution/config.js +31 -13
  303. package/dist/lib/execution/devcontainer.js +13 -7
  304. package/dist/lib/execution/runners.js +24 -7
  305. package/dist/lib/execution/spawner.js +19 -0
  306. package/dist/lib/flags/index.d.ts +4 -0
  307. package/dist/lib/flags/index.js +4 -0
  308. package/dist/lib/flags/resolver.d.ts +224 -0
  309. package/dist/lib/flags/resolver.js +313 -0
  310. package/dist/lib/pmo/base-command.d.ts +53 -3
  311. package/dist/lib/pmo/base-command.js +92 -13
  312. package/dist/lib/pmo/find-pmo.d.ts +1 -1
  313. package/dist/lib/pmo/find-pmo.js +4 -4
  314. package/dist/lib/pmo/index.d.ts +1 -1
  315. package/dist/lib/pmo/index.js +1 -1
  316. package/dist/lib/pmo/storage/helpers.js +2 -1
  317. package/dist/lib/pmo/storage/index.d.ts +9 -0
  318. package/dist/lib/pmo/storage/index.js +14 -0
  319. package/dist/lib/pmo/storage/projects.d.ts +28 -13
  320. package/dist/lib/pmo/storage/projects.js +110 -34
  321. package/dist/lib/pmo/storage/roadmaps.d.ts +2 -0
  322. package/dist/lib/pmo/storage/roadmaps.js +182 -111
  323. package/dist/lib/pmo/storage/specs.js +13 -16
  324. package/dist/lib/pmo/storage/subtasks.js +17 -2
  325. package/dist/lib/pmo/storage/tickets.d.ts +12 -2
  326. package/dist/lib/pmo/storage/tickets.js +63 -5
  327. package/dist/lib/pmo/storage/types.d.ts +7 -3
  328. package/dist/lib/pmo/storage/views.d.ts +12 -1
  329. package/dist/lib/pmo/storage/views.js +61 -6
  330. package/dist/lib/prompt-command.d.ts +90 -0
  331. package/dist/lib/prompt-command.js +102 -0
  332. package/dist/lib/prompt-json.d.ts +34 -4
  333. package/dist/lib/prompt-json.js +35 -3
  334. package/dist/lib/repos/index.js +15 -15
  335. package/dist/lib/workspace.d.ts +4 -3
  336. package/dist/lib/workspace.js +3 -3
  337. package/oclif.manifest.json +4610 -2997
  338. package/package.json +13 -5
@@ -7,7 +7,7 @@ import inquirer from 'inquirer';
7
7
  import Database from 'better-sqlite3';
8
8
  import { findHQRoot } from '../lib/workspace.js';
9
9
  import { getWorkspaceInfo, createEphemeralAgent, } from '../lib/agents/commands.js';
10
- import { shouldOutputJson, outputPromptAsJson, outputErrorAsJson, createMetadata, buildPromptConfig, } from '../lib/prompt-json.js';
10
+ import { shouldOutputJson, isAgentMode, outputPromptAsJson, outputErrorAsJson, createMetadata, normalizeChoices, } from '../lib/prompt-json.js';
11
11
  import { styles } from '../lib/styles.js';
12
12
  import { DEFAULT_EXECUTION_CONFIG, } from '../lib/execution/types.js';
13
13
  import { runExecution, isDockerRunning, isGitHubTokenAvailable, isDevcontainerCliInstalled } from '../lib/execution/runners.js';
@@ -88,6 +88,28 @@ export default class Claude extends Command {
88
88
  description: 'Ticket title (inside HQ only)',
89
89
  }),
90
90
  };
91
+ /**
92
+ * Prompt wrapper - handles both JSON mode and interactive mode.
93
+ * In JSON mode: outputs prompt as JSON and exits.
94
+ * In interactive mode: calls inquirer.prompt normally.
95
+ */
96
+ async prompt(questions, jsonModeConfig) {
97
+ if (jsonModeConfig && isAgentMode(jsonModeConfig.flags)) {
98
+ const firstQuestion = questions[0];
99
+ if (firstQuestion) {
100
+ const choices = firstQuestion.choices ? normalizeChoices(firstQuestion.choices) : undefined;
101
+ outputPromptAsJson({
102
+ type: firstQuestion.type,
103
+ name: firstQuestion.name,
104
+ message: firstQuestion.message,
105
+ choices,
106
+ default: firstQuestion.default,
107
+ }, createMetadata(jsonModeConfig.commandName, jsonModeConfig.flags));
108
+ }
109
+ return {};
110
+ }
111
+ return inquirer.prompt(questions);
112
+ }
91
113
  async run() {
92
114
  const { flags } = await this.parse(Claude);
93
115
  const jsonMode = shouldOutputJson(flags);
@@ -119,16 +141,10 @@ export default class Claude extends Command {
119
141
  this.log(styles.muted(' No HQ detected - running without tracking'));
120
142
  this.log('');
121
143
  // Prompt for slug (session name)
144
+ const jsonModeConfig = jsonMode ? { flags: flags, commandName: 'claude' } : null;
122
145
  let slug = flags.slug;
123
146
  if (!slug) {
124
- if (jsonMode) {
125
- outputPromptAsJson({
126
- type: 'input',
127
- name: 'slug',
128
- message: 'Session name (for tab/pane title):',
129
- }, createMetadata('claude', flags));
130
- }
131
- const { inputSlug } = await inquirer.prompt([
147
+ const { inputSlug } = await this.prompt([
132
148
  {
133
149
  type: 'input',
134
150
  name: 'inputSlug',
@@ -136,7 +152,7 @@ export default class Claude extends Command {
136
152
  default: path.basename(workDir),
137
153
  validate: (input) => input.trim() ? true : 'Session name required',
138
154
  },
139
- ]);
155
+ ], jsonModeConfig);
140
156
  slug = inputSlug.trim();
141
157
  }
142
158
  // Determine if devcontainer is available
@@ -146,7 +162,7 @@ export default class Claude extends Command {
146
162
  if (flags.environment) {
147
163
  environment = flags.environment;
148
164
  }
149
- else if (!jsonMode) {
165
+ else {
150
166
  // Check devcontainer prerequisites upfront
151
167
  const dockerRunning = isDockerRunning();
152
168
  const devcontainerCliInstalled = isDevcontainerCliInstalled();
@@ -163,11 +179,36 @@ export default class Claude extends Command {
163
179
  missing.push('devcontainer CLI');
164
180
  devcontainerLabel = `🐳 devcontainer (requires: ${missing.join(', ')})`;
165
181
  }
166
- // Loop to handle Docker not running
182
+ // In JSON mode, output environment prompt and exit
183
+ if (jsonMode) {
184
+ await this.prompt([
185
+ {
186
+ type: 'list',
187
+ name: 'selectedEnv',
188
+ message: 'Where should Claude run?',
189
+ choices: [
190
+ {
191
+ name: devcontainerLabel,
192
+ value: 'devcontainer',
193
+ disabled: !devcontainerReady,
194
+ command: `prlt claude --slug "${slug}" --environment devcontainer --json`,
195
+ },
196
+ {
197
+ name: '💻 host (runs directly on your machine)',
198
+ value: 'host',
199
+ command: `prlt claude --slug "${slug}" --environment host --json`,
200
+ },
201
+ ],
202
+ default: devcontainerReady ? 'devcontainer' : 'host',
203
+ },
204
+ ], jsonModeConfig);
205
+ return; // unreachable, but satisfies TypeScript
206
+ }
207
+ // Interactive mode: loop to handle Docker not running
167
208
  let environmentSelected = false;
168
209
  while (!environmentSelected) {
169
210
  // eslint-disable-next-line no-await-in-loop -- Interactive user prompt in loop
170
- const { selectedEnv } = await inquirer.prompt([
211
+ const { selectedEnv } = await this.prompt([
171
212
  {
172
213
  type: 'list',
173
214
  name: 'selectedEnv',
@@ -182,7 +223,7 @@ export default class Claude extends Command {
182
223
  ],
183
224
  default: devcontainerReady ? 'devcontainer' : 'host',
184
225
  },
185
- ]);
226
+ ], null);
186
227
  if (selectedEnv === 'devcontainer') {
187
228
  // Double-check prerequisites (in case user retried after starting Docker)
188
229
  if (!isDockerRunning()) {
@@ -202,22 +243,18 @@ export default class Claude extends Command {
202
243
  // Check GitHub token is available for git push operations
203
244
  if (!isGitHubTokenAvailable()) {
204
245
  const tokenChoices = [
205
- { name: 'Yes, continue anyway (git push may fail)', value: 'continue' },
246
+ { name: 'Yes, continue anyway (git push may fail)', value: 'continue', command: `prlt claude --slug "${slug}" --environment devcontainer --json` },
206
247
  { name: 'No, let me run gh auth login first', value: 'cancel' },
207
- { name: 'Switch to host mode instead', value: 'host' },
248
+ { name: 'Switch to host mode instead', value: 'host', command: `prlt claude --slug "${slug}" --environment host --json` },
208
249
  ];
209
250
  const tokenMessage = 'GitHub token not found. Git push may fail. Continue without token?';
210
- if (jsonMode) {
211
- outputPromptAsJson(buildPromptConfig('list', 'tokenAction', tokenMessage, tokenChoices), createMetadata('claude', flags));
212
- return;
213
- }
214
251
  this.log('');
215
252
  this.warn('GitHub token not found.\n' +
216
253
  'Git push operations may fail inside the container.\n' +
217
254
  'Run `gh auth login` to authenticate, or continue without token.');
218
255
  this.log('');
219
256
  // eslint-disable-next-line no-await-in-loop -- Interactive user prompt in loop
220
- const { tokenAction } = await inquirer.prompt([
257
+ const { tokenAction } = await this.prompt([
221
258
  {
222
259
  type: 'list',
223
260
  name: 'tokenAction',
@@ -225,7 +262,7 @@ export default class Claude extends Command {
225
262
  choices: tokenChoices,
226
263
  default: 'continue',
227
264
  },
228
- ]);
265
+ ], null);
229
266
  if (tokenAction === 'cancel') {
230
267
  this.log(styles.muted('Run `gh auth login` and try again.'));
231
268
  return;
@@ -247,20 +284,20 @@ export default class Claude extends Command {
247
284
  if (flags['display-mode']) {
248
285
  displayMode = flags['display-mode'];
249
286
  }
250
- else if (!jsonMode) {
251
- const { selectedDisplay } = await inquirer.prompt([
287
+ else {
288
+ const { selectedDisplay } = await this.prompt([
252
289
  {
253
290
  type: 'list',
254
291
  name: 'selectedDisplay',
255
292
  message: 'How should output be displayed?',
256
293
  choices: [
257
- { name: '🖥️ New tab - Opens in new terminal tab (recommended)', value: 'terminal' },
258
- { name: '▶️ Foreground - Run in current terminal (blocking)', value: 'foreground' },
259
- { name: '📦 Background - Runs detached, reattach later', value: 'background' },
294
+ { name: '🖥️ New tab - Opens in new terminal tab (recommended)', value: 'terminal', command: `prlt claude --slug "${slug}" --environment ${environment} --display-mode terminal --json` },
295
+ { name: '▶️ Foreground - Run in current terminal (blocking)', value: 'foreground', command: `prlt claude --slug "${slug}" --environment ${environment} --display-mode foreground --json` },
296
+ { name: '📦 Background - Runs detached, reattach later', value: 'background', command: `prlt claude --slug "${slug}" --environment ${environment} --display-mode background --json` },
260
297
  ],
261
298
  default: 'terminal',
262
299
  },
263
- ]);
300
+ ], jsonModeConfig);
264
301
  displayMode = selectedDisplay;
265
302
  }
266
303
  // Prompt for permission mode
@@ -268,19 +305,19 @@ export default class Claude extends Command {
268
305
  if (flags['permission-mode']) {
269
306
  sandboxed = flags['permission-mode'] === 'safe';
270
307
  }
271
- else if (!jsonMode) {
272
- const { permissionMode } = await inquirer.prompt([
308
+ else {
309
+ const { permissionMode } = await this.prompt([
273
310
  {
274
311
  type: 'list',
275
312
  name: 'permissionMode',
276
313
  message: 'Permission mode:',
277
314
  choices: [
278
- { name: '⚠️ danger - Skip permission checks (faster)', value: 'danger' },
279
- { name: '🔒 safe - Requires approval for dangerous operations', value: 'safe' },
315
+ { name: '⚠️ danger - Skip permission checks (faster)', value: 'danger', command: `prlt claude --slug "${slug}" --environment ${environment} --display-mode ${displayMode} --permission-mode danger --json` },
316
+ { name: '🔒 safe - Requires approval for dangerous operations', value: 'safe', command: `prlt claude --slug "${slug}" --environment ${environment} --display-mode ${displayMode} --permission-mode safe --json` },
280
317
  ],
281
318
  default: 'danger',
282
319
  },
283
- ]);
320
+ ], jsonModeConfig);
284
321
  sandboxed = permissionMode === 'safe';
285
322
  }
286
323
  // Warn about uncommitted changes in danger mode
@@ -289,23 +326,21 @@ export default class Claude extends Command {
289
326
  this.warn('Running in danger mode with uncommitted changes!');
290
327
  this.log(styles.muted(' Consider committing or stashing changes first.'));
291
328
  this.log('');
292
- if (!jsonMode) {
293
- const { proceed } = await inquirer.prompt([
294
- {
295
- type: 'list',
296
- name: 'proceed',
297
- message: 'Continue anyway?',
298
- choices: [
299
- { name: 'Yes, proceed', value: true },
300
- { name: 'No, cancel', value: false },
301
- ],
302
- default: true,
303
- },
304
- ]);
305
- if (!proceed) {
306
- this.log(styles.muted('Cancelled.'));
307
- return;
308
- }
329
+ const { proceed } = await this.prompt([
330
+ {
331
+ type: 'list',
332
+ name: 'proceed',
333
+ message: 'Continue anyway?',
334
+ choices: [
335
+ { name: 'Yes, proceed', value: 'true' },
336
+ { name: 'No, cancel', value: 'false' },
337
+ ],
338
+ default: 'true',
339
+ },
340
+ ], null);
341
+ if (proceed !== 'true') {
342
+ this.log(styles.muted('Cancelled.'));
343
+ return;
309
344
  }
310
345
  }
311
346
  // Build session name
@@ -463,6 +498,7 @@ export default class Claude extends Command {
463
498
  this.error('PMO not found. Run "prlt pmo init" first.');
464
499
  }
465
500
  // Select project
501
+ const jsonModeConfig = jsonMode ? { flags: flags, commandName: 'claude' } : null;
466
502
  let projectId = flags.project;
467
503
  if (!projectId) {
468
504
  const projects = await storage.listProjects();
@@ -474,35 +510,29 @@ export default class Claude extends Command {
474
510
  }
475
511
  this.error('No projects found. Create a project first.');
476
512
  }
477
- if (jsonMode) {
478
- outputPromptAsJson({
479
- type: 'list',
480
- name: 'project',
481
- message: 'Select project for adhoc ticket:',
482
- choices: projects.map((p) => ({ name: `${p.name} (${p.id})`, value: p.id })),
483
- }, createMetadata('claude', flags));
513
+ if (projects.length === 1) {
514
+ projectId = projects[0].id;
515
+ }
516
+ else {
517
+ const { selectedProject } = await this.prompt([
518
+ {
519
+ type: 'list',
520
+ name: 'selectedProject',
521
+ message: 'Select project for adhoc ticket:',
522
+ choices: projects.map((p) => ({
523
+ name: `${p.name} (${p.id})`,
524
+ value: p.id,
525
+ command: `prlt claude --project ${p.id} --json`,
526
+ })),
527
+ },
528
+ ], jsonModeConfig);
529
+ projectId = selectedProject;
484
530
  }
485
- const { selectedProject } = await inquirer.prompt([
486
- {
487
- type: 'list',
488
- name: 'selectedProject',
489
- message: 'Select project for adhoc ticket:',
490
- choices: projects.map((p) => ({ name: `${p.name} (${p.id})`, value: p.id })),
491
- },
492
- ]);
493
- projectId = selectedProject;
494
531
  }
495
532
  // Get ticket title
496
533
  let ticketTitle = flags.title;
497
534
  if (!ticketTitle) {
498
- if (jsonMode) {
499
- outputPromptAsJson({
500
- type: 'input',
501
- name: 'title',
502
- message: 'Ticket title:',
503
- }, createMetadata('claude', flags));
504
- }
505
- const { inputTitle } = await inquirer.prompt([
535
+ const { inputTitle } = await this.prompt([
506
536
  {
507
537
  type: 'input',
508
538
  name: 'inputTitle',
@@ -510,19 +540,19 @@ export default class Claude extends Command {
510
540
  default: `Ad-hoc session: ${path.basename(workDir)}`,
511
541
  validate: (input) => input.trim() ? true : 'Title required',
512
542
  },
513
- ]);
543
+ ], jsonModeConfig);
514
544
  ticketTitle = inputTitle.trim();
515
545
  }
516
546
  // Get optional description
517
547
  let ticketDescription;
518
548
  if (!jsonMode) {
519
- const { inputDesc } = await inquirer.prompt([
549
+ const { inputDesc } = await this.prompt([
520
550
  {
521
551
  type: 'input',
522
552
  name: 'inputDesc',
523
553
  message: 'Description (optional):',
524
554
  },
525
- ]);
555
+ ], null);
526
556
  if (inputDesc.trim()) {
527
557
  ticketDescription = inputDesc.trim();
528
558
  }
@@ -549,11 +579,38 @@ export default class Claude extends Command {
549
579
  if (flags.environment) {
550
580
  environment = flags.environment;
551
581
  }
552
- else if (!jsonMode) {
582
+ else {
583
+ // In JSON mode, output environment prompt and exit
584
+ if (jsonMode) {
585
+ await this.prompt([
586
+ {
587
+ type: 'list',
588
+ name: 'selectedEnv',
589
+ message: 'Where should Claude run?',
590
+ choices: [
591
+ {
592
+ name: devcontainerLabel,
593
+ value: 'devcontainer',
594
+ disabled: !devcontainerReady,
595
+ command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment devcontainer --json`,
596
+ },
597
+ {
598
+ name: '💻 host (runs directly on your machine)',
599
+ value: 'host',
600
+ command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment host --json`,
601
+ },
602
+ ],
603
+ default: devcontainerReady ? 'devcontainer' : 'host',
604
+ },
605
+ ], jsonModeConfig);
606
+ db.close();
607
+ return; // unreachable, but satisfies TypeScript
608
+ }
609
+ // Interactive mode: loop to handle Docker not running
553
610
  let environmentSelected = false;
554
611
  while (!environmentSelected) {
555
612
  // eslint-disable-next-line no-await-in-loop -- Interactive user prompt in loop
556
- const { selectedEnv } = await inquirer.prompt([
613
+ const { selectedEnv } = await this.prompt([
557
614
  {
558
615
  type: 'list',
559
616
  name: 'selectedEnv',
@@ -568,7 +625,7 @@ export default class Claude extends Command {
568
625
  ],
569
626
  default: devcontainerReady ? 'devcontainer' : 'host',
570
627
  },
571
- ]);
628
+ ], null);
572
629
  if (selectedEnv === 'devcontainer') {
573
630
  // Double-check prerequisites (in case user retried after starting Docker)
574
631
  if (!isDockerRunning()) {
@@ -593,18 +650,13 @@ export default class Claude extends Command {
593
650
  { name: 'Switch to host mode instead', value: 'host' },
594
651
  ];
595
652
  const tokenMessage = 'GitHub token not found. Git push may fail. Continue without token?';
596
- if (jsonMode) {
597
- outputPromptAsJson(buildPromptConfig('list', 'tokenAction', tokenMessage, tokenChoices), createMetadata('claude', flags));
598
- db.close();
599
- return;
600
- }
601
653
  this.log('');
602
654
  this.warn('GitHub token not found.\n' +
603
655
  'Git push operations may fail inside the container.\n' +
604
656
  'Run `gh auth login` to authenticate, or continue without token.');
605
657
  this.log('');
606
658
  // eslint-disable-next-line no-await-in-loop -- Interactive user prompt in loop
607
- const { tokenAction } = await inquirer.prompt([
659
+ const { tokenAction } = await this.prompt([
608
660
  {
609
661
  type: 'list',
610
662
  name: 'tokenAction',
@@ -612,7 +664,7 @@ export default class Claude extends Command {
612
664
  choices: tokenChoices,
613
665
  default: 'continue',
614
666
  },
615
- ]);
667
+ ], null);
616
668
  if (tokenAction === 'cancel') {
617
669
  db.close();
618
670
  this.log(styles.muted('Run `gh auth login` and try again.'));
@@ -635,20 +687,20 @@ export default class Claude extends Command {
635
687
  if (flags['display-mode']) {
636
688
  displayMode = flags['display-mode'];
637
689
  }
638
- else if (!jsonMode) {
639
- const { selectedDisplay } = await inquirer.prompt([
690
+ else {
691
+ const { selectedDisplay } = await this.prompt([
640
692
  {
641
693
  type: 'list',
642
694
  name: 'selectedDisplay',
643
695
  message: 'How should output be displayed?',
644
696
  choices: [
645
- { name: '🖥️ New tab - Opens in new terminal tab (recommended)', value: 'terminal' },
646
- { name: '▶️ Foreground - Run in current terminal (blocking)', value: 'foreground' },
647
- { name: '📦 Background - Runs detached, reattach later', value: 'background' },
697
+ { name: '🖥️ New tab - Opens in new terminal tab (recommended)', value: 'terminal', command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment ${environment} --display-mode terminal --json` },
698
+ { name: '▶️ Foreground - Run in current terminal (blocking)', value: 'foreground', command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment ${environment} --display-mode foreground --json` },
699
+ { name: '📦 Background - Runs detached, reattach later', value: 'background', command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment ${environment} --display-mode background --json` },
648
700
  ],
649
701
  default: 'terminal',
650
702
  },
651
- ]);
703
+ ], jsonModeConfig);
652
704
  displayMode = selectedDisplay;
653
705
  }
654
706
  // Prompt for permission mode
@@ -656,20 +708,20 @@ export default class Claude extends Command {
656
708
  if (flags['permission-mode']) {
657
709
  sandboxed = flags['permission-mode'] === 'safe';
658
710
  }
659
- else if (!jsonMode) {
711
+ else {
660
712
  const containerNote = environment === 'devcontainer' ? ' (container provides additional isolation)' : '';
661
- const { permissionMode } = await inquirer.prompt([
713
+ const { permissionMode } = await this.prompt([
662
714
  {
663
715
  type: 'list',
664
716
  name: 'permissionMode',
665
717
  message: `Permission mode${containerNote}:`,
666
718
  choices: [
667
- { name: '⚠️ danger - Skip permission checks (faster)', value: 'danger' },
668
- { name: '🔒 safe - Requires approval for dangerous operations', value: 'safe' },
719
+ { name: '⚠️ danger - Skip permission checks (faster)', value: 'danger', command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment ${environment} --display-mode ${displayMode} --permission-mode danger --json` },
720
+ { name: '🔒 safe - Requires approval for dangerous operations', value: 'safe', command: `prlt claude --project ${projectId} --title "${ticketTitle}" --environment ${environment} --display-mode ${displayMode} --permission-mode safe --json` },
669
721
  ],
670
722
  default: 'danger',
671
723
  },
672
- ]);
724
+ ], jsonModeConfig);
673
725
  sandboxed = permissionMode === 'safe';
674
726
  }
675
727
  // Warn about uncommitted changes in danger mode
@@ -678,24 +730,22 @@ export default class Claude extends Command {
678
730
  this.warn('Running in danger mode with uncommitted changes!');
679
731
  this.log(styles.muted(' Consider committing or stashing changes first.'));
680
732
  this.log('');
681
- if (!jsonMode) {
682
- const { proceed } = await inquirer.prompt([
683
- {
684
- type: 'list',
685
- name: 'proceed',
686
- message: 'Continue anyway?',
687
- choices: [
688
- { name: 'Yes, proceed', value: true },
689
- { name: 'No, cancel', value: false },
690
- ],
691
- default: true,
692
- },
693
- ]);
694
- if (!proceed) {
695
- this.log(styles.muted('Cancelled.'));
696
- db.close();
697
- return;
698
- }
733
+ const { proceed } = await this.prompt([
734
+ {
735
+ type: 'list',
736
+ name: 'proceed',
737
+ message: 'Continue anyway?',
738
+ choices: [
739
+ { name: 'Yes, proceed', value: 'true' },
740
+ { name: 'No, cancel', value: 'false' },
741
+ ],
742
+ default: 'true',
743
+ },
744
+ ], null);
745
+ if (proceed !== 'true') {
746
+ this.log(styles.muted('Cancelled.'));
747
+ db.close();
748
+ return;
699
749
  }
700
750
  }
701
751
  // Now create ticket (after all prompts so user can cancel early without orphaned ticket)
@@ -66,6 +66,12 @@ export default class Commit extends Command {
66
66
  'dry-run': import("@oclif/core/interfaces").BooleanFlag<boolean>;
67
67
  json: import("@oclif/core/interfaces").BooleanFlag<boolean>;
68
68
  };
69
+ /**
70
+ * Prompt wrapper - handles both JSON mode and interactive mode.
71
+ * In JSON mode: outputs prompt as JSON and exits.
72
+ * In interactive mode: calls inquirer.prompt normally.
73
+ */
74
+ private prompt;
69
75
  run(): Promise<void>;
70
76
  }
71
77
  export {};