verbolab 0.1.0-alpha.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (493) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +71 -0
  3. package/dist/bin/verbo.d.ts +3 -0
  4. package/dist/bin/verbo.d.ts.map +1 -0
  5. package/dist/bin/verbo.js +1156 -0
  6. package/dist/bin/verbo.js.map +1 -0
  7. package/dist/relay/index.d.ts +2 -0
  8. package/dist/relay/index.d.ts.map +1 -0
  9. package/dist/relay/index.js +15 -0
  10. package/dist/relay/index.js.map +1 -0
  11. package/dist/src/agent/agent-launcher.d.ts +64 -0
  12. package/dist/src/agent/agent-launcher.d.ts.map +1 -0
  13. package/dist/src/agent/agent-launcher.js +326 -0
  14. package/dist/src/agent/agent-launcher.js.map +1 -0
  15. package/dist/src/agent/agent-monitor.d.ts +16 -0
  16. package/dist/src/agent/agent-monitor.d.ts.map +1 -0
  17. package/dist/src/agent/agent-monitor.js +41 -0
  18. package/dist/src/agent/agent-monitor.js.map +1 -0
  19. package/dist/src/agent/fun-names.d.ts +9 -0
  20. package/dist/src/agent/fun-names.d.ts.map +1 -0
  21. package/dist/src/agent/fun-names.js +118 -0
  22. package/dist/src/agent/fun-names.js.map +1 -0
  23. package/dist/src/agent/mcp-shim.d.ts +45 -0
  24. package/dist/src/agent/mcp-shim.d.ts.map +1 -0
  25. package/dist/src/agent/mcp-shim.js +192 -0
  26. package/dist/src/agent/mcp-shim.js.map +1 -0
  27. package/dist/src/agent/personas.d.ts +47 -0
  28. package/dist/src/agent/personas.d.ts.map +1 -0
  29. package/dist/src/agent/personas.js +86 -0
  30. package/dist/src/agent/personas.js.map +1 -0
  31. package/dist/src/agent/provider-detection.d.ts +21 -0
  32. package/dist/src/agent/provider-detection.d.ts.map +1 -0
  33. package/dist/src/agent/provider-detection.js +47 -0
  34. package/dist/src/agent/provider-detection.js.map +1 -0
  35. package/dist/src/agent/providers/claude-provider.d.ts +3 -0
  36. package/dist/src/agent/providers/claude-provider.d.ts.map +1 -0
  37. package/dist/src/agent/providers/claude-provider.js +119 -0
  38. package/dist/src/agent/providers/claude-provider.js.map +1 -0
  39. package/dist/src/agent/providers/gemini-provider.d.ts +13 -0
  40. package/dist/src/agent/providers/gemini-provider.d.ts.map +1 -0
  41. package/dist/src/agent/providers/gemini-provider.js +143 -0
  42. package/dist/src/agent/providers/gemini-provider.js.map +1 -0
  43. package/dist/src/agent/providers/openai-provider.d.ts +3 -0
  44. package/dist/src/agent/providers/openai-provider.d.ts.map +1 -0
  45. package/dist/src/agent/providers/openai-provider.js +127 -0
  46. package/dist/src/agent/providers/openai-provider.js.map +1 -0
  47. package/dist/src/agent/providers/registry.d.ts +19 -0
  48. package/dist/src/agent/providers/registry.d.ts.map +1 -0
  49. package/dist/src/agent/providers/registry.js +30 -0
  50. package/dist/src/agent/providers/registry.js.map +1 -0
  51. package/dist/src/agent/providers/types.d.ts +118 -0
  52. package/dist/src/agent/providers/types.d.ts.map +1 -0
  53. package/dist/src/agent/providers/types.js +2 -0
  54. package/dist/src/agent/providers/types.js.map +1 -0
  55. package/dist/src/approval/approval-server.d.ts +17 -0
  56. package/dist/src/approval/approval-server.d.ts.map +1 -0
  57. package/dist/src/approval/approval-server.js +90 -0
  58. package/dist/src/approval/approval-server.js.map +1 -0
  59. package/dist/src/approval/approval-store.d.ts +29 -0
  60. package/dist/src/approval/approval-store.d.ts.map +1 -0
  61. package/dist/src/approval/approval-store.js +94 -0
  62. package/dist/src/approval/approval-store.js.map +1 -0
  63. package/dist/src/auth/auth-store.d.ts +18 -0
  64. package/dist/src/auth/auth-store.d.ts.map +1 -0
  65. package/dist/src/auth/auth-store.js +34 -0
  66. package/dist/src/auth/auth-store.js.map +1 -0
  67. package/dist/src/auth/device-code-client.d.ts +32 -0
  68. package/dist/src/auth/device-code-client.d.ts.map +1 -0
  69. package/dist/src/auth/device-code-client.js +41 -0
  70. package/dist/src/auth/device-code-client.js.map +1 -0
  71. package/dist/src/auth/plan-enforcer.d.ts +8 -0
  72. package/dist/src/auth/plan-enforcer.d.ts.map +1 -0
  73. package/dist/src/auth/plan-enforcer.js +14 -0
  74. package/dist/src/auth/plan-enforcer.js.map +1 -0
  75. package/dist/src/commands/audit.d.ts +7 -0
  76. package/dist/src/commands/audit.d.ts.map +1 -0
  77. package/dist/src/commands/audit.js +92 -0
  78. package/dist/src/commands/audit.js.map +1 -0
  79. package/dist/src/commands/team.d.ts +48 -0
  80. package/dist/src/commands/team.d.ts.map +1 -0
  81. package/dist/src/commands/team.js +175 -0
  82. package/dist/src/commands/team.js.map +1 -0
  83. package/dist/src/config/verbo-config.d.ts +43 -0
  84. package/dist/src/config/verbo-config.d.ts.map +1 -0
  85. package/dist/src/config/verbo-config.js +111 -0
  86. package/dist/src/config/verbo-config.js.map +1 -0
  87. package/dist/src/core/agent-session-store.d.ts +69 -0
  88. package/dist/src/core/agent-session-store.d.ts.map +1 -0
  89. package/dist/src/core/agent-session-store.js +168 -0
  90. package/dist/src/core/agent-session-store.js.map +1 -0
  91. package/dist/src/core/audit-log-store.d.ts +33 -0
  92. package/dist/src/core/audit-log-store.d.ts.map +1 -0
  93. package/dist/src/core/audit-log-store.js +104 -0
  94. package/dist/src/core/audit-log-store.js.map +1 -0
  95. package/dist/src/core/compliance.d.ts +50 -0
  96. package/dist/src/core/compliance.d.ts.map +1 -0
  97. package/dist/src/core/compliance.js +59 -0
  98. package/dist/src/core/compliance.js.map +1 -0
  99. package/dist/src/core/conflict-detector.d.ts +19 -0
  100. package/dist/src/core/conflict-detector.d.ts.map +1 -0
  101. package/dist/src/core/conflict-detector.js +87 -0
  102. package/dist/src/core/conflict-detector.js.map +1 -0
  103. package/dist/src/core/conflict-enforcer.d.ts +37 -0
  104. package/dist/src/core/conflict-enforcer.d.ts.map +1 -0
  105. package/dist/src/core/conflict-enforcer.js +139 -0
  106. package/dist/src/core/conflict-enforcer.js.map +1 -0
  107. package/dist/src/core/cost-store.d.ts +55 -0
  108. package/dist/src/core/cost-store.d.ts.map +1 -0
  109. package/dist/src/core/cost-store.js +140 -0
  110. package/dist/src/core/cost-store.js.map +1 -0
  111. package/dist/src/core/hot-files.d.ts +19 -0
  112. package/dist/src/core/hot-files.d.ts.map +1 -0
  113. package/dist/src/core/hot-files.js +64 -0
  114. package/dist/src/core/hot-files.js.map +1 -0
  115. package/dist/src/core/human-action-store.d.ts +33 -0
  116. package/dist/src/core/human-action-store.d.ts.map +1 -0
  117. package/dist/src/core/human-action-store.js +92 -0
  118. package/dist/src/core/human-action-store.js.map +1 -0
  119. package/dist/src/core/learning-store.d.ts +32 -0
  120. package/dist/src/core/learning-store.d.ts.map +1 -0
  121. package/dist/src/core/learning-store.js +95 -0
  122. package/dist/src/core/learning-store.js.map +1 -0
  123. package/dist/src/core/merge-queue.d.ts +28 -0
  124. package/dist/src/core/merge-queue.d.ts.map +1 -0
  125. package/dist/src/core/merge-queue.js +92 -0
  126. package/dist/src/core/merge-queue.js.map +1 -0
  127. package/dist/src/core/notification-service.d.ts +13 -0
  128. package/dist/src/core/notification-service.d.ts.map +1 -0
  129. package/dist/src/core/notification-service.js +126 -0
  130. package/dist/src/core/notification-service.js.map +1 -0
  131. package/dist/src/core/notifications.d.ts +10 -0
  132. package/dist/src/core/notifications.d.ts.map +1 -0
  133. package/dist/src/core/notifications.js +33 -0
  134. package/dist/src/core/notifications.js.map +1 -0
  135. package/dist/src/core/orchestrator-store.d.ts +44 -0
  136. package/dist/src/core/orchestrator-store.d.ts.map +1 -0
  137. package/dist/src/core/orchestrator-store.js +69 -0
  138. package/dist/src/core/orchestrator-store.js.map +1 -0
  139. package/dist/src/core/parallelizer.d.ts +47 -0
  140. package/dist/src/core/parallelizer.d.ts.map +1 -0
  141. package/dist/src/core/parallelizer.js +224 -0
  142. package/dist/src/core/parallelizer.js.map +1 -0
  143. package/dist/src/core/pipeline-rollback.d.ts +29 -0
  144. package/dist/src/core/pipeline-rollback.d.ts.map +1 -0
  145. package/dist/src/core/pipeline-rollback.js +84 -0
  146. package/dist/src/core/pipeline-rollback.js.map +1 -0
  147. package/dist/src/core/pipeline-runner.d.ts +73 -0
  148. package/dist/src/core/pipeline-runner.d.ts.map +1 -0
  149. package/dist/src/core/pipeline-runner.js +165 -0
  150. package/dist/src/core/pipeline-runner.js.map +1 -0
  151. package/dist/src/core/pr-creator.d.ts +22 -0
  152. package/dist/src/core/pr-creator.d.ts.map +1 -0
  153. package/dist/src/core/pr-creator.js +55 -0
  154. package/dist/src/core/pr-creator.js.map +1 -0
  155. package/dist/src/core/rbac.d.ts +27 -0
  156. package/dist/src/core/rbac.d.ts.map +1 -0
  157. package/dist/src/core/rbac.js +76 -0
  158. package/dist/src/core/rbac.js.map +1 -0
  159. package/dist/src/core/startup-cleanup.d.ts +47 -0
  160. package/dist/src/core/startup-cleanup.d.ts.map +1 -0
  161. package/dist/src/core/startup-cleanup.js +150 -0
  162. package/dist/src/core/startup-cleanup.js.map +1 -0
  163. package/dist/src/core/task-store.d.ts +96 -0
  164. package/dist/src/core/task-store.d.ts.map +1 -0
  165. package/dist/src/core/task-store.js +309 -0
  166. package/dist/src/core/task-store.js.map +1 -0
  167. package/dist/src/core/verbo-config-editor.d.ts +44 -0
  168. package/dist/src/core/verbo-config-editor.d.ts.map +1 -0
  169. package/dist/src/core/verbo-config-editor.js +204 -0
  170. package/dist/src/core/verbo-config-editor.js.map +1 -0
  171. package/dist/src/core/verbo-config.d.ts +35 -0
  172. package/dist/src/core/verbo-config.d.ts.map +1 -0
  173. package/dist/src/core/verbo-config.js +55 -0
  174. package/dist/src/core/verbo-config.js.map +1 -0
  175. package/dist/src/core/verbo-md.d.ts +96 -0
  176. package/dist/src/core/verbo-md.d.ts.map +1 -0
  177. package/dist/src/core/verbo-md.js +410 -0
  178. package/dist/src/core/verbo-md.js.map +1 -0
  179. package/dist/src/db/database.d.ts +9 -0
  180. package/dist/src/db/database.d.ts.map +1 -0
  181. package/dist/src/db/database.js +37 -0
  182. package/dist/src/db/database.js.map +1 -0
  183. package/dist/src/db/migrations/001-personas-subtasks.d.ts +10 -0
  184. package/dist/src/db/migrations/001-personas-subtasks.d.ts.map +1 -0
  185. package/dist/src/db/migrations/001-personas-subtasks.js +32 -0
  186. package/dist/src/db/migrations/001-personas-subtasks.js.map +1 -0
  187. package/dist/src/db/migrations/002-rbac.d.ts +9 -0
  188. package/dist/src/db/migrations/002-rbac.d.ts.map +1 -0
  189. package/dist/src/db/migrations/002-rbac.js +31 -0
  190. package/dist/src/db/migrations/002-rbac.js.map +1 -0
  191. package/dist/src/db/migrations/003-provider-column.d.ts +8 -0
  192. package/dist/src/db/migrations/003-provider-column.d.ts.map +1 -0
  193. package/dist/src/db/migrations/003-provider-column.js +12 -0
  194. package/dist/src/db/migrations/003-provider-column.js.map +1 -0
  195. package/dist/src/db/migrations/004-pipeline-cost.d.ts +8 -0
  196. package/dist/src/db/migrations/004-pipeline-cost.d.ts.map +1 -0
  197. package/dist/src/db/migrations/004-pipeline-cost.js +23 -0
  198. package/dist/src/db/migrations/004-pipeline-cost.js.map +1 -0
  199. package/dist/src/db/migrations/005-audit-log-timestamp.d.ts +10 -0
  200. package/dist/src/db/migrations/005-audit-log-timestamp.d.ts.map +1 -0
  201. package/dist/src/db/migrations/005-audit-log-timestamp.js +39 -0
  202. package/dist/src/db/migrations/005-audit-log-timestamp.js.map +1 -0
  203. package/dist/src/db/migrations/006-human-action-type.d.ts +9 -0
  204. package/dist/src/db/migrations/006-human-action-type.d.ts.map +1 -0
  205. package/dist/src/db/migrations/006-human-action-type.js +16 -0
  206. package/dist/src/db/migrations/006-human-action-type.js.map +1 -0
  207. package/dist/src/db/schema.d.ts +6 -0
  208. package/dist/src/db/schema.d.ts.map +1 -0
  209. package/dist/src/db/schema.js +255 -0
  210. package/dist/src/db/schema.js.map +1 -0
  211. package/dist/src/deps/dependabot-generator.d.ts +22 -0
  212. package/dist/src/deps/dependabot-generator.d.ts.map +1 -0
  213. package/dist/src/deps/dependabot-generator.js +83 -0
  214. package/dist/src/deps/dependabot-generator.js.map +1 -0
  215. package/dist/src/deps/dependabot-monitor.d.ts +22 -0
  216. package/dist/src/deps/dependabot-monitor.d.ts.map +1 -0
  217. package/dist/src/deps/dependabot-monitor.js +28 -0
  218. package/dist/src/deps/dependabot-monitor.js.map +1 -0
  219. package/dist/src/deps/package-auditor.d.ts +24 -0
  220. package/dist/src/deps/package-auditor.d.ts.map +1 -0
  221. package/dist/src/deps/package-auditor.js +118 -0
  222. package/dist/src/deps/package-auditor.js.map +1 -0
  223. package/dist/src/init/ensure-init.d.ts +6 -0
  224. package/dist/src/init/ensure-init.d.ts.map +1 -0
  225. package/dist/src/init/ensure-init.js +27 -0
  226. package/dist/src/init/ensure-init.js.map +1 -0
  227. package/dist/src/init/project-detector.d.ts +11 -0
  228. package/dist/src/init/project-detector.d.ts.map +1 -0
  229. package/dist/src/init/project-detector.js +117 -0
  230. package/dist/src/init/project-detector.js.map +1 -0
  231. package/dist/src/init/questionnaire.d.ts +5 -0
  232. package/dist/src/init/questionnaire.d.ts.map +1 -0
  233. package/dist/src/init/questionnaire.js +112 -0
  234. package/dist/src/init/questionnaire.js.map +1 -0
  235. package/dist/src/init/template.d.ts +17 -0
  236. package/dist/src/init/template.d.ts.map +1 -0
  237. package/dist/src/init/template.js +46 -0
  238. package/dist/src/init/template.js.map +1 -0
  239. package/dist/src/intelligence/claude-client.d.ts +3 -0
  240. package/dist/src/intelligence/claude-client.d.ts.map +1 -0
  241. package/dist/src/intelligence/claude-client.js +12 -0
  242. package/dist/src/intelligence/claude-client.js.map +1 -0
  243. package/dist/src/intelligence/conflict-mediator.d.ts +17 -0
  244. package/dist/src/intelligence/conflict-mediator.d.ts.map +1 -0
  245. package/dist/src/intelligence/conflict-mediator.js +83 -0
  246. package/dist/src/intelligence/conflict-mediator.js.map +1 -0
  247. package/dist/src/intelligence/github-orchestrator.d.ts +30 -0
  248. package/dist/src/intelligence/github-orchestrator.d.ts.map +1 -0
  249. package/dist/src/intelligence/github-orchestrator.js +270 -0
  250. package/dist/src/intelligence/github-orchestrator.js.map +1 -0
  251. package/dist/src/intelligence/kill-switch.d.ts +10 -0
  252. package/dist/src/intelligence/kill-switch.d.ts.map +1 -0
  253. package/dist/src/intelligence/kill-switch.js +12 -0
  254. package/dist/src/intelligence/kill-switch.js.map +1 -0
  255. package/dist/src/intelligence/learnings-extractor.d.ts +13 -0
  256. package/dist/src/intelligence/learnings-extractor.d.ts.map +1 -0
  257. package/dist/src/intelligence/learnings-extractor.js +74 -0
  258. package/dist/src/intelligence/learnings-extractor.js.map +1 -0
  259. package/dist/src/intelligence/project-scanner.d.ts +2 -0
  260. package/dist/src/intelligence/project-scanner.d.ts.map +1 -0
  261. package/dist/src/intelligence/project-scanner.js +28 -0
  262. package/dist/src/intelligence/project-scanner.js.map +1 -0
  263. package/dist/src/intelligence/task-decomposer.d.ts +14 -0
  264. package/dist/src/intelligence/task-decomposer.d.ts.map +1 -0
  265. package/dist/src/intelligence/task-decomposer.js +97 -0
  266. package/dist/src/intelligence/task-decomposer.js.map +1 -0
  267. package/dist/src/intelligence/types.d.ts +14 -0
  268. package/dist/src/intelligence/types.d.ts.map +1 -0
  269. package/dist/src/intelligence/types.js +2 -0
  270. package/dist/src/intelligence/types.js.map +1 -0
  271. package/dist/src/mcp/server.d.ts +63 -0
  272. package/dist/src/mcp/server.d.ts.map +1 -0
  273. package/dist/src/mcp/server.js +537 -0
  274. package/dist/src/mcp/server.js.map +1 -0
  275. package/dist/src/mcp/stdio-entry.d.ts +2 -0
  276. package/dist/src/mcp/stdio-entry.d.ts.map +1 -0
  277. package/dist/src/mcp/stdio-entry.js +124 -0
  278. package/dist/src/mcp/stdio-entry.js.map +1 -0
  279. package/dist/src/mcp/subtask-handlers.d.ts +7 -0
  280. package/dist/src/mcp/subtask-handlers.d.ts.map +1 -0
  281. package/dist/src/mcp/subtask-handlers.js +50 -0
  282. package/dist/src/mcp/subtask-handlers.js.map +1 -0
  283. package/dist/src/security/network-proxy.d.ts +20 -0
  284. package/dist/src/security/network-proxy.d.ts.map +1 -0
  285. package/dist/src/security/network-proxy.js +125 -0
  286. package/dist/src/security/network-proxy.js.map +1 -0
  287. package/dist/src/security/network-sandbox.d.ts +19 -0
  288. package/dist/src/security/network-sandbox.d.ts.map +1 -0
  289. package/dist/src/security/network-sandbox.js +100 -0
  290. package/dist/src/security/network-sandbox.js.map +1 -0
  291. package/dist/src/security/sanitize.d.ts +13 -0
  292. package/dist/src/security/sanitize.d.ts.map +1 -0
  293. package/dist/src/security/sanitize.js +19 -0
  294. package/dist/src/security/sanitize.js.map +1 -0
  295. package/dist/src/security/secrets-patterns.d.ts +29 -0
  296. package/dist/src/security/secrets-patterns.d.ts.map +1 -0
  297. package/dist/src/security/secrets-patterns.js +430 -0
  298. package/dist/src/security/secrets-patterns.js.map +1 -0
  299. package/dist/src/security/secrets-scanner.d.ts +26 -0
  300. package/dist/src/security/secrets-scanner.d.ts.map +1 -0
  301. package/dist/src/security/secrets-scanner.js +62 -0
  302. package/dist/src/security/secrets-scanner.js.map +1 -0
  303. package/dist/src/skills/classifier.d.ts +9 -0
  304. package/dist/src/skills/classifier.d.ts.map +1 -0
  305. package/dist/src/skills/classifier.js +41 -0
  306. package/dist/src/skills/classifier.js.map +1 -0
  307. package/dist/src/skills/registry.d.ts +16 -0
  308. package/dist/src/skills/registry.d.ts.map +1 -0
  309. package/dist/src/skills/registry.js +61 -0
  310. package/dist/src/skills/registry.js.map +1 -0
  311. package/dist/src/sync/events.d.ts +9 -0
  312. package/dist/src/sync/events.d.ts.map +1 -0
  313. package/dist/src/sync/events.js +2 -0
  314. package/dist/src/sync/events.js.map +1 -0
  315. package/dist/src/sync/relay-server.d.ts +18 -0
  316. package/dist/src/sync/relay-server.d.ts.map +1 -0
  317. package/dist/src/sync/relay-server.js +131 -0
  318. package/dist/src/sync/relay-server.js.map +1 -0
  319. package/dist/src/sync/sync-client.d.ts +31 -0
  320. package/dist/src/sync/sync-client.d.ts.map +1 -0
  321. package/dist/src/sync/sync-client.js +314 -0
  322. package/dist/src/sync/sync-client.js.map +1 -0
  323. package/dist/src/tui/app.d.ts +35 -0
  324. package/dist/src/tui/app.d.ts.map +1 -0
  325. package/dist/src/tui/app.js +676 -0
  326. package/dist/src/tui/app.js.map +1 -0
  327. package/dist/src/tui/components/activity-feed.d.ts +12 -0
  328. package/dist/src/tui/components/activity-feed.d.ts.map +1 -0
  329. package/dist/src/tui/components/activity-feed.js +82 -0
  330. package/dist/src/tui/components/activity-feed.js.map +1 -0
  331. package/dist/src/tui/components/agent-list.d.ts +19 -0
  332. package/dist/src/tui/components/agent-list.d.ts.map +1 -0
  333. package/dist/src/tui/components/agent-list.js +33 -0
  334. package/dist/src/tui/components/agent-list.js.map +1 -0
  335. package/dist/src/tui/components/agent-row.d.ts +12 -0
  336. package/dist/src/tui/components/agent-row.d.ts.map +1 -0
  337. package/dist/src/tui/components/agent-row.js +37 -0
  338. package/dist/src/tui/components/agent-row.js.map +1 -0
  339. package/dist/src/tui/components/approval-terminal.d.ts +13 -0
  340. package/dist/src/tui/components/approval-terminal.d.ts.map +1 -0
  341. package/dist/src/tui/components/approval-terminal.js +34 -0
  342. package/dist/src/tui/components/approval-terminal.js.map +1 -0
  343. package/dist/src/tui/components/audit-viewer.d.ts +16 -0
  344. package/dist/src/tui/components/audit-viewer.d.ts.map +1 -0
  345. package/dist/src/tui/components/audit-viewer.js +46 -0
  346. package/dist/src/tui/components/audit-viewer.js.map +1 -0
  347. package/dist/src/tui/components/auth-gate.d.ts +9 -0
  348. package/dist/src/tui/components/auth-gate.d.ts.map +1 -0
  349. package/dist/src/tui/components/auth-gate.js +112 -0
  350. package/dist/src/tui/components/auth-gate.js.map +1 -0
  351. package/dist/src/tui/components/command-palette.d.ts +12 -0
  352. package/dist/src/tui/components/command-palette.d.ts.map +1 -0
  353. package/dist/src/tui/components/command-palette.js +51 -0
  354. package/dist/src/tui/components/command-palette.js.map +1 -0
  355. package/dist/src/tui/components/compliance-badge.d.ts +11 -0
  356. package/dist/src/tui/components/compliance-badge.d.ts.map +1 -0
  357. package/dist/src/tui/components/compliance-badge.js +12 -0
  358. package/dist/src/tui/components/compliance-badge.js.map +1 -0
  359. package/dist/src/tui/components/decomposition-review.d.ts +10 -0
  360. package/dist/src/tui/components/decomposition-review.d.ts.map +1 -0
  361. package/dist/src/tui/components/decomposition-review.js +19 -0
  362. package/dist/src/tui/components/decomposition-review.js.map +1 -0
  363. package/dist/src/tui/components/dependency-graph.d.ts +13 -0
  364. package/dist/src/tui/components/dependency-graph.d.ts.map +1 -0
  365. package/dist/src/tui/components/dependency-graph.js +143 -0
  366. package/dist/src/tui/components/dependency-graph.js.map +1 -0
  367. package/dist/src/tui/components/diff-viewer.d.ts +11 -0
  368. package/dist/src/tui/components/diff-viewer.d.ts.map +1 -0
  369. package/dist/src/tui/components/diff-viewer.js +82 -0
  370. package/dist/src/tui/components/diff-viewer.js.map +1 -0
  371. package/dist/src/tui/components/edit-task-input.d.ts +10 -0
  372. package/dist/src/tui/components/edit-task-input.d.ts.map +1 -0
  373. package/dist/src/tui/components/edit-task-input.js +20 -0
  374. package/dist/src/tui/components/edit-task-input.js.map +1 -0
  375. package/dist/src/tui/components/footer.d.ts +12 -0
  376. package/dist/src/tui/components/footer.d.ts.map +1 -0
  377. package/dist/src/tui/components/footer.js +41 -0
  378. package/dist/src/tui/components/footer.js.map +1 -0
  379. package/dist/src/tui/components/header.d.ts +8 -0
  380. package/dist/src/tui/components/header.d.ts.map +1 -0
  381. package/dist/src/tui/components/header.js +20 -0
  382. package/dist/src/tui/components/header.js.map +1 -0
  383. package/dist/src/tui/components/human-actions.d.ts +14 -0
  384. package/dist/src/tui/components/human-actions.d.ts.map +1 -0
  385. package/dist/src/tui/components/human-actions.js +43 -0
  386. package/dist/src/tui/components/human-actions.js.map +1 -0
  387. package/dist/src/tui/components/log-panel.d.ts +10 -0
  388. package/dist/src/tui/components/log-panel.d.ts.map +1 -0
  389. package/dist/src/tui/components/log-panel.js +38 -0
  390. package/dist/src/tui/components/log-panel.js.map +1 -0
  391. package/dist/src/tui/components/memory-viewer.d.ts +10 -0
  392. package/dist/src/tui/components/memory-viewer.d.ts.map +1 -0
  393. package/dist/src/tui/components/memory-viewer.js +44 -0
  394. package/dist/src/tui/components/memory-viewer.js.map +1 -0
  395. package/dist/src/tui/components/new-task-input.d.ts +9 -0
  396. package/dist/src/tui/components/new-task-input.d.ts.map +1 -0
  397. package/dist/src/tui/components/new-task-input.js +21 -0
  398. package/dist/src/tui/components/new-task-input.js.map +1 -0
  399. package/dist/src/tui/components/orchestrator-status.d.ts +9 -0
  400. package/dist/src/tui/components/orchestrator-status.d.ts.map +1 -0
  401. package/dist/src/tui/components/orchestrator-status.js +15 -0
  402. package/dist/src/tui/components/orchestrator-status.js.map +1 -0
  403. package/dist/src/tui/components/parallelize-banner.d.ts +8 -0
  404. package/dist/src/tui/components/parallelize-banner.d.ts.map +1 -0
  405. package/dist/src/tui/components/parallelize-banner.js +9 -0
  406. package/dist/src/tui/components/parallelize-banner.js.map +1 -0
  407. package/dist/src/tui/components/progress-bar.d.ts +9 -0
  408. package/dist/src/tui/components/progress-bar.d.ts.map +1 -0
  409. package/dist/src/tui/components/progress-bar.js +15 -0
  410. package/dist/src/tui/components/progress-bar.js.map +1 -0
  411. package/dist/src/tui/components/review-queue.d.ts +13 -0
  412. package/dist/src/tui/components/review-queue.d.ts.map +1 -0
  413. package/dist/src/tui/components/review-queue.js +78 -0
  414. package/dist/src/tui/components/review-queue.js.map +1 -0
  415. package/dist/src/tui/components/rich-header.d.ts +11 -0
  416. package/dist/src/tui/components/rich-header.d.ts.map +1 -0
  417. package/dist/src/tui/components/rich-header.js +25 -0
  418. package/dist/src/tui/components/rich-header.js.map +1 -0
  419. package/dist/src/tui/components/spinner.d.ts +7 -0
  420. package/dist/src/tui/components/spinner.d.ts.map +1 -0
  421. package/dist/src/tui/components/spinner.js +8 -0
  422. package/dist/src/tui/components/spinner.js.map +1 -0
  423. package/dist/src/tui/components/status-bar.d.ts +23 -0
  424. package/dist/src/tui/components/status-bar.d.ts.map +1 -0
  425. package/dist/src/tui/components/status-bar.js +28 -0
  426. package/dist/src/tui/components/status-bar.js.map +1 -0
  427. package/dist/src/tui/components/task-queue.d.ts +11 -0
  428. package/dist/src/tui/components/task-queue.d.ts.map +1 -0
  429. package/dist/src/tui/components/task-queue.js +30 -0
  430. package/dist/src/tui/components/task-queue.js.map +1 -0
  431. package/dist/src/tui/components/team-view.d.ts +13 -0
  432. package/dist/src/tui/components/team-view.d.ts.map +1 -0
  433. package/dist/src/tui/components/team-view.js +12 -0
  434. package/dist/src/tui/components/team-view.js.map +1 -0
  435. package/dist/src/tui/graph-renderer.d.ts +11 -0
  436. package/dist/src/tui/graph-renderer.d.ts.map +1 -0
  437. package/dist/src/tui/graph-renderer.js +296 -0
  438. package/dist/src/tui/graph-renderer.js.map +1 -0
  439. package/dist/src/tui/hooks/use-bell.d.ts +21 -0
  440. package/dist/src/tui/hooks/use-bell.d.ts.map +1 -0
  441. package/dist/src/tui/hooks/use-bell.js +38 -0
  442. package/dist/src/tui/hooks/use-bell.js.map +1 -0
  443. package/dist/src/tui/hooks/use-ci-status.d.ts +16 -0
  444. package/dist/src/tui/hooks/use-ci-status.d.ts.map +1 -0
  445. package/dist/src/tui/hooks/use-ci-status.js +97 -0
  446. package/dist/src/tui/hooks/use-ci-status.js.map +1 -0
  447. package/dist/src/tui/hooks/use-command-palette.d.ts +37 -0
  448. package/dist/src/tui/hooks/use-command-palette.d.ts.map +1 -0
  449. package/dist/src/tui/hooks/use-command-palette.js +108 -0
  450. package/dist/src/tui/hooks/use-command-palette.js.map +1 -0
  451. package/dist/src/tui/hooks/use-diff-view.d.ts +16 -0
  452. package/dist/src/tui/hooks/use-diff-view.d.ts.map +1 -0
  453. package/dist/src/tui/hooks/use-diff-view.js +75 -0
  454. package/dist/src/tui/hooks/use-diff-view.js.map +1 -0
  455. package/dist/src/tui/hooks/use-keyboard.d.ts +3 -0
  456. package/dist/src/tui/hooks/use-keyboard.d.ts.map +1 -0
  457. package/dist/src/tui/hooks/use-keyboard.js +70 -0
  458. package/dist/src/tui/hooks/use-keyboard.js.map +1 -0
  459. package/dist/src/tui/hooks/use-log-stream.d.ts +25 -0
  460. package/dist/src/tui/hooks/use-log-stream.d.ts.map +1 -0
  461. package/dist/src/tui/hooks/use-log-stream.js +83 -0
  462. package/dist/src/tui/hooks/use-log-stream.js.map +1 -0
  463. package/dist/src/tui/hooks/use-spinner.d.ts +3 -0
  464. package/dist/src/tui/hooks/use-spinner.d.ts.map +1 -0
  465. package/dist/src/tui/hooks/use-spinner.js +13 -0
  466. package/dist/src/tui/hooks/use-spinner.js.map +1 -0
  467. package/dist/src/tui/hooks/use-store.d.ts +33 -0
  468. package/dist/src/tui/hooks/use-store.d.ts.map +1 -0
  469. package/dist/src/tui/hooks/use-store.js +21 -0
  470. package/dist/src/tui/hooks/use-store.js.map +1 -0
  471. package/dist/src/tui/lib/diff-parser.d.ts +24 -0
  472. package/dist/src/tui/lib/diff-parser.d.ts.map +1 -0
  473. package/dist/src/tui/lib/diff-parser.js +115 -0
  474. package/dist/src/tui/lib/diff-parser.js.map +1 -0
  475. package/dist/src/tui/lib/palette-commands.d.ts +14 -0
  476. package/dist/src/tui/lib/palette-commands.d.ts.map +1 -0
  477. package/dist/src/tui/lib/palette-commands.js +101 -0
  478. package/dist/src/tui/lib/palette-commands.js.map +1 -0
  479. package/dist/src/tui/tui.d.ts +8 -0
  480. package/dist/src/tui/tui.d.ts.map +1 -0
  481. package/dist/src/tui/tui.js +8 -0
  482. package/dist/src/tui/tui.js.map +1 -0
  483. package/package.json +66 -0
  484. package/skills/api-design.md +84 -0
  485. package/skills/backend-typescript.md +76 -0
  486. package/skills/data-modeling.md +73 -0
  487. package/skills/devops-ci.md +82 -0
  488. package/skills/frontend-design.md +69 -0
  489. package/skills/observability.md +73 -0
  490. package/skills/react-nextjs.md +76 -0
  491. package/skills/refactoring.md +77 -0
  492. package/skills/security.md +75 -0
  493. package/skills/testing.md +69 -0
@@ -0,0 +1,21 @@
1
+ import { useState, useEffect, useRef } from 'react';
2
+ export function useStore(getState, intervalMs = 1000) {
3
+ const [state, setState] = useState(getState);
4
+ const snapshotRef = useRef('');
5
+ useEffect(() => {
6
+ // Store initial snapshot
7
+ snapshotRef.current = JSON.stringify(state);
8
+ const timer = setInterval(() => {
9
+ const next = getState();
10
+ const nextSnapshot = JSON.stringify(next);
11
+ // Only trigger re-render when state actually changed
12
+ if (nextSnapshot !== snapshotRef.current) {
13
+ snapshotRef.current = nextSnapshot;
14
+ setState(next);
15
+ }
16
+ }, intervalMs);
17
+ return () => clearInterval(timer);
18
+ }, [getState, intervalMs]);
19
+ return state;
20
+ }
21
+ //# sourceMappingURL=use-store.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-store.js","sourceRoot":"","sources":["../../../../src/tui/hooks/use-store.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,OAAO,CAAC;AAmCpD,MAAM,UAAU,QAAQ,CACtB,QAA0B,EAC1B,UAAU,GAAG,IAAI;IAEjB,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,GAAG,QAAQ,CAAa,QAAQ,CAAC,CAAC;IACzD,MAAM,WAAW,GAAG,MAAM,CAAS,EAAE,CAAC,CAAC;IAEvC,SAAS,CAAC,GAAG,EAAE;QACb,yBAAyB;QACzB,WAAW,CAAC,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC;QAE5C,MAAM,KAAK,GAAG,WAAW,CAAC,GAAG,EAAE;YAC7B,MAAM,IAAI,GAAG,QAAQ,EAAE,CAAC;YACxB,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC;YAC1C,qDAAqD;YACrD,IAAI,YAAY,KAAK,WAAW,CAAC,OAAO,EAAE,CAAC;gBACzC,WAAW,CAAC,OAAO,GAAG,YAAY,CAAC;gBACnC,QAAQ,CAAC,IAAI,CAAC,CAAC;YACjB,CAAC;QACH,CAAC,EAAE,UAAU,CAAC,CAAC;QACf,OAAO,GAAG,EAAE,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC;IACpC,CAAC,EAAE,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC,CAAC;IAE3B,OAAO,KAAK,CAAC;AACf,CAAC"}
@@ -0,0 +1,24 @@
1
+ export interface DiffLine {
2
+ type: 'context' | 'added' | 'removed';
3
+ content: string;
4
+ oldLineNo: number | null;
5
+ newLineNo: number | null;
6
+ }
7
+ export interface DiffHunk {
8
+ header: string;
9
+ oldStart: number;
10
+ oldCount: number;
11
+ newStart: number;
12
+ newCount: number;
13
+ lines: DiffLine[];
14
+ }
15
+ export interface DiffFile {
16
+ oldPath: string;
17
+ newPath: string;
18
+ hunks: DiffHunk[];
19
+ isNew: boolean;
20
+ isDeleted: boolean;
21
+ isBinary: boolean;
22
+ }
23
+ export declare function parseDiff(raw: string): DiffFile[];
24
+ //# sourceMappingURL=diff-parser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"diff-parser.d.ts","sourceRoot":"","sources":["../../../../src/tui/lib/diff-parser.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,QAAQ;IACvB,IAAI,EAAE,SAAS,GAAG,OAAO,GAAG,SAAS,CAAC;IACtC,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,GAAG,IAAI,CAAC;CAC1B;AAED,MAAM,WAAW,QAAQ;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,QAAQ,EAAE,CAAC;CACnB;AAED,MAAM,WAAW,QAAQ;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,KAAK,EAAE,OAAO,CAAC;IACf,SAAS,EAAE,OAAO,CAAC;IACnB,QAAQ,EAAE,OAAO,CAAC;CACnB;AAwCD,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,QAAQ,EAAE,CAkFjD"}
@@ -0,0 +1,115 @@
1
+ // Unified diff parser: converts raw `git diff` output into structured DiffFile[].
2
+ // Regex for unified diff hunk header: @@ -oldStart,oldCount +newStart,newCount @@
3
+ const HUNK_HEADER_RE = /^@@ -(\d+)(?:,(\d+))? \+(\d+)(?:,(\d+))? @@(.*)/;
4
+ function stripGitPrefix(raw) {
5
+ if (raw.startsWith('a/') || raw.startsWith('b/'))
6
+ return raw.slice(2);
7
+ return raw;
8
+ }
9
+ function parseHunk(header, bodyLines) {
10
+ const m = HUNK_HEADER_RE.exec(header);
11
+ if (!m) {
12
+ return { header, oldStart: 0, oldCount: 0, newStart: 0, newCount: 0, lines: [] };
13
+ }
14
+ const oldStart = parseInt(m[1], 10);
15
+ const oldCount = m[2] !== undefined ? parseInt(m[2], 10) : 1;
16
+ const newStart = parseInt(m[3], 10);
17
+ const newCount = m[4] !== undefined ? parseInt(m[4], 10) : 1;
18
+ const contextSuffix = m[5] ?? '';
19
+ const lines = [];
20
+ let oldNo = oldStart;
21
+ let newNo = newStart;
22
+ for (const raw of bodyLines) {
23
+ if (raw.startsWith('+') && !raw.startsWith('+++')) {
24
+ lines.push({ type: 'added', content: raw.slice(1), oldLineNo: null, newLineNo: newNo++ });
25
+ }
26
+ else if (raw.startsWith('-') && !raw.startsWith('---')) {
27
+ lines.push({ type: 'removed', content: raw.slice(1), oldLineNo: oldNo++, newLineNo: null });
28
+ }
29
+ else if (raw.startsWith(' ')) {
30
+ lines.push({ type: 'context', content: raw.slice(1), oldLineNo: oldNo++, newLineNo: newNo++ });
31
+ }
32
+ // Skip '\' and other meta-lines
33
+ }
34
+ return { header: header + contextSuffix, oldStart, oldCount, newStart, newCount, lines };
35
+ }
36
+ export function parseDiff(raw) {
37
+ if (!raw || raw.trim() === '')
38
+ return [];
39
+ const files = [];
40
+ const lines = raw.split('\n');
41
+ let i = 0;
42
+ while (i < lines.length) {
43
+ if (!lines[i].startsWith('diff --git ')) {
44
+ i++;
45
+ continue;
46
+ }
47
+ // Extract paths from "diff --git a/X b/Y"
48
+ const diffLine = lines[i];
49
+ const gitPathMatch = /^diff --git a\/(.+) b\/(.+)$/.exec(diffLine);
50
+ let oldPath = gitPathMatch ? gitPathMatch[1] : '';
51
+ let newPath = gitPathMatch ? gitPathMatch[2] : '';
52
+ let isNew = false;
53
+ let isDeleted = false;
54
+ let isBinary = false;
55
+ const hunks = [];
56
+ i++;
57
+ // Parse file header block until first hunk or next diff header
58
+ while (i < lines.length && !lines[i].startsWith('diff --git ')) {
59
+ const l = lines[i];
60
+ if (l.startsWith('new file mode')) {
61
+ isNew = true;
62
+ i++;
63
+ }
64
+ else if (l.startsWith('deleted file mode')) {
65
+ isDeleted = true;
66
+ i++;
67
+ }
68
+ else if (l.startsWith('Binary files')) {
69
+ isBinary = true;
70
+ const binM = /^Binary files (.+) and (.+) differ/.exec(l);
71
+ if (binM) {
72
+ oldPath = stripGitPrefix(binM[1]);
73
+ newPath = stripGitPrefix(binM[2]);
74
+ }
75
+ i++;
76
+ }
77
+ else if (l.startsWith('--- ')) {
78
+ const stripped = l.slice(4);
79
+ oldPath = stripped === '/dev/null' ? '/dev/null' : stripGitPrefix(stripped);
80
+ i++;
81
+ }
82
+ else if (l.startsWith('+++ ')) {
83
+ const stripped = l.slice(4);
84
+ newPath = stripped === '/dev/null' ? '/dev/null' : stripGitPrefix(stripped);
85
+ i++;
86
+ }
87
+ else if (HUNK_HEADER_RE.test(l)) {
88
+ const hunkHeader = l;
89
+ i++;
90
+ const hunkBody = [];
91
+ while (i < lines.length &&
92
+ !lines[i].startsWith('diff --git ') &&
93
+ !HUNK_HEADER_RE.test(lines[i])) {
94
+ hunkBody.push(lines[i]);
95
+ i++;
96
+ }
97
+ hunks.push(parseHunk(hunkHeader, hunkBody));
98
+ // Don't increment — outer loop will check for another hunk header
99
+ }
100
+ else {
101
+ i++;
102
+ }
103
+ }
104
+ files.push({
105
+ oldPath: oldPath || newPath,
106
+ newPath: newPath || oldPath,
107
+ hunks,
108
+ isNew,
109
+ isDeleted,
110
+ isBinary,
111
+ });
112
+ }
113
+ return files;
114
+ }
115
+ //# sourceMappingURL=diff-parser.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"diff-parser.js","sourceRoot":"","sources":["../../../../src/tui/lib/diff-parser.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,14 @@
1
+ import type { KeyAction } from '../hooks/use-keyboard.js';
2
+ export interface PaletteCommand {
3
+ id: string;
4
+ label: string;
5
+ description: string;
6
+ shortcut?: string;
7
+ action: KeyAction;
8
+ }
9
+ export interface PaletteCommandContext {
10
+ hasLogLines: boolean;
11
+ hasLearnings: boolean;
12
+ }
13
+ export declare function buildPaletteCommands(ctx: PaletteCommandContext): PaletteCommand[];
14
+ //# sourceMappingURL=palette-commands.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"palette-commands.d.ts","sourceRoot":"","sources":["../../../../src/tui/lib/palette-commands.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,0BAA0B,CAAC;AAE1D,MAAM,WAAW,cAAc;IAC7B,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,SAAS,CAAC;CACnB;AAED,MAAM,WAAW,qBAAqB;IACpC,WAAW,EAAE,OAAO,CAAC;IACrB,YAAY,EAAE,OAAO,CAAC;CACvB;AAED,wBAAgB,oBAAoB,CAAC,GAAG,EAAE,qBAAqB,GAAG,cAAc,EAAE,CAsGjF"}
@@ -0,0 +1,101 @@
1
+ export function buildPaletteCommands(ctx) {
2
+ const commands = [
3
+ {
4
+ id: 'new-task',
5
+ label: 'New Task',
6
+ description: 'Create a new task',
7
+ shortcut: 'n',
8
+ action: 'new-task',
9
+ },
10
+ {
11
+ id: 'launch',
12
+ label: 'Launch Agent',
13
+ description: 'Launch agent for selected task',
14
+ shortcut: 'l',
15
+ action: 'launch',
16
+ },
17
+ {
18
+ id: 'kill',
19
+ label: 'Kill Agent',
20
+ description: 'Kill selected running agent',
21
+ shortcut: 'x',
22
+ action: 'kill',
23
+ },
24
+ {
25
+ id: 'parallelize',
26
+ label: 'Parallelize Batch',
27
+ description: 'Launch all queued parallel tasks',
28
+ shortcut: '↵',
29
+ action: 'parallelize',
30
+ },
31
+ {
32
+ id: 'toggle-review',
33
+ label: 'Toggle Review Queue',
34
+ description: 'Show or hide the PR review queue',
35
+ shortcut: 'r',
36
+ action: 'toggle-review',
37
+ },
38
+ {
39
+ id: 'toggle-feed',
40
+ label: 'Toggle Activity Feed',
41
+ description: 'Show or hide the activity feed',
42
+ shortcut: 'f',
43
+ action: 'toggle-feed',
44
+ },
45
+ {
46
+ id: 'yolo-toggle',
47
+ label: 'Toggle Auto Mode',
48
+ description: 'Auto-approve all agent actions',
49
+ shortcut: '!',
50
+ action: 'yolo-toggle',
51
+ },
52
+ {
53
+ id: 'factory-toggle',
54
+ label: 'Toggle Factory Mode',
55
+ description: 'Enable continuous task generation',
56
+ shortcut: '@',
57
+ action: 'factory-toggle',
58
+ },
59
+ {
60
+ id: 'cycle-trust',
61
+ label: 'Cycle Trust Level',
62
+ description: 'Switch trust level: low → medium → high',
63
+ shortcut: 'T',
64
+ action: 'cycle-trust',
65
+ },
66
+ {
67
+ id: 'diff',
68
+ label: 'Diff / Decompose',
69
+ description: 'View worktree diff or decompose selected task',
70
+ shortcut: 'd',
71
+ action: 'diff',
72
+ },
73
+ {
74
+ id: 'help',
75
+ label: 'Toggle Help',
76
+ description: 'Show or hide keyboard shortcuts reference',
77
+ shortcut: '?',
78
+ action: 'help',
79
+ },
80
+ ];
81
+ if (ctx.hasLogLines) {
82
+ commands.push({
83
+ id: 'open-log',
84
+ label: 'Open Log Panel',
85
+ description: 'View streaming agent logs',
86
+ shortcut: 'o',
87
+ action: 'open-log',
88
+ });
89
+ }
90
+ if (ctx.hasLearnings) {
91
+ commands.push({
92
+ id: 'memory',
93
+ label: 'Memory Viewer',
94
+ description: 'Browse agent learnings and context',
95
+ shortcut: 'm',
96
+ action: 'memory',
97
+ });
98
+ }
99
+ return commands;
100
+ }
101
+ //# sourceMappingURL=palette-commands.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"palette-commands.js","sourceRoot":"","sources":["../../../../src/tui/lib/palette-commands.ts"],"names":[],"mappings":"AAeA,MAAM,UAAU,oBAAoB,CAAC,GAA0B;IAC7D,MAAM,QAAQ,GAAqB;QACjC;YACE,EAAE,EAAE,UAAU;YACd,KAAK,EAAE,UAAU;YACjB,WAAW,EAAE,mBAAmB;YAChC,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,UAAU;SACnB;QACD;YACE,EAAE,EAAE,QAAQ;YACZ,KAAK,EAAE,cAAc;YACrB,WAAW,EAAE,gCAAgC;YAC7C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,QAAQ;SACjB;QACD;YACE,EAAE,EAAE,MAAM;YACV,KAAK,EAAE,YAAY;YACnB,WAAW,EAAE,6BAA6B;YAC1C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,MAAM;SACf;QACD;YACE,EAAE,EAAE,aAAa;YACjB,KAAK,EAAE,mBAAmB;YAC1B,WAAW,EAAE,kCAAkC;YAC/C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,aAAa;SACtB;QACD;YACE,EAAE,EAAE,eAAe;YACnB,KAAK,EAAE,qBAAqB;YAC5B,WAAW,EAAE,kCAAkC;YAC/C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,eAAe;SACxB;QACD;YACE,EAAE,EAAE,aAAa;YACjB,KAAK,EAAE,sBAAsB;YAC7B,WAAW,EAAE,gCAAgC;YAC7C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,aAAa;SACtB;QACD;YACE,EAAE,EAAE,aAAa;YACjB,KAAK,EAAE,kBAAkB;YACzB,WAAW,EAAE,gCAAgC;YAC7C,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,aAAa;SACtB;QACD;YACE,EAAE,EAAE,gBAAgB;YACpB,KAAK,EAAE,qBAAqB;YAC5B,WAAW,EAAE,mCAAmC;YAChD,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,gBAAgB;SACzB;QACD;YACE,EAAE,EAAE,aAAa;YACjB,KAAK,EAAE,mBAAmB;YAC1B,WAAW,EAAE,yCAAyC;YACtD,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,aAAa;SACtB;QACD;YACE,EAAE,EAAE,MAAM;YACV,KAAK,EAAE,kBAAkB;YACzB,WAAW,EAAE,+CAA+C;YAC5D,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,MAAM;SACf;QACD;YACE,EAAE,EAAE,MAAM;YACV,KAAK,EAAE,aAAa;YACpB,WAAW,EAAE,2CAA2C;YACxD,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,MAAM;SACf;KACF,CAAC;IAEF,IAAI,GAAG,CAAC,WAAW,EAAE,CAAC;QACpB,QAAQ,CAAC,IAAI,CAAC;YACZ,EAAE,EAAE,UAAU;YACd,KAAK,EAAE,gBAAgB;YACvB,WAAW,EAAE,2BAA2B;YACxC,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,UAAU;SACnB,CAAC,CAAC;IACL,CAAC;IAED,IAAI,GAAG,CAAC,YAAY,EAAE,CAAC;QACrB,QAAQ,CAAC,IAAI,CAAC;YACZ,EAAE,EAAE,QAAQ;YACZ,KAAK,EAAE,eAAe;YACtB,WAAW,EAAE,oCAAoC;YACjD,QAAQ,EAAE,GAAG;YACb,MAAM,EAAE,QAAQ;SACjB,CAAC,CAAC;IACL,CAAC;IAED,OAAO,QAAQ,CAAC;AAClB,CAAC"}
@@ -0,0 +1,8 @@
1
+ import type { AppProps } from './app.js';
2
+ export type TuiOptions = AppProps;
3
+ export interface TuiInstance {
4
+ waitUntilExit: () => Promise<unknown>;
5
+ unmount: () => void;
6
+ }
7
+ export declare function startTui(options: TuiOptions): TuiInstance;
8
+ //# sourceMappingURL=tui.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tui.d.ts","sourceRoot":"","sources":["../../../src/tui/tui.tsx"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,UAAU,CAAC;AAEzC,MAAM,MAAM,UAAU,GAAG,QAAQ,CAAC;AAElC,MAAM,WAAW,WAAW;IAC1B,aAAa,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IACtC,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED,wBAAgB,QAAQ,CAAC,OAAO,EAAE,UAAU,GAAG,WAAW,CAGzD"}
@@ -0,0 +1,8 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { render } from 'ink';
3
+ import { App } from './app.js';
4
+ export function startTui(options) {
5
+ const { waitUntilExit, unmount } = render(_jsx(App, { ...options }));
6
+ return { waitUntilExit, unmount };
7
+ }
8
+ //# sourceMappingURL=tui.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tui.js","sourceRoot":"","sources":["../../../src/tui/tui.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,MAAM,EAAE,MAAM,KAAK,CAAC;AAC7B,OAAO,EAAE,GAAG,EAAE,MAAM,UAAU,CAAC;AAU/B,MAAM,UAAU,QAAQ,CAAC,OAAmB;IAC1C,MAAM,EAAE,aAAa,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,KAAC,GAAG,OAAK,OAAO,GAAI,CAAC,CAAC;IAChE,OAAO,EAAE,aAAa,EAAE,OAAO,EAAE,CAAC;AACpC,CAAC"}
package/package.json ADDED
@@ -0,0 +1,66 @@
1
+ {
2
+ "name": "verbolab",
3
+ "version": "0.1.0-alpha.1",
4
+ "description": "Orchestrate multiple AI coding agents with human control",
5
+ "main": "dist/bin/verbo.js",
6
+ "type": "module",
7
+ "bin": {
8
+ "verbo": "./dist/bin/verbo.js"
9
+ },
10
+ "files": [
11
+ "dist/",
12
+ "skills/",
13
+ "README.md",
14
+ "LICENSE"
15
+ ],
16
+ "scripts": {
17
+ "dev": "tsx bin/verbo.ts",
18
+ "test": "vitest run",
19
+ "test:watch": "vitest",
20
+ "build": "tsc",
21
+ "prepublishOnly": "npm run build",
22
+ "postinstall": "echo 'Run: verbo --help'",
23
+ "relay": "tsx relay/index.ts"
24
+ },
25
+ "keywords": [
26
+ "ai",
27
+ "agents",
28
+ "claude",
29
+ "orchestration",
30
+ "cli",
31
+ "developer-tools"
32
+ ],
33
+ "repository": {
34
+ "type": "git",
35
+ "url": "https://github.com/franciscomelloc/Verbo-orchestra.git"
36
+ },
37
+ "author": "VerboLab",
38
+ "license": "MIT",
39
+ "dependencies": {
40
+ "@anthropic-ai/sdk": "^0.80.0",
41
+ "@modelcontextprotocol/sdk": "^1.28.0",
42
+ "@octokit/rest": "^22.0.1",
43
+ "better-sqlite3": "^12.8.0",
44
+ "commander": "^14.0.3",
45
+ "ink": "^6.8.0",
46
+ "ink-text-input": "^6.0.0",
47
+ "minimatch": "^10.2.4",
48
+ "react": "^19.2.4",
49
+ "simple-git": "^3.33.0",
50
+ "smol-toml": "^1.6.1",
51
+ "ulid": "^3.0.2",
52
+ "ws": "^8.20.0",
53
+ "zod": "^4.3.6"
54
+ },
55
+ "devDependencies": {
56
+ "@types/better-sqlite3": "^7.6.13",
57
+ "@types/minimatch": "^5.1.2",
58
+ "@types/node": "^25.5.0",
59
+ "@types/react": "^19.2.14",
60
+ "@types/ws": "^8.18.1",
61
+ "@vitest/coverage-v8": "^4.1.2",
62
+ "tsx": "^4.21.0",
63
+ "typescript": "^6.0.2",
64
+ "vitest": "^4.1.2"
65
+ }
66
+ }
@@ -0,0 +1,84 @@
1
+ ---
2
+ name: api-design
3
+ description: REST maturity, contract-first design, validation, idempotency, error envelopes, versioning
4
+ domain: engineering
5
+ subdomain: api
6
+ ---
7
+
8
+ # API Design
9
+
10
+ ## Context
11
+ You are designing or modifying a REST API — adding endpoints, defining request/response shapes, handling errors, or planning versioning. Apply contract-first design, validate at boundaries, and aim for Richardson Maturity Level 2+.
12
+
13
+ ## Core Principles
14
+
15
+ **Richardson Maturity Model** (Richardson & Amundsen, *RESTful Web APIs*): Level 0 — single URI, single verb (RPC tunnel). Level 1 — individual resources (`/tasks/123`). Level 2 — correct HTTP verbs and status codes (GET reads, POST creates, PUT replaces, PATCH updates, DELETE removes). Level 3 — hypermedia controls (HATEOAS). Target Level 2 minimum; add Level 3 links when clients benefit from discoverability.
16
+
17
+ **Contract-First Design** (Zalando, *RESTful API Guidelines*): Define the OpenAPI/JSON Schema before writing implementation code. The schema is the source of truth — generate types and validation from it. Changing the contract is a deliberate decision, not a side effect of refactoring.
18
+
19
+ **Validate at Boundaries** (RFC 7231): Never trust caller input. Parse and validate every request body, query param, and path param at the handler layer using a schema validator (zod, ajv). Internal service code receives already-validated, typed data.
20
+
21
+ **Idempotency Keys for Unsafe Methods**: POST and PATCH are not inherently idempotent. Accept an `Idempotency-Key` header; store the response for that key and replay it on retry. PUT and DELETE are idempotent by definition — no key needed.
22
+
23
+ **Never Break Consumers** (Zalando, *RESTful API Guidelines*): Version via URI prefix (`/v1/`) for public APIs or `Accept` header for internal APIs. Additive changes (new fields, new endpoints) are non-breaking. Removing or renaming fields is breaking — deprecate first, remove in the next major version.
24
+
25
+ ## Patterns
26
+
27
+ **Structured error envelope:**
28
+ ```typescript
29
+ // Every error response uses this shape
30
+ interface ErrorResponse {
31
+ error: {
32
+ code: string; // machine-readable, e.g. "VALIDATION_FAILED"
33
+ message: string; // human-readable summary
34
+ details?: unknown; // optional field-level errors or context
35
+ };
36
+ }
37
+ // Usage
38
+ res.status(422).json({
39
+ error: { code: 'VALIDATION_FAILED', message: 'Invalid input', details: issues }
40
+ });
41
+ ```
42
+
43
+ **Idempotency key middleware:**
44
+ ```typescript
45
+ async function idempotency(req, res, next) {
46
+ const key = req.headers['idempotency-key'];
47
+ if (!key) return next();
48
+ const cached = await store.get(key);
49
+ if (cached) return res.status(cached.status).json(cached.body);
50
+ res.on('finish', () => store.set(key, { status: res.statusCode, body: res.body }));
51
+ next();
52
+ }
53
+ ```
54
+
55
+ **Contract-first with zod:**
56
+ ```typescript
57
+ // Define schema first — derive type from it
58
+ const CreateTaskBody = z.object({ title: z.string().min(1), priority: z.enum(['p0','p1','p2']) });
59
+ type CreateTaskBody = z.infer<typeof CreateTaskBody>;
60
+ // Validate at handler boundary
61
+ const body = CreateTaskBody.parse(req.body); // throws ZodError → caught by error middleware
62
+ ```
63
+
64
+ ## Anti-patterns
65
+ - Tunneling all operations through POST to a single endpoint — stuck at Level 0.
66
+ - Returning `200 OK` with an error body — use correct status codes (4xx for client errors, 5xx for server errors).
67
+ - Validating inside business logic instead of at the handler boundary — mixes concerns.
68
+ - Exposing internal IDs, stack traces, or DB column names in error responses.
69
+ - Versioning by adding `?v=2` query params — use URI prefix or Accept header.
70
+ - Making POST endpoints without idempotency protection — clients that retry create duplicates.
71
+
72
+ ## Checklist
73
+ - [ ] Every endpoint uses correct HTTP verb and status code (Level 2+)
74
+ - [ ] Request/response schemas defined before implementation
75
+ - [ ] All input validated with zod/ajv at the handler layer
76
+ - [ ] Error responses follow `{ error: { code, message, details } }` envelope
77
+ - [ ] POST/PATCH endpoints accept `Idempotency-Key` header
78
+ - [ ] No breaking changes to existing consumers — additive only or versioned
79
+ - [ ] No internal details leaked in error responses (stack traces, DB columns)
80
+
81
+ ## References
82
+ - *RESTful Web APIs* — Leonard Richardson & Mike Amundsen
83
+ - *RFC 7231: HTTP/1.1 Semantics and Content* — IETF
84
+ - *RESTful API Guidelines* — Zalando
@@ -0,0 +1,76 @@
1
+ ---
2
+ name: backend-typescript
3
+ description: Node.js/TypeScript backend patterns, async, DI, error handling
4
+ domain: engineering
5
+ subdomain: backend
6
+ ---
7
+
8
+ # Backend TypeScript
9
+
10
+ ## Context
11
+ You are working on a Node.js/TypeScript backend. Apply Clean Architecture layering, factory-based dependency injection, and structured error handling. Tasks include adding endpoints, business logic, DB queries, or refactoring existing modules.
12
+
13
+ ## Core Principles
14
+
15
+ **Dependency Rule** (Martin, *Clean Architecture*): Source code dependencies point inward only — domain logic never imports infrastructure. Inject all I/O through interfaces at the boundary.
16
+
17
+ **Factory Dependency Injection** (Casciaro, *Node.js Design Patterns*): Prefer factory functions (`createX(deps): X`) over classes with `new`. Factories make dependencies explicit and enable easy mocking without class hierarchies.
18
+
19
+ **Typed Error Hierarchy**: Define a base `AppError` class; derive specific errors from it. Callers can `instanceof`-check without parsing strings. Never throw generic `Error` from domain code.
20
+
21
+ **Explicit Contracts**: Every exported function carries explicit return types and input validation via zod at the system boundary — trust nothing from outside, trust everything that passed the boundary.
22
+
23
+ **Graceful Shutdown**: Register `SIGTERM`/`SIGINT` handlers that stop accepting connections, drain in-flight requests, close DB, then `process.exit(0)`. Skipping this causes data loss in containers.
24
+
25
+ ## Patterns
26
+
27
+ **Factory DI:**
28
+ ```typescript
29
+ // deps interface keeps module testable
30
+ export interface TaskRepoDeps { db: Database }
31
+ export function createTaskRepo(deps: TaskRepoDeps): TaskRepo {
32
+ const insert = deps.db.prepare('INSERT INTO tasks ...');
33
+ return { create: (t) => insert.run(t) };
34
+ }
35
+ ```
36
+
37
+ **AppError hierarchy:**
38
+ ```typescript
39
+ export class AppError extends Error {
40
+ constructor(message: string, public readonly code: string) {
41
+ super(message); this.name = 'AppError';
42
+ }
43
+ }
44
+ export class NotFoundError extends AppError {
45
+ constructor(id: string) { super(`Not found: ${id}`, 'NOT_FOUND'); }
46
+ }
47
+ ```
48
+
49
+ **Graceful shutdown:**
50
+ ```typescript
51
+ const shutdown = async () => {
52
+ server.close(() => { db.close(); process.exit(0); });
53
+ };
54
+ process.on('SIGTERM', shutdown);
55
+ process.on('SIGINT', shutdown);
56
+ ```
57
+
58
+ ## Anti-patterns
59
+ - Classes with `new` for modules — use factory functions.
60
+ - `any` type — use `unknown` and narrow with guards.
61
+ - Mutable shared state between modules — pass state through DI.
62
+ - `try/catch` that swallows errors silently — always rethrow or return typed error.
63
+ - Domain logic importing DB/HTTP directly — violates Dependency Rule.
64
+
65
+ ## Checklist
66
+ - [ ] All exported functions have explicit return types
67
+ - [ ] No `any` types introduced
68
+ - [ ] Factory pattern used for new modules
69
+ - [ ] AppError subclass thrown, not generic Error
70
+ - [ ] No SQL string interpolation
71
+ - [ ] Graceful shutdown handles SIGTERM
72
+ - [ ] Input validated with zod at system boundary
73
+
74
+ ## References
75
+ - *Clean Architecture* — Robert C. Martin
76
+ - *Node.js Design Patterns* — Mario Casciaro & Luciano Mammino
@@ -0,0 +1,73 @@
1
+ ---
2
+ name: data-modeling
3
+ description: SQLite schema design, WAL mode, JSON fields, migrations, queries
4
+ domain: engineering
5
+ subdomain: data
6
+ ---
7
+
8
+ # Data Modeling
9
+
10
+ ## Context
11
+ You are working with SQLite databases — schema design, queries, indexes, migrations, or data access patterns. Apply normalization deliberately, index for your query patterns, and use WAL mode for concurrent workloads.
12
+
13
+ ## Core Principles
14
+
15
+ **Normal Form Decision Tree** (Kleppmann, *Designing Data-Intensive Applications*): 1NF (atomic values, no repeating groups) → 2NF (no partial key dependency) → 3NF (no transitive dependency). Stop at 3NF for OLTP. Denormalize only when profiling confirms a join is a bottleneck — not by anticipation.
16
+
17
+ **Composite Index Column Order** (SQLite Documentation, Hipp): Place equality-filtered columns first, range-filtered columns last. An index on `(status, created_at)` serves `WHERE status = ? AND created_at > ?` perfectly; reversed it cannot use the range efficiently.
18
+
19
+ **N+1 Detection Pattern** (Kleppmann, *Designing Data-Intensive Applications*): If you load a list then fetch related rows in a loop, you have N+1. Fix with a JOIN or a single `WHERE id IN (...)` query. One SQL statement per request, not one per row.
20
+
21
+ **WAL Mode Rationale** (SQLite Documentation, Hipp): WAL (Write-Ahead Log) allows concurrent reads during a write transaction — readers never block writers, writers never block readers. Essential for any multi-process or multi-thread SQLite usage. Enable at connection time: `PRAGMA journal_mode=WAL`.
22
+
23
+ **JSON Column Discipline**: Queryable fields belong in typed columns with indexes. Use JSON only for opaque blobs — configuration objects, metadata, serialized state — where you never filter or sort by inner fields in SQL.
24
+
25
+ ## Patterns
26
+
27
+ **Connection initialization:**
28
+ ```typescript
29
+ const db = new Database('app.db');
30
+ db.pragma('journal_mode = WAL');
31
+ db.pragma('foreign_keys = ON');
32
+ ```
33
+
34
+ **Composite index for common query pattern:**
35
+ ```sql
36
+ -- Query: WHERE status = ? AND created_at > ? ORDER BY created_at
37
+ CREATE INDEX idx_tasks_status_created ON tasks (status, created_at);
38
+ ```
39
+
40
+ **Fix N+1 with IN clause:**
41
+ ```typescript
42
+ // Bad: N+1
43
+ const tasks = db.prepare('SELECT * FROM tasks').all();
44
+ tasks.forEach(t => t.user = db.prepare('SELECT * FROM users WHERE id = ?').get(t.userId));
45
+
46
+ // Good: single query
47
+ const ids = tasks.map(t => t.userId);
48
+ const users = db.prepare(`SELECT * FROM users WHERE id IN (${ids.map(() => '?').join(',')})`).all(...ids);
49
+ ```
50
+
51
+ **Safe JSON field read:**
52
+ ```typescript
53
+ const meta = (() => { try { return JSON.parse(row.meta); } catch { return {}; } })();
54
+ ```
55
+
56
+ ## Anti-patterns
57
+ - String interpolation in SQL — parameterize everything.
58
+ - Missing indexes on WHERE/JOIN columns — profile first, index what you query.
59
+ - Storing queryable values in JSON columns — they can't be indexed.
60
+ - `DATETIME('now')` in SQL — use application-level ISO 8601 timestamps for portability.
61
+ - Schema changes without migration plan — existing data must satisfy new constraints.
62
+
63
+ ## Checklist
64
+ - [ ] WAL mode and foreign keys enabled at connection init
65
+ - [ ] Composite indexes ordered: equality columns first, range last
66
+ - [ ] No N+1 queries: lists use JOIN or IN clause
67
+ - [ ] JSON fields parsed with try/catch fallback
68
+ - [ ] All queries use prepared statements with named parameters
69
+ - [ ] Timestamps are ISO 8601 strings from application code
70
+
71
+ ## References
72
+ - *Designing Data-Intensive Applications* — Martin Kleppmann
73
+ - *SQLite Documentation* — D. Richard Hipp