@cyanautomation/kaseki-agent 1.4.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 (459) hide show
  1. package/.dockerignore +54 -0
  2. package/.eslintignore +11 -0
  3. package/.eslintrc.json +95 -0
  4. package/.github/ISSUE_TEMPLATE/bug_report.md +53 -0
  5. package/.github/ISSUE_TEMPLATE/feature_request.md +53 -0
  6. package/.github/ISSUE_TEMPLATE/security.md +51 -0
  7. package/.github/PULL_REQUEST_TEMPLATE/default.md +71 -0
  8. package/.github/dependabot.yml +38 -0
  9. package/.github/skills/dependency-cache-optimization/SKILL.md +526 -0
  10. package/.github/skills/docker-image-management/SKILL.md +532 -0
  11. package/.github/skills/frontend-design/SKILL.md +782 -0
  12. package/.github/skills/prompt-engineering/SKILL.md +360 -0
  13. package/.github/skills/quality-gate-config/SKILL.md +591 -0
  14. package/.github/skills/result-report-analysis/SKILL.md +576 -0
  15. package/.github/skills/test-automation/SKILL.md +593 -0
  16. package/.github/skills/workflow-diagnosis/SKILL.md +468 -0
  17. package/.github/workflows/build-docker-image.yml +453 -0
  18. package/.github/workflows/release.yml +68 -0
  19. package/.releaserc.json +135 -0
  20. package/CHANGELOG.md +117 -0
  21. package/CLAUDE.md +336 -0
  22. package/CONTRIBUTING.md +339 -0
  23. package/Dockerfile +217 -0
  24. package/README.md +1527 -0
  25. package/STYLE.md +521 -0
  26. package/add-js-extensions.d.ts +9 -0
  27. package/add-js-extensions.d.ts.map +1 -0
  28. package/add-js-extensions.js.map +1 -0
  29. package/dist/add-js-extensions.d.ts +9 -0
  30. package/dist/add-js-extensions.d.ts.map +1 -0
  31. package/dist/add-js-extensions.js +52 -0
  32. package/dist/add-js-extensions.js.map +1 -0
  33. package/dist/ansi-colors.d.ts +26 -0
  34. package/dist/ansi-colors.d.ts.map +1 -0
  35. package/dist/ansi-colors.js +51 -0
  36. package/dist/ansi-colors.js.map +1 -0
  37. package/dist/cli/BaseCommand.d.ts +18 -0
  38. package/dist/cli/BaseCommand.d.ts.map +1 -0
  39. package/dist/cli/BaseCommand.js +31 -0
  40. package/dist/cli/BaseCommand.js.map +1 -0
  41. package/dist/cli/KasekiCLI.d.ts +30 -0
  42. package/dist/cli/KasekiCLI.d.ts.map +1 -0
  43. package/dist/cli/KasekiCLI.js +134 -0
  44. package/dist/cli/KasekiCLI.js.map +1 -0
  45. package/dist/cli/commands/ConfigCommand.d.ts +13 -0
  46. package/dist/cli/commands/ConfigCommand.d.ts.map +1 -0
  47. package/dist/cli/commands/ConfigCommand.js +131 -0
  48. package/dist/cli/commands/ConfigCommand.js.map +1 -0
  49. package/dist/cli/commands/DoctorCommand.d.ts +45 -0
  50. package/dist/cli/commands/DoctorCommand.d.ts.map +1 -0
  51. package/dist/cli/commands/DoctorCommand.js +309 -0
  52. package/dist/cli/commands/DoctorCommand.js.map +1 -0
  53. package/dist/cli/commands/ListCommand.d.ts +9 -0
  54. package/dist/cli/commands/ListCommand.d.ts.map +1 -0
  55. package/dist/cli/commands/ListCommand.js +81 -0
  56. package/dist/cli/commands/ListCommand.js.map +1 -0
  57. package/dist/cli/commands/ReportCommand.d.ts +9 -0
  58. package/dist/cli/commands/ReportCommand.d.ts.map +1 -0
  59. package/dist/cli/commands/ReportCommand.js +98 -0
  60. package/dist/cli/commands/ReportCommand.js.map +1 -0
  61. package/dist/cli/commands/RunCommand.d.ts +13 -0
  62. package/dist/cli/commands/RunCommand.d.ts.map +1 -0
  63. package/dist/cli/commands/RunCommand.js +191 -0
  64. package/dist/cli/commands/RunCommand.js.map +1 -0
  65. package/dist/cli/commands/SecretsCommand.d.ts +9 -0
  66. package/dist/cli/commands/SecretsCommand.d.ts.map +1 -0
  67. package/dist/cli/commands/SecretsCommand.js +109 -0
  68. package/dist/cli/commands/SecretsCommand.js.map +1 -0
  69. package/dist/cli/commands/ServeCommand.d.ts +9 -0
  70. package/dist/cli/commands/ServeCommand.d.ts.map +1 -0
  71. package/dist/cli/commands/ServeCommand.js +50 -0
  72. package/dist/cli/commands/ServeCommand.js.map +1 -0
  73. package/dist/cli/commands/SetupCommand.d.ts +42 -0
  74. package/dist/cli/commands/SetupCommand.d.ts.map +1 -0
  75. package/dist/cli/commands/SetupCommand.js +249 -0
  76. package/dist/cli/commands/SetupCommand.js.map +1 -0
  77. package/dist/cli.d.ts +9 -0
  78. package/dist/cli.d.ts.map +1 -0
  79. package/dist/cli.js +130 -0
  80. package/dist/cli.js.map +1 -0
  81. package/dist/config/ConfigManager.d.ts +395 -0
  82. package/dist/config/ConfigManager.d.ts.map +1 -0
  83. package/dist/config/ConfigManager.js +446 -0
  84. package/dist/config/ConfigManager.js.map +1 -0
  85. package/dist/docker/DockerManager.d.ts +69 -0
  86. package/dist/docker/DockerManager.d.ts.map +1 -0
  87. package/dist/docker/DockerManager.js +266 -0
  88. package/dist/docker/DockerManager.js.map +1 -0
  89. package/dist/event-aggregator.d.ts +71 -0
  90. package/dist/event-aggregator.d.ts.map +1 -0
  91. package/dist/event-aggregator.js +95 -0
  92. package/dist/event-aggregator.js.map +1 -0
  93. package/dist/github-app-token.d.ts +16 -0
  94. package/dist/github-app-token.d.ts.map +1 -0
  95. package/dist/github-app-token.js +148 -0
  96. package/dist/github-app-token.js.map +1 -0
  97. package/dist/idempotency-store.d.ts +61 -0
  98. package/dist/idempotency-store.d.ts.map +1 -0
  99. package/dist/idempotency-store.js +321 -0
  100. package/dist/idempotency-store.js.map +1 -0
  101. package/dist/index.d.ts +25 -0
  102. package/dist/index.d.ts.map +1 -0
  103. package/dist/index.js +31 -0
  104. package/dist/index.js.map +1 -0
  105. package/dist/instance/InstanceManager.d.ts +81 -0
  106. package/dist/instance/InstanceManager.d.ts.map +1 -0
  107. package/dist/instance/InstanceManager.js +220 -0
  108. package/dist/instance/InstanceManager.js.map +1 -0
  109. package/dist/instance-metadata-reader.d.ts +48 -0
  110. package/dist/instance-metadata-reader.d.ts.map +1 -0
  111. package/dist/instance-metadata-reader.js +94 -0
  112. package/dist/instance-metadata-reader.js.map +1 -0
  113. package/dist/instance-state-derivation.d.ts +42 -0
  114. package/dist/instance-state-derivation.d.ts.map +1 -0
  115. package/dist/instance-state-derivation.js +133 -0
  116. package/dist/instance-state-derivation.js.map +1 -0
  117. package/dist/job-scheduler.d.ts +124 -0
  118. package/dist/job-scheduler.d.ts.map +1 -0
  119. package/dist/job-scheduler.js +992 -0
  120. package/dist/job-scheduler.js.map +1 -0
  121. package/dist/kaseki-api-client.d.ts +89 -0
  122. package/dist/kaseki-api-client.d.ts.map +1 -0
  123. package/dist/kaseki-api-client.js +405 -0
  124. package/dist/kaseki-api-client.js.map +1 -0
  125. package/dist/kaseki-api-config.d.ts +34 -0
  126. package/dist/kaseki-api-config.d.ts.map +1 -0
  127. package/dist/kaseki-api-config.js +113 -0
  128. package/dist/kaseki-api-config.js.map +1 -0
  129. package/dist/kaseki-api-routes.d.ts +13 -0
  130. package/dist/kaseki-api-routes.d.ts.map +1 -0
  131. package/dist/kaseki-api-routes.js +559 -0
  132. package/dist/kaseki-api-routes.js.map +1 -0
  133. package/dist/kaseki-api-service-wrapper.d.ts +43 -0
  134. package/dist/kaseki-api-service-wrapper.d.ts.map +1 -0
  135. package/dist/kaseki-api-service-wrapper.js +150 -0
  136. package/dist/kaseki-api-service-wrapper.js.map +1 -0
  137. package/dist/kaseki-api-service.d.ts +16 -0
  138. package/dist/kaseki-api-service.d.ts.map +1 -0
  139. package/dist/kaseki-api-service.js +143 -0
  140. package/dist/kaseki-api-service.js.map +1 -0
  141. package/dist/kaseki-api-types.d.ts +440 -0
  142. package/dist/kaseki-api-types.d.ts.map +1 -0
  143. package/dist/kaseki-api-types.js +64 -0
  144. package/dist/kaseki-api-types.js.map +1 -0
  145. package/dist/kaseki-cli-lib.d.ts +219 -0
  146. package/dist/kaseki-cli-lib.d.ts.map +1 -0
  147. package/dist/kaseki-cli-lib.js +523 -0
  148. package/dist/kaseki-cli-lib.js.map +1 -0
  149. package/dist/kaseki-cli.d.ts +38 -0
  150. package/dist/kaseki-cli.d.ts.map +1 -0
  151. package/dist/kaseki-cli.js +559 -0
  152. package/dist/kaseki-cli.js.map +1 -0
  153. package/dist/kaseki-report.d.ts +3 -0
  154. package/dist/kaseki-report.d.ts.map +1 -0
  155. package/dist/kaseki-report.js +140 -0
  156. package/dist/kaseki-report.js.map +1 -0
  157. package/dist/lib/subprocess-helpers.d.ts +98 -0
  158. package/dist/lib/subprocess-helpers.d.ts.map +1 -0
  159. package/dist/lib/subprocess-helpers.js +136 -0
  160. package/dist/lib/subprocess-helpers.js.map +1 -0
  161. package/dist/logger.d.ts +39 -0
  162. package/dist/logger.d.ts.map +1 -0
  163. package/dist/logger.js +79 -0
  164. package/dist/logger.js.map +1 -0
  165. package/dist/metrics.d.ts +19 -0
  166. package/dist/metrics.d.ts.map +1 -0
  167. package/dist/metrics.js +59 -0
  168. package/dist/metrics.js.map +1 -0
  169. package/dist/middleware/job-lookup.d.ts +27 -0
  170. package/dist/middleware/job-lookup.d.ts.map +1 -0
  171. package/dist/middleware/job-lookup.js +28 -0
  172. package/dist/middleware/job-lookup.js.map +1 -0
  173. package/dist/pi-event-filter.d.ts +3 -0
  174. package/dist/pi-event-filter.d.ts.map +1 -0
  175. package/dist/pi-event-filter.js +126 -0
  176. package/dist/pi-event-filter.js.map +1 -0
  177. package/dist/pi-progress-stream.d.ts +3 -0
  178. package/dist/pi-progress-stream.d.ts.map +1 -0
  179. package/dist/pi-progress-stream.js +205 -0
  180. package/dist/pi-progress-stream.js.map +1 -0
  181. package/dist/pi-progress-summarizer.d.ts +61 -0
  182. package/dist/pi-progress-summarizer.d.ts.map +1 -0
  183. package/dist/pi-progress-summarizer.js +246 -0
  184. package/dist/pi-progress-summarizer.js.map +1 -0
  185. package/dist/pre-flight-validator.d.ts +72 -0
  186. package/dist/pre-flight-validator.d.ts.map +1 -0
  187. package/dist/pre-flight-validator.js +513 -0
  188. package/dist/pre-flight-validator.js.map +1 -0
  189. package/dist/progress-stream-utils.d.ts +3 -0
  190. package/dist/progress-stream-utils.d.ts.map +1 -0
  191. package/dist/progress-stream-utils.js +15 -0
  192. package/dist/progress-stream-utils.js.map +1 -0
  193. package/dist/result-cache.d.ts +52 -0
  194. package/dist/result-cache.d.ts.map +1 -0
  195. package/dist/result-cache.js +134 -0
  196. package/dist/result-cache.js.map +1 -0
  197. package/dist/routes/artifact-routes.d.ts +10 -0
  198. package/dist/routes/artifact-routes.d.ts.map +1 -0
  199. package/dist/routes/artifact-routes.js +126 -0
  200. package/dist/routes/artifact-routes.js.map +1 -0
  201. package/dist/routes/log-routes.d.ts +8 -0
  202. package/dist/routes/log-routes.d.ts.map +1 -0
  203. package/dist/routes/log-routes.js +345 -0
  204. package/dist/routes/log-routes.js.map +1 -0
  205. package/dist/routes/status-routes.d.ts +8 -0
  206. package/dist/routes/status-routes.d.ts.map +1 -0
  207. package/dist/routes/status-routes.js +82 -0
  208. package/dist/routes/status-routes.js.map +1 -0
  209. package/dist/routes/webhook-routes.d.ts +6 -0
  210. package/dist/routes/webhook-routes.d.ts.map +1 -0
  211. package/dist/routes/webhook-routes.js +86 -0
  212. package/dist/routes/webhook-routes.js.map +1 -0
  213. package/dist/run-artifact-metadata-cache.d.ts +42 -0
  214. package/dist/run-artifact-metadata-cache.d.ts.map +1 -0
  215. package/dist/run-artifact-metadata-cache.js +139 -0
  216. package/dist/run-artifact-metadata-cache.js.map +1 -0
  217. package/dist/secret-value-cache.d.ts +13 -0
  218. package/dist/secret-value-cache.d.ts.map +1 -0
  219. package/dist/secret-value-cache.js +44 -0
  220. package/dist/secret-value-cache.js.map +1 -0
  221. package/dist/secrets/SecretsManager.d.ts +80 -0
  222. package/dist/secrets/SecretsManager.d.ts.map +1 -0
  223. package/dist/secrets/SecretsManager.js +306 -0
  224. package/dist/secrets/SecretsManager.js.map +1 -0
  225. package/dist/test-utils.d.ts +55 -0
  226. package/dist/test-utils.d.ts.map +1 -0
  227. package/dist/test-utils.js +48 -0
  228. package/dist/test-utils.js.map +1 -0
  229. package/dist/timestamp-tracker.d.ts +75 -0
  230. package/dist/timestamp-tracker.d.ts.map +1 -0
  231. package/dist/timestamp-tracker.js +121 -0
  232. package/dist/timestamp-tracker.js.map +1 -0
  233. package/dist/utils/failure-artifact-writer.d.ts +29 -0
  234. package/dist/utils/failure-artifact-writer.d.ts.map +1 -0
  235. package/dist/utils/failure-artifact-writer.js +157 -0
  236. package/dist/utils/failure-artifact-writer.js.map +1 -0
  237. package/dist/utils/file-helpers.d.ts +41 -0
  238. package/dist/utils/file-helpers.d.ts.map +1 -0
  239. package/dist/utils/file-helpers.js +143 -0
  240. package/dist/utils/file-helpers.js.map +1 -0
  241. package/dist/utils/http-client-factory.d.ts +46 -0
  242. package/dist/utils/http-client-factory.d.ts.map +1 -0
  243. package/dist/utils/http-client-factory.js +114 -0
  244. package/dist/utils/http-client-factory.js.map +1 -0
  245. package/dist/utils/progress-normalizer.d.ts +13 -0
  246. package/dist/utils/progress-normalizer.d.ts.map +1 -0
  247. package/dist/utils/progress-normalizer.js +57 -0
  248. package/dist/utils/progress-normalizer.js.map +1 -0
  249. package/dist/utils/response-helpers.d.ts +34 -0
  250. package/dist/utils/response-helpers.d.ts.map +1 -0
  251. package/dist/utils/response-helpers.js +78 -0
  252. package/dist/utils/response-helpers.js.map +1 -0
  253. package/dist/utils/route-helpers.d.ts +17 -0
  254. package/dist/utils/route-helpers.d.ts.map +1 -0
  255. package/dist/utils/route-helpers.js +22 -0
  256. package/dist/utils/route-helpers.js.map +1 -0
  257. package/dist/utils/status-response-builder.d.ts +23 -0
  258. package/dist/utils/status-response-builder.d.ts.map +1 -0
  259. package/dist/utils/status-response-builder.js +144 -0
  260. package/dist/utils/status-response-builder.js.map +1 -0
  261. package/dist/utils/type-guards.d.ts +37 -0
  262. package/dist/utils/type-guards.d.ts.map +1 -0
  263. package/dist/utils/type-guards.js +45 -0
  264. package/dist/utils/type-guards.js.map +1 -0
  265. package/dist/utils/utf8-helpers.d.ts +32 -0
  266. package/dist/utils/utf8-helpers.d.ts.map +1 -0
  267. package/dist/utils/utf8-helpers.js +97 -0
  268. package/dist/utils/utf8-helpers.js.map +1 -0
  269. package/dist/utils/webhook-event-builder.d.ts +26 -0
  270. package/dist/utils/webhook-event-builder.d.ts.map +1 -0
  271. package/dist/utils/webhook-event-builder.js +77 -0
  272. package/dist/utils/webhook-event-builder.js.map +1 -0
  273. package/dist/webhook-manager.d.ts +56 -0
  274. package/dist/webhook-manager.d.ts.map +1 -0
  275. package/dist/webhook-manager.js +359 -0
  276. package/dist/webhook-manager.js.map +1 -0
  277. package/docker/workspace-cache/package-lock.json +13 -0
  278. package/docker/workspace-cache/package.json +7 -0
  279. package/docker-compose.yml +53 -0
  280. package/docs/API.md +708 -0
  281. package/docs/BACKLOG.md +19 -0
  282. package/docs/BUILD_STRATEGY.md +404 -0
  283. package/docs/CLI.md +569 -0
  284. package/docs/DEPLOYMENT.md +521 -0
  285. package/docs/DEVELOPMENT.md +459 -0
  286. package/docs/DOCKER_SETUP.md +522 -0
  287. package/docs/ENHANCED_PROGRESS_LOGS.md +264 -0
  288. package/docs/IMPLEMENTATION_SUMMARY.md +549 -0
  289. package/docs/INTEGRATION_EXAMPLE.md +217 -0
  290. package/docs/NPM_SETUP.md +468 -0
  291. package/docs/PHASE1-4_IMPLEMENTATION.md +302 -0
  292. package/docs/PHASE1_COMPLETION.md +192 -0
  293. package/docs/PHASE2_COMPLETION.md +134 -0
  294. package/docs/PHASE6_MIGRATION.md +392 -0
  295. package/docs/PRINTF_SAFETY_FIX.md +282 -0
  296. package/docs/QUALITY_GATES.md +369 -0
  297. package/docs/SETUP_GUIDE.md +482 -0
  298. package/docs/TASK_PROMPT_TEMPLATES.md +533 -0
  299. package/docs/VALIDATION_FIX.md +139 -0
  300. package/docs/VERIFICATION_CHECKLIST.md +335 -0
  301. package/docs/repo-maturity.md +760 -0
  302. package/fix-tests.d.ts +9 -0
  303. package/fix-tests.d.ts.map +1 -0
  304. package/fix-tests.js.map +1 -0
  305. package/fix-tests.ts +53 -0
  306. package/jest.config.ts +31 -0
  307. package/kaseki +183 -0
  308. package/kaseki-agent.sh +1961 -0
  309. package/ops/logrotate/kaseki +10 -0
  310. package/package.json +83 -0
  311. package/perf/README.md +54 -0
  312. package/perf/pi-event-filter.benchmark.test.ts +98 -0
  313. package/run-kaseki-json.test.sh +106 -0
  314. package/run-kaseki.sh +990 -0
  315. package/scripts/allowlist-helper.sh +56 -0
  316. package/scripts/cleanup-kaseki.sh +168 -0
  317. package/scripts/deploy-pi-template.sh +293 -0
  318. package/scripts/docker-entrypoint.sh +71 -0
  319. package/scripts/dry-run-allowlist.sh +161 -0
  320. package/scripts/kaseki-activate.sh +396 -0
  321. package/scripts/kaseki-api.service +62 -0
  322. package/scripts/kaseki-container-entrypoint-wrapper.sh +119 -0
  323. package/scripts/kaseki-container-setup-remote.sh +172 -0
  324. package/scripts/kaseki-container-setup.sh +193 -0
  325. package/scripts/kaseki-healthcheck.sh +95 -0
  326. package/scripts/kaseki-install.sh +50 -0
  327. package/scripts/kaseki-maturity-score.sh +291 -0
  328. package/scripts/kaseki-performance-metrics.sh +122 -0
  329. package/scripts/kaseki-preflight.sh +270 -0
  330. package/scripts/kaseki-setup.sh +265 -0
  331. package/scripts/pi-setup-remote.sh +213 -0
  332. package/scripts/setup-github-labels.sh +42 -0
  333. package/scripts/suggest-allowlist.sh +68 -0
  334. package/scripts/templates/MULTI_HOST_DISTRIBUTED.md +337 -0
  335. package/scripts/templates/REST_API_SERVICE.md +490 -0
  336. package/scripts/templates/SINGLE_HOST_CLI.md +194 -0
  337. package/scripts/test-github-app.sh +248 -0
  338. package/src/add-js-extensions.ts +61 -0
  339. package/src/ansi-colors.test.ts +62 -0
  340. package/src/ansi-colors.ts +67 -0
  341. package/src/cli/BaseCommand.ts +40 -0
  342. package/src/cli/KasekiCLI.ts +154 -0
  343. package/src/cli/commands/ConfigCommand.ts +145 -0
  344. package/src/cli/commands/DoctorCommand.ts +329 -0
  345. package/src/cli/commands/ListCommand.ts +105 -0
  346. package/src/cli/commands/ReportCommand.ts +110 -0
  347. package/src/cli/commands/RunCommand.ts +218 -0
  348. package/src/cli/commands/SecretsCommand.ts +120 -0
  349. package/src/cli/commands/ServeCommand.ts +62 -0
  350. package/src/cli/commands/SetupCommand.ts +301 -0
  351. package/src/cli.ts +138 -0
  352. package/src/config/ConfigManager.ts +476 -0
  353. package/src/docker/DockerManager.ts +319 -0
  354. package/src/docker-entrypoint-packaging.test.ts +33 -0
  355. package/src/event-aggregator.test.ts +117 -0
  356. package/src/event-aggregator.ts +126 -0
  357. package/src/github-app-token.ts +215 -0
  358. package/src/idempotency-store.test.ts +117 -0
  359. package/src/idempotency-store.ts +385 -0
  360. package/src/index.ts +89 -0
  361. package/src/instance/InstanceManager.ts +285 -0
  362. package/src/instance-metadata-reader.test.ts +190 -0
  363. package/src/instance-metadata-reader.ts +129 -0
  364. package/src/instance-state-derivation.test.ts +263 -0
  365. package/src/instance-state-derivation.ts +148 -0
  366. package/src/job-scheduler.test.ts +1236 -0
  367. package/src/job-scheduler.ts +1117 -0
  368. package/src/kaseki-api-client.ts +488 -0
  369. package/src/kaseki-api-config.test.ts +315 -0
  370. package/src/kaseki-api-config.ts +175 -0
  371. package/src/kaseki-api-routes.test.ts +1615 -0
  372. package/src/kaseki-api-routes.ts +643 -0
  373. package/src/kaseki-api-service-wrapper.ts +188 -0
  374. package/src/kaseki-api-service.test.ts +418 -0
  375. package/src/kaseki-api-service.ts +192 -0
  376. package/src/kaseki-api-types.ts +320 -0
  377. package/src/kaseki-cli-lib.test.ts +552 -0
  378. package/src/kaseki-cli-lib.ts +760 -0
  379. package/src/kaseki-cli.ts +682 -0
  380. package/src/kaseki-report.test.ts +118 -0
  381. package/src/kaseki-report.ts +192 -0
  382. package/src/lib/subprocess-helpers.ts +177 -0
  383. package/src/logger.ts +114 -0
  384. package/src/metrics.ts +66 -0
  385. package/src/middleware/job-lookup.test.ts +113 -0
  386. package/src/middleware/job-lookup.ts +45 -0
  387. package/src/pi-event-filter.test.ts +183 -0
  388. package/src/pi-event-filter.ts +183 -0
  389. package/src/pi-progress-stream.ts +287 -0
  390. package/src/pi-progress-summarizer.test.ts +302 -0
  391. package/src/pi-progress-summarizer.ts +287 -0
  392. package/src/pre-flight-validator.test.ts +512 -0
  393. package/src/pre-flight-validator.ts +618 -0
  394. package/src/progress-stream-utils.test.ts +35 -0
  395. package/src/progress-stream-utils.ts +14 -0
  396. package/src/result-cache.test.ts +195 -0
  397. package/src/result-cache.ts +181 -0
  398. package/src/routes/artifact-routes.ts +169 -0
  399. package/src/routes/log-routes.ts +391 -0
  400. package/src/routes/status-routes.ts +92 -0
  401. package/src/routes/webhook-routes.ts +97 -0
  402. package/src/run-artifact-metadata-cache.test.ts +80 -0
  403. package/src/run-artifact-metadata-cache.ts +184 -0
  404. package/src/secret-value-cache.test.ts +66 -0
  405. package/src/secret-value-cache.ts +55 -0
  406. package/src/secrets/SecretsManager.ts +343 -0
  407. package/src/test-utils.ts +81 -0
  408. package/src/timestamp-tracker.test.ts +134 -0
  409. package/src/timestamp-tracker.ts +132 -0
  410. package/src/utils/failure-artifact-writer.ts +187 -0
  411. package/src/utils/file-helpers.test.ts +235 -0
  412. package/src/utils/file-helpers.ts +150 -0
  413. package/src/utils/http-client-factory.test.ts +245 -0
  414. package/src/utils/http-client-factory.ts +157 -0
  415. package/src/utils/progress-normalizer.test.ts +442 -0
  416. package/src/utils/progress-normalizer.ts +68 -0
  417. package/src/utils/response-helpers.test.ts +122 -0
  418. package/src/utils/response-helpers.ts +101 -0
  419. package/src/utils/route-helpers.ts +30 -0
  420. package/src/utils/status-response-builder.ts +159 -0
  421. package/src/utils/type-guards.ts +52 -0
  422. package/src/utils/utf8-helpers.ts +102 -0
  423. package/src/utils/webhook-event-builder.test.ts +143 -0
  424. package/src/utils/webhook-event-builder.ts +87 -0
  425. package/src/webhook-manager.test.ts +152 -0
  426. package/src/webhook-manager.ts +445 -0
  427. package/templates/allowlist-api-route.txt +7 -0
  428. package/templates/allowlist-comprehensive.txt +8 -0
  429. package/templates/allowlist-parser-fix.txt +6 -0
  430. package/templates/allowlist-ui-component.txt +9 -0
  431. package/templates/allowlist-utility.txt +9 -0
  432. package/test/actual-model-metadata.test.sh +102 -0
  433. package/test/dry-run.test.sh +131 -0
  434. package/test/fixtures/kaseki-report-exit-codes/metadata-exit-0.json +1 -0
  435. package/test/fixtures/kaseki-report-exit-codes/metadata-exit-1.json +1 -0
  436. package/test/fixtures/kaseki-report-exit-codes/metadata-exit-invalid.json +1 -0
  437. package/test/fixtures/kaseki-report-exit-codes/metadata-exit-str-0.json +1 -0
  438. package/test/fixtures/kaseki-report-exit-codes/metadata-exit-str-1.json +1 -0
  439. package/test/kaseki-api.integration.test.sh +165 -0
  440. package/test/pi-event-filter-failure.test.sh +83 -0
  441. package/test/printf-safety-focused.test.sh +99 -0
  442. package/test/printf-safety-results/results/restoration.jsonl +10 -0
  443. package/test/printf-safety-results/results/test.jsonl +0 -0
  444. package/test/printf-safety.test.sh +297 -0
  445. package/test/validation-fix.test.sh +79 -0
  446. package/test/validation-integration.test.sh +109 -0
  447. package/tests/allowlist-glob.test.sh +61 -0
  448. package/tests/dependency-cache-key.test.sh +48 -0
  449. package/tests/dependency-restore-mode.test.sh +48 -0
  450. package/tests/doctor-template-parity.test.sh +95 -0
  451. package/tests/github-operations.test.sh +142 -0
  452. package/tests/npm-install-flags.test.sh +58 -0
  453. package/tests/quality-gates.test.sh +178 -0
  454. package/tests/repo-memory.test.sh +103 -0
  455. package/tests/restore-disallowed-changes.test.sh +80 -0
  456. package/tests/validation-missing-npm-scripts.test.sh +93 -0
  457. package/tests/validation-strict-mode.test.sh +118 -0
  458. package/tsconfig.changed.json +7 -0
  459. package/tsconfig.json +39 -0
@@ -0,0 +1,192 @@
1
+ import express from 'express';
2
+ import type { Server } from 'http';
3
+ import { loadConfig } from './kaseki-api-config';
4
+ import { JobScheduler } from './job-scheduler';
5
+ import { WebhookManager } from './webhook-manager';
6
+ import { IdempotencyStore } from './idempotency-store';
7
+ import { PreFlightValidator } from './pre-flight-validator';
8
+ import { createApiRouter } from './kaseki-api-routes';
9
+ import { createEventLogger } from './logger';
10
+ import { ResultCache } from './result-cache';
11
+
12
+ type ShutdownDeps = {
13
+ server: Server;
14
+ scheduler: Pick<JobScheduler, 'shutdown'>;
15
+ webhookManager: WebhookManager;
16
+ idempotencyStore: IdempotencyStore;
17
+ forceExitAfterMs?: number;
18
+ exit?: (code: number) => never;
19
+ };
20
+
21
+ export function createGracefulShutdown({
22
+ server,
23
+ scheduler,
24
+ webhookManager,
25
+ idempotencyStore,
26
+ forceExitAfterMs = 8000,
27
+ exit = process.exit,
28
+ }: ShutdownDeps): (signal: string) => Promise<void> {
29
+ const logger = createEventLogger('kaseki-api');
30
+
31
+ return async (signal: string) => {
32
+ logger.info(`Received ${signal}, shutting down gracefully...`);
33
+
34
+ const hardTimeout = setTimeout(() => {
35
+ logger.error(
36
+ `Graceful shutdown timeout after ${forceExitAfterMs}ms, forcing exit`,
37
+ );
38
+ exit(1);
39
+ }, forceExitAfterMs);
40
+
41
+ try {
42
+ await new Promise<void>((resolve, reject) => {
43
+ server.close((err?: Error) => {
44
+ if (err) {
45
+ reject(err);
46
+ return;
47
+ }
48
+ logger.info('HTTP server closed');
49
+ resolve();
50
+ });
51
+ });
52
+
53
+ scheduler.shutdown();
54
+ logger.info('Job scheduler shutdown');
55
+
56
+ await webhookManager.shutdown();
57
+ logger.info('Webhook manager shutdown');
58
+
59
+ idempotencyStore.shutdown();
60
+ logger.info('Idempotency store shutdown');
61
+
62
+ exit(0);
63
+ } catch (err) {
64
+ logger.error('Error during graceful shutdown:', { error: String(err) });
65
+ exit(1);
66
+ } finally {
67
+ clearTimeout(hardTimeout);
68
+ }
69
+ };
70
+ }
71
+
72
+ export function assertSupportedNodeVersion(
73
+ version: string = process.versions.node,
74
+ minimumMajor: number = 24,
75
+ ): void {
76
+ const normalizedVersion = version.trim();
77
+ const isValidVersion = /^\d+(?:\.\d+){0,2}$/.test(normalizedVersion);
78
+ const major = Number.parseInt(normalizedVersion.split('.')[0] ?? '', 10);
79
+
80
+ const logger = createEventLogger('kaseki-api');
81
+ logger.info(`Node runtime detected: v${normalizedVersion}`);
82
+
83
+ if (!isValidVersion || !Number.isFinite(major) || major < minimumMajor) {
84
+ logger.error(
85
+ `Unsupported Node.js runtime v${normalizedVersion}. Kaseki API service requires Node.js >= ${minimumMajor}. Please upgrade Node or deploy the Docker image built from this repo's Dockerfile (node:24-bookworm-slim).`,
86
+ );
87
+ process.exit(1);
88
+ }
89
+ }
90
+
91
+ /**
92
+ * Main Kaseki API service.
93
+ */
94
+ async function main(): Promise<void> {
95
+ const logger = createEventLogger('kaseki-api');
96
+
97
+ assertSupportedNodeVersion();
98
+
99
+ // Load configuration
100
+ let config;
101
+ try {
102
+ config = loadConfig();
103
+ } catch (err) {
104
+ logger.error('Configuration error:', { error: String(err) });
105
+ process.exit(1);
106
+ }
107
+
108
+ // Log detailed startup information
109
+ logger.event('service_startup_config', {
110
+ port: config.port,
111
+ logLevel: config.logLevel,
112
+ maxConcurrentRuns: config.maxConcurrentRuns,
113
+ resultsDir: config.resultsDir,
114
+ maxDiffBytes: config.maxDiffBytes,
115
+ agentTimeoutSeconds: config.agentTimeoutSeconds,
116
+ artifactCacheMaxEntries: config.artifactCacheMaxEntries,
117
+ artifactCacheTtlMs: config.artifactCacheTtlMs,
118
+ artifactCacheMaxFileBytes: config.artifactCacheMaxFileBytes,
119
+ nodeVersion: process.versions.node,
120
+ npmVersion: process.versions.npm || 'unknown',
121
+ platform: process.platform,
122
+ arch: process.arch,
123
+ });
124
+
125
+ // Log environment info
126
+ logger.event('service_startup_environment', {
127
+ pid: process.pid,
128
+ uptime: process.uptime(),
129
+ memoryUsage: JSON.stringify(process.memoryUsage()),
130
+ cpuUsage: JSON.stringify(process.cpuUsage()),
131
+ });
132
+
133
+ // Create Express app
134
+ const app = express();
135
+ app.use(express.json());
136
+
137
+ // Create shared artifact content cache
138
+ const artifactCache = new ResultCache({
139
+ maxEntries: config.artifactCacheMaxEntries,
140
+ ttlMs: config.artifactCacheTtlMs,
141
+ maxFileBytes: config.artifactCacheMaxFileBytes,
142
+ });
143
+
144
+ // Create webhook manager
145
+ const webhookManager = new WebhookManager(config.resultsDir);
146
+
147
+ // Create idempotency store
148
+ const idempotencyStore = new IdempotencyStore(config.resultsDir, 24);
149
+
150
+ // Create pre-flight validator
151
+ const preFlightValidator = new PreFlightValidator();
152
+
153
+ // Create scheduler
154
+ const scheduler = new JobScheduler(config, webhookManager, artifactCache);
155
+
156
+ // Mount API routes
157
+ const apiRouter = createApiRouter(scheduler, config, idempotencyStore, preFlightValidator, artifactCache);
158
+ app.use('/api', apiRouter);
159
+ app.use('/', apiRouter);
160
+
161
+ // Start server
162
+ const server = app.listen(config.port, () => {
163
+ logger.event('service_started', {
164
+ port: config.port,
165
+ logLevel: config.logLevel,
166
+ maxConcurrentRuns: config.maxConcurrentRuns,
167
+ resultsDir: config.resultsDir,
168
+ nodeVersion: process.versions.node,
169
+ });
170
+ });
171
+
172
+ // Graceful shutdown
173
+ const gracefulShutdown = createGracefulShutdown({ server, scheduler, webhookManager, idempotencyStore });
174
+
175
+ process.on('SIGTERM', () => void gracefulShutdown('SIGTERM'));
176
+ process.on('SIGINT', () => void gracefulShutdown('SIGINT'));
177
+
178
+ // Catch unhandled errors
179
+ process.on('uncaughtException', (err) => {
180
+ logger.error('Uncaught exception:', { error: String(err), stack: err instanceof Error ? err.stack : undefined });
181
+ process.exit(1);
182
+ });
183
+
184
+ process.on('unhandledRejection', (reason) => {
185
+ logger.error('Unhandled rejection:', { reason: String(reason) });
186
+ process.exit(1);
187
+ });
188
+ }
189
+
190
+ if (!process.env.JEST_WORKER_ID) {
191
+ void main();
192
+ }
@@ -0,0 +1,320 @@
1
+ import { z } from 'zod';
2
+
3
+ /**
4
+ * Webhook event types.
5
+ */
6
+ export enum WebhookEventType {
7
+ JOB_SUBMITTED = 'job.submitted',
8
+ JOB_STARTED = 'job.started',
9
+ JOB_PROGRESS = 'job.progress',
10
+ JOB_COMPLETED = 'job.completed',
11
+ JOB_FAILED = 'job.failed',
12
+ JOB_CANCELLED = 'job.cancelled',
13
+ }
14
+
15
+ /**
16
+ * Webhook configuration for a run.
17
+ */
18
+ export const WebhookConfigSchema = z.object({
19
+ url: z.string().url('Webhook URL must be valid'),
20
+ secret: z.string().min(16).optional().describe('HMAC secret for signature verification'),
21
+ events: z.array(z.nativeEnum(WebhookEventType)).optional().describe('Event types to deliver'),
22
+ retryPolicy: z.object({
23
+ maxAttempts: z.number().int().min(1).max(10).default(5),
24
+ initialDelayMs: z.number().int().min(100).max(5000).default(1000),
25
+ maxDelayMs: z.number().int().min(1000).max(60000).default(30000),
26
+ }).optional(),
27
+ });
28
+
29
+ export type WebhookConfig = z.infer<typeof WebhookConfigSchema>;
30
+
31
+ /**
32
+ * Webhook payload event.
33
+ */
34
+ export interface WebhookPayload {
35
+ eventType: WebhookEventType;
36
+ jobId: string;
37
+ timestamp: string; // ISO 8601
38
+ data: {
39
+ status?: 'queued' | 'running' | 'completed' | 'failed';
40
+ stage?: string;
41
+ elapsed?: number; // seconds
42
+ timeoutRiskPercent?: number;
43
+ exitCode?: number;
44
+ failureClass?: string;
45
+ error?: string;
46
+ };
47
+ }
48
+
49
+ /**
50
+ * Request tracing info.
51
+ */
52
+ export const RequestTracingSchema = z.object({
53
+ correlationId: z.string().uuid().optional().describe('Correlation ID for tracking'),
54
+ requestId: z.string().uuid().optional().describe('Unique request ID'),
55
+ });
56
+
57
+ export type RequestTracing = z.infer<typeof RequestTracingSchema>;
58
+
59
+ /**
60
+ * Request to trigger a new kaseki run.
61
+ */
62
+ export const RunRequestSchema = z.object({
63
+ repoUrl: z.string().url('Repository URL must be valid').describe('Git repository URL'),
64
+ ref: z.string().min(1).default('main').describe('Git branch/tag/commit'),
65
+ taskPrompt: z.string().min(10).optional().describe('Task prompt for Pi agent'),
66
+ changedFilesAllowlist: z.array(z.string()).optional().describe('Space-separated file patterns'),
67
+ allowlist: z
68
+ .object({
69
+ include: z.array(z.string()).optional().describe('Alias for changedFilesAllowlist'),
70
+ })
71
+ .optional()
72
+ .describe('Controller-friendly allowlist alias'),
73
+ maxDiffBytes: z.number().int().positive().optional().describe('Max diff size in bytes'),
74
+ validationCommands: z.array(z.string()).optional().describe('Validation commands to run'),
75
+ validation: z
76
+ .object({
77
+ commands: z.array(z.string()).optional().describe('Alias for validationCommands'),
78
+ })
79
+ .optional()
80
+ .describe('Controller-friendly validation alias'),
81
+ taskMode: z.enum(['patch', 'inspect']).optional().describe('Task mode: patch or inspect'),
82
+ publishMode: z.enum(['none', 'branch', 'draft_pr']).optional().describe('Publishing mode after validation'),
83
+ startupCheck: z.boolean().optional().describe('Start a worker container and exit after boot/runtime checks'),
84
+ webhookConfig: WebhookConfigSchema.optional().describe('Webhook configuration for job events'),
85
+ tracing: RequestTracingSchema.optional().describe('Request tracing identifiers'),
86
+ idempotencyKey: z.string().uuid().optional().describe('Idempotency key for safe retries'),
87
+ timeoutSeconds: z.number().int().min(60).max(10800).optional().describe('Per-run timeout in seconds'),
88
+ });
89
+
90
+ export type RunRequest = z.infer<typeof RunRequestSchema>;
91
+
92
+ /**
93
+ * Response after triggering a run.
94
+ */
95
+ export interface RunResponse {
96
+ id: string; // kaseki-N instance ID
97
+ status: 'queued' | 'running' | 'completed' | 'failed';
98
+ createdAt: string; // ISO 8601
99
+ correlationId?: string; // Request correlation ID
100
+ requestId?: string; // Unique request ID
101
+ cached?: boolean; // True when returned from an idempotency replay
102
+ completedAt?: string; // ISO 8601 when replaying a terminal run
103
+ exitCode?: number;
104
+ failureClass?: string;
105
+ error?: string;
106
+ }
107
+
108
+ /**
109
+ * Structured progress information for a run.
110
+ */
111
+ export interface StructuredProgress {
112
+ stage: string; // Required: current stage name
113
+ percentComplete?: number; // Optional: 0-100
114
+ message?: string; // Optional: detailed message
115
+ updatedAt?: string; // Optional: ISO 8601 timestamp
116
+ }
117
+
118
+ /**
119
+ * Status poll response.
120
+ */
121
+ export interface StatusResponse {
122
+ id: string;
123
+ status: 'queued' | 'running' | 'completed' | 'failed';
124
+ progress?: StructuredProgress;
125
+ elapsedSeconds?: number;
126
+ timeoutRiskPercent?: number;
127
+ exitCode?: number;
128
+ failureClass?: string;
129
+ validationFailureReason?: string; // e.g., "validation_command_failed: npm run test (exit 1)"
130
+ qualityFailureReason?: string; // e.g., "max_diff_bytes: 250KB exceeds limit of 200KB"
131
+ error?: string;
132
+ resultDir?: string;
133
+ correlationId?: string; // Request correlation ID
134
+ requestId?: string; // Unique request ID
135
+ artifacts?: {
136
+ metadataJson: boolean;
137
+ analysisMd: boolean;
138
+ resultSummaryMd: boolean;
139
+ failureJson: boolean;
140
+ stderrLog: boolean;
141
+ availableFiles: string[];
142
+ };
143
+ diagnosticEntryPoint?: 'failure.json' | 'analysis.md' | 'result-summary.md';
144
+ }
145
+
146
+ /**
147
+ * Pre-flight validation check result.
148
+ */
149
+ export interface ValidationCheck {
150
+ name: string; // e.g., 'repo-reachable', 'ref-exists', 'repo-size'
151
+ status: 'pass' | 'fail' | 'warning';
152
+ message: string;
153
+ detail?: string;
154
+ }
155
+
156
+ /**
157
+ * Pre-flight validation response.
158
+ */
159
+ export interface ValidationResponse {
160
+ isValid: boolean;
161
+ checks: ValidationCheck[];
162
+ warnings: string[];
163
+ errors: string[];
164
+ estimatedDurationSeconds?: number;
165
+ }
166
+
167
+ /**
168
+ * Log retrieval response.
169
+ */
170
+ export interface LogResponse {
171
+ logType: 'stdout' | 'stderr' | 'validation' | 'progress' | 'quality' | 'secret-scan';
172
+ content: string;
173
+ size: number;
174
+ }
175
+
176
+ /**
177
+ * Artifact download response.
178
+ */
179
+ export interface ArtifactResponse {
180
+ file: string;
181
+ contentType: string;
182
+ size: number;
183
+ content?: string; // For text artifacts
184
+ url?: string; // For large artifacts, provide signed URL
185
+ }
186
+
187
+ export interface RunArtifactFileMetadata {
188
+ name: string;
189
+ size: number;
190
+ contentType: string;
191
+ available: boolean;
192
+ }
193
+
194
+ export interface RunArtifactsResponse {
195
+ id: string;
196
+ runStatus: 'queued' | 'running' | 'completed' | 'failed';
197
+ exitCode?: number;
198
+ artifacts: RunArtifactFileMetadata[];
199
+ recommended: string[];
200
+ }
201
+
202
+ /**
203
+ * Run analysis response (comprehensive summary).
204
+ */
205
+ export interface AnalysisResponse {
206
+ id: string;
207
+ status: 'queued' | 'running' | 'completed' | 'failed';
208
+ createdAt: string;
209
+ completedAt?: string;
210
+ elapsedSeconds?: number;
211
+ exitCode?: number;
212
+ failureClass?: string;
213
+ metadata?: {
214
+ model?: string;
215
+ instance?: string;
216
+ repo?: string;
217
+ ref?: string;
218
+ };
219
+ changes?: {
220
+ changedFiles: string[];
221
+ diffSize: number;
222
+ };
223
+ validation?: {
224
+ passed: boolean;
225
+ commandResults: Array<{
226
+ command: string;
227
+ exitCode: number;
228
+ elapsed: number;
229
+ }>;
230
+ };
231
+ errors?: string[];
232
+ }
233
+
234
+ /**
235
+ * List runs response.
236
+ */
237
+ export interface RunsListResponse {
238
+ runs: Array<{
239
+ id: string;
240
+ status: 'queued' | 'running' | 'completed' | 'failed';
241
+ createdAt: string;
242
+ completedAt?: string;
243
+ resultDir?: string;
244
+ exitCode?: number;
245
+ failureClass?: string;
246
+ error?: string;
247
+ }>;
248
+ total: number;
249
+ retention?: {
250
+ terminalJobIndexMaxEntries: number;
251
+ note: string;
252
+ };
253
+ }
254
+
255
+ export interface PreflightCheck {
256
+ name: string;
257
+ ok: boolean;
258
+ detail?: string;
259
+ remediation?: string;
260
+ }
261
+
262
+ export interface PreflightResponse {
263
+ status: 'ok' | 'degraded' | 'error';
264
+ timestamp: string;
265
+ checks: PreflightCheck[];
266
+ image?: string;
267
+ imageDigest?: string;
268
+ templateImage?: string;
269
+ templateImageDigest?: string;
270
+ templateDir?: string;
271
+ templateRef?: string;
272
+ resultsDir: string;
273
+ runtime?: {
274
+ nodeVersion: string;
275
+ uid?: number;
276
+ gid?: number;
277
+ groups?: number[];
278
+ };
279
+ docker?: {
280
+ version?: string;
281
+ clientVersion?: string;
282
+ serverVersion?: string;
283
+ };
284
+ }
285
+
286
+ /**
287
+ * Error response (RFC 7807 Problem Details).
288
+ */
289
+ export interface ErrorResponse {
290
+ type: string; // e.g., 'https://api.kaseki.local/errors#unauthorized'
291
+ title: string; // e.g., 'Unauthorized'
292
+ status: number;
293
+ detail: string;
294
+ instance?: string; // Run ID if applicable
295
+ }
296
+
297
+ /**
298
+ * Internal job representation.
299
+ */
300
+ export interface Job {
301
+ id: string; // kaseki-N instance ID
302
+ status: 'queued' | 'running' | 'completed' | 'failed';
303
+ request: RunRequest;
304
+ createdAt: Date;
305
+ startedAt?: Date;
306
+ completedAt?: Date;
307
+ exitCode?: number;
308
+ failureClass?: string;
309
+ error?: string;
310
+ resultDir?: string;
311
+ processId?: number;
312
+ timeout?: NodeJS.Timeout;
313
+ finalized?: boolean;
314
+ webhookConfig?: WebhookConfig; // Webhook delivery config
315
+ correlationId?: string; // Request correlation ID
316
+ requestId?: string; // Unique request ID
317
+ currentStage?: string; // Current job stage for progress tracking
318
+ idempotencyKey?: string; // Idempotency key for deduplication
319
+ effectiveTimeoutSeconds?: number; // Resolved timeout applied to this job
320
+ }