@quickchatai/quickreview 1.2.0 → 1.3.2

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 (350) hide show
  1. package/README.md +116 -53
  2. package/bin/qcr.js +1 -1
  3. package/config.example.toml +25 -7
  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/selfimprove.js +18 -0
  11. package/dist/extensions/cli/selfimprove.js.map +1 -0
  12. package/dist/extensions/home.js +350 -0
  13. package/dist/extensions/home.js.map +1 -0
  14. package/dist/extensions/login-route.js +1 -1
  15. package/dist/extensions/login-route.js.map +1 -1
  16. package/dist/extensions/onboarding.js +8 -7
  17. package/dist/extensions/onboarding.js.map +1 -1
  18. package/dist/extensions/selfimprove.js +49 -0
  19. package/dist/extensions/selfimprove.js.map +1 -0
  20. package/dist/extensions/setup-scan.js +23 -592
  21. package/dist/extensions/setup-scan.js.map +1 -1
  22. package/dist/extensions/setup.js +2 -47
  23. package/dist/extensions/setup.js.map +1 -1
  24. package/dist/extensions/vendor/openviking-pi/index.js +4 -0
  25. package/dist/extensions/vendor/openviking-pi/index.js.map +1 -1
  26. package/dist/extensions/vendor/openviking-pi/qcr-hooks.js +3 -1
  27. package/dist/extensions/vendor/openviking-pi/qcr-hooks.js.map +1 -1
  28. package/dist/extensions/vendor/openviking-pi/sync.js +81 -0
  29. package/dist/extensions/vendor/openviking-pi/sync.js.map +1 -1
  30. package/dist/src/archive/restore.js +18 -15
  31. package/dist/src/archive/restore.js.map +1 -1
  32. package/dist/src/botworker.js +13 -2
  33. package/dist/src/botworker.js.map +1 -1
  34. package/dist/src/channelfs.js +3 -26
  35. package/dist/src/channelfs.js.map +1 -1
  36. package/dist/src/cli.js +14 -50
  37. package/dist/src/cli.js.map +1 -1
  38. package/dist/src/config.js +16 -0
  39. package/dist/src/config.js.map +1 -1
  40. package/dist/src/daemon.js +33 -4
  41. package/dist/src/daemon.js.map +1 -1
  42. package/dist/src/debuground.js +1 -0
  43. package/dist/src/debuground.js.map +1 -1
  44. package/dist/src/debugroundpi.js +1 -0
  45. package/dist/src/debugroundpi.js.map +1 -1
  46. package/dist/src/engine/caserunner-sdk.js +15 -251
  47. package/dist/src/engine/caserunner-sdk.js.map +1 -1
  48. package/dist/src/home/adapters.js +349 -0
  49. package/dist/src/home/adapters.js.map +1 -0
  50. package/dist/src/home/advanced.js +318 -0
  51. package/dist/src/home/advanced.js.map +1 -0
  52. package/dist/src/home/advancedtools.js +57 -0
  53. package/dist/src/home/advancedtools.js.map +1 -0
  54. package/dist/src/home/autoreview.js +325 -0
  55. package/dist/src/home/autoreview.js.map +1 -0
  56. package/dist/src/home/daemonstatus.js +32 -0
  57. package/dist/src/home/daemonstatus.js.map +1 -0
  58. package/dist/src/home/devicelogin.js +61 -0
  59. package/dist/src/home/devicelogin.js.map +1 -0
  60. package/dist/src/home/launch.js +202 -0
  61. package/dist/src/home/launch.js.map +1 -0
  62. package/dist/src/home/loginowner.js +205 -0
  63. package/dist/src/home/loginowner.js.map +1 -0
  64. package/dist/src/home/memory.js +122 -0
  65. package/dist/src/home/memory.js.map +1 -0
  66. package/dist/src/home/model.js +811 -0
  67. package/dist/src/home/model.js.map +1 -0
  68. package/dist/src/home/panel.js +520 -0
  69. package/dist/src/home/panel.js.map +1 -0
  70. package/dist/src/home/ports.js +19 -0
  71. package/dist/src/home/ports.js.map +1 -0
  72. package/dist/src/home/review.js +163 -0
  73. package/dist/src/home/review.js.map +1 -0
  74. package/dist/src/home/reviews.js +478 -0
  75. package/dist/src/home/reviews.js.map +1 -0
  76. package/dist/src/home/setup.js +507 -0
  77. package/dist/src/home/setup.js.map +1 -0
  78. package/dist/src/home/setupadapters.js +214 -0
  79. package/dist/src/home/setupadapters.js.map +1 -0
  80. package/dist/src/home/setupcard.js +199 -0
  81. package/dist/src/home/setupcard.js.map +1 -0
  82. package/dist/src/home/setuptools.js +45 -0
  83. package/dist/src/home/setuptools.js.map +1 -0
  84. package/dist/src/home/spend.js +160 -0
  85. package/dist/src/home/spend.js.map +1 -0
  86. package/dist/src/home/switches.js +209 -0
  87. package/dist/src/home/switches.js.map +1 -0
  88. package/dist/src/home/switchon.js +439 -0
  89. package/dist/src/home/switchon.js.map +1 -0
  90. package/dist/src/home/toolnames.js +41 -0
  91. package/dist/src/home/toolnames.js.map +1 -0
  92. package/dist/src/home/tune.js +341 -0
  93. package/dist/src/home/tune.js.map +1 -0
  94. package/dist/src/home/words.js +7 -0
  95. package/dist/src/home/words.js.map +1 -0
  96. package/dist/src/homes.js +14 -0
  97. package/dist/src/homes.js.map +1 -1
  98. package/dist/src/install.js +1 -1
  99. package/dist/src/install.js.map +1 -1
  100. package/dist/src/ipc/workerspec.js +8 -0
  101. package/dist/src/ipc/workerspec.js.map +1 -1
  102. package/dist/src/ledgercheck.js +39 -10
  103. package/dist/src/ledgercheck.js.map +1 -1
  104. package/dist/src/live/publish.js +1 -1
  105. package/dist/src/live/publish.js.map +1 -1
  106. package/dist/src/livecli.js +1 -1
  107. package/dist/src/livecli.js.map +1 -1
  108. package/dist/src/loginrefresh/handover.js +121 -0
  109. package/dist/src/loginrefresh/handover.js.map +1 -0
  110. package/dist/src/loginrefresh/lock.js +54 -3
  111. package/dist/src/loginrefresh/lock.js.map +1 -1
  112. package/dist/src/loginrefresh/refresher.js +33 -5
  113. package/dist/src/loginrefresh/refresher.js.map +1 -1
  114. package/dist/src/loginrefresh/supervisor.js +18 -1
  115. package/dist/src/loginrefresh/supervisor.js.map +1 -1
  116. package/dist/src/npmverbs.js +42 -12
  117. package/dist/src/npmverbs.js.map +1 -1
  118. package/dist/src/onboard/choices.js +6 -3
  119. package/dist/src/onboard/choices.js.map +1 -1
  120. package/dist/src/onboard/engine.js +33 -292
  121. package/dist/src/onboard/engine.js.map +1 -1
  122. package/dist/src/onboard/steps/bringup.js +3 -2
  123. package/dist/src/onboard/steps/bringup.js.map +1 -1
  124. package/dist/src/onboard/steps/configfill.js +18 -7
  125. package/dist/src/onboard/steps/configfill.js.map +1 -1
  126. package/dist/src/onboard/steps/loginshare.js +213 -0
  127. package/dist/src/onboard/steps/loginshare.js.map +1 -0
  128. package/dist/src/onboard/steps/memory.js +14 -2
  129. package/dist/src/onboard/steps/memory.js.map +1 -1
  130. package/dist/src/onboard/steps/repoconfig.js +72 -0
  131. package/dist/src/onboard/steps/repoconfig.js.map +1 -0
  132. package/dist/src/onboard/toolnames.js +2 -2
  133. package/dist/src/onboard/toolnames.js.map +1 -1
  134. package/dist/src/piagentdir.js +13 -0
  135. package/dist/src/piagentdir.js.map +1 -0
  136. package/dist/src/pilogin.js +31 -16
  137. package/dist/src/pilogin.js.map +1 -1
  138. package/dist/src/qcrbin.js +16 -11
  139. package/dist/src/qcrbin.js.map +1 -1
  140. package/dist/src/reviewargs.js +122 -0
  141. package/dist/src/reviewargs.js.map +1 -0
  142. package/dist/src/reviewcli.js +7 -161
  143. package/dist/src/reviewcli.js.map +1 -1
  144. package/dist/src/reviewdetach.js +76 -11
  145. package/dist/src/reviewdetach.js.map +1 -1
  146. package/dist/src/scancli.js +39 -691
  147. package/dist/src/scancli.js.map +1 -1
  148. package/dist/src/selfimprove.js +66 -0
  149. package/dist/src/selfimprove.js.map +1 -0
  150. package/dist/src/session-command-supervisor.js +38 -9
  151. package/dist/src/session-command-supervisor.js.map +1 -1
  152. package/dist/src/setup/adapters.js +5 -223
  153. package/dist/src/setup/adapters.js.map +1 -1
  154. package/dist/src/setup/caserunner.js +15 -249
  155. package/dist/src/setup/caserunner.js.map +1 -1
  156. package/dist/src/setup/engine.js +32 -341
  157. package/dist/src/setup/engine.js.map +1 -1
  158. package/dist/src/setup/facts.js +3 -592
  159. package/dist/src/setup/facts.js.map +1 -1
  160. package/dist/src/setup/findings.js +3 -947
  161. package/dist/src/setup/findings.js.map +1 -1
  162. package/dist/src/setup/presentation.js +3 -8
  163. package/dist/src/setup/presentation.js.map +1 -1
  164. package/dist/src/setup/scan.js +3 -724
  165. package/dist/src/setup/scan.js.map +1 -1
  166. package/dist/src/setup/scanbuild.js +9 -92
  167. package/dist/src/setup/scanbuild.js.map +1 -1
  168. package/dist/src/setup/scanlease.js +3 -250
  169. package/dist/src/setup/scanlease.js.map +1 -1
  170. package/dist/src/setup/scanreport.js +3 -288
  171. package/dist/src/setup/scanreport.js.map +1 -1
  172. package/dist/src/setup/scanrun.js +3 -1732
  173. package/dist/src/setup/scanrun.js.map +1 -1
  174. package/dist/src/setup/scantree.js +3 -256
  175. package/dist/src/setup/scantree.js.map +1 -1
  176. package/dist/src/setup/stage2request.js +3 -258
  177. package/dist/src/setup/stage2request.js.map +1 -1
  178. package/dist/src/setup/unitcut.js +3 -436
  179. package/dist/src/setup/unitcut.js.map +1 -1
  180. package/dist/src/state.js +75 -9
  181. package/dist/src/state.js.map +1 -1
  182. package/dist/src/takeover.js +1 -0
  183. package/dist/src/takeover.js.map +1 -1
  184. package/dist/src/takeoverpi.js +2 -1
  185. package/dist/src/takeoverpi.js.map +1 -1
  186. package/dist/src/tui/alerts.js +4 -1
  187. package/dist/src/tui/alerts.js.map +1 -1
  188. package/dist/src/tui/board.js +2 -2
  189. package/dist/src/tui/board.js.map +1 -1
  190. package/dist/src/tui/companion.js +2 -1
  191. package/dist/src/tui/companion.js.map +1 -1
  192. package/dist/src/tui/deploytab.js +2 -2
  193. package/dist/src/tui/deploytab.js.map +1 -1
  194. package/dist/src/tui/index.js +9 -6
  195. package/dist/src/tui/index.js.map +1 -1
  196. package/dist/src/tui/memory.js +3 -16
  197. package/dist/src/tui/memory.js.map +1 -1
  198. package/dist/src/tui/memoryurl.js +22 -0
  199. package/dist/src/tui/memoryurl.js.map +1 -0
  200. package/dist/src/tui/remote.js +1 -1
  201. package/dist/src/tui/remote.js.map +1 -1
  202. package/dist/src/tui/route.js +2 -2
  203. package/dist/src/tui/route.js.map +1 -1
  204. package/dist/src/tui/setupstate.js +8 -5
  205. package/dist/src/tui/setupstate.js.map +1 -1
  206. package/dist/src/tui/sshtriage.js +1 -1
  207. package/dist/src/tui/sshtriage.js.map +1 -1
  208. package/dist/src/verdicts.js +12 -0
  209. package/dist/src/verdicts.js.map +1 -1
  210. package/dist/src/wire.js +9 -4
  211. package/dist/src/wire.js.map +1 -1
  212. package/dist/src/workerbreaker.js +32 -5
  213. package/dist/src/workerbreaker.js.map +1 -1
  214. package/dist/src/workerworld.js +4 -0
  215. package/dist/src/workerworld.js.map +1 -1
  216. package/docker/README.md +1 -1
  217. package/docker/entrypoint.sh +40 -6
  218. package/docker-compose.yml +16 -1
  219. package/extensions/cli/home.ts +14 -0
  220. package/extensions/cli/selfimprove.ts +18 -0
  221. package/extensions/home.ts +484 -0
  222. package/extensions/login-route.ts +1 -1
  223. package/extensions/onboarding.ts +8 -7
  224. package/extensions/selfimprove.ts +65 -0
  225. package/extensions/setup-scan.ts +79 -766
  226. package/extensions/setup.ts +14 -70
  227. package/extensions/vendor/openviking-pi/NOTICE +5 -0
  228. package/extensions/vendor/openviking-pi/README.md +39 -5
  229. package/extensions/vendor/openviking-pi/index.ts +4 -0
  230. package/extensions/vendor/openviking-pi/patches/0014-one-turn-sync-in-flight.patch +239 -0
  231. package/extensions/vendor/openviking-pi/qcr-hooks.ts +3 -1
  232. package/extensions/vendor/openviking-pi/sync.ts +80 -0
  233. package/extensions/vendor/openviking-pi/upstream.json +2 -1
  234. package/package.json +6 -4
  235. package/prompts/onboarding.md +8 -7
  236. package/schemas/review-result.v1.json +60 -0
  237. package/scripts/deploy.sh +8 -6
  238. package/scripts/qcr-host.sh +28 -5
  239. package/scripts/vm-ghcr-login.sh +7 -4
  240. package/src/archive/restore.ts +18 -21
  241. package/src/botworker.ts +13 -2
  242. package/src/channelfs.ts +3 -26
  243. package/src/cli.ts +13 -54
  244. package/src/config.ts +38 -0
  245. package/src/daemon.ts +34 -4
  246. package/src/debuground.ts +3 -0
  247. package/src/debugroundpi.ts +1 -0
  248. package/src/engine/caserunner-sdk.ts +29 -314
  249. package/src/home/adapters.ts +418 -0
  250. package/src/home/advanced.ts +421 -0
  251. package/src/home/advancedtools.ts +96 -0
  252. package/src/home/autoreview.ts +385 -0
  253. package/src/home/daemonstatus.ts +55 -0
  254. package/src/home/devicelogin.ts +107 -0
  255. package/src/home/launch.ts +257 -0
  256. package/src/home/loginowner.ts +248 -0
  257. package/src/home/memory.ts +176 -0
  258. package/src/home/model.ts +965 -0
  259. package/src/home/panel.ts +666 -0
  260. package/src/home/ports.ts +338 -0
  261. package/src/home/review.ts +206 -0
  262. package/src/home/reviews.ts +565 -0
  263. package/src/home/setup.ts +689 -0
  264. package/src/home/setupadapters.ts +217 -0
  265. package/src/home/setupcard.ts +288 -0
  266. package/src/home/setuptools.ts +57 -0
  267. package/src/home/spend.ts +194 -0
  268. package/src/home/switches.ts +293 -0
  269. package/src/home/switchon.ts +554 -0
  270. package/src/home/toolnames.ts +46 -0
  271. package/src/home/tune.ts +405 -0
  272. package/src/home/words.ts +8 -0
  273. package/src/homes.ts +17 -0
  274. package/src/install.ts +1 -1
  275. package/src/ipc/workerspec.ts +15 -0
  276. package/src/ledgercheck.ts +45 -9
  277. package/src/live/publish.ts +4 -1
  278. package/src/livecli.ts +6 -1
  279. package/src/loginrefresh/handover.ts +138 -0
  280. package/src/loginrefresh/lock.ts +72 -3
  281. package/src/loginrefresh/refresher.ts +34 -5
  282. package/src/loginrefresh/supervisor.ts +25 -2
  283. package/src/npmverbs.ts +51 -11
  284. package/src/onboard/choices.ts +6 -3
  285. package/src/onboard/engine.ts +64 -434
  286. package/src/onboard/steps/bringup.ts +3 -2
  287. package/src/onboard/steps/configfill.ts +23 -7
  288. package/src/onboard/steps/loginshare.ts +258 -0
  289. package/src/onboard/steps/memory.ts +18 -2
  290. package/src/onboard/steps/repoconfig.ts +85 -0
  291. package/src/onboard/toolnames.ts +2 -2
  292. package/src/piagentdir.ts +12 -0
  293. package/src/pilogin.ts +32 -16
  294. package/src/qcrbin.ts +16 -11
  295. package/src/reviewargs.ts +119 -0
  296. package/src/reviewcli.ts +6 -167
  297. package/src/reviewdetach.ts +107 -13
  298. package/src/scancli.ts +75 -826
  299. package/src/selfimprove.ts +90 -0
  300. package/src/session-command-supervisor.ts +41 -8
  301. package/src/setup/adapters.ts +13 -221
  302. package/src/setup/caserunner.ts +34 -273
  303. package/src/setup/engine.ts +62 -496
  304. package/src/setup/facts.ts +3 -627
  305. package/src/setup/findings.ts +3 -1264
  306. package/src/setup/presentation.ts +3 -18
  307. package/src/setup/scan.ts +3 -1033
  308. package/src/setup/scanbuild.ts +20 -114
  309. package/src/setup/scanlease.ts +3 -297
  310. package/src/setup/scanreport.ts +3 -373
  311. package/src/setup/scanrun.ts +3 -2268
  312. package/src/setup/scantree.ts +3 -259
  313. package/src/setup/stage2request.ts +3 -347
  314. package/src/setup/unitcut.ts +3 -523
  315. package/src/state.ts +126 -11
  316. package/src/takeover.ts +5 -0
  317. package/src/takeoverpi.ts +3 -2
  318. package/src/tui/alerts.ts +9 -2
  319. package/src/tui/board.ts +2 -2
  320. package/src/tui/companion.ts +2 -1
  321. package/src/tui/deploytab.ts +2 -2
  322. package/src/tui/index.ts +9 -6
  323. package/src/tui/memory.ts +3 -15
  324. package/src/tui/memoryurl.ts +22 -0
  325. package/src/tui/remote.ts +1 -1
  326. package/src/tui/route.ts +2 -2
  327. package/src/tui/setupstate.ts +20 -16
  328. package/src/tui/sshtriage.ts +1 -1
  329. package/src/verdicts.ts +13 -0
  330. package/src/wire.ts +9 -4
  331. package/src/workerbreaker.ts +41 -5
  332. package/src/workerworld.ts +9 -1
  333. package/dist/src/live/projection.js +0 -450
  334. package/dist/src/live/projection.js.map +0 -1
  335. package/dist/src/live/read.js +0 -60
  336. package/dist/src/live/read.js.map +0 -1
  337. package/dist/src/onboard/launch.js +0 -75
  338. package/dist/src/onboard/launch.js.map +0 -1
  339. package/dist/src/setup/ledger.js +0 -207
  340. package/dist/src/setup/ledger.js.map +0 -1
  341. package/dist/src/setup/stage2.js +0 -617
  342. package/dist/src/setup/stage2.js.map +0 -1
  343. package/dist/src/setup/textsniff.js +0 -89
  344. package/dist/src/setup/textsniff.js.map +0 -1
  345. package/src/live/projection.ts +0 -491
  346. package/src/live/read.ts +0 -86
  347. package/src/onboard/launch.ts +0 -103
  348. package/src/setup/ledger.ts +0 -324
  349. package/src/setup/stage2.ts +0 -926
  350. package/src/setup/textsniff.ts +0 -95
@@ -0,0 +1,214 @@
1
+ // The setup checklist's real ports (src/home/setup.ts), and the one function
2
+ // that turns a process's environment into them: the env shim
3
+ // (extensions/cli/home.ts) calls `homeSetupFromEnv(process.env, VERSION)`.
4
+ //
5
+ // first-run checks the plugin's pi-version and git steps, over a
6
+ // PluginHost of this process (its PATH, the running pi)
7
+ // repository pick `gh`: the person's recently pushed repositories, the
8
+ // chosen one's canonical name and default branch, and the
9
+ // account's login and name
10
+ // the write the app config the home's repo port reads
11
+ // (locateConfig: $QCR_CONFIG, else the install home's
12
+ // config.toml), patched the way the onboarding config
13
+ // fill patches it (src/onboard/steps/configfill.ts):
14
+ // comment-preserving, only the keys that change, never
15
+ // dry_run. A fresh config starts from the shipped
16
+ // template, whose dry_run = true it keeps (invariant 6).
17
+ // timezone the machine's IANA zone, as Intl resolves it
18
+ //
19
+ // The silent defaults ride on the repository write: the base branch is the
20
+ // chosen repository's (always: it belongs to that repository), and the
21
+ // timezone and the owner's name and login fill a value only while it is
22
+ // empty (or the config is new), so an owner's own choice is never overwritten.
23
+ import { readFileSync } from "node:fs";
24
+ import { homedir } from "node:os";
25
+ import { join } from "node:path";
26
+ import { assetRoot } from "@quickchatai/pi-quickreview/src/assetroot.js";
27
+ import { nodeRunner } from "@quickchatai/pi-quickreview/src/plugin/runner.js";
28
+ import { declaredPiRange } from "@quickchatai/pi-quickreview/src/plugin/versiongate.js";
29
+ import { writeAtomic } from "@quickchatai/pi-quickreview/src/setupchecklist.js";
30
+ import { locateConfig, stateHome } from "../homes.js";
31
+ import { piAgentDir } from "../piagentdir.js";
32
+ import { execRunner } from "./adapters.js";
33
+ import { known, unknown } from "./ports.js";
34
+ const firstLine = (s) => s.trim().split("\n")[0]?.trim() || "no output";
35
+ const message = (err) => (err instanceof Error ? err.message : String(err));
36
+ /** gh's words for "you are not signed in". */
37
+ const SIGNED_OUT = /gh auth login|not logged in|authentication required|HTTP 401|bad credentials/i;
38
+ function ghWhy(r) {
39
+ if (r.missing)
40
+ return "gh is not installed";
41
+ if (SIGNED_OUT.test(r.stderr))
42
+ return "gh is signed out: run `gh auth login`";
43
+ return firstLine(r.stderr);
44
+ }
45
+ /** The machine's IANA timezone, or null when Intl cannot say. */
46
+ export function systemTimezone() {
47
+ try {
48
+ const tz = Intl.DateTimeFormat().resolvedOptions().timeZone;
49
+ return typeof tz === "string" && tz !== "" ? tz : null;
50
+ }
51
+ catch {
52
+ return null;
53
+ }
54
+ }
55
+ /** A file's text; null only when it does not exist. Any other failure
56
+ * throws: a config that exists and cannot be read is never "no config", or
57
+ * the template would be written over it. */
58
+ function readIfThere(path) {
59
+ try {
60
+ return readFileSync(path, "utf8");
61
+ }
62
+ catch (err) {
63
+ if (err?.code === "ENOENT")
64
+ return null;
65
+ throw err;
66
+ }
67
+ }
68
+ export function repoPickPort(o) {
69
+ const read = o.read ?? readIfThere;
70
+ const write = o.write ?? writeAtomic;
71
+ return {
72
+ recent: async () => {
73
+ const r = await o.runner.run("gh", [
74
+ "repo",
75
+ "list",
76
+ "--limit",
77
+ "8",
78
+ "--json",
79
+ "nameWithOwner",
80
+ ]);
81
+ if (r.code !== 0)
82
+ return unknown(ghWhy(r));
83
+ try {
84
+ const rows = JSON.parse(r.stdout);
85
+ if (!Array.isArray(rows))
86
+ return unknown("gh's answer is not a list");
87
+ return known(rows.flatMap((x) => typeof x?.nameWithOwner === "string" ? [x.nameWithOwner] : []));
88
+ }
89
+ catch (err) {
90
+ return unknown(`gh's answer is not JSON: ${message(err)}`);
91
+ }
92
+ },
93
+ describe: async (repo) => {
94
+ const r = await o.runner.run("gh", [
95
+ "repo",
96
+ "view",
97
+ repo,
98
+ "--json",
99
+ "nameWithOwner,defaultBranchRef",
100
+ ]);
101
+ if (r.code !== 0)
102
+ return { ok: false, why: ghWhy(r) };
103
+ try {
104
+ const v = JSON.parse(r.stdout);
105
+ const branch = v.defaultBranchRef?.name;
106
+ return {
107
+ ok: true,
108
+ repo: typeof v.nameWithOwner === "string" ? v.nameWithOwner : repo,
109
+ defaultBranch: typeof branch === "string" && branch !== "" ? branch : null,
110
+ };
111
+ }
112
+ catch (err) {
113
+ return { ok: false, why: `gh's answer is not JSON: ${message(err)}` };
114
+ }
115
+ },
116
+ profile: async () => {
117
+ const r = await o.runner.run("gh", ["api", "user"]);
118
+ if (r.code !== 0)
119
+ return unknown(ghWhy(r));
120
+ try {
121
+ const v = JSON.parse(r.stdout);
122
+ if (typeof v.login !== "string")
123
+ return unknown("gh's account has no login");
124
+ return known({
125
+ login: v.login,
126
+ name: typeof v.name === "string" && v.name.trim() !== "" ? v.name.trim() : null,
127
+ });
128
+ }
129
+ catch (err) {
130
+ return unknown(`gh's answer is not JSON: ${message(err)}`);
131
+ }
132
+ },
133
+ write: async (choice) => {
134
+ let path;
135
+ try {
136
+ path = o.configPath();
137
+ }
138
+ catch (err) {
139
+ return { ok: false, why: message(err) };
140
+ }
141
+ let existing;
142
+ let template = "";
143
+ try {
144
+ existing = read(path);
145
+ }
146
+ catch (err) {
147
+ return { ok: false, why: `can't read ${path} (${message(err)}); nothing was written` };
148
+ }
149
+ try {
150
+ if (existing === null)
151
+ template = read(o.templatePath());
152
+ }
153
+ catch {
154
+ template = null;
155
+ }
156
+ if (template === null)
157
+ return { ok: false, why: `there is no ${path} and the shipped template is not readable` };
158
+ // the config fill's writer, loaded only when a repository is written
159
+ const { renderRepoConfig } = await import("../onboard/steps/repoconfig.js");
160
+ const r = renderRepoConfig(existing, template, choice);
161
+ if (!r.ok)
162
+ return r;
163
+ try {
164
+ if (r.text !== existing)
165
+ write(path, r.text);
166
+ }
167
+ catch (err) {
168
+ return { ok: false, why: `can't write ${path}: ${message(err)}` };
169
+ }
170
+ return { ok: true, path, wrote: r.wrote };
171
+ },
172
+ };
173
+ }
174
+ /** The PluginHost the first-run checks read: this process's PATH and the
175
+ * running pi (its version, which the env shim reads off pi). Only the
176
+ * plugin's pi-version and git steps run over it, so its auth answers
177
+ * nothing. */
178
+ export function firstRunHost(env, piVersion) {
179
+ return {
180
+ cwd: join(stateHome(env), "home"),
181
+ env,
182
+ home: (env["HOME"] ?? "").trim() || homedir(),
183
+ piVersion,
184
+ agentDir: piAgentDir(env),
185
+ auth: {
186
+ logins: () => ({}),
187
+ configured: () => false,
188
+ refresh: () => Promise.reject(new Error("the home's first-run checks hold no login")),
189
+ },
190
+ runner: nodeRunner(env),
191
+ shutdown: new AbortController().signal,
192
+ };
193
+ }
194
+ /** The setup's options from a process's environment and the running pi's
195
+ * version: the env shim's one call. */
196
+ export function homeSetupFromEnv(env, piVersion) {
197
+ let range = null;
198
+ try {
199
+ range = declaredPiRange();
200
+ }
201
+ catch {
202
+ range = null;
203
+ }
204
+ return {
205
+ ...(range !== null ? { firstRun: { host: firstRunHost(env, piVersion), range } } : {}),
206
+ repos: repoPickPort({
207
+ runner: execRunner,
208
+ configPath: () => locateConfig({ env }).path,
209
+ templatePath: () => join(assetRoot(), "config.example.toml"),
210
+ }),
211
+ timezone: systemTimezone,
212
+ };
213
+ }
214
+ //# sourceMappingURL=setupadapters.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"setupadapters.js","sourceRoot":"","sources":["../../../src/home/setupadapters.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,199 @@
1
+ import { matchesKey, truncateToWidth, visibleWidth, wrapTextWithAnsi, } from "@earendil-works/pi-tui";
2
+ import { loginFailureText } from "./setup.js";
3
+ /** Where the card sits: centred, half the width. */
4
+ export const SETUP_OVERLAY = {
5
+ anchor: "center",
6
+ width: "50%",
7
+ minWidth: 80,
8
+ nonCapturing: true,
9
+ };
10
+ /** The share of the terminal's height the card fills. */
11
+ export const CARD_HEIGHT = 0.5;
12
+ /** Sub-rows (instructions, the device code) are indented under the label. */
13
+ const INDENT = " ";
14
+ const NOTICE_ROWS = 3;
15
+ const SPIN = ["⠋", "⠙", "⠹", "⠸", "⠼", "⠴", "⠦", "⠧", "⠇", "⠏"];
16
+ /** What each step's key does, in the hint beside it. */
17
+ const VERB = {
18
+ login: "sign in",
19
+ github: "check",
20
+ repo: "choose",
21
+ };
22
+ export class SetupCard {
23
+ th;
24
+ host;
25
+ constructor(th, host) {
26
+ this.th = th;
27
+ this.host = host;
28
+ }
29
+ c(color, s) {
30
+ return this.th.fg(color, s);
31
+ }
32
+ spin() {
33
+ return SPIN[this.host.frame() % SPIN.length];
34
+ }
35
+ edge(s) {
36
+ return this.c(this.host.focused() ? "borderAccent" : "borderMuted", s);
37
+ }
38
+ /** The key that runs the next step now. */
39
+ key() {
40
+ return this.host.focused() ? "⏎" : "alt+n";
41
+ }
42
+ row(w, left, right = "", selected = false) {
43
+ const inner = w - 4;
44
+ const r = right ? ` ${right}` : "";
45
+ const l = truncateToWidth(left, Math.max(1, inner - visibleWidth(r)), "…");
46
+ const gap = Math.max(0, inner - visibleWidth(l) - visibleWidth(r));
47
+ let text = ` ${l}${" ".repeat(gap)}${r} `;
48
+ if (selected)
49
+ text = this.th.bg("selectedBg", text);
50
+ return `${this.edge("│")}${text}${this.edge("│")}`;
51
+ }
52
+ /** Text under a step, wrapped inside the frame. */
53
+ sub(w, text, color = "muted") {
54
+ const room = Math.max(10, w - 4 - INDENT.length);
55
+ return wrapTextWithAnsi(text, room).map((l) => this.row(w, `${INDENT}${this.c(color, l)}`));
56
+ }
57
+ top(w) {
58
+ const left = `${this.edge("╭─ ")}${this.th.bold(this.c("accent", "quickreview"))} `;
59
+ const right = ` ${this.c("muted", "setup")}${this.edge(" ─╮")}`;
60
+ const fill = Math.max(0, w - visibleWidth(left) - visibleWidth(right));
61
+ return `${left}${this.edge("─".repeat(fill))}${right}`;
62
+ }
63
+ rule(w) {
64
+ return this.edge(`├${"─".repeat(Math.max(0, w - 2))}┤`);
65
+ }
66
+ bottom(w) {
67
+ return this.edge(`╰${"─".repeat(Math.max(0, w - 2))}╯`);
68
+ }
69
+ stepRows(w, s) {
70
+ const v = this.host.setup.view();
71
+ const out = [];
72
+ const k = this.key();
73
+ let mark;
74
+ let label;
75
+ let right = "";
76
+ if (s.state === "done") {
77
+ mark = this.c("success", "✓");
78
+ label = this.c("muted", s.title);
79
+ right = this.c("muted", s.found ?? "done");
80
+ }
81
+ else if (s.state === "running") {
82
+ mark = this.c("accent", this.spin());
83
+ label = this.th.bold(this.c("text", s.title));
84
+ right = this.c("dim", v.login.code ? "waiting for you…" : "starting…");
85
+ }
86
+ else if (s.unknown !== undefined) {
87
+ mark = this.c("dim", "?");
88
+ label = s.next ? this.th.bold(this.c("text", s.title)) : this.c("text", s.title);
89
+ right = s.next
90
+ ? `${this.c("accent", k)} ${this.c("muted", VERB[s.id])}`
91
+ : this.c("dim", "unknown");
92
+ }
93
+ else if (s.next) {
94
+ mark = this.c("accent", "▸");
95
+ label = this.th.bold(this.c("text", s.title));
96
+ right = `${this.c("accent", k)} ${this.c("muted", VERB[s.id])}`;
97
+ }
98
+ else {
99
+ mark = this.c("dim", "○");
100
+ label = this.c("dim", s.title);
101
+ }
102
+ out.push(this.row(w, ` ${mark} ${label}`, right, s.next));
103
+ if (s.state === "done")
104
+ return out;
105
+ if (s.id === "login")
106
+ out.push(...this.loginRows(w, s));
107
+ else if (s.unknown !== undefined)
108
+ out.push(...this.sub(w, `Unknown — ${s.unknown}.`, "warning"));
109
+ else if (s.next && s.id === "github" && s.missing)
110
+ out.push(...this.sub(w, `${capital(s.missing)}, then ${k} checks again.`, "warning"));
111
+ else if (s.next && s.id === "repo")
112
+ out.push(...this.sub(w, "One of your recently pushed repositories, or paste any owner/name or GitHub URL."));
113
+ return out;
114
+ }
115
+ loginRows(w, s) {
116
+ const v = this.host.setup.view();
117
+ const k = this.key();
118
+ const out = [];
119
+ const chatgpt = v.provider === "OpenAI";
120
+ const setting = "Device-code login must be on first: ChatGPT → Settings → Security.";
121
+ if (s.state === "running") {
122
+ const code = v.login.code;
123
+ if (!code) {
124
+ if (chatgpt)
125
+ out.push(...this.sub(w, setting));
126
+ out.push(this.row(w, `${INDENT}${this.c("accent", this.spin())} ${this.c("dim", "asking for a code…")}`));
127
+ return out;
128
+ }
129
+ out.push(this.row(w, ""));
130
+ out.push(this.row(w, `${INDENT}${this.c("muted", "1 Open ")} ${this.c("accent", code.verificationUri)}`));
131
+ out.push(this.row(w, `${INDENT}${this.c("muted", "2 Enter")} ${this.th.bold(this.c("text", code.userCode))}`));
132
+ out.push(this.row(w, ""));
133
+ if (chatgpt)
134
+ out.push(...this.sub(w, setting, "dim"));
135
+ out.push(this.row(w, `${INDENT}${this.c("accent", this.spin())} ${this.c("dim", "waiting for you to approve…")}`));
136
+ return out;
137
+ }
138
+ if (v.login.failure)
139
+ out.push(...this.sub(w, loginFailureText(v.login.failure, k), "warning"));
140
+ if (s.unknown !== undefined)
141
+ out.push(...this.sub(w, `Unknown — ${s.unknown}.`, "warning"));
142
+ if (s.next && chatgpt && v.login.failure?.kind !== "not_enabled")
143
+ out.push(...this.sub(w, setting));
144
+ return out;
145
+ }
146
+ hints(w) {
147
+ const k = (key, label) => `${this.c("accent", key)} ${this.c("muted", label)}`;
148
+ return this.row(w, this.host.focused()
149
+ ? `${k("⏎", "next step")} ${k("esc", "back to the chat")}`
150
+ : `${k("alt+n", "next step")} ${k("f2", "focus the card")} ${this.c("dim", "· or just type to ask pi")}`);
151
+ }
152
+ render(width) {
153
+ const w = Math.max(40, width);
154
+ const v = this.host.setup.view();
155
+ const body = [
156
+ this.row(w, ""),
157
+ this.row(w, ` ${this.th.bold(this.c("text", "Welcome to quickreview"))}`, this.c("muted", `${v.done} of ${v.total} done `)),
158
+ this.row(w, ` ${this.c("muted", "Sign in once, choose a repository, and review your first pull request.")}`),
159
+ this.row(w, ""),
160
+ ];
161
+ for (const c of v.checks) {
162
+ body.push(this.row(w, ` ${this.c("warning", "✗")} ${this.th.bold(this.c("text", c.title))}`, c.next ? `${this.c("accent", this.key())} ${this.c("muted", "check")}` : "", c.next));
163
+ body.push(...this.sub(w, `${capital(c.why)}${c.next ? `, then ${this.key()} checks again.` : "."}`, "warning"));
164
+ }
165
+ for (const s of v.steps)
166
+ body.push(...this.stepRows(w, s));
167
+ body.push(this.row(w, ""));
168
+ const foot = [this.rule(w)];
169
+ const n = this.host.model.notice;
170
+ if (n) {
171
+ const color = n.kind === "ok" ? "success" : n.kind === "warn" ? "warning" : "text";
172
+ for (const l of wrapTextWithAnsi(n.text, w - 4).slice(0, NOTICE_ROWS))
173
+ foot.push(this.row(w, this.c(color, l)));
174
+ }
175
+ foot.push(this.hints(w), this.bottom(w));
176
+ const target = Math.round(this.host.rows() * CARD_HEIGHT);
177
+ const spare = Math.max(0, target - 1 - body.length - foot.length);
178
+ const blank = (k) => Array.from({ length: k }, () => this.row(w, ""));
179
+ return [
180
+ this.top(w),
181
+ ...blank(Math.floor(spare / 2)),
182
+ ...body,
183
+ ...blank(Math.ceil(spare / 2)),
184
+ ...foot,
185
+ ].map((l) => truncateToWidth(l, w));
186
+ }
187
+ handleInput(data) {
188
+ if (matchesKey(data, "escape"))
189
+ this.host.unfocus();
190
+ else if (matchesKey(data, "enter"))
191
+ this.host.next();
192
+ }
193
+ handleMouse(e) {
194
+ return e.type === "click" ? { focus: true } : undefined;
195
+ }
196
+ invalidate() { }
197
+ }
198
+ const capital = (s) => (s ? `${s[0].toUpperCase()}${s.slice(1)}` : s);
199
+ //# sourceMappingURL=setupcard.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"setupcard.js","sourceRoot":"","sources":["../../../src/home/setupcard.ts"],"names":[],"mappings":"AAgBA,OAAO,EACL,UAAU,EACV,eAAe,EACf,YAAY,EACZ,gBAAgB,GACjB,MAAM,wBAAwB,CAAC;AAEhC,OAAO,EAAE,gBAAgB,EAAsC,MAAM,YAAY,CAAC;AAIlF,oDAAoD;AACpD,MAAM,CAAC,MAAM,aAAa,GAAG;IAC3B,MAAM,EAAE,QAAQ;IAChB,KAAK,EAAE,KAAK;IACZ,QAAQ,EAAE,EAAE;IACZ,YAAY,EAAE,IAAI;CACV,CAAC;AAEX,yDAAyD;AACzD,MAAM,CAAC,MAAM,WAAW,GAAG,GAAG,CAAC;AAC/B,6EAA6E;AAC7E,MAAM,MAAM,GAAG,SAAS,CAAC;AACzB,MAAM,WAAW,GAAG,CAAC,CAAC;AACtB,MAAM,IAAI,GAAG,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC;AAchE,wDAAwD;AACxD,MAAM,IAAI,GAAwC;IAChD,KAAK,EAAE,SAAS;IAChB,MAAM,EAAE,OAAO;IACf,IAAI,EAAE,QAAQ;CACf,CAAC;AAEF,MAAM,OAAO,SAAS;IAED;IACA;IAFnB,YACmB,EAAS,EACT,IAAc;QADd,OAAE,GAAF,EAAE,CAAO;QACT,SAAI,GAAJ,IAAI,CAAU;IAC9B,CAAC;IAEI,CAAC,CAAC,KAAS,EAAE,CAAS;QAC5B,OAAO,IAAI,CAAC,EAAE,CAAC,EAAE,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC;IAC9B,CAAC;IAEO,IAAI;QACV,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,GAAG,IAAI,CAAC,MAAM,CAAE,CAAC;IAChD,CAAC;IAEO,IAAI,CAAC,CAAS;QACpB,OAAO,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,cAAc,CAAC,CAAC,CAAC,aAAa,EAAE,CAAC,CAAC,CAAC;IACzE,CAAC;IAED,2CAA2C;IACnC,GAAG;QACT,OAAO,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,OAAO,CAAC;IAC7C,CAAC;IAEO,GAAG,CAAC,CAAS,EAAE,IAAY,EAAE,KAAK,GAAG,EAAE,EAAE,QAAQ,GAAG,KAAK;QAC/D,MAAM,KAAK,GAAG,CAAC,GAAG,CAAC,CAAC;QACpB,MAAM,CAAC,GAAG,KAAK,CAAC,CAAC,CAAC,IAAI,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QACnC,MAAM,CAAC,GAAG,eAAe,CAAC,IAAI,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,GAAG,YAAY,CAAC,CAAC,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC;QAC3E,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,GAAG,YAAY,CAAC,CAAC,CAAC,GAAG,YAAY,CAAC,CAAC,CAAC,CAAC,CAAC;QACnE,IAAI,IAAI,GAAG,IAAI,CAAC,GAAG,GAAG,CAAC,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,GAAG,CAAC;QAC1C,IAAI,QAAQ;YAAE,IAAI,GAAG,IAAI,CAAC,EAAE,CAAC,EAAE,CAAC,YAAY,EAAE,IAAI,CAAC,CAAC;QACpD,OAAO,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;IACrD,CAAC;IAED,mDAAmD;IAC3C,GAAG,CAAC,CAAS,EAAE,IAAY,EAAE,QAAY,OAAO;QACtD,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC;QACjD,OAAO,gBAAgB,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,GAAG,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IAC9F,CAAC;IAEO,GAAG,CAAC,CAAS;QACnB,MAAM,IAAI,GAAG,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,aAAa,CAAC,CAAC,GAAG,CAAC;QACpF,MAAM,KAAK,GAAG,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,OAAO,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;QAChE,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,GAAG,YAAY,CAAC,IAAI,CAAC,GAAG,YAAY,CAAC,KAAK,CAAC,CAAC,CAAC;QACvE,OAAO,GAAG,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,GAAG,KAAK,EAAE,CAAC;IACzD,CAAC;IAEO,IAAI,CAAC,CAAS;QACpB,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC;IAC1D,CAAC;IAEO,MAAM,CAAC,CAAS;QACtB,OAAO,IAAI,CAAC,IAAI,CAAC,IAAI,GAAG,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC;IAC1D,CAAC;IAEO,QAAQ,CAAC,CAAS,EAAE,CAAgB;QAC1C,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;QACjC,MAAM,GAAG,GAAa,EAAE,CAAC;QACzB,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACrB,IAAI,IAAY,CAAC;QACjB,IAAI,KAAa,CAAC;QAClB,IAAI,KAAK,GAAG,EAAE,CAAC;QACf,IAAI,CAAC,CAAC,KAAK,KAAK,MAAM,EAAE,CAAC;YACvB,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,SAAS,EAAE,GAAG,CAAC,CAAC;YAC9B,KAAK,GAAG,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC;YACjC,KAAK,GAAG,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC,CAAC,KAAK,IAAI,MAAM,CAAC,CAAC;QAC7C,CAAC;aAAM,IAAI,CAAC,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;YACjC,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC;YACrC,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC;YAC9C,KAAK,GAAG,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC;QACzE,CAAC;aAAM,IAAI,CAAC,CAAC,OAAO,KAAK,SAAS,EAAE,CAAC;YACnC,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC;YAC1B,KAAK,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC;YACjF,KAAK,GAAG,CAAC,CAAC,IAAI;gBACZ,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE;gBACzD,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,SAAS,CAAC,CAAC;QAC/B,CAAC;aAAM,IAAI,CAAC,CAAC,IAAI,EAAE,CAAC;YAClB,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,GAAG,CAAC,CAAC;YAC7B,KAAK,GAAG,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC;YAC9C,KAAK,GAAG,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC;QAClE,CAAC;aAAM,CAAC;YACN,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC;YAC1B,KAAK,GAAG,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC;QACjC,CAAC;QACD,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,IAAI,KAAK,KAAK,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;QAC5D,IAAI,CAAC,CAAC,KAAK,KAAK,MAAM;YAAE,OAAO,GAAG,CAAC;QACnC,IAAI,CAAC,CAAC,EAAE,KAAK,OAAO;YAAE,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;aACnD,IAAI,CAAC,CAAC,OAAO,KAAK,SAAS;YAC9B,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,aAAa,CAAC,CAAC,OAAO,GAAG,EAAE,SAAS,CAAC,CAAC,CAAC;aAC5D,IAAI,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,EAAE,KAAK,QAAQ,IAAI,CAAC,CAAC,OAAO;YAC/C,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,GAAG,OAAO,CAAC,CAAC,CAAC,OAAO,CAAC,UAAU,CAAC,gBAAgB,EAAE,SAAS,CAAC,CAAC,CAAC;aACnF,IAAI,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,EAAE,KAAK,MAAM;YAChC,GAAG,CAAC,IAAI,CACN,GAAG,IAAI,CAAC,GAAG,CACT,CAAC,EACD,kFAAkF,CACnF,CACF,CAAC;QACJ,OAAO,GAAG,CAAC;IACb,CAAC;IAEO,SAAS,CAAC,CAAS,EAAE,CAAgB;QAC3C,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;QACjC,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACrB,MAAM,GAAG,GAAa,EAAE,CAAC;QACzB,MAAM,OAAO,GAAG,CAAC,CAAC,QAAQ,KAAK,QAAQ,CAAC;QACxC,MAAM,OAAO,GAAG,oEAAoE,CAAC;QACrF,IAAI,CAAC,CAAC,KAAK,KAAK,SAAS,EAAE,CAAC;YAC1B,MAAM,IAAI,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC;YAC1B,IAAI,CAAC,IAAI,EAAE,CAAC;gBACV,IAAI,OAAO;oBAAE,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;gBAC/C,GAAG,CAAC,IAAI,CACN,IAAI,CAAC,GAAG,CACN,CAAC,EACD,GAAG,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,oBAAoB,CAAC,EAAE,CACnF,CACF,CAAC;gBACF,OAAO,GAAG,CAAC;YACb,CAAC;YACD,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;YAC1B,GAAG,CAAC,IAAI,CACN,IAAI,CAAC,GAAG,CACN,CAAC,EACD,GAAG,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,UAAU,CAAC,KAAK,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,eAAe,CAAC,EAAE,CACrF,CACF,CAAC;YACF,GAAG,CAAC,IAAI,CACN,IAAI,CAAC,GAAG,CACN,CAAC,EACD,GAAG,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,UAAU,CAAC,KAAK,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC,EAAE,CAC1F,CACF,CAAC;YACF,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;YAC1B,IAAI,OAAO;gBAAE,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,EAAE,KAAK,CAAC,CAAC,CAAC;YACtD,GAAG,CAAC,IAAI,CACN,IAAI,CAAC,GAAG,CACN,CAAC,EACD,GAAG,MAAM,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,IAAI,EAAE,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,6BAA6B,CAAC,EAAE,CAC5F,CACF,CAAC;YACF,OAAO,GAAG,CAAC;QACb,CAAC;QACD,IAAI,CAAC,CAAC,KAAK,CAAC,OAAO;YAAE,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,gBAAgB,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC,EAAE,SAAS,CAAC,CAAC,CAAC;QAC/F,IAAI,CAAC,CAAC,OAAO,KAAK,SAAS;YAAE,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,aAAa,CAAC,CAAC,OAAO,GAAG,EAAE,SAAS,CAAC,CAAC,CAAC;QAC5F,IAAI,CAAC,CAAC,IAAI,IAAI,OAAO,IAAI,CAAC,CAAC,KAAK,CAAC,OAAO,EAAE,IAAI,KAAK,aAAa;YAC9D,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,CAAC;QACpC,OAAO,GAAG,CAAC;IACb,CAAC;IAEO,KAAK,CAAC,CAAS;QACrB,MAAM,CAAC,GAAG,CAAC,GAAW,EAAE,KAAa,EAAU,EAAE,CAC/C,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,GAAG,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,KAAK,CAAC,EAAE,CAAC;QACvD,OAAO,IAAI,CAAC,GAAG,CACb,CAAC,EACD,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE;YACjB,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,EAAE,WAAW,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,kBAAkB,CAAC,EAAE;YAC3D,CAAC,CAAC,GAAG,CAAC,CAAC,OAAO,EAAE,WAAW,CAAC,KAAK,CAAC,CAAC,IAAI,EAAE,gBAAgB,CAAC,KAAK,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,0BAA0B,CAAC,EAAE,CAC7G,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,KAAa;QAClB,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,EAAE,EAAE,KAAK,CAAC,CAAC;QAC9B,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;QACjC,MAAM,IAAI,GAAG;YACX,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC;YACf,IAAI,CAAC,GAAG,CACN,CAAC,EACD,KAAK,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,wBAAwB,CAAC,CAAC,EAAE,EAC7D,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,GAAG,CAAC,CAAC,IAAI,OAAO,CAAC,CAAC,KAAK,SAAS,CAAC,CAClD;YACD,IAAI,CAAC,GAAG,CACN,CAAC,EACD,KAAK,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,wEAAwE,CAAC,EAAE,CACjG;YACD,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC;SAChB,CAAC;QACF,KAAK,MAAM,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,CAAC;YACzB,IAAI,CAAC,IAAI,CACP,IAAI,CAAC,GAAG,CACN,CAAC,EACD,KAAK,IAAI,CAAC,CAAC,CAAC,SAAS,EAAE,GAAG,CAAC,KAAK,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,EACvE,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,QAAQ,EAAE,IAAI,CAAC,GAAG,EAAE,CAAC,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,OAAO,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,EAC3E,CAAC,CAAC,IAAI,CACP,CACF,CAAC;YACF,IAAI,CAAC,IAAI,CACP,GAAG,IAAI,CAAC,GAAG,CACT,CAAC,EACD,GAAG,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,UAAU,IAAI,CAAC,GAAG,EAAE,gBAAgB,CAAC,CAAC,CAAC,GAAG,EAAE,EACzE,SAAS,CACV,CACF,CAAC;QACJ,CAAC;QACD,KAAK,MAAM,CAAC,IAAI,CAAC,CAAC,KAAK;YAAE,IAAI,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;QAC3D,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;QAC3B,MAAM,IAAI,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC;QAC5B,MAAM,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC;QACjC,IAAI,CAAC,EAAE,CAAC;YACN,MAAM,KAAK,GAAO,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,KAAK,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,MAAM,CAAC;YACvF,KAAK,MAAM,CAAC,IAAI,gBAAgB,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,WAAW,CAAC;gBACnE,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC7C,CAAC;QACD,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;QACzC,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,GAAG,WAAW,CAAC,CAAC;QAC1D,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,MAAM,GAAG,CAAC,GAAG,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC;QAClE,MAAM,KAAK,GAAG,CAAC,CAAS,EAAY,EAAE,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,EAAE,GAAG,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;QACxF,OAAO;YACL,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC;YACX,GAAG,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;YAC/B,GAAG,IAAI;YACP,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;YAC9B,GAAG,IAAI;SACR,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,eAAe,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;IACtC,CAAC;IAED,WAAW,CAAC,IAAY;QACtB,IAAI,UAAU,CAAC,IAAI,EAAE,QAAQ,CAAC;YAAE,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC;aAC/C,IAAI,UAAU,CAAC,IAAI,EAAE,OAAO,CAAC;YAAE,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;IACvD,CAAC;IAED,WAAW,CAAC,CAAgB;QAC1B,OAAO,CAAC,CAAC,IAAI,KAAK,OAAO,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC;IAC1D,CAAC;IAED,UAAU,KAAU,CAAC;CACtB;AAED,MAAM,OAAO,GAAG,CAAC,CAAS,EAAU,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAE,CAAC,WAAW,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC"}
@@ -0,0 +1,45 @@
1
+ // The setup checklist's `home_*` tools: each step's action, as the model in
2
+ // the chat calls it. The keys call the same HomeSetup methods
3
+ // (extensions/home.ts), so a key and a tool never do two different things.
4
+ import { textResult } from "@quickchatai/pi-quickreview/extensions/pi-tool.js";
5
+ const NO_PARAMS = { type: "object", properties: {}, additionalProperties: false };
6
+ /** One definition per HOME_SETUP_TOOL_NAMES entry. */
7
+ export function setupTools(setup) {
8
+ return {
9
+ home_setup_next: {
10
+ name: "home_setup_next",
11
+ label: "Home: next setup step",
12
+ description: "Run the next step of the quickreview home's setup checklist (sign in, connect GitHub, choose a repository), as alt+n does. Answers what happened, or that setup is done.",
13
+ parameters: NO_PARAMS,
14
+ execute: async () => textResult(await setup.next()),
15
+ },
16
+ home_sign_in: {
17
+ name: "home_sign_in",
18
+ label: "Home: sign in",
19
+ description: "Start pi's own device-code login for the provider the chat runs on. Answers with the URL and the code to enter once pi has them; the sign-in finishes in the background when the person approves it. Device-code login must be on in ChatGPT → Settings → Security.",
20
+ parameters: NO_PARAMS,
21
+ execute: async () => textResult(await setup.signIn()),
22
+ },
23
+ home_check_github: {
24
+ name: "home_check_github",
25
+ label: "Home: check GitHub",
26
+ description: "Check again whether gh is installed and signed in. When it is not, the answer says what to run.",
27
+ parameters: NO_PARAMS,
28
+ execute: async () => textResult(await setup.checkGithub()),
29
+ },
30
+ home_choose_repo: {
31
+ name: "home_choose_repo",
32
+ label: "Home: choose a repository",
33
+ description: "Set the repository the home reviews: owner/name or any GitHub URL of it. It is written to the qcr config's [github] repo. Without `repo`, answers the person's recently pushed repositories to choose from.",
34
+ parameters: {
35
+ type: "object",
36
+ properties: {
37
+ repo: { type: "string", description: "owner/name, or a GitHub URL of the repository." },
38
+ },
39
+ additionalProperties: false,
40
+ },
41
+ execute: async (_id, p) => textResult(await setup.chooseRepo(typeof p["repo"] === "string" ? p["repo"] : undefined)),
42
+ },
43
+ };
44
+ }
45
+ //# sourceMappingURL=setuptools.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"setuptools.js","sourceRoot":"","sources":["../../../src/home/setuptools.ts"],"names":[],"mappings":"AAAA,4EAA4E;AAC5E,8DAA8D;AAC9D,2EAA2E;AAC3E,OAAO,EAAE,UAAU,EAAgB,MAAM,mDAAmD,CAAC;AAM7F,MAAM,SAAS,GAAG,EAAE,IAAI,EAAE,QAAQ,EAAE,UAAU,EAAE,EAAE,EAAE,oBAAoB,EAAE,KAAK,EAAW,CAAC;AAE3F,sDAAsD;AACtD,MAAM,UAAU,UAAU,CAAC,KAAgB;IAGzC,OAAO;QACL,eAAe,EAAE;YACf,IAAI,EAAE,iBAAiB;YACvB,KAAK,EAAE,uBAAuB;YAC9B,WAAW,EACT,0KAA0K;YAC5K,UAAU,EAAE,SAAS;YACrB,OAAO,EAAE,KAAK,IAAI,EAAE,CAAC,UAAU,CAAC,MAAM,KAAK,CAAC,IAAI,EAAE,CAAC;SACpD;QACD,YAAY,EAAE;YACZ,IAAI,EAAE,cAAc;YACpB,KAAK,EAAE,eAAe;YACtB,WAAW,EACT,qQAAqQ;YACvQ,UAAU,EAAE,SAAS;YACrB,OAAO,EAAE,KAAK,IAAI,EAAE,CAAC,UAAU,CAAC,MAAM,KAAK,CAAC,MAAM,EAAE,CAAC;SACtD;QACD,iBAAiB,EAAE;YACjB,IAAI,EAAE,mBAAmB;YACzB,KAAK,EAAE,oBAAoB;YAC3B,WAAW,EACT,iGAAiG;YACnG,UAAU,EAAE,SAAS;YACrB,OAAO,EAAE,KAAK,IAAI,EAAE,CAAC,UAAU,CAAC,MAAM,KAAK,CAAC,WAAW,EAAE,CAAC;SAC3D;QACD,gBAAgB,EAAE;YAChB,IAAI,EAAE,kBAAkB;YACxB,KAAK,EAAE,2BAA2B;YAClC,WAAW,EACT,6MAA6M;YAC/M,UAAU,EAAE;gBACV,IAAI,EAAE,QAAQ;gBACd,UAAU,EAAE;oBACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,gDAAgD,EAAE;iBACxF;gBACD,oBAAoB,EAAE,KAAK;aAC5B;YACD,OAAO,EAAE,KAAK,EAAE,GAAG,EAAE,CAAC,EAAE,EAAE,CACxB,UAAU,CAAC,MAAM,KAAK,CAAC,UAAU,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC;SAC5F;KACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1,160 @@
1
+ // The home's spend line: today's and this month's review cost, summed from
2
+ // two sources (src/home/ports.ts `SpendPort`):
3
+ //
4
+ // the home the app's detached review runs (`<state home>/review/
5
+ // detached`, the registry the review button starts in): each
6
+ // run that has ended and whose result says what it cost, in
7
+ // the day and month it ended
8
+ // auto-review the daemon's recorded costs: its status snapshot's
9
+ // `today_spend_usd` and `month_spend_usd`, read from the
10
+ // daemon's own state on this machine's compose stack
11
+ //
12
+ // Today and this month are UTC days and months, the daemon's own (its
13
+ // snapshot, `qcr spend`): the two halves are summed over one calendar.
14
+ //
15
+ // When either source cannot be read, the total is unknown, with why (invariant
16
+ // 9): never a zero, and never the half that could be read passed off as the
17
+ // whole. A source that cannot hold a cost is a known zero, as a missing auth
18
+ // file is no login: a registry with no runs yet, a machine with no Docker, or
19
+ // a stack that was never brought up (no state volume) recorded nothing.
20
+ //
21
+ // A run still going is not counted until its result says what it cost; a run
22
+ // whose result names no cost has nothing to add.
23
+ import { listRunViews } from "../reviewdetach.js";
24
+ import { daemonSnapshot } from "./daemonstatus.js";
25
+ import { known, unknown } from "./ports.js";
26
+ import { parseRunStatus } from "./reviews.js";
27
+ const message = (err) => (err instanceof Error ? err.message : String(err));
28
+ /** The UTC day (`YYYY-MM-DD`) and month (`YYYY-MM`) of `ms`. */
29
+ export function utcPeriod(ms) {
30
+ const iso = new Date(ms).toISOString();
31
+ return { day: iso.slice(0, 10), month: iso.slice(0, 7) };
32
+ }
33
+ async function safe(read) {
34
+ try {
35
+ return await read();
36
+ }
37
+ catch (err) {
38
+ return unknown(message(err));
39
+ }
40
+ }
41
+ /** The spend port over its two sources: both read, or unknown. */
42
+ export function spendPort(src, now) {
43
+ return {
44
+ totals: async () => {
45
+ const at = now();
46
+ const [home, auto] = await Promise.all([safe(() => src.home()), safe(() => src.auto(at))]);
47
+ if (home.kind === "unknown")
48
+ return unknown(`the home's reviews: ${home.why}`);
49
+ if (auto.kind === "unknown")
50
+ return unknown(`auto-review's: ${auto.why}`);
51
+ const { day, month } = utcPeriod(at);
52
+ let today = auto.value.today;
53
+ let thisMonth = auto.value.month;
54
+ for (const c of home.value) {
55
+ if (!Number.isFinite(c.at) || !Number.isFinite(c.usd))
56
+ continue;
57
+ const p = utcPeriod(c.at);
58
+ if (p.month !== month)
59
+ continue;
60
+ thisMonth += c.usd;
61
+ if (p.day === day)
62
+ today += c.usd;
63
+ }
64
+ return known({ today, month: thisMonth });
65
+ },
66
+ };
67
+ }
68
+ // ---- the home's half: the detached registry -------------------------------
69
+ /** Is the process with this pid alive? */
70
+ const alive = (pid) => {
71
+ try {
72
+ process.kill(pid, 0);
73
+ return true;
74
+ }
75
+ catch {
76
+ return false;
77
+ }
78
+ };
79
+ /** The costs of every run in the registry at `registry` that has ended with
80
+ * a cost, at the time it ended. */
81
+ export function registryCosts(registry, o = { now: Date.now }) {
82
+ return async () => {
83
+ let views;
84
+ try {
85
+ views = listRunViews(registry, { alive: o.alive ?? alive, now: o.now });
86
+ }
87
+ catch (err) {
88
+ return unknown(`can't read the review runs in ${registry}: ${message(err)}`);
89
+ }
90
+ const out = [];
91
+ for (const v of views) {
92
+ const s = parseRunStatus(v.view, v.argv);
93
+ const usd = s?.result?.costUsd;
94
+ if (s === null || s.state === "running" || usd === null || usd === undefined)
95
+ continue;
96
+ out.push({ at: s.endedAt ?? s.startedAt, usd });
97
+ }
98
+ return known(out);
99
+ };
100
+ }
101
+ const isObj = (v) => typeof v === "object" && v !== null && !Array.isArray(v);
102
+ const usd = (v) => (typeof v === "number" && Number.isFinite(v) ? v : null);
103
+ /** What a status snapshot's text says auto-review spent, for the UTC day and
104
+ * month of `now`. Pure. A snapshot written on an earlier day is the daemon's
105
+ * last word: it has recorded nothing since (it writes one every heartbeat
106
+ * while it runs), so the days after it add nothing. */
107
+ export function snapshotSpend(text, now) {
108
+ let s;
109
+ try {
110
+ s = JSON.parse(text);
111
+ }
112
+ catch {
113
+ return unknown("its status.json is not readable JSON");
114
+ }
115
+ if (!isObj(s))
116
+ return unknown("its status.json is not an object");
117
+ const written = typeof s["written_at"] === "string" ? Date.parse(s["written_at"]) : NaN;
118
+ if (!Number.isFinite(written))
119
+ return unknown("its status has no time it was written");
120
+ const today = usd(s["today_spend_usd"]);
121
+ const month = usd(s["month_spend_usd"]);
122
+ if (month === null)
123
+ return unknown("its status has no month's spend (an older daemon)");
124
+ if (today === null)
125
+ return unknown("its status has no day's spend");
126
+ const at = utcPeriod(written);
127
+ const want = utcPeriod(now);
128
+ if (at.month !== want.month)
129
+ return known({ today: 0, month: 0 });
130
+ return known({ today: at.day === want.day ? today : 0, month });
131
+ }
132
+ /** Auto-review's recorded costs on this machine's compose stack: read from
133
+ * the daemon's own status.json while it runs (src/home/daemonstatus.ts). A
134
+ * daemon that is off keeps its costs in its state volume, where the home
135
+ * cannot read them: unknown. */
136
+ export function composeAutoSpend(o) {
137
+ return async (now) => {
138
+ const s = await daemonSnapshot(o.runner, o.root);
139
+ if (s.kind === "text")
140
+ return snapshotSpend(s.text, now);
141
+ if (s.kind === "none")
142
+ return known({ today: 0, month: 0 });
143
+ if (s.kind === "off")
144
+ return unknown("auto-review is off, and its costs are read from it while it runs");
145
+ return unknown(s.why);
146
+ };
147
+ }
148
+ /** The spend port as the home's env shim builds it: the install's registry
149
+ * in the state home, and the compose stack at `root` (null: no stack, so
150
+ * auto-review recorded nothing here). */
151
+ export function realSpendPort(o) {
152
+ const now = o.now ?? Date.now;
153
+ return spendPort({
154
+ home: registryCosts(o.registry, { now }),
155
+ auto: o.root === null
156
+ ? async () => known({ today: 0, month: 0 })
157
+ : composeAutoSpend({ root: o.root, runner: o.runner }),
158
+ }, now);
159
+ }
160
+ //# sourceMappingURL=spend.js.map