@quickchatai/quickreview 1.1.0 → 1.3.1

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 (471) hide show
  1. package/README.md +137 -57
  2. package/bin/qcr.js +1 -1
  3. package/config.example.toml +60 -14
  4. package/deploy/ansible/README.md +20 -12
  5. package/deploy/ansible/inventory.example.ini +1 -1
  6. package/deploy/collect-secrets.sh +1 -1
  7. package/deploy/qcr-update.sh +1 -1
  8. package/dist/extensions/cli/home.js +14 -0
  9. package/dist/extensions/cli/home.js.map +1 -0
  10. package/dist/extensions/cli/login-route.js +5 -0
  11. package/dist/extensions/cli/login-route.js.map +1 -0
  12. package/dist/extensions/cli/selfimprove.js +18 -0
  13. package/dist/extensions/cli/selfimprove.js.map +1 -0
  14. package/dist/extensions/home.js +350 -0
  15. package/dist/extensions/home.js.map +1 -0
  16. package/dist/extensions/login-route.js +180 -0
  17. package/dist/extensions/login-route.js.map +1 -0
  18. package/dist/extensions/onboarding.js +35 -11
  19. package/dist/extensions/onboarding.js.map +1 -1
  20. package/dist/extensions/selfimprove.js +49 -0
  21. package/dist/extensions/selfimprove.js.map +1 -0
  22. package/dist/extensions/setup-scan.js +23 -592
  23. package/dist/extensions/setup-scan.js.map +1 -1
  24. package/dist/extensions/setup.js +2 -47
  25. package/dist/extensions/setup.js.map +1 -1
  26. package/dist/src/archive/restore.js +18 -15
  27. package/dist/src/archive/restore.js.map +1 -1
  28. package/dist/src/botworker.js +13 -2
  29. package/dist/src/botworker.js.map +1 -1
  30. package/dist/src/channelfs.js +3 -26
  31. package/dist/src/channelfs.js.map +1 -1
  32. package/dist/src/ciretry.js +2 -1
  33. package/dist/src/ciretry.js.map +1 -1
  34. package/dist/src/cli.js +54 -61
  35. package/dist/src/cli.js.map +1 -1
  36. package/dist/src/cliops.js +3 -2
  37. package/dist/src/cliops.js.map +1 -1
  38. package/dist/src/commands.js +25 -2
  39. package/dist/src/commands.js.map +1 -1
  40. package/dist/src/config.js +32 -2
  41. package/dist/src/config.js.map +1 -1
  42. package/dist/src/daemon.js +50 -8
  43. package/dist/src/daemon.js.map +1 -1
  44. package/dist/src/debuground.js +1 -0
  45. package/dist/src/debuground.js.map +1 -1
  46. package/dist/src/debugroundpi.js +6 -1
  47. package/dist/src/debugroundpi.js.map +1 -1
  48. package/dist/src/dispatch.js +5 -4
  49. package/dist/src/dispatch.js.map +1 -1
  50. package/dist/src/engine/caserunner-sdk.js +15 -251
  51. package/dist/src/engine/caserunner-sdk.js.map +1 -1
  52. package/dist/src/engine/debugpi.js +17 -5
  53. package/dist/src/engine/debugpi.js.map +1 -1
  54. package/dist/src/execboundary.js +10 -3
  55. package/dist/src/execboundary.js.map +1 -1
  56. package/dist/src/github.js +51 -16
  57. package/dist/src/github.js.map +1 -1
  58. package/dist/src/githubtoken.js +346 -0
  59. package/dist/src/githubtoken.js.map +1 -0
  60. package/dist/src/home/adapters.js +349 -0
  61. package/dist/src/home/adapters.js.map +1 -0
  62. package/dist/src/home/advanced.js +318 -0
  63. package/dist/src/home/advanced.js.map +1 -0
  64. package/dist/src/home/advancedtools.js +57 -0
  65. package/dist/src/home/advancedtools.js.map +1 -0
  66. package/dist/src/home/autoreview.js +325 -0
  67. package/dist/src/home/autoreview.js.map +1 -0
  68. package/dist/src/home/daemonstatus.js +32 -0
  69. package/dist/src/home/daemonstatus.js.map +1 -0
  70. package/dist/src/home/devicelogin.js +61 -0
  71. package/dist/src/home/devicelogin.js.map +1 -0
  72. package/dist/src/home/launch.js +202 -0
  73. package/dist/src/home/launch.js.map +1 -0
  74. package/dist/src/home/loginowner.js +205 -0
  75. package/dist/src/home/loginowner.js.map +1 -0
  76. package/dist/src/home/memory.js +122 -0
  77. package/dist/src/home/memory.js.map +1 -0
  78. package/dist/src/home/model.js +811 -0
  79. package/dist/src/home/model.js.map +1 -0
  80. package/dist/src/home/panel.js +520 -0
  81. package/dist/src/home/panel.js.map +1 -0
  82. package/dist/src/home/ports.js +19 -0
  83. package/dist/src/home/ports.js.map +1 -0
  84. package/dist/src/home/review.js +163 -0
  85. package/dist/src/home/review.js.map +1 -0
  86. package/dist/src/home/reviews.js +478 -0
  87. package/dist/src/home/reviews.js.map +1 -0
  88. package/dist/src/home/setup.js +507 -0
  89. package/dist/src/home/setup.js.map +1 -0
  90. package/dist/src/home/setupadapters.js +214 -0
  91. package/dist/src/home/setupadapters.js.map +1 -0
  92. package/dist/src/home/setupcard.js +199 -0
  93. package/dist/src/home/setupcard.js.map +1 -0
  94. package/dist/src/home/setuptools.js +45 -0
  95. package/dist/src/home/setuptools.js.map +1 -0
  96. package/dist/src/home/spend.js +160 -0
  97. package/dist/src/home/spend.js.map +1 -0
  98. package/dist/src/home/switches.js +209 -0
  99. package/dist/src/home/switches.js.map +1 -0
  100. package/dist/src/home/switchon.js +439 -0
  101. package/dist/src/home/switchon.js.map +1 -0
  102. package/dist/src/home/toolnames.js +41 -0
  103. package/dist/src/home/toolnames.js.map +1 -0
  104. package/dist/src/home/tune.js +341 -0
  105. package/dist/src/home/tune.js.map +1 -0
  106. package/dist/src/home/words.js +7 -0
  107. package/dist/src/home/words.js.map +1 -0
  108. package/dist/src/homes.js +14 -0
  109. package/dist/src/homes.js.map +1 -1
  110. package/dist/src/install.js +1 -1
  111. package/dist/src/install.js.map +1 -1
  112. package/dist/src/ipc/workerspec.js +8 -0
  113. package/dist/src/ipc/workerspec.js.map +1 -1
  114. package/dist/src/live/publish.js +1 -1
  115. package/dist/src/live/publish.js.map +1 -1
  116. package/dist/src/livecli.js +1 -1
  117. package/dist/src/livecli.js.map +1 -1
  118. package/dist/src/loginhint.js +8 -3
  119. package/dist/src/loginhint.js.map +1 -1
  120. package/dist/src/loginrefresh/handover.js +121 -0
  121. package/dist/src/loginrefresh/handover.js.map +1 -0
  122. package/dist/src/loginrefresh/lock.js +54 -3
  123. package/dist/src/loginrefresh/lock.js.map +1 -1
  124. package/dist/src/loginrefresh/pirefresh.js +3 -0
  125. package/dist/src/loginrefresh/pirefresh.js.map +1 -1
  126. package/dist/src/loginrefresh/refresher.js +33 -5
  127. package/dist/src/loginrefresh/refresher.js.map +1 -1
  128. package/dist/src/loginrefresh/supervisor.js +18 -1
  129. package/dist/src/loginrefresh/supervisor.js.map +1 -1
  130. package/dist/src/npmverbs.js +46 -14
  131. package/dist/src/npmverbs.js.map +1 -1
  132. package/dist/src/onboard/choices.js +35 -4
  133. package/dist/src/onboard/choices.js.map +1 -1
  134. package/dist/src/onboard/engine.js +32 -306
  135. package/dist/src/onboard/engine.js.map +1 -1
  136. package/dist/src/onboard/pipin.js +22 -0
  137. package/dist/src/onboard/pipin.js.map +1 -0
  138. package/dist/src/onboard/stepforward.js +41 -0
  139. package/dist/src/onboard/stepforward.js.map +1 -0
  140. package/dist/src/onboard/steps/appslug.js +4 -1
  141. package/dist/src/onboard/steps/appslug.js.map +1 -1
  142. package/dist/src/onboard/steps/bringup.js +3 -2
  143. package/dist/src/onboard/steps/bringup.js.map +1 -1
  144. package/dist/src/onboard/steps/compose.js +29 -0
  145. package/dist/src/onboard/steps/compose.js.map +1 -1
  146. package/dist/src/onboard/steps/configfill.js +120 -39
  147. package/dist/src/onboard/steps/configfill.js.map +1 -1
  148. package/dist/src/onboard/steps/githubaccount.js +595 -0
  149. package/dist/src/onboard/steps/githubaccount.js.map +1 -0
  150. package/dist/src/onboard/steps/githubapp.js +65 -7
  151. package/dist/src/onboard/steps/githubapp.js.map +1 -1
  152. package/dist/src/onboard/steps/golive.js +2 -0
  153. package/dist/src/onboard/steps/golive.js.map +1 -1
  154. package/dist/src/onboard/steps/index.js +11 -0
  155. package/dist/src/onboard/steps/index.js.map +1 -1
  156. package/dist/src/onboard/steps/ingress.js +80 -25
  157. package/dist/src/onboard/steps/ingress.js.map +1 -1
  158. package/dist/src/onboard/steps/llmauth.js +103 -30
  159. package/dist/src/onboard/steps/llmauth.js.map +1 -1
  160. package/dist/src/onboard/steps/loginshare.js +213 -0
  161. package/dist/src/onboard/steps/loginshare.js.map +1 -0
  162. package/dist/src/onboard/steps/memory.js +67 -3
  163. package/dist/src/onboard/steps/memory.js.map +1 -1
  164. package/dist/src/onboard/steps/proof.js +366 -56
  165. package/dist/src/onboard/steps/proof.js.map +1 -1
  166. package/dist/src/onboard/steps/repoconfig.js +72 -0
  167. package/dist/src/onboard/steps/repoconfig.js.map +1 -0
  168. package/dist/src/onboard/steps/topology.js +6 -6
  169. package/dist/src/onboard/steps/topology.js.map +1 -1
  170. package/dist/src/onboard/steps/transport.js +9 -1
  171. package/dist/src/onboard/steps/transport.js.map +1 -1
  172. package/dist/src/onboard/steps/tuiroute.js +102 -0
  173. package/dist/src/onboard/steps/tuiroute.js.map +1 -0
  174. package/dist/src/onboard/steps/verifyup.js +17 -1
  175. package/dist/src/onboard/steps/verifyup.js.map +1 -1
  176. package/dist/src/onboard/toolnames.js +30 -0
  177. package/dist/src/onboard/toolnames.js.map +1 -0
  178. package/dist/src/operatorwrite.js +23 -0
  179. package/dist/src/operatorwrite.js.map +1 -0
  180. package/dist/src/outcomes.js +4 -1
  181. package/dist/src/outcomes.js.map +1 -1
  182. package/dist/src/piagentdir.js +13 -0
  183. package/dist/src/piagentdir.js.map +1 -0
  184. package/dist/src/pilogin.js +31 -16
  185. package/dist/src/pilogin.js.map +1 -1
  186. package/dist/src/posting-journal.js +2 -1
  187. package/dist/src/posting-journal.js.map +1 -1
  188. package/dist/src/posting-outbox.js +6 -2
  189. package/dist/src/posting-outbox.js.map +1 -1
  190. package/dist/src/posting-receipt.js +14 -1
  191. package/dist/src/posting-receipt.js.map +1 -1
  192. package/dist/src/qcrbin.js +16 -11
  193. package/dist/src/qcrbin.js.map +1 -1
  194. package/dist/src/recheck.js +2 -1
  195. package/dist/src/recheck.js.map +1 -1
  196. package/dist/src/reconcile.js +22 -2
  197. package/dist/src/reconcile.js.map +1 -1
  198. package/dist/src/reviewargs.js +122 -0
  199. package/dist/src/reviewargs.js.map +1 -0
  200. package/dist/src/reviewcli.js +7 -161
  201. package/dist/src/reviewcli.js.map +1 -1
  202. package/dist/src/reviewdetach.js +76 -11
  203. package/dist/src/reviewdetach.js.map +1 -1
  204. package/dist/src/reviewhistory.js +32 -6
  205. package/dist/src/reviewhistory.js.map +1 -1
  206. package/dist/src/reviewnow.js +45 -0
  207. package/dist/src/reviewnow.js.map +1 -0
  208. package/dist/src/scancli.js +39 -691
  209. package/dist/src/scancli.js.map +1 -1
  210. package/dist/src/selfimprove.js +66 -0
  211. package/dist/src/selfimprove.js.map +1 -0
  212. package/dist/src/setup/adapters.js +5 -223
  213. package/dist/src/setup/adapters.js.map +1 -1
  214. package/dist/src/setup/caserunner.js +15 -249
  215. package/dist/src/setup/caserunner.js.map +1 -1
  216. package/dist/src/setup/engine.js +32 -341
  217. package/dist/src/setup/engine.js.map +1 -1
  218. package/dist/src/setup/facts.js +3 -592
  219. package/dist/src/setup/facts.js.map +1 -1
  220. package/dist/src/setup/findings.js +3 -947
  221. package/dist/src/setup/findings.js.map +1 -1
  222. package/dist/src/setup/presentation.js +3 -8
  223. package/dist/src/setup/presentation.js.map +1 -1
  224. package/dist/src/setup/scan.js +3 -724
  225. package/dist/src/setup/scan.js.map +1 -1
  226. package/dist/src/setup/scanbuild.js +9 -92
  227. package/dist/src/setup/scanbuild.js.map +1 -1
  228. package/dist/src/setup/scanlease.js +3 -250
  229. package/dist/src/setup/scanlease.js.map +1 -1
  230. package/dist/src/setup/scanreport.js +3 -288
  231. package/dist/src/setup/scanreport.js.map +1 -1
  232. package/dist/src/setup/scanrun.js +3 -1732
  233. package/dist/src/setup/scanrun.js.map +1 -1
  234. package/dist/src/setup/scantree.js +3 -256
  235. package/dist/src/setup/scantree.js.map +1 -1
  236. package/dist/src/setup/stage2request.js +3 -258
  237. package/dist/src/setup/stage2request.js.map +1 -1
  238. package/dist/src/setup/unitcut.js +3 -436
  239. package/dist/src/setup/unitcut.js.map +1 -1
  240. package/dist/src/state.js +2 -0
  241. package/dist/src/state.js.map +1 -1
  242. package/dist/src/statemachine.js +4 -1
  243. package/dist/src/statemachine.js.map +1 -1
  244. package/dist/src/takeover.js +1 -0
  245. package/dist/src/takeover.js.map +1 -1
  246. package/dist/src/takeoverpi.js +15 -1
  247. package/dist/src/takeoverpi.js.map +1 -1
  248. package/dist/src/tui/app.js +49 -0
  249. package/dist/src/tui/app.js.map +1 -1
  250. package/dist/src/tui/board.js +88 -12
  251. package/dist/src/tui/board.js.map +1 -1
  252. package/dist/src/tui/cmdbar.js +4 -1
  253. package/dist/src/tui/cmdbar.js.map +1 -1
  254. package/dist/src/tui/companion.js +76 -11
  255. package/dist/src/tui/companion.js.map +1 -1
  256. package/dist/src/tui/connect.js +7 -1
  257. package/dist/src/tui/connect.js.map +1 -1
  258. package/dist/src/tui/deploytab.js +2 -2
  259. package/dist/src/tui/deploytab.js.map +1 -1
  260. package/dist/src/tui/filters.js +5 -2
  261. package/dist/src/tui/filters.js.map +1 -1
  262. package/dist/src/tui/ghread.js +61 -5
  263. package/dist/src/tui/ghread.js.map +1 -1
  264. package/dist/src/tui/index.js +109 -20
  265. package/dist/src/tui/index.js.map +1 -1
  266. package/dist/src/tui/memforward.js +39 -2
  267. package/dist/src/tui/memforward.js.map +1 -1
  268. package/dist/src/tui/memory.js +3 -16
  269. package/dist/src/tui/memory.js.map +1 -1
  270. package/dist/src/tui/memoryurl.js +22 -0
  271. package/dist/src/tui/memoryurl.js.map +1 -0
  272. package/dist/src/tui/model.js +25 -0
  273. package/dist/src/tui/model.js.map +1 -1
  274. package/dist/src/tui/prpause.js +7 -0
  275. package/dist/src/tui/prpause.js.map +1 -1
  276. package/dist/src/tui/remote.js +7 -1
  277. package/dist/src/tui/remote.js.map +1 -1
  278. package/dist/src/tui/route.js +143 -0
  279. package/dist/src/tui/route.js.map +1 -0
  280. package/dist/src/tui/setupstate.js +32 -0
  281. package/dist/src/tui/setupstate.js.map +1 -0
  282. package/dist/src/tui/sshtriage.js +102 -5
  283. package/dist/src/tui/sshtriage.js.map +1 -1
  284. package/dist/src/tui/theme.js +2 -1
  285. package/dist/src/tui/theme.js.map +1 -1
  286. package/dist/src/tui/unwedge.js +2 -12
  287. package/dist/src/tui/unwedge.js.map +1 -1
  288. package/dist/src/verdicts.js +17 -5
  289. package/dist/src/verdicts.js.map +1 -1
  290. package/dist/src/version.js +1 -1
  291. package/dist/src/version.js.map +1 -1
  292. package/dist/src/webhook.js +12 -1
  293. package/dist/src/webhook.js.map +1 -1
  294. package/dist/src/wire.js +34 -8
  295. package/dist/src/wire.js.map +1 -1
  296. package/dist/src/workerworld.js +11 -1
  297. package/dist/src/workerworld.js.map +1 -1
  298. package/docker/README.md +1 -1
  299. package/docker/companion/entrypoint.sh +20 -1
  300. package/docker/entrypoint.sh +57 -6
  301. package/docker-compose.yml +16 -1
  302. package/extensions/cli/home.ts +14 -0
  303. package/extensions/cli/login-route.ts +10 -0
  304. package/extensions/cli/selfimprove.ts +18 -0
  305. package/extensions/home.ts +484 -0
  306. package/extensions/login-route.ts +220 -0
  307. package/extensions/onboarding.ts +41 -11
  308. package/extensions/selfimprove.ts +65 -0
  309. package/extensions/setup-scan.ts +79 -766
  310. package/extensions/setup.ts +14 -70
  311. package/package.json +6 -4
  312. package/prompts/onboarding.md +58 -18
  313. package/schemas/review-result.v1.json +60 -0
  314. package/scripts/deploy.sh +8 -6
  315. package/scripts/mint-token.sh +25 -4
  316. package/scripts/qcr-host.sh +28 -5
  317. package/scripts/vm-ghcr-login.sh +7 -4
  318. package/src/archive/restore.ts +18 -21
  319. package/src/botworker.ts +13 -2
  320. package/src/channelfs.ts +3 -26
  321. package/src/ciretry.ts +2 -1
  322. package/src/cli.ts +59 -67
  323. package/src/cliops.ts +3 -2
  324. package/src/commands.ts +28 -2
  325. package/src/config.ts +62 -4
  326. package/src/daemon.ts +58 -7
  327. package/src/debuground.ts +3 -0
  328. package/src/debugroundpi.ts +12 -1
  329. package/src/dispatch.ts +5 -4
  330. package/src/engine/caserunner-sdk.ts +29 -314
  331. package/src/engine/debugpi.ts +17 -5
  332. package/src/execboundary.ts +16 -4
  333. package/src/github.ts +57 -15
  334. package/src/githubtoken.ts +435 -0
  335. package/src/home/adapters.ts +418 -0
  336. package/src/home/advanced.ts +421 -0
  337. package/src/home/advancedtools.ts +96 -0
  338. package/src/home/autoreview.ts +385 -0
  339. package/src/home/daemonstatus.ts +55 -0
  340. package/src/home/devicelogin.ts +107 -0
  341. package/src/home/launch.ts +257 -0
  342. package/src/home/loginowner.ts +248 -0
  343. package/src/home/memory.ts +176 -0
  344. package/src/home/model.ts +965 -0
  345. package/src/home/panel.ts +666 -0
  346. package/src/home/ports.ts +338 -0
  347. package/src/home/review.ts +206 -0
  348. package/src/home/reviews.ts +565 -0
  349. package/src/home/setup.ts +689 -0
  350. package/src/home/setupadapters.ts +217 -0
  351. package/src/home/setupcard.ts +288 -0
  352. package/src/home/setuptools.ts +57 -0
  353. package/src/home/spend.ts +194 -0
  354. package/src/home/switches.ts +293 -0
  355. package/src/home/switchon.ts +554 -0
  356. package/src/home/toolnames.ts +46 -0
  357. package/src/home/tune.ts +405 -0
  358. package/src/home/words.ts +8 -0
  359. package/src/homes.ts +17 -0
  360. package/src/install.ts +1 -1
  361. package/src/ipc/workerspec.ts +15 -0
  362. package/src/live/publish.ts +4 -1
  363. package/src/livecli.ts +6 -1
  364. package/src/loginhint.ts +8 -3
  365. package/src/loginrefresh/handover.ts +138 -0
  366. package/src/loginrefresh/lock.ts +72 -3
  367. package/src/loginrefresh/pirefresh.ts +3 -0
  368. package/src/loginrefresh/refresher.ts +34 -5
  369. package/src/loginrefresh/supervisor.ts +25 -2
  370. package/src/npmverbs.ts +55 -13
  371. package/src/onboard/choices.ts +40 -4
  372. package/src/onboard/engine.ts +70 -421
  373. package/src/onboard/pipin.ts +31 -0
  374. package/src/onboard/stepforward.ts +61 -0
  375. package/src/onboard/steps/appslug.ts +4 -1
  376. package/src/onboard/steps/bringup.ts +3 -2
  377. package/src/onboard/steps/compose.ts +31 -0
  378. package/src/onboard/steps/configfill.ts +144 -40
  379. package/src/onboard/steps/githubaccount.ts +716 -0
  380. package/src/onboard/steps/githubapp.ts +92 -8
  381. package/src/onboard/steps/golive.ts +2 -0
  382. package/src/onboard/steps/index.ts +11 -0
  383. package/src/onboard/steps/ingress.ts +98 -31
  384. package/src/onboard/steps/llmauth.ts +114 -29
  385. package/src/onboard/steps/loginshare.ts +258 -0
  386. package/src/onboard/steps/memory.ts +76 -3
  387. package/src/onboard/steps/proof.ts +473 -55
  388. package/src/onboard/steps/repoconfig.ts +85 -0
  389. package/src/onboard/steps/topology.ts +7 -6
  390. package/src/onboard/steps/transport.ts +15 -0
  391. package/src/onboard/steps/tuiroute.ts +119 -0
  392. package/src/onboard/steps/verifyup.ts +20 -1
  393. package/src/onboard/toolnames.ts +34 -0
  394. package/src/operatorwrite.ts +25 -0
  395. package/src/outcomes.ts +8 -1
  396. package/src/piagentdir.ts +12 -0
  397. package/src/pilogin.ts +32 -16
  398. package/src/posting-journal.ts +6 -1
  399. package/src/posting-outbox.ts +10 -2
  400. package/src/posting-receipt.ts +17 -0
  401. package/src/qcrbin.ts +16 -11
  402. package/src/recheck.ts +2 -1
  403. package/src/reconcile.ts +29 -3
  404. package/src/reviewargs.ts +119 -0
  405. package/src/reviewcli.ts +6 -167
  406. package/src/reviewdetach.ts +107 -13
  407. package/src/reviewhistory.ts +20 -6
  408. package/src/reviewnow.ts +76 -0
  409. package/src/scancli.ts +75 -826
  410. package/src/selfimprove.ts +90 -0
  411. package/src/setup/adapters.ts +13 -221
  412. package/src/setup/caserunner.ts +34 -273
  413. package/src/setup/engine.ts +62 -496
  414. package/src/setup/facts.ts +3 -627
  415. package/src/setup/findings.ts +3 -1264
  416. package/src/setup/presentation.ts +3 -18
  417. package/src/setup/scan.ts +3 -1033
  418. package/src/setup/scanbuild.ts +20 -114
  419. package/src/setup/scanlease.ts +3 -297
  420. package/src/setup/scanreport.ts +3 -373
  421. package/src/setup/scanrun.ts +3 -2268
  422. package/src/setup/scantree.ts +3 -259
  423. package/src/setup/stage2request.ts +3 -347
  424. package/src/setup/unitcut.ts +3 -523
  425. package/src/state.ts +43 -0
  426. package/src/statemachine.ts +4 -1
  427. package/src/takeover.ts +5 -0
  428. package/src/takeoverpi.ts +16 -2
  429. package/src/tui/app.ts +47 -0
  430. package/src/tui/board.ts +111 -14
  431. package/src/tui/cmdbar.ts +4 -1
  432. package/src/tui/companion.ts +80 -11
  433. package/src/tui/connect.ts +7 -1
  434. package/src/tui/deploytab.ts +2 -2
  435. package/src/tui/filters.ts +7 -3
  436. package/src/tui/ghread.ts +74 -7
  437. package/src/tui/index.ts +117 -23
  438. package/src/tui/memforward.ts +52 -3
  439. package/src/tui/memory.ts +3 -15
  440. package/src/tui/memoryurl.ts +22 -0
  441. package/src/tui/model.ts +36 -2
  442. package/src/tui/prpause.ts +11 -2
  443. package/src/tui/remote.ts +9 -1
  444. package/src/tui/route.ts +173 -0
  445. package/src/tui/setupstate.ts +56 -0
  446. package/src/tui/sshtriage.ts +127 -6
  447. package/src/tui/theme.ts +2 -1
  448. package/src/tui/unwedge.ts +2 -14
  449. package/src/verdicts.ts +23 -5
  450. package/src/version.ts +1 -1
  451. package/src/webhook.ts +10 -1
  452. package/src/wire.ts +42 -9
  453. package/src/workerworld.ts +16 -2
  454. package/dist/src/live/projection.js +0 -450
  455. package/dist/src/live/projection.js.map +0 -1
  456. package/dist/src/live/read.js +0 -60
  457. package/dist/src/live/read.js.map +0 -1
  458. package/dist/src/onboard/launch.js +0 -83
  459. package/dist/src/onboard/launch.js.map +0 -1
  460. package/dist/src/setup/ledger.js +0 -207
  461. package/dist/src/setup/ledger.js.map +0 -1
  462. package/dist/src/setup/stage2.js +0 -617
  463. package/dist/src/setup/stage2.js.map +0 -1
  464. package/dist/src/setup/textsniff.js +0 -89
  465. package/dist/src/setup/textsniff.js.map +0 -1
  466. package/src/live/projection.ts +0 -491
  467. package/src/live/read.ts +0 -86
  468. package/src/onboard/launch.ts +0 -115
  469. package/src/setup/ledger.ts +0 -324
  470. package/src/setup/stage2.ts +0 -926
  471. package/src/setup/textsniff.ts +0 -95
@@ -0,0 +1,220 @@
1
+ // login-route — a pi that has no usable model login says so, and opens pi's
2
+ // own /login; a pi whose model names one OpenAI provider while the person
3
+ // logged in with the other runs the same model on the login that exists.
4
+ //
5
+ // Loaded by every CLI pi Quickreview starts for a person: the onboarding
6
+ // wizard (registered by extensions/onboarding.ts, which opens the login for
7
+ // the person), the companion, a takeover and a debug round (the env shim
8
+ // extensions/cli/login-route.ts, which prefills it). An SDK session needs none
9
+ // of this: PiHost routes its model the same way (packages/pi-plugin/src/engine/pisdk.ts).
10
+ //
11
+ // Three behaviours, each on pi's own API:
12
+ // - Model route. On session_start and before every prompt (the `input`
13
+ // event, which pi runs before it checks the model's credential), a model
14
+ // whose provider has no credential is switched to its OpenAI twin when the
15
+ // twin has one and serves the same id (packages/pi-plugin/src/modelroute.ts).
16
+ // The provider the spec names always wins when its login exists, so an
17
+ // install that works today is untouched. pi.setModel does not persist the
18
+ // switch to settings.
19
+ // - Login hint. When no usable model is left, a widget says exactly what to
20
+ // do, and pi's input line holds `/login`, so one Enter opens pi's login.
21
+ // The widget clears once a model is selected (`model_select`).
22
+ // - Open (the wizard only). pi runs `/login` only from its editor's submit
23
+ // (an extension cannot call the command), and the one public way to reach
24
+ // that submit is an editor component: pi wires its own submit handler
25
+ // onto every editor an extension installs. So the login is opened by
26
+ // installing a stock CustomEditor for an instant, submitting `/login`
27
+ // through the handler pi gave it, and restoring the editor that was there.
28
+ // When that wiring is not found, the prefilled `/login` is the fallback.
29
+ import {
30
+ CustomEditor,
31
+ type ExtensionAPI,
32
+ type ExtensionContext,
33
+ type ExtensionFactory,
34
+ type ExtensionUIContext,
35
+ } from "@earendil-works/pi-coding-agent";
36
+ import type { Api, Model } from "@earendil-works/pi-ai";
37
+ import { routeProvider, twinProvider } from "@quickchatai/pi-quickreview/src/modelroute.js";
38
+
39
+ /** The widget key the hint is shown under. */
40
+ export const LOGIN_WIDGET = "qcr-login";
41
+
42
+ /** The command the hint prefills and the wizard submits: pi's own login,
43
+ * with every provider it offers. */
44
+ export const LOGIN_COMMAND = "/login";
45
+
46
+ /** What the person reads above the input line while no model is usable:
47
+ * which logins work and how to reach them in pi's menu (pi 1.4.0's labels),
48
+ * then how to (re)open the menu. `opened` says whether the menu is on screen. */
49
+ export function loginHintLines(opened: boolean): string[] {
50
+ return [
51
+ "Quickreview needs a model login before it can do anything. Any OpenAI login works:",
52
+ ' - "Sign in with an account", then "OpenAI" (Sign in with ChatGPT) or "OpenAI Codex (legacy)";',
53
+ ' - "Sign in with an API key", then type openai, pick "OpenAI" and paste your key (sk-...).',
54
+ opened
55
+ ? `pi's login menu is open below. Closed it? Type ${LOGIN_COMMAND} and press Enter.`
56
+ : `Press Enter to open pi's login menu (${LOGIN_COMMAND} is on the input line).`,
57
+ ];
58
+ }
59
+
60
+ /** How a pi opens the login when it needs one. */
61
+ export type LoginOpen = "submit" | "prefill";
62
+
63
+ export interface LoginRouteConfig {
64
+ /** "submit" opens pi's login menu; "prefill" leaves `/login` on the input
65
+ * line for one Enter. */
66
+ open: LoginOpen;
67
+ }
68
+
69
+ /** The config the env describes: QCR_LOGIN_OPEN=submit, else prefill. */
70
+ export function loginRouteConfigFromEnv(env: NodeJS.ProcessEnv): LoginRouteConfig {
71
+ return { open: env.QCR_LOGIN_OPEN === "submit" ? "submit" : "prefill" };
72
+ }
73
+
74
+ /** What the model route did. */
75
+ export type ModelRouteOutcome =
76
+ /** The current model's provider has a credential. */
77
+ | "usable"
78
+ /** The model was moved to its OpenAI twin, whose login exists. */
79
+ | "switched"
80
+ /** There is a model, and neither it nor a twin has a credential. */
81
+ | "unusable"
82
+ /** There is no model at all. */
83
+ | "none";
84
+
85
+ type Registry = Pick<
86
+ ExtensionContext["modelRegistry"],
87
+ "find" | "getAvailable" | "getProviderAuthStatus"
88
+ >;
89
+
90
+ function hasCredential(registry: Registry, provider: string): boolean {
91
+ try {
92
+ return registry.getProviderAuthStatus(provider).configured;
93
+ } catch {
94
+ return false;
95
+ }
96
+ }
97
+
98
+ /**
99
+ * Keep the session's model on a login that exists: the model as it is when its
100
+ * provider has a credential, else its OpenAI twin when that has one.
101
+ *
102
+ * VERIFY-ON-PIN (pi 1.4.0): ModelRegistry.getProviderAuthStatus(p).configured
103
+ * covers a stored login, a stored or runtime key and an environment key, and
104
+ * the extension pi.setModel returns false (switching nothing) for a provider
105
+ * without a credential.
106
+ */
107
+ export async function routeSessionModel(
108
+ pi: Pick<ExtensionAPI, "setModel">,
109
+ ctx: { model: Model<Api> | undefined; modelRegistry: Registry },
110
+ ): Promise<ModelRouteOutcome> {
111
+ const model = ctx.model;
112
+ if (!model) return "none";
113
+ const registry = ctx.modelRegistry;
114
+ if (hasCredential(registry, model.provider)) return "usable";
115
+ if (twinProvider(model.provider) === undefined) return "unusable";
116
+ const provider = routeProvider(model.provider, model.id, {
117
+ hasCredential: (p) => hasCredential(registry, p),
118
+ hasModel: (p, id) => registry.find(p, id) !== undefined,
119
+ });
120
+ if (provider === model.provider) return "unusable";
121
+ const twin = registry.find(provider, model.id);
122
+ if (twin && (await pi.setModel(twin))) return "switched";
123
+ return "unusable";
124
+ }
125
+
126
+ /** Does this pi need a login: no usable model, and none pi could pick? */
127
+ export function needsLogin(outcome: ModelRouteOutcome, registry: Registry): boolean {
128
+ if (outcome === "usable" || outcome === "switched") return false;
129
+ if (outcome === "unusable") return true;
130
+ try {
131
+ return registry.getAvailable().length === 0;
132
+ } catch {
133
+ return true;
134
+ }
135
+ }
136
+
137
+ type EditorUi = Pick<ExtensionUIContext, "setEditorComponent" | "getEditorComponent">;
138
+ type MakeEditor = Parameters<ExtensionUIContext["setEditorComponent"]>[0] & {};
139
+
140
+ /**
141
+ * Submit `text` through pi's own editor submit, as if typed and Entered. pi
142
+ * runs its built-in commands (`/login` among them) only from that handler, and
143
+ * hands it to every editor component an extension installs: so a stock editor
144
+ * is installed, its handler taken, and the previous editor (pi's default, or
145
+ * another extension's) restored before anything renders. Returns false, having
146
+ * submitted nothing, when pi did not wire a handler.
147
+ *
148
+ * VERIFY-ON-PIN (pi 1.4.0, interactive-mode.js setCustomEditorComponent):
149
+ * `newEditor.onSubmit = this.defaultEditor.onSubmit` runs synchronously inside
150
+ * setEditorComponent, and setEditorComponent(undefined) restores the default
151
+ * editor with its text.
152
+ */
153
+ export function submitThroughEditor(
154
+ ui: EditorUi,
155
+ text: string,
156
+ makeEditor: MakeEditor = (tui, theme, keybindings) => new CustomEditor(tui, theme, keybindings),
157
+ ): boolean {
158
+ let made: { onSubmit?: (text: string) => void } | undefined;
159
+ const previous = ui.getEditorComponent();
160
+ try {
161
+ ui.setEditorComponent((tui, theme, keybindings) => {
162
+ const editor = makeEditor(tui, theme, keybindings);
163
+ made = editor;
164
+ return editor;
165
+ });
166
+ } catch {
167
+ made = undefined;
168
+ }
169
+ const submit = made?.onSubmit;
170
+ ui.setEditorComponent(previous);
171
+ if (typeof submit !== "function") return false;
172
+ void Promise.resolve()
173
+ .then(() => submit(text))
174
+ .catch(() => undefined);
175
+ return true;
176
+ }
177
+
178
+ type HintUi = Pick<ExtensionUIContext, "setWidget" | "setEditorText"> & EditorUi;
179
+
180
+ /** Show the hint and open (or prefill) pi's login. Returns how it was opened. */
181
+ export function openLogin(ui: HintUi, open: LoginOpen): "submitted" | "prefilled" {
182
+ if (open === "submit" && submitThroughEditor(ui, LOGIN_COMMAND)) {
183
+ ui.setWidget(LOGIN_WIDGET, loginHintLines(true), { placement: "aboveEditor" });
184
+ return "submitted";
185
+ }
186
+ ui.setWidget(LOGIN_WIDGET, loginHintLines(false), { placement: "aboveEditor" });
187
+ ui.setEditorText(LOGIN_COMMAND);
188
+ return "prefilled";
189
+ }
190
+
191
+ /** Register the model route and the login hint on `pi`. Exported so a host that
192
+ * builds its own onboarding extension (over `toolDefinitions`) gets the same
193
+ * first-run login as the onboarding wizard. */
194
+ export function registerLoginRoute(pi: ExtensionAPI, config: LoginRouteConfig): void {
195
+ if (typeof pi.on !== "function") return;
196
+ let shown = false;
197
+ pi.on("session_start", async (_event, ctx) => {
198
+ const outcome = await routeSessionModel(pi, ctx);
199
+ if (!ctx.hasUI || !needsLogin(outcome, ctx.modelRegistry)) return;
200
+ shown = true;
201
+ openLogin(ctx.ui, config.open);
202
+ });
203
+ // pi checks the model's credential after this event, so a login made inside
204
+ // the session (its default model stays the spec's provider) is routed here.
205
+ pi.on("input", async (_event, ctx) => {
206
+ await routeSessionModel(pi, ctx);
207
+ return { action: "continue" };
208
+ });
209
+ pi.on("model_select", (_event, ctx) => {
210
+ if (!shown || !ctx.hasUI) return;
211
+ shown = false;
212
+ ctx.ui.setWidget(LOGIN_WIDGET, undefined);
213
+ });
214
+ }
215
+
216
+ /** The factory, for a pi that loads the route by path (its shim) or a host
217
+ * that composes factories. */
218
+ export function createLoginRoute(config: LoginRouteConfig): ExtensionFactory {
219
+ return (pi) => registerLoginRoute(pi, config);
220
+ }
@@ -1,6 +1,8 @@
1
- // onboarding — the wizard's tool belt. Loaded ONLY by `qcr onboard`
2
- // (per spawn, `-e`, alongside --no-extensions — no ambient extension rides the
3
- // onboarding session), never registered globally. pi jiti-loads this TS source
1
+ // onboarding — the wizard's tool belt. Loaded ONLY by a pi started with it
2
+ // named by path (its env shim, extensions/cli/onboarding.ts, as `-e` alongside
3
+ // --no-extensions, so no ambient extension rides that session), never
4
+ // registered globally. No qcr verb starts such a session any more: the home
5
+ // runs the wizard's steps itself (src/home/switchon.ts, Advanced). pi jiti-loads this TS source
4
6
  // on the HOST, so it imports the OnboardingEngine source directly and runs it
5
7
  // in-process: pi talks, these deterministic tools act, and the LLM never
6
8
  // freestyles a shell command (the built-in belt is read-only by argv).
@@ -11,8 +13,7 @@
11
13
  // - finish_and_exit: re-runs the FULL verification; anything red comes back
12
14
  // as the tool result (no exit, ever, while red); all green marks the
13
15
  // checklist complete, writes the companion's first-run marker
14
- // (state/companion/first-run.json), and triggers pi's deferred shutdown —
15
- // the `qcr onboard` process then opens the TUI.
16
+ // (state/companion/first-run.json), and triggers pi's deferred shutdown.
16
17
  //
17
18
  // Convention notes (same shape as companion-guard/tui-view): degrade, never
18
19
  // wedge — a pi without registerTool registers nothing and says so; a missing
@@ -38,7 +39,14 @@ import {
38
39
  type StepStatusLine,
39
40
  } from "../src/onboard/engine.js";
40
41
  import { defaultSteps } from "../src/onboard/steps/index.js";
42
+ import { openStepMemoryForward } from "../src/onboard/stepforward.js";
41
43
  import { locateConfig } from "../src/install.js";
44
+ import { registerLoginRoute } from "./login-route.js";
45
+ import {
46
+ ONBOARD_FINISH_TOOL,
47
+ ONBOARD_STATUS_TOOL,
48
+ onboardStepToolName,
49
+ } from "../src/onboard/toolnames.js";
42
50
 
43
51
  const NO_PARAMS = { type: "object", properties: {} } as const;
44
52
 
@@ -71,6 +79,7 @@ export function realAdapters(root: string): OnboardAdapters {
71
79
  // $QCR_CONFIG, else the install's config home (never the checkout's).
72
80
  paths: { stateDir: join(root, "state"), configPath: locateConfig().path },
73
81
  log: (line) => console.error(line),
82
+ memoryForward: (req) => openStepMemoryForward(req),
74
83
  };
75
84
  }
76
85
 
@@ -89,7 +98,14 @@ export function renderStatus(
89
98
  reconciled: ReconcileReport,
90
99
  ): string {
91
100
  const rows = lines.map((l) => {
92
- const mark = l.status === "done" ? "[done]" : l.status === "disabled" ? "[skipped]" : "[ ]";
101
+ const mark =
102
+ l.status === "done"
103
+ ? "[done]"
104
+ : l.status === "disabled"
105
+ ? "[skipped]"
106
+ : l.optional
107
+ ? "[after setup]"
108
+ : "[ ]";
93
109
  return `${mark} ${l.id} — ${l.title}${l.note ? ` (${l.note})` : ""}`;
94
110
  });
95
111
  const demoted = reconciled.demoted.map(
@@ -114,7 +130,7 @@ export function toolDefinitions(
114
130
  shutdown: (ctx?: Pick<ExtensionToolContext, "shutdown">) => void,
115
131
  ): QcrTool[] {
116
132
  const stepTools: QcrTool[] = engine.stepDefs().map((step) => ({
117
- name: `onboard_${step.id}`,
133
+ name: onboardStepToolName(step.id),
118
134
  label: step.title,
119
135
  description:
120
136
  `${step.explain} Deterministic: runs the "${step.id}" onboarding step's real checks and returns one ✓/✗ line per check. ` +
@@ -141,7 +157,7 @@ export function toolDefinitions(
141
157
  }));
142
158
 
143
159
  const status: QcrTool = {
144
- name: "onboard_status",
160
+ name: ONBOARD_STATUS_TOOL,
145
161
  label: "Onboarding status",
146
162
  description:
147
163
  "The checklist: every step in order with its status. Re-verifies each claimed-done step against reality first " +
@@ -155,7 +171,7 @@ export function toolDefinitions(
155
171
  };
156
172
 
157
173
  const finish: QcrTool = {
158
- name: "finish_and_exit",
174
+ name: ONBOARD_FINISH_TOOL,
159
175
  label: "Finish onboarding",
160
176
  description:
161
177
  "Re-run EVERY verification. While anything is red this refuses and returns the failures — it never exits on red. " +
@@ -167,7 +183,7 @@ export function toolDefinitions(
167
183
  const result = await engine.finish();
168
184
  if (!result.ok) {
169
185
  const red = result.results
170
- .filter((r) => !r.ok)
186
+ .filter((r) => !r.ok && !r.optional)
171
187
  .map((r) => `✗ ${r.id}: ${r.failures.join("; ") || "not verified"}`);
172
188
  return text(
173
189
  `Not finished — these verifications are red:\n${red.join("\n")}\n` +
@@ -182,7 +198,8 @@ export function toolDefinitions(
182
198
  return text(
183
199
  `Every step verified green — onboarding is complete (recorded ${result.completed_at}).\n` +
184
200
  `${result.marker_written ? "First-run marker written for the companion greeting." : "First-run marker already present — left untouched."}\n` +
185
- "This session now shuts down and the TUI opens.",
201
+ "This session now shuts down and the TUI opens: the board lists the repository's open pull requests — " +
202
+ "select one and press R to review it now (dry-run: nothing is posted).",
186
203
  );
187
204
  },
188
205
  };
@@ -208,7 +225,20 @@ export function createOnboarding(config: OnboardingConfig): ExtensionFactory {
208
225
  return (pi) => registerOnboarding(pi, config);
209
226
  }
210
227
 
228
+ /**
229
+ * The onboarding session's first-run login: when pi has no usable model
230
+ * login, pi's own /login menu opens with a widget that says which logins work
231
+ * (any OpenAI one), and an OpenAI model whose provider has no login runs on
232
+ * the twin login that exists (extensions/login-route.ts). The wizard's
233
+ * session registers it with the tools; a host that builds its own onboarding
234
+ * extension over `toolDefinitions` + `registerQcrTool` calls it too.
235
+ */
236
+ export function registerOnboardingSession(pi: ExtensionAPI): void {
237
+ registerLoginRoute(pi, { open: "submit" });
238
+ }
239
+
211
240
  function registerOnboarding(pi: ExtensionAPI, config: OnboardingConfig): void {
241
+ registerOnboardingSession(pi);
212
242
  if (typeof pi.registerTool !== "function") {
213
243
  // Degrade loudly, never wedge: pi still starts, the guide can only talk.
214
244
  console.error(
@@ -0,0 +1,65 @@
1
+ // /selfimprove in the app's own pi (`qcr pi`, src/npmverbs.ts): scan this
2
+ // repo, then have this session's agent fix the findings (src/selfimprove.ts).
3
+ // The plugin, loaded beside it, carries /qcr-review, /qcr-scan and /qcr-setup;
4
+ // this command is the app's (ADR 0001). A factory over its config: the env
5
+ // shim extensions/cli/selfimprove.ts reads the process.
6
+ import {
7
+ getAgentDir,
8
+ type ExtensionAPI,
9
+ type ExtensionCommandContext,
10
+ } from "@earendil-works/pi-coding-agent";
11
+ import { hostAuth, sessionUi } from "@quickchatai/pi-quickreview/extensions/quickreview.js";
12
+ import type { PluginHost, Runner } from "@quickchatai/pi-quickreview/src/plugin/session.js";
13
+ import { runSelfImproveCommand } from "../src/selfimprove.js";
14
+
15
+ export interface SelfImproveConfig {
16
+ /** The process environment, read once by the shim. */
17
+ env: NodeJS.ProcessEnv;
18
+ /** The user's home. */
19
+ home: string;
20
+ runner: Runner;
21
+ /** Standard output (pi's print mode shows a command's result there). */
22
+ print: (text: string) => void;
23
+ /** Test seams: the running pi's version and its agent dir. */
24
+ piVersion?: string;
25
+ agentDir?: string;
26
+ }
27
+
28
+ /** The extension factory: registers /selfimprove, one run at a time. */
29
+ export function createSelfImprove(config: SelfImproveConfig): (pi: ExtensionAPI) => void {
30
+ return (pi) => {
31
+ // The current session's end: a scan in flight stops with it.
32
+ let shutdown = new AbortController();
33
+ pi.on("session_start", () => {
34
+ if (shutdown.signal.aborted) shutdown = new AbortController();
35
+ });
36
+ pi.on("session_shutdown", () => shutdown.abort());
37
+ let busy = false;
38
+ pi.registerCommand("selfimprove", {
39
+ description: "QuickReview: scan this repo, then have this session's agent fix the findings",
40
+ handler: async (args: string, ctx: ExtensionCommandContext) => {
41
+ if (busy) {
42
+ ctx.ui.notify("/selfimprove is already running in this session", "warning");
43
+ return;
44
+ }
45
+ busy = true;
46
+ try {
47
+ const agentDir = config.agentDir ?? getAgentDir();
48
+ const host: PluginHost = {
49
+ cwd: ctx.cwd,
50
+ env: config.env,
51
+ home: config.home,
52
+ piVersion: config.piVersion ?? "",
53
+ agentDir,
54
+ auth: hostAuth(ctx, agentDir),
55
+ runner: config.runner,
56
+ shutdown: shutdown.signal,
57
+ };
58
+ await runSelfImproveCommand(args.trim(), host, sessionUi(pi, ctx, config.print));
59
+ } finally {
60
+ busy = false;
61
+ }
62
+ },
63
+ });
64
+ };
65
+ }