@pugi/cli 0.1.0-beta.10 → 0.1.0-beta.101

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 (464) hide show
  1. package/CHANGELOG.md +132 -0
  2. package/LICENSE +1 -1
  3. package/README.md +55 -11
  4. package/assets/pugi-prozr2-mascot.ansi +9 -0
  5. package/bin/run.js +33 -1
  6. package/dist/commands/deploy.js +40 -40
  7. package/dist/commands/flatten.js +191 -0
  8. package/dist/commands/jobs-watch.js +201 -0
  9. package/dist/commands/jobs.js +42 -27
  10. package/dist/commands/retro.js +210 -0
  11. package/dist/commands/smoke.js +133 -0
  12. package/dist/core/agent-progress/cleanup.js +134 -0
  13. package/dist/core/agent-progress/schema.js +144 -0
  14. package/dist/core/agent-progress/writer.js +101 -0
  15. package/dist/core/agents/adaptive-router.js +330 -0
  16. package/dist/core/agents/query-decomposer.js +297 -0
  17. package/dist/core/agents/registry.js +3 -3
  18. package/dist/core/approvals/shortcut-resolver.js +98 -0
  19. package/dist/core/artifact-chain/dispatcher.js +148 -0
  20. package/dist/core/artifact-chain/exporter.js +164 -0
  21. package/dist/core/artifact-chain/state.js +243 -0
  22. package/dist/core/artifact-chain/steps.js +169 -0
  23. package/dist/core/ask-user/question.js +92 -0
  24. package/dist/core/audit/audit-trail.js +275 -0
  25. package/dist/core/auth/ensure-authenticated.js +129 -0
  26. package/dist/core/auth/env-provider.js +238 -0
  27. package/dist/core/auto-open-browser.js +4 -4
  28. package/dist/core/auto-update/channels.js +122 -0
  29. package/dist/core/auto-update/checker.js +241 -0
  30. package/dist/core/auto-update/state.js +235 -0
  31. package/dist/core/bare-mode/index.js +107 -0
  32. package/dist/core/bash/redirect.js +281 -0
  33. package/dist/core/bash-classifier.js +436 -40
  34. package/dist/core/checkpoint/resumer.js +149 -0
  35. package/dist/core/checkpoint/rewinder.js +291 -0
  36. package/dist/core/checkpoints/shadow-git.js +670 -0
  37. package/dist/core/citations/parser.js +109 -0
  38. package/dist/core/classifier/yolo-classifier.js +88 -0
  39. package/dist/core/codegraph/db.js +506 -0
  40. package/dist/core/codegraph/decision-store.js +248 -0
  41. package/dist/core/codegraph/detect-repo.js +459 -0
  42. package/dist/core/codegraph/install.js +134 -0
  43. package/dist/core/codegraph/offer-hook.js +220 -0
  44. package/dist/core/codegraph/parser.js +598 -0
  45. package/dist/core/codegraph/queries/go.scm +57 -0
  46. package/dist/core/codegraph/queries/javascript.scm +56 -0
  47. package/dist/core/codegraph/queries/python.scm +55 -0
  48. package/dist/core/codegraph/queries/rust.scm +63 -0
  49. package/dist/core/codegraph/queries/typescript.scm +91 -0
  50. package/dist/core/codegraph/reindex.js +218 -0
  51. package/dist/core/codegraph/resolve-edges.js +107 -0
  52. package/dist/core/codegraph/types.js +34 -0
  53. package/dist/core/codegraph/watcher.js +440 -0
  54. package/dist/core/compact/auto-trigger.js +96 -0
  55. package/dist/core/compact/buffer-rewriter.js +115 -0
  56. package/dist/core/compact/summarizer.js +208 -0
  57. package/dist/core/compact/token-counter.js +108 -0
  58. package/dist/core/consensus/anvil-fanout.js +25 -25
  59. package/dist/core/consensus/diff-capture.js +121 -12
  60. package/dist/core/consensus/rubric.js +21 -21
  61. package/dist/core/context/builder.js +6 -6
  62. package/dist/core/context/compaction-events.js +8 -8
  63. package/dist/core/context/compaction.js +31 -31
  64. package/dist/core/context/index.js +15 -8
  65. package/dist/core/context/invariants.js +51 -51
  66. package/dist/core/context/markdown-loader.js +28 -10
  67. package/dist/core/context/markdown-traverse.js +255 -0
  68. package/dist/core/context/pugiignore.js +41 -41
  69. package/dist/core/context/repo-skeleton.js +37 -37
  70. package/dist/core/context/tool-eviction.js +55 -0
  71. package/dist/core/context/watcher.js +32 -32
  72. package/dist/core/context/working-set.js +23 -23
  73. package/dist/core/coordinator/agent-tools.js +77 -0
  74. package/dist/core/coordinator/agent-toolset.js +65 -0
  75. package/dist/core/coordinator/fsm.js +73 -0
  76. package/dist/core/coordinator/mode-fsm.js +70 -0
  77. package/dist/core/cost/rate-card.js +129 -0
  78. package/dist/core/cost/tracker.js +221 -0
  79. package/dist/core/credentials.js +13 -13
  80. package/dist/core/cron/scheduler.js +138 -0
  81. package/dist/core/denial-tracking/index.js +8 -0
  82. package/dist/core/denial-tracking/state.js +264 -0
  83. package/dist/core/diagnostics/probe-runner.js +93 -0
  84. package/dist/core/diagnostics/probes/api.js +46 -0
  85. package/dist/core/diagnostics/probes/auth.js +93 -0
  86. package/dist/core/diagnostics/probes/bare-mode.js +42 -0
  87. package/dist/core/diagnostics/probes/cli-version.js +127 -0
  88. package/dist/core/diagnostics/probes/config.js +72 -0
  89. package/dist/core/diagnostics/probes/denial-tracking.js +57 -0
  90. package/dist/core/diagnostics/probes/disk.js +81 -0
  91. package/dist/core/diagnostics/probes/engine-live.js +46 -0
  92. package/dist/core/diagnostics/probes/git.js +65 -0
  93. package/dist/core/diagnostics/probes/hooks.js +118 -0
  94. package/dist/core/diagnostics/probes/mcp.js +75 -0
  95. package/dist/core/diagnostics/probes/node.js +59 -0
  96. package/dist/core/diagnostics/probes/pnpm.js +36 -0
  97. package/dist/core/diagnostics/probes/pugi-md.js +89 -0
  98. package/dist/core/diagnostics/probes/sandbox.js +67 -0
  99. package/dist/core/diagnostics/probes/session.js +74 -0
  100. package/dist/core/diagnostics/probes/status-snapshot.js +488 -0
  101. package/dist/core/diagnostics/probes/workspace.js +63 -0
  102. package/dist/core/diagnostics/types.js +70 -0
  103. package/dist/core/dispatch/cache-cleanup.js +197 -0
  104. package/dist/core/dispatch/cache-handoff.js +295 -0
  105. package/dist/core/edits/apply-patch-layer-e.js +189 -0
  106. package/dist/core/edits/dispatch.js +333 -7
  107. package/dist/core/edits/format-detector.js +260 -0
  108. package/dist/core/edits/format-matrix.js +26 -0
  109. package/dist/core/edits/fuzzy-ladder.js +650 -0
  110. package/dist/core/edits/index.js +5 -1
  111. package/dist/core/edits/journal.js +199 -0
  112. package/dist/core/edits/layer-a-apply.js +15 -15
  113. package/dist/core/edits/layer-a-fuzzy-apply.js +198 -0
  114. package/dist/core/edits/layer-b-apply.js +9 -9
  115. package/dist/core/edits/layer-c-apply.js +6 -6
  116. package/dist/core/edits/layer-d-ast.js +557 -14
  117. package/dist/core/edits/marker-parser.js +12 -12
  118. package/dist/core/edits/security-gate.js +27 -27
  119. package/dist/core/edits/verify-hook.js +273 -0
  120. package/dist/core/edits/worktree.js +29 -29
  121. package/dist/core/engine/anvil-client.js +214 -26
  122. package/dist/core/engine/auto-compact.js +247 -0
  123. package/dist/core/engine/budgets.js +220 -0
  124. package/dist/core/engine/compact-llm-summarizer.js +124 -0
  125. package/dist/core/engine/context-prefix.js +155 -0
  126. package/dist/core/engine/index.js +1 -1
  127. package/dist/core/engine/intensity.js +163 -0
  128. package/dist/core/engine/intent.js +260 -0
  129. package/dist/core/engine/native-pugi.js +1559 -227
  130. package/dist/core/engine/prompts.js +219 -19
  131. package/dist/core/engine/strip-internal-fields.js +124 -0
  132. package/dist/core/engine/tool-bridge.js +1887 -59
  133. package/dist/core/engine/verification-patterns.js +195 -0
  134. package/dist/core/eval/v1/ledger.js +83 -0
  135. package/dist/core/eval/v1/runner.js +280 -0
  136. package/dist/core/eval/v1/scoring.js +68 -0
  137. package/dist/core/eval/v1/task-loader.js +191 -0
  138. package/dist/core/eval/v1/types.js +14 -0
  139. package/dist/core/eval/v1/verifier.js +176 -0
  140. package/dist/core/eval/v1/yaml-parser.js +250 -0
  141. package/dist/core/evaluation/golden-dataset.js +293 -0
  142. package/dist/core/feedback/queue.js +177 -0
  143. package/dist/core/feedback/submitter.js +145 -0
  144. package/dist/core/file-cache.js +113 -1
  145. package/dist/core/flatten/flatten-repo.js +439 -0
  146. package/dist/core/format/osc8-link.js +28 -0
  147. package/dist/core/hook-chains.js +392 -0
  148. package/dist/core/hooks/citation-verify-hook.js +138 -0
  149. package/dist/core/hooks/citation-verify.js +112 -0
  150. package/dist/core/hooks/events.js +46 -0
  151. package/dist/core/hooks/index.js +15 -0
  152. package/dist/core/hooks/registry.js +216 -0
  153. package/dist/core/hooks/runner.js +236 -0
  154. package/dist/core/hooks/v2/event-emitter.js +115 -0
  155. package/dist/core/hooks/v2/executor.js +282 -0
  156. package/dist/core/hooks/v2/index.js +25 -0
  157. package/dist/core/hooks/v2/lifecycle.js +104 -0
  158. package/dist/core/hooks/v2/loader.js +216 -0
  159. package/dist/core/hooks/v2/matcher.js +125 -0
  160. package/dist/core/hooks/v2/trust.js +143 -0
  161. package/dist/core/hooks/v2/types.js +86 -0
  162. package/dist/core/hooks/worktree-events.js +158 -0
  163. package/dist/core/image/renderer.js +71 -0
  164. package/dist/core/init/detector.js +582 -0
  165. package/dist/core/init/template-renderer.js +242 -0
  166. package/dist/core/jobs/registry.js +18 -18
  167. package/dist/core/ledger/results-tsv.js +142 -0
  168. package/dist/core/log-discipline/stdout-redirect.js +51 -0
  169. package/dist/core/lsp/cache.js +105 -0
  170. package/dist/core/lsp/client.js +551 -41
  171. package/dist/core/lsp/language-detect.js +66 -0
  172. package/dist/core/lsp/post-edit-diagnostics.js +171 -0
  173. package/dist/core/lsp/server-detect.js +173 -0
  174. package/dist/core/lsp/symbol-cache.js +162 -0
  175. package/dist/core/lsp/symbol-tools.js +664 -0
  176. package/dist/core/mcp/client.js +97 -28
  177. package/dist/core/mcp/http-server.js +553 -0
  178. package/dist/core/mcp/orchestrator-config.js +192 -0
  179. package/dist/core/mcp/orchestrator-tools.js +806 -0
  180. package/dist/core/mcp/permission.js +190 -0
  181. package/dist/core/mcp/registry.js +39 -17
  182. package/dist/core/mcp/server-tools.js +219 -0
  183. package/dist/core/mcp/server.js +397 -0
  184. package/dist/core/mcp/trust.js +10 -10
  185. package/dist/core/memory/dual-write.js +416 -0
  186. package/dist/core/memory/passive-extract.js +130 -0
  187. package/dist/core/memory/phase1-kinds.js +20 -0
  188. package/dist/core/memory/secret-scanner.js +304 -0
  189. package/dist/core/memory-sync/queue.js +170 -0
  190. package/dist/core/metrics/extract.js +113 -0
  191. package/dist/core/modes/roo-modes.js +68 -0
  192. package/dist/core/notes/notes-paths.js +113 -0
  193. package/dist/core/notes/notes-recorder.js +140 -0
  194. package/dist/core/notes/notes-writer.js +53 -0
  195. package/dist/core/notes/renderers.js +0 -0
  196. package/dist/core/notes/slug.js +105 -0
  197. package/dist/core/onboarding/ensure-initialized.js +133 -0
  198. package/dist/core/onboarding/marker.js +111 -0
  199. package/dist/core/onboarding/telemetry-state.js +108 -0
  200. package/dist/core/output-style/presets.js +176 -0
  201. package/dist/core/output-style/state.js +185 -0
  202. package/dist/core/path-security.js +287 -5
  203. package/dist/core/permission.js +82 -22
  204. package/dist/core/permissions/auto-classifier.js +124 -0
  205. package/dist/core/permissions/bash-parser.js +371 -0
  206. package/dist/core/permissions/circuit-breaker.js +83 -0
  207. package/dist/core/permissions/constrained-edit.js +91 -0
  208. package/dist/core/permissions/gate.js +278 -0
  209. package/dist/core/permissions/index.js +20 -0
  210. package/dist/core/permissions/mode.js +174 -0
  211. package/dist/core/permissions/network-egress.js +137 -0
  212. package/dist/core/permissions/state.js +241 -0
  213. package/dist/core/permissions/tool-class.js +107 -0
  214. package/dist/core/plan-mode/ui-state.js +51 -0
  215. package/dist/core/plans/plan-artifact.js +721 -0
  216. package/dist/core/policy-limits/etag-store.js +122 -0
  217. package/dist/core/prd-check/parser.js +215 -0
  218. package/dist/core/prd-check/reporter.js +127 -0
  219. package/dist/core/prd-check/session-review.js +557 -0
  220. package/dist/core/prd-check/verifiers.js +223 -0
  221. package/dist/core/prompt-cache/client-cache.js +99 -0
  222. package/dist/core/prompts/assembly.js +29 -0
  223. package/dist/core/prompts/registry.js +364 -0
  224. package/dist/core/pugi-gitignore.js +52 -0
  225. package/dist/core/pugi-md/cc-compat-rules.js +735 -0
  226. package/dist/core/pugi-md/context-injector.js +76 -0
  227. package/dist/core/pugi-md/walk-up.js +207 -0
  228. package/dist/core/python/uv-installer.js +270 -0
  229. package/dist/core/python/uv-resolver.js +83 -0
  230. package/dist/core/rate-limit/narrator.js +146 -0
  231. package/dist/core/recipes/cli-types.js +20 -0
  232. package/dist/core/recipes/loader.js +103 -0
  233. package/dist/core/recipes/runner.js +345 -0
  234. package/dist/core/recipes/schema.js +587 -0
  235. package/dist/core/release-notes/parser.js +241 -0
  236. package/dist/core/release-notes/state.js +116 -0
  237. package/dist/core/repl/ask.js +37 -37
  238. package/dist/core/repl/cancellation.js +26 -26
  239. package/dist/core/repl/cap-warning.js +4 -4
  240. package/dist/core/repl/clipboard-read.js +11 -11
  241. package/dist/core/repl/dispatch-fsm.js +12 -12
  242. package/dist/core/repl/engine-bridge.js +303 -0
  243. package/dist/core/repl/history-search.js +15 -15
  244. package/dist/core/repl/history.js +28 -18
  245. package/dist/core/repl/kill-ring.js +5 -5
  246. package/dist/core/repl/model-pricing.js +135 -0
  247. package/dist/core/repl/privacy-banner.js +22 -22
  248. package/dist/core/repl/session.js +2690 -229
  249. package/dist/core/repl/slash-commands.js +540 -41
  250. package/dist/core/repl/store/index.js +1 -1
  251. package/dist/core/repl/store/jsonl-log.js +22 -22
  252. package/dist/core/repl/store/lockfile.js +10 -10
  253. package/dist/core/repl/store/session-store.js +136 -107
  254. package/dist/core/repl/store/types.js +15 -15
  255. package/dist/core/repl/store/uuid-v7.js +12 -12
  256. package/dist/core/repl/tool-route.js +382 -0
  257. package/dist/core/repl/workspace-context.js +43 -21
  258. package/dist/core/repo-map/build.js +125 -0
  259. package/dist/core/repo-map/cache.js +185 -0
  260. package/dist/core/repo-map/extractor.js +254 -0
  261. package/dist/core/repo-map/formatter.js +145 -0
  262. package/dist/core/repo-map/page-rank.js +105 -0
  263. package/dist/core/repo-map/scanner.js +211 -0
  264. package/dist/core/retro/git-collector.js +251 -0
  265. package/dist/core/retro/health-card.js +25 -0
  266. package/dist/core/retro/metrics.js +342 -0
  267. package/dist/core/retro/narrative.js +249 -0
  268. package/dist/core/retro/plane-collector.js +274 -0
  269. package/dist/core/retro/pr-issue-link.js +65 -0
  270. package/dist/core/retro/types.js +16 -0
  271. package/dist/core/retry-budget/budget.js +284 -0
  272. package/dist/core/retry-budget/index.js +5 -0
  273. package/dist/core/retry-budget/retry-cap.js +74 -0
  274. package/dist/core/routing/lead-worker.js +43 -0
  275. package/dist/core/routing/pre-flight-estimator.js +108 -0
  276. package/dist/core/runs/run-tree.js +103 -0
  277. package/dist/core/sandboxing/adapter.js +43 -0
  278. package/dist/core/sandboxing/bubblewrap.js +209 -0
  279. package/dist/core/sandboxing/index.js +78 -0
  280. package/dist/core/sandboxing/none.js +19 -0
  281. package/dist/core/sandboxing/policy.js +97 -0
  282. package/dist/core/sandboxing/seatbelt.js +231 -0
  283. package/dist/core/security/injection-scanner.js +367 -0
  284. package/dist/core/security/output-filter.js +418 -0
  285. package/dist/core/session/env-file.js +105 -0
  286. package/dist/core/session/section-budgets.js +140 -0
  287. package/dist/core/session.js +119 -0
  288. package/dist/core/settings.js +402 -5
  289. package/dist/core/share/formatter.js +271 -0
  290. package/dist/core/share/redactor.js +221 -0
  291. package/dist/core/share/uploader.js +267 -0
  292. package/dist/core/skills/defaults.js +30 -30
  293. package/dist/core/skills/loader.js +22 -22
  294. package/dist/core/skills/sources.js +27 -27
  295. package/dist/core/smoke/headless-driver.js +174 -0
  296. package/dist/core/smoke/orchestrator.js +194 -0
  297. package/dist/core/smoke/runner.js +238 -0
  298. package/dist/core/smoke/scenario-parser.js +316 -0
  299. package/dist/core/statusline.js +99 -0
  300. package/dist/core/subagents/dispatcher-real.js +600 -0
  301. package/dist/core/subagents/dispatcher.js +146 -52
  302. package/dist/core/subagents/index.js +19 -6
  303. package/dist/core/subagents/isolation-matrix.js +213 -0
  304. package/dist/core/subagents/spawn.js +19 -4
  305. package/dist/core/telemetry/emitter.js +229 -0
  306. package/dist/core/telemetry/queue.js +251 -0
  307. package/dist/core/theme/context.js +91 -0
  308. package/dist/core/theme/presets.js +228 -0
  309. package/dist/core/theme/state.js +181 -0
  310. package/dist/core/todos/invariant.js +10 -0
  311. package/dist/core/todos/state.js +177 -0
  312. package/dist/core/tool-schema/compressor.js +89 -0
  313. package/dist/core/transport/version-interceptor.js +166 -0
  314. package/dist/core/trust.js +2 -2
  315. package/dist/core/tui/thinking-block.js +64 -0
  316. package/dist/core/vim/keymap.js +288 -0
  317. package/dist/core/vim/state.js +92 -0
  318. package/dist/core/watch-markers/marker-watcher.js +133 -0
  319. package/dist/core/worktree/include-parser.js +249 -0
  320. package/dist/core/worktree-manager/cleanup.js +123 -0
  321. package/dist/core/worktree-manager/manager.js +303 -0
  322. package/dist/index.js +36 -0
  323. package/dist/runtime/bootstrap.js +190 -0
  324. package/dist/runtime/cli.js +4403 -561
  325. package/dist/runtime/commands/agents.js +31 -31
  326. package/dist/runtime/commands/budget.js +5 -5
  327. package/dist/runtime/commands/cancel.js +231 -0
  328. package/dist/runtime/commands/chain.js +489 -0
  329. package/dist/runtime/commands/codegraph-status.js +227 -0
  330. package/dist/runtime/commands/compact.js +297 -0
  331. package/dist/runtime/commands/config.js +74 -40
  332. package/dist/runtime/commands/cost.js +199 -0
  333. package/dist/runtime/commands/delegate.js +27 -4
  334. package/dist/runtime/commands/dispatch.js +126 -0
  335. package/dist/runtime/commands/doctor.js +579 -0
  336. package/dist/runtime/commands/eval-v1.js +266 -0
  337. package/dist/runtime/commands/feedback.js +184 -0
  338. package/dist/runtime/commands/hooks.js +187 -0
  339. package/dist/runtime/commands/index-cmd.js +459 -0
  340. package/dist/runtime/commands/init.js +254 -0
  341. package/dist/runtime/commands/lsp.js +200 -38
  342. package/dist/runtime/commands/mcp.js +935 -0
  343. package/dist/runtime/commands/memory.js +582 -0
  344. package/dist/runtime/commands/model.js +237 -0
  345. package/dist/runtime/commands/onboarding.js +275 -0
  346. package/dist/runtime/commands/patch.js +12 -12
  347. package/dist/runtime/commands/permissions.js +112 -0
  348. package/dist/runtime/commands/plan.js +143 -0
  349. package/dist/runtime/commands/prd-check.js +285 -0
  350. package/dist/runtime/commands/privacy.js +17 -17
  351. package/dist/runtime/commands/recipe.js +325 -0
  352. package/dist/runtime/commands/redo-blob-store.js +92 -0
  353. package/dist/runtime/commands/redo.js +361 -0
  354. package/dist/runtime/commands/release-notes.js +229 -0
  355. package/dist/runtime/commands/repo-map.js +95 -0
  356. package/dist/runtime/commands/report.js +299 -0
  357. package/dist/runtime/commands/resume.js +118 -0
  358. package/dist/runtime/commands/review-consensus.js +68 -53
  359. package/dist/runtime/commands/rewind.js +333 -0
  360. package/dist/runtime/commands/roster.js +14 -14
  361. package/dist/runtime/commands/servers-cli.js +182 -0
  362. package/dist/runtime/commands/servers.js +236 -0
  363. package/dist/runtime/commands/sessions.js +163 -0
  364. package/dist/runtime/commands/share.js +316 -0
  365. package/dist/runtime/commands/skills.js +31 -31
  366. package/dist/runtime/commands/status.js +186 -0
  367. package/dist/runtime/commands/stickers.js +82 -0
  368. package/dist/runtime/commands/style.js +194 -0
  369. package/dist/runtime/commands/theme.js +196 -0
  370. package/dist/runtime/commands/undo.js +54 -22
  371. package/dist/runtime/commands/update.js +289 -0
  372. package/dist/runtime/commands/vim.js +140 -0
  373. package/dist/runtime/commands/worktree.js +8 -8
  374. package/dist/runtime/commands/worktrees.js +155 -0
  375. package/dist/runtime/deprecation-warning.js +69 -0
  376. package/dist/runtime/engine-exit-code.js +50 -0
  377. package/dist/runtime/headless-repl.js +195 -0
  378. package/dist/runtime/headless.js +548 -0
  379. package/dist/runtime/load-hooks-or-exit.js +71 -0
  380. package/dist/runtime/plan-decompose.js +22 -22
  381. package/dist/runtime/sigint-guard.js +272 -0
  382. package/dist/runtime/stream-renderer.js +195 -0
  383. package/dist/runtime/update-check.js +28 -28
  384. package/dist/runtime/version.js +65 -0
  385. package/dist/runtime/worktree-bootstrap.js +579 -0
  386. package/dist/skills/bundled/batch.js +617 -0
  387. package/dist/skills/bundled/index.js +45 -0
  388. package/dist/skills/bundled/loop.js +358 -0
  389. package/dist/skills/bundled/remember.js +383 -0
  390. package/dist/skills/bundled/simplify.js +289 -0
  391. package/dist/skills/bundled/skillify.js +373 -0
  392. package/dist/skills/bundled/stuck.js +558 -0
  393. package/dist/skills/bundled/verify.js +439 -0
  394. package/dist/testing/vcr.js +486 -0
  395. package/dist/tools/agent-tool.js +229 -0
  396. package/dist/tools/apply-patch.js +89 -28
  397. package/dist/tools/ask-user-question.js +337 -0
  398. package/dist/tools/ask-user.js +115 -0
  399. package/dist/tools/bash.js +811 -49
  400. package/dist/tools/brief.js +224 -0
  401. package/dist/tools/cron.js +433 -0
  402. package/dist/tools/enter-worktree.js +250 -0
  403. package/dist/tools/exit-worktree.js +147 -0
  404. package/dist/tools/file-tools.js +161 -44
  405. package/dist/tools/http-request.js +336 -0
  406. package/dist/tools/lsp-tools.js +377 -1
  407. package/dist/tools/mcp-tool.js +260 -0
  408. package/dist/tools/multi-edit.js +361 -0
  409. package/dist/tools/powershell.js +268 -0
  410. package/dist/tools/registry.js +120 -5
  411. package/dist/tools/server-tools.js +892 -0
  412. package/dist/tools/skill-tool.js +96 -0
  413. package/dist/tools/sleep.js +99 -0
  414. package/dist/tools/synthetic-output.js +133 -0
  415. package/dist/tools/tasks.js +208 -0
  416. package/dist/tools/todo-write.js +184 -0
  417. package/dist/tools/verify-plan-execution.js +295 -0
  418. package/dist/tools/web-fetch-injection-scanner.js +207 -0
  419. package/dist/tools/web-fetch.js +195 -10
  420. package/dist/tools/web-search.js +458 -0
  421. package/dist/tui/agent-progress-card.js +111 -0
  422. package/dist/tui/agent-tree.js +22 -1
  423. package/dist/tui/ask-modal.js +14 -14
  424. package/dist/tui/ask-user-question-chips.js +315 -0
  425. package/dist/tui/ask-user-question-prompt.js +203 -0
  426. package/dist/tui/compact-banner.js +81 -0
  427. package/dist/tui/conversation-pane.js +85 -11
  428. package/dist/tui/cost-table.js +111 -0
  429. package/dist/tui/device-flow.js +2 -2
  430. package/dist/tui/doctor-table.js +46 -0
  431. package/dist/tui/feedback-prompt.js +156 -0
  432. package/dist/tui/input-box.js +247 -32
  433. package/dist/tui/login-picker.js +3 -3
  434. package/dist/tui/markdown-render.js +6 -6
  435. package/dist/tui/multi-file-diff-approval.js +375 -0
  436. package/dist/tui/onboarding-wizard.js +240 -0
  437. package/dist/tui/permissions-picker.js +86 -0
  438. package/dist/tui/render.js +36 -1
  439. package/dist/tui/repl-render.js +239 -25
  440. package/dist/tui/repl-splash-art.js +16 -16
  441. package/dist/tui/repl-splash-mascot.js +48 -24
  442. package/dist/tui/repl-splash.js +22 -22
  443. package/dist/tui/repl.js +125 -45
  444. package/dist/tui/slash-palette.js +6 -6
  445. package/dist/tui/splash.js +2 -2
  446. package/dist/tui/status-bar.js +109 -31
  447. package/dist/tui/status-table.js +7 -0
  448. package/dist/tui/stickers-art.js +136 -0
  449. package/dist/tui/style-table.js +28 -0
  450. package/dist/tui/theme-table.js +29 -0
  451. package/dist/tui/thinking-spinner.js +123 -0
  452. package/dist/tui/tool-stream-pane.js +53 -4
  453. package/dist/tui/update-banner.js +27 -2
  454. package/dist/tui/vim-input.js +267 -0
  455. package/dist/tui/welcome-banner.js +107 -0
  456. package/dist/tui/welcome-data.js +293 -0
  457. package/dist/tui/workspace-context.js +2 -2
  458. package/package.json +29 -6
  459. package/test/scenarios/codegen-create-file.scenario.txt +13 -0
  460. package/test/scenarios/compact-force.scenario.txt +12 -0
  461. package/test/scenarios/identity.scenario.txt +11 -0
  462. package/test/scenarios/persona-handoff.scenario.txt +12 -0
  463. package/test/scenarios/walkback.scenario.txt +12 -0
  464. package/dist/core/engine/compaction-hook.js +0 -154
package/CHANGELOG.md ADDED
@@ -0,0 +1,132 @@
1
+ # Changelog
2
+
3
+ All notable changes to `@pugi/cli` are documented here. The file follows the
4
+ [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) convention with newer
5
+ releases listed first. Section format: `## [<version>] - <YYYY-MM-DD>`.
6
+
7
+ The bundled `pugi release-notes` command parses this file and renders sections
8
+ strictly newer than `~/.pugi/.last-seen-version` after every upgrade.
9
+
10
+ ## [0.1.0-beta.88] - 2026-06-02
11
+
12
+ ### Fixed
13
+ - **Pugi identity intro no longer chants on later turns**. The output gate now
14
+ strips the canonical long-form intro ("I'm Pugi - your engineering copilot.
15
+ Tell me what you need...") and its Russian variant on mid-thread replies.
16
+ Operators were seeing the intro re-emit on turn 2+ after a session-resume
17
+ or autonomous tick.
18
+ - **Ctrl+C double-press exit guard**. A single Ctrl+C in the REPL no longer
19
+ kills the CLI. First press prompts "Press Ctrl+C again to exit (within 2s)
20
+ or any key to continue". Second press within 2s exits cleanly; any other
21
+ key cancels. Headless mode emits a `session-end` envelope and exits 0.
22
+ - **Persona no longer over-clarifies trivial creative tasks**. Asking for a
23
+ well-known game / demo / todo app now picks reasonable defaults and starts
24
+ building in one turn. Ambiguous tasks (auth, deploy targets) still ask
25
+ ≤ 3 short choices via the `ask_user_question` tool.
26
+
27
+ ### Added
28
+ - **Short-format AskUserQuestion chip renderer**. Up to 3 questions render
29
+ side-by-side as Ink chips with ▸ default highlight, ↑↓ in-question nav,
30
+ ←→/Tab between questions, 1-9 jump, [s] skip-with-default, [Esc] cancel,
31
+ [Enter] commit. Labels truncate at 5 words / 22 chars. Caller can opt
32
+ into a non-TTY numbered fallback via `forceFallback`.
33
+
34
+ ### Security
35
+ - **npm publish leak-gate hardening**. `prepublishOnly` now runs a
36
+ banned-string scan against the staged tarball (`tools/scrub/scan-tarball.sh`)
37
+ covering personal names, competitor refs, internal codenames, engineering
38
+ provenance, absolute paths, brand legacy, and secret-token shapes.
39
+ Per-line `[pugi-leak-ok]` allowlist marker for legitimate references;
40
+ path allowlist for LICENSE / THIRD_PARTY_NOTICES files where MIT requires
41
+ copyright-holder name. Synthetic injection regression test runs in CI.
42
+
43
+ ### Chore
44
+ - MIT LICENSE copyright holder set to `Pugi.io` (was personal name).
45
+
46
+ ## [0.1.0-beta.26] - 2026-05-27
47
+
48
+ ### Added
49
+ - RAG consumer middleware on admin-api () — XML `<rag-context>`
50
+ block, persona allowlist (Pugi / Hiroshi / Vera), 2000-token cap,
51
+ and the Pugi observability stack () shipped earlier today.
52
+
53
+ ### Notes
54
+ - CLI surface unchanged in this bump — the version bump tracks lockstep with
55
+ the admin-api redeploy so `--version` reflects the live server's
56
+ feature set during the alpha-7 sprint.
57
+
58
+ ## [0.1.0-beta.23] - 2026-05-27
59
+
60
+ ### Added
61
+ - L30 `pugi theme` + `/theme` — TUI color presets (default / dark / light / colorblind) ().
62
+ - L24 `pugi release-notes` + `/release-notes` — changelog diff after upgrade
63
+ with `~/.pugi/.last-seen-version` tracking and `--reset` flag ().
64
+
65
+ ### Fixed
66
+ - vim-input — useRef for shadow cursor + pending, lift `onSubmit` out of `setState` ().
67
+
68
+ ## [0.1.0-beta.22] - 2026-05-27
69
+
70
+ ### Added
71
+ - L24 `pugi release-notes` + `/release-notes` — changelog diff after upgrade
72
+ with `~/.pugi/.last-seen-version` tracking and `--reset` flag.
73
+ - L25 `/onboarding` first-run interactive setup wizard ().
74
+ - L18 output-style presets — voice register dial ().
75
+ - L33 `/stickers` brand-personality gimmick ().
76
+ - L16 `TodoWriteTool` single-in-progress invariant ().
77
+ - L22 `--bare` flag — skip project auto-discovery ().
78
+ - L21 `/feedback` in-CLI collector.
79
+ - L20 `/share` session transcript export.
80
+
81
+ ### Fixed
82
+ - P1 stickers await + style buffered output + todo-write zod parse ().
83
+
84
+ ## [0.1.0-beta.21] - 2026-05-27
85
+
86
+ ### Added
87
+ - L7 `/plan` quick mode-switch + one-shot dispatch ().
88
+ - L31 tool retry budget per command ().
89
+ - L19 `/cost` + `/usage` token + dollar accounting ().
90
+ - L34 `pugi status` — session snapshot ().
91
+ - L11 `DenialTrackingState` model-facing denial aggregate ().
92
+ - L6 permission modes — canonical 4-mode gate ().
93
+ - L8 `/compact` command + auto-trigger + boundary marker ().
94
+ - L17 `pugi doctor` — environment health report ().
95
+ - L13 `/mcp remove` + `doctor` + `logs` + `restart` subcommands ().
96
+ - L3 internal underscore-prefix tool-arg convention ().
97
+ - L2 `z.strictObject` all tool schemas + revert beta.17 aliases ().
98
+ - L5 `AskUserQuestionTool` structured multi-choice — kills fake-dispatch ().
99
+ - L1 stale-read gate — reject `FileEdit` if file changed since last read ().
100
+
101
+ ### Fixed
102
+ - Pugi-review per-file chunking — unblock multi-file diffs (Anvil HTTP 400) ().
103
+ - Privacy `PiiScrubberService` regex fallback + `@Inject` DI fix ().
104
+
105
+ ## [0.1.0-beta.20] - 2026-05-26
106
+
107
+ ### Added
108
+ - Pugi codegen real dispatch — Pugi actually writes files instead of describing
109
+ them ().
110
+ - Live agent progress display — `pugi jobs --watch` (CC compact style) ().
111
+ - PAVF-7 `pugi report --from-error` — field bug capture ().
112
+ - Opensource template fetch + bundled starters — не reinventing ().
113
+
114
+ ### Fixed
115
+ - Dialog quality — RU mirror + brevity + memory + force dispatch + render ().
116
+ - Pugi anti-greenfield + anti-emoji discipline rules ().
117
+ - Persona output gate — Pugi strip + fake-dispatch detector (P0) ().
118
+
119
+ ## [0.1.0-beta.19] - 2026-05-26
120
+
121
+ ### Added
122
+ - Pugi-review batch review followups — silent PASS + safeGit split + quota
123
+ migration + cleanup dead code ().
124
+
125
+ ### Fixed
126
+ - Replace CJS `require()` в ESM bundle — bare REPL crash on beta.16 ().
127
+
128
+ ## [0.1.0-beta.18] - 2026-05-26
129
+
130
+ ### Added
131
+ - Initial public beta of `@pugi/cli` with REPL, dispatch, sync, review, and
132
+ doctor surfaces. Establishes the baseline for the leak-parity sprint.
package/LICENSE CHANGED
@@ -1,6 +1,6 @@
1
1
  MIT License
2
2
 
3
- Copyright (c) 2026 Yurii Bulakh
3
+ Copyright (c) 2026 Pugi.io
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
package/README.md CHANGED
@@ -1,23 +1,65 @@
1
1
  # Pugi CLI
2
2
 
3
3
  `pugi` — terminal-native software execution system. Run agents on your repo,
4
- hand jobs off to the cabinet or a remote runner, and keep every artifact local
5
- by default.
4
+ hand jobs off to the Pugi Console or a remote runner, and keep every artifact
5
+ local by default.
6
+
7
+ Current published version: **`@pugi/cli@0.1.0-beta.99`** (2026-06-05).
6
8
 
7
9
  - **Local-first.** Every plan, diff, and artifact lives under `.pugi/` in your
8
10
  repo. Nothing leaves the machine unless you explicitly run `pugi handoff` or
9
11
  `pugi sync`.
12
+ - **REPL-default.** Type `pugi` with no arguments and you drop into an
13
+ engine-backed chat REPL that can write files, start dev servers, probe
14
+ health, and run tests against real evidence (beta.96+).
10
15
  - **Web continuation.** When a job needs collaboration, an approval, or a clean
11
- Linux runner, hand it off to the cabinet at `app.pugi.io`.
16
+ Linux runner, hand it off to the Console at `app.pugi.io`.
12
17
  - **One CLI, three install paths.** npm, Homebrew tap, and a one-liner shell
13
18
  script.
14
19
 
20
+ ## Recent shipped (beta.94 → beta.99)
21
+
22
+ - **REPL as first-class engine path** (beta.96, PR A). REPL chat goes through
23
+ the Pugi engine loop, advertises tools, writes files on disk.
24
+ - **Phase 1 runtime primitives** (beta.97, ): `server_start`,
25
+ `server_stop`, `server_health`, `server_logs`, `http_request` available in
26
+ the tool surface so the agent can prove a server is up (pid + health 200)
27
+ rather than narrating it.
28
+ - **Conversation-aware artifact intent** (beta.97, ). Multi-turn
29
+ confirmation triggers auto-dispatch; the agent stops asking "should I?" mid
30
+ build.
31
+ - **Multi-turn context threading** (beta.98, PR C). REPL `dispatchBrief`
32
+ threads recent turns to the engine bridge; engine budget bumped к 400K.
33
+ - **Budget cap removed** (beta.99). 120K cap retired in favour of the
34
+ Claude/Codex/Aider auto-compact pattern. Effective ceiling is now 5M tokens
35
+ on the long-context lane.
36
+ - **Verification gate** (beta.94, ). Failing `npm test` propagates
37
+ `exit != 0` and forces `status != done`. No more "fake green" completions.
38
+
39
+ ## Coming next (open PRs, awaiting merge as of 2026-06-05)
40
+
41
+ - **LLM-summary auto-compact** (PR E #916). REPL session history is summarized
42
+ via Gemini Flash on the Anvil gateway before re-entering the context window,
43
+ so long sessions stay coherent instead of getting truncated.
44
+ - **Obsidian-style notes** (PR F #918). Every session writes to
45
+ `.pugi/notes/<session-id>.md`, per-file notes to `.pugi/notes/files/<path>.md`,
46
+ and a daily journal entry to `.pugi/journal/YYYY-MM-DD.md`. Backed by
47
+ Obsidian-compatible wiki-link syntax.
48
+ - **`/servers` slash command** (PR H #919). List and kill dev servers spawned
49
+ via `server_start` from the REPL. `/servers` prints the running set,
50
+ `/servers stop <jobId>` terminates one.
51
+ - **USD + English defaults for generated apps** (PR I #920). When you brief the
52
+ agent in Russian or any other locale, generated UIs default к **English text
53
+ + USD prices** unless you explicitly say "target market is X" in the brief.
54
+ Eliminates the "₽ rubles in a UI for US customers" regression. Pair with the
55
+ `/servers stop` hint в the `code` / `build` / `fix` prompts.
56
+
15
57
  ## Install
16
58
 
17
59
  ### npm (works everywhere with Node 20+)
18
60
 
19
61
  ```bash
20
- npm install -g pugi
62
+ npm install -g @pugi/cli
21
63
  pugi --version
22
64
  ```
23
65
 
@@ -29,7 +71,7 @@ pugi --version
29
71
  ```
30
72
 
31
73
  The formula declares a Node 20+ runtime dependency and downloads the published
32
- npm tarball, so the result is identical to `npm install -g pugi`.
74
+ npm tarball, so the result is identical to `npm install -g @pugi/cli`.
33
75
 
34
76
  ### One-liner (curl)
35
77
 
@@ -38,8 +80,8 @@ curl -fsSL https://pugi.dev/install | sh
38
80
  ```
39
81
 
40
82
  The script detects your OS (Darwin / Linux), bootstraps Node 20+ via Homebrew
41
- or `apt` if it is missing, and then runs `npm install -g pugi`. It prints the
42
- installed version on success and exits non-zero on any failure. The script
83
+ or `apt` if it is missing, and then runs `npm install -g @pugi/cli`. It prints
84
+ the installed version on success and exits non-zero on any failure. The script
43
85
  itself is served from `pugi.dev`; review it at `https://pugi.dev/install` or
44
86
  in `apps/admin-api/public/install.sh` before piping into a shell.
45
87
 
@@ -92,6 +134,8 @@ pugi review --triple # local triple-review evidence bundle
92
134
  pugi review --triple --remote
93
135
  # call Anvil for 3-model consensus
94
136
  pugi handoff --web # hand the session off to the cabinet
137
+ pugi servers # list dev servers tracked by server_start
138
+ pugi servers stop all # kill every alive tracked server (orphan rescue)
95
139
  pugi sessions # list sessions from .pugi/index.json
96
140
  pugi sessions --rebuild # rebuild the index from events.jsonl
97
141
  pugi deploy --target vercel my-vercel-project --project proj_42
@@ -143,15 +187,15 @@ returns `status: blocked, reason: sync_upload_not_implemented`).
143
187
  ## Updating
144
188
 
145
189
  ```bash
146
- npm install -g pugi@latest # if you installed via npm
147
- brew upgrade pugi # if you installed via Homebrew
148
- curl -fsSL https://pugi.dev/install | sh # one-liner re-run is idempotent
190
+ npm install -g @pugi/cli@latest # if you installed via npm
191
+ brew upgrade pugi # if you installed via Homebrew
192
+ curl -fsSL https://pugi.dev/install | sh # one-liner re-run is idempotent
149
193
  ```
150
194
 
151
195
  ## Uninstall
152
196
 
153
197
  ```bash
154
- npm uninstall -g pugi
198
+ npm uninstall -g @pugi/cli
155
199
  # or
156
200
  brew uninstall pugi
157
201
  ```
@@ -0,0 +1,9 @@
1
+ [?25l 
2
+ 
3
+ ▄▄▄▄▄▄▄▄ 
4
+ ▄▄▄▄▄▄ 
5
+ ▄▄▄▄▄▄ 
6
+ ▄▄ 
7
+ ▄ 
8
+ 
9
+ [?25h
package/bin/run.js CHANGED
@@ -1,2 +1,34 @@
1
1
  #!/usr/bin/env node
2
- import '../dist/index.js';
2
+ // 2026-05-27 — silence the noisy `node:sqlite` ExperimentalWarning.
3
+ // Node 22.x prints a multi-line warning the first time any consumer
4
+ // imports `node:sqlite` (see core/repl/store/session-store.ts). CEO has
5
+ // pinged this surface twice now ("(node:XXXXX) ExperimentalWarning:
6
+ // SQLite is an experimental feature and might change at any time" +
7
+ // trace-warnings hint). Hiding it cleanly requires a tap on
8
+ // process.emitWarning BEFORE any module loads the sqlite binding —
9
+ // hence wiring it here in the binary entry, not deep inside the CLI.
10
+ //
11
+ // We allowlist only the exact sqlite warning + leave every other
12
+ // runtime warning (deprecation, security, custom code paths) intact.
13
+ // Operator can still re-enable the noise by exporting
14
+ // PUGI_SHOW_EXPERIMENTAL_WARNINGS=1 — useful when debugging a node
15
+ // version bump that might surface a new experimental flag we should
16
+ // notice.
17
+ if (!process.env.PUGI_SHOW_EXPERIMENTAL_WARNINGS) {
18
+ const originalEmit = process.emit;
19
+ process.emit = function patchedEmit(name, ...args) {
20
+ if (name === 'warning') {
21
+ const w = args[0];
22
+ const isSqliteExperimental =
23
+ w &&
24
+ typeof w === 'object' &&
25
+ w.name === 'ExperimentalWarning' &&
26
+ typeof w.message === 'string' &&
27
+ /SQLite is an experimental feature/i.test(w.message);
28
+ if (isSqliteExperimental) return false;
29
+ }
30
+ return originalEmit.call(this, name, ...args);
31
+ };
32
+ }
33
+
34
+ import('../dist/index.js');
@@ -1,27 +1,27 @@
1
1
  /**
2
- * `pugi deploy` command surface — Wave 3 P2 (Task #34, 2026-05-25).
2
+ * `pugi deploy` command surface — P2 (Task #34).
3
3
  *
4
4
  * Subcommands:
5
- * pugi deploy --target vercel <vercelProject> [--project <id>] [--ref <ref>] [--target-env production|preview] [--integration <id>]
6
- * pugi deploy --target render <renderService> [--project <id>] [--ref <ref>]
7
- * pugi deploy --status <deployment-id>
8
- * pugi deploy --logs <deployment-id> [--tail]
5
+ * pugi deploy --target vercel <vercelProject> [--project <id>] [--ref <ref>] [--target-env production|preview] [--integration <id>]
6
+ * pugi deploy --target render <renderService> [--project <id>] [--ref <ref>]
7
+ * pugi deploy --status <deployment-id>
8
+ * pugi deploy --logs <deployment-id> [--tail]
9
9
  *
10
10
  * Exit codes (per task spec):
11
- * 0 success (trigger queued, status terminal=ready, logs printed)
12
- * 1 deployment failed (status=error or trigger refused)
13
- * 2 transient (rate-limited, runtime down, retry-safe)
11
+ * 0 success (trigger queued, status terminal=ready, logs printed)
12
+ * 1 deployment failed (status=error or trigger refused)
13
+ * 2 transient (rate-limited, runtime down, retry-safe)
14
14
  *
15
15
  * Project resolution:
16
- * `--project <id>` is required for trigger commands because the CLI's
17
- * credential store is tenant-scoped but not project-scoped. A future
18
- * sprint (Wave 4) auto-detects the project from `.pugi/settings.json`
19
- * bound to the workspace; until then the operator passes it explicitly.
16
+ * `--project <id>` is required for trigger commands because the CLI's
17
+ * credential store is tenant-scoped but not project-scoped. A future
18
+ * sprint auto-detects the project from `.pugi/settings.json`
19
+ * bound to the workspace; until then the operator passes it explicitly.
20
20
  *
21
- * Local-first invariant (ADR-0037):
22
- * `pugi deploy` does NOT read repository files. The Vercel deploy
23
- * resolves source from the existing ProjectGitBinding row on the
24
- * admin-api side — the CLI is only a request initiator + status poller.
21
+ * Local-first invariant :
22
+ * `pugi deploy` does NOT read repository files. The Vercel deploy
23
+ * resolves source from the existing ProjectGitBinding row on the
24
+ * admin-api side — the CLI is only a request initiator + status poller.
25
25
  */
26
26
  import { fetchDeployStatus, fetchDeployLogs, submitDeployTrigger, } from '@pugi/sdk';
27
27
  /**
@@ -143,26 +143,26 @@ export function parseDeployArgs(args) {
143
143
  export function usage() {
144
144
  return [
145
145
  'Usage:',
146
- ' pugi deploy --target vercel <vercelProject> --project <id> [--target-env production|preview] [--ref <git-ref>] [--integration <id>]',
147
- ' pugi deploy --target render <renderService> --project <id> [--ref <git-ref>]',
148
- ' pugi deploy --status <deployment-id>',
149
- ' pugi deploy --logs <deployment-id> [--tail]',
146
+ ' pugi deploy --target vercel <vercelProject> --project <id> [--target-env production|preview] [--ref <git-ref>] [--integration <id>]',
147
+ ' pugi deploy --target render <renderService> --project <id> [--ref <git-ref>]',
148
+ ' pugi deploy --status <deployment-id>',
149
+ ' pugi deploy --logs <deployment-id> [--tail]',
150
150
  '',
151
151
  'Flags:',
152
- ' --target vercel|render Provider to deploy to.',
153
- ' --project <id> Pugi project id (required for trigger).',
154
- ' --ref <git-ref> Optional Git ref. Defaults to the binding default branch.',
155
- ' --target-env production|preview',
156
- ' Vercel deploy environment. Defaults to production.',
157
- ' --integration <id> Disambiguate when multiple integrations are active.',
158
- ' --status <id> Show the current status for a deployment.',
159
- ' --logs <id> [--tail] Fetch log tail. With --tail, polls until terminal.',
160
- ' --json Emit machine-readable JSON envelopes.',
152
+ ' --target vercel|render Provider to deploy to.',
153
+ ' --project <id> Pugi project id (required for trigger).',
154
+ ' --ref <git-ref> Optional Git ref. Defaults to the binding default branch.',
155
+ ' --target-env production|preview',
156
+ ' Vercel deploy environment. Defaults to production.',
157
+ ' --integration <id> Disambiguate when multiple integrations are active.',
158
+ ' --status <id> Show the current status for a deployment.',
159
+ ' --logs <id> [--tail] Fetch log tail. With --tail, polls until terminal.',
160
+ ' --json Emit machine-readable JSON envelopes.',
161
161
  '',
162
162
  'Exit codes:',
163
- ' 0 success',
164
- ' 1 deployment failed / refused',
165
- ' 2 transient (rate-limited, runtime down, retry-safe)',
163
+ ' 0 success',
164
+ ' 1 deployment failed / refused',
165
+ ' 2 transient (rate-limited, runtime down, retry-safe)',
166
166
  ].join('\n');
167
167
  }
168
168
  /**
@@ -418,16 +418,16 @@ function statusToExitCode(status) {
418
418
  function renderStatusTable(response, context) {
419
419
  const lines = [];
420
420
  lines.push(context === 'queued' ? 'Deployment queued.' : 'Deployment status:');
421
- lines.push(` id: ${response.id}`);
422
- lines.push(` provider: ${response.provider}`);
423
- lines.push(` project: ${response.projectId}`);
424
- lines.push(` status: ${response.status}`);
421
+ lines.push(` id: ${response.id}`);
422
+ lines.push(` provider: ${response.provider}`);
423
+ lines.push(` project: ${response.projectId}`);
424
+ lines.push(` status: ${response.status}`);
425
425
  if (response.url)
426
- lines.push(` url: ${response.url}`);
426
+ lines.push(` url: ${response.url}`);
427
427
  if (response.providerDeploymentId)
428
- lines.push(` providerDeploymentId: ${response.providerDeploymentId}`);
429
- lines.push(` createdAt: ${response.createdAt}`);
430
- lines.push(` updatedAt: ${response.updatedAt}`);
428
+ lines.push(` providerDeploymentId: ${response.providerDeploymentId}`);
429
+ lines.push(` createdAt: ${response.createdAt}`);
430
+ lines.push(` updatedAt: ${response.updatedAt}`);
431
431
  if (response.error) {
432
432
  lines.push('');
433
433
  lines.push('--- build error tail ---');
@@ -0,0 +1,191 @@
1
+ /**
2
+ * `pugi flatten` — CLI surface for the rendergit-port flatten engine.
3
+ *
4
+ * The runner lives here (not in `runtime/cli.ts`) so the dispatch
5
+ * surface stays focused on argv routing. This module owns:
6
+ *
7
+ * - Parsing the command-local flags (`--mode`, `--max-file-size`,
8
+ * `--include`, `--exclude`, `--stdout`, `--open`, `--out`).
9
+ * - Routing to `flattenRepo` with a resolved option bag.
10
+ * - Forwarding the rendered text + summary through the unified
11
+ * `writeOutput` writer so `--json` mode works without a second
12
+ * code path.
13
+ *
14
+ * Ported from karpathy/rendergit (BSD-0). License compatible with
15
+ * Pugi's open-source posture.
16
+ */
17
+ import { resolve } from 'node:path';
18
+ import { DEFAULT_MAX_FILE_SIZE, flattenRepo, } from '../core/flatten/flatten-repo.js';
19
+ /**
20
+ * Entry point invoked by `runtime/cli.ts::dispatchFlatten`. Returns
21
+ * the desired process exit code so the dispatcher can set
22
+ * `process.exitCode` without a second round-trip.
23
+ */
24
+ export async function runFlattenCommand(ctx) {
25
+ const parsed = parseArgs(ctx.args);
26
+ if ('error' in parsed) {
27
+ ctx.writeOutput({ ok: false, error: parsed.error }, `pugi flatten: ${parsed.error}`);
28
+ return 2;
29
+ }
30
+ const options = {
31
+ cwd: parsed.cwd,
32
+ mode: parsed.mode,
33
+ stdout: parsed.stdout,
34
+ maxFileSize: parsed.maxFileSize,
35
+ include: parsed.include,
36
+ exclude: parsed.exclude,
37
+ open: parsed.open,
38
+ };
39
+ try {
40
+ const result = await flattenRepo(options);
41
+ if (parsed.stdout) {
42
+ // Always emit the rendered text to stdout. JSON mode wraps it
43
+ // in an envelope so scripted callers can demux the result from
44
+ // the summary line.
45
+ if (ctx.json) {
46
+ ctx.writeOutput({
47
+ ok: true,
48
+ mode: parsed.mode,
49
+ files: result.files.length,
50
+ skipped: result.skipped.length,
51
+ html: result.html,
52
+ }, result.html);
53
+ }
54
+ else {
55
+ process.stdout.write(result.html);
56
+ }
57
+ return 0;
58
+ }
59
+ const summary = `pugi flatten: wrote ${result.files.length} files (${result.skipped.length} skipped) to ${result.path ?? '<unknown>'}`;
60
+ ctx.writeOutput({
61
+ ok: true,
62
+ mode: parsed.mode,
63
+ path: result.path,
64
+ files: result.files.length,
65
+ skipped: result.skipped.length,
66
+ }, summary);
67
+ return 0;
68
+ }
69
+ catch (err) {
70
+ const msg = err instanceof Error ? err.message : String(err);
71
+ ctx.writeOutput({ ok: false, error: msg }, `pugi flatten: ${msg}`);
72
+ return 1;
73
+ }
74
+ }
75
+ function parseArgs(args) {
76
+ let cwd = process.cwd();
77
+ let mode = 'human';
78
+ let stdout = false;
79
+ let open = false;
80
+ let maxFileSize = DEFAULT_MAX_FILE_SIZE;
81
+ const include = [];
82
+ const exclude = [];
83
+ let positionalConsumed = false;
84
+ for (let i = 0; i < args.length; i += 1) {
85
+ const arg = args[i] ?? '';
86
+ if (arg === '--stdout') {
87
+ stdout = true;
88
+ continue;
89
+ }
90
+ if (arg === '--open') {
91
+ open = true;
92
+ continue;
93
+ }
94
+ if (arg === '--mode') {
95
+ const next = args[i + 1];
96
+ if (!next)
97
+ return { error: '--mode requires a value (human | llm)' };
98
+ const m = parseMode(next);
99
+ if (!m)
100
+ return { error: `--mode: unknown value "${next}" (expected human | llm)` };
101
+ mode = m;
102
+ i += 1;
103
+ continue;
104
+ }
105
+ if (arg.startsWith('--mode=')) {
106
+ const m = parseMode(arg.slice('--mode='.length));
107
+ if (!m)
108
+ return { error: `--mode: unknown value "${arg.slice('--mode='.length)}" (expected human | llm)` };
109
+ mode = m;
110
+ continue;
111
+ }
112
+ if (arg === '--max-file-size') {
113
+ const next = args[i + 1];
114
+ if (!next)
115
+ return { error: '--max-file-size requires a value (e.g. 200kb)' };
116
+ const n = parseSize(next);
117
+ if (n === undefined)
118
+ return { error: `--max-file-size: cannot parse "${next}"` };
119
+ maxFileSize = n;
120
+ i += 1;
121
+ continue;
122
+ }
123
+ if (arg.startsWith('--max-file-size=')) {
124
+ const v = arg.slice('--max-file-size='.length);
125
+ const n = parseSize(v);
126
+ if (n === undefined)
127
+ return { error: `--max-file-size: cannot parse "${v}"` };
128
+ maxFileSize = n;
129
+ continue;
130
+ }
131
+ if (arg === '--include') {
132
+ const next = args[i + 1];
133
+ if (!next)
134
+ return { error: '--include requires a pattern' };
135
+ include.push(next);
136
+ i += 1;
137
+ continue;
138
+ }
139
+ if (arg.startsWith('--include=')) {
140
+ include.push(arg.slice('--include='.length));
141
+ continue;
142
+ }
143
+ if (arg === '--exclude') {
144
+ const next = args[i + 1];
145
+ if (!next)
146
+ return { error: '--exclude requires a pattern' };
147
+ exclude.push(next);
148
+ i += 1;
149
+ continue;
150
+ }
151
+ if (arg.startsWith('--exclude=')) {
152
+ exclude.push(arg.slice('--exclude='.length));
153
+ continue;
154
+ }
155
+ if (arg.startsWith('--')) {
156
+ return { error: `unknown flag "${arg}"` };
157
+ }
158
+ // Positional: workspace path. Only the first non-flag wins; extras
159
+ // are an error so a typo (`pugi flatten . foo`) surfaces.
160
+ if (positionalConsumed) {
161
+ return { error: `unexpected positional argument "${arg}"` };
162
+ }
163
+ cwd = resolve(arg);
164
+ positionalConsumed = true;
165
+ }
166
+ return { cwd, mode, stdout, open, maxFileSize, include, exclude };
167
+ }
168
+ function parseMode(v) {
169
+ if (v === 'human' || v === 'llm')
170
+ return v;
171
+ return undefined;
172
+ }
173
+ /**
174
+ * Parse a size literal: bare number = bytes; `200kb` / `1mb` / `2gb`
175
+ * (case-insensitive, binary units — 1KB = 1024 bytes).
176
+ */
177
+ export function parseSize(raw) {
178
+ const trimmed = raw.trim().toLowerCase();
179
+ if (trimmed.length === 0)
180
+ return undefined;
181
+ const match = /^(\d+(?:\.\d+)?)\s*(b|kb|mb|gb)?$/.exec(trimmed);
182
+ if (!match)
183
+ return undefined;
184
+ const n = Number(match[1]);
185
+ if (!Number.isFinite(n) || n < 0)
186
+ return undefined;
187
+ const unit = match[2] ?? 'b';
188
+ const multiplier = unit === 'b' ? 1 : unit === 'kb' ? 1024 : unit === 'mb' ? 1024 * 1024 : 1024 * 1024 * 1024;
189
+ return Math.floor(n * multiplier);
190
+ }
191
+ //# sourceMappingURL=flatten.js.map