@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,339 @@
1
+ # Contributing to Kaseki Agent
2
+
3
+ Thanks for helping improve Kaseki Agent. This repo is the host/container orchestration layer for running ephemeral coding-agent jobs, so changes here should stay bounded, reproducible, and operator-friendly.
4
+
5
+ ## 1) Proposing or updating `TASK_PROMPT` defaults and guardrails
6
+
7
+ `TASK_PROMPT` defaults are currently defined in both runtime entrypoints:
8
+
9
+ - Host launcher: `run-kaseki.sh`
10
+ - Container runner: `kaseki-agent.sh`
11
+
12
+ When changing default prompt behavior, update both files in the same PR so host metadata and in-container execution stay aligned.
13
+
14
+ ### What to include in prompt changes
15
+
16
+ - **Task objective clarity:** what behavior the downstream agent should change.
17
+ - **Scope boundaries:** which files/types of changes are allowed.
18
+ - **Security guardrails:** explicit instruction to avoid printing/exposing secrets, credentials, or env vars.
19
+ - **Test expectation in prompt:** call out the focused test file(s) to update when behavior changes.
20
+
21
+ ### PR expectations for prompt changes
22
+
23
+ - Explain *why* the prompt default changed and what failure mode it addresses.
24
+ - Include before/after prompt snippets (or a concise diff summary).
25
+ - Confirm both scripts were updated together (unless intentionally diverged, which should be justified).
26
+
27
+ ## 2) Test expectations for upstream target repos
28
+
29
+ Behavior changes in target repos must include corresponding tests. In particular:
30
+
31
+ - Add or update **focused Vitest coverage** whenever behavior changes.
32
+ - Prefer narrow, deterministic tests near the touched behavior (for example, parser-focused tests rather than broad end-to-end-only coverage).
33
+ - Ensure `KASEKI_VALIDATION_COMMANDS` still reflects the expected upstream validation sequence.
34
+
35
+ If a prompt requests behavior changes but no focused Vitest update is present, treat that as an incomplete contribution.
36
+
37
+ ### Validation fail-fast behavior
38
+
39
+ Kaseki Agent validates changes using a **fail-fast pipeline** to minimize wasted CI time:
40
+
41
+ - **Quality gates run first** — Diff size, allowlist, and secret scans run before validation commands. If any quality gate fails, validation is skipped entirely.
42
+ - **Validation stops at first failure** — By default (`KASEKI_VALIDATION_FAIL_FAST=1`), validation stops at the first command failure instead of running all commands. This saves 10-60s per run when early commands fail.
43
+ - **Missing npm scripts are skipped** — Validation commands like `npm run check` are skipped automatically if the script doesn't exist in `package.json`, with a warning logged.
44
+
45
+ **Controlling fail-fast behavior:**
46
+
47
+ | Variable | Default | Notes |
48
+ |---|---|---|
49
+ | `KASEKI_VALIDATION_FAIL_FAST` | 1 | Set to 0 to run all validation commands despite early failures (old behavior) |
50
+ | `KASEKI_STRICT_SCRIPT_CHECK` | 0 | Set to 1 to fail validation if any npm script is missing (for strict repos) |
51
+
52
+ **Example:** If `npm run check` (missing), `npm run test`, and `npm run build` are configured, with fail-fast enabled:
53
+
54
+ 1. `npm run check` is skipped (script missing) → warning logged
55
+ 2. `npm run test` runs and fails → validation stops
56
+ 3. `npm run build` is NOT run (fail-fast stopped the loop)
57
+
58
+ **Metadata tracking:** Kaseki records fail-fast decisions in `metadata.json`:
59
+
60
+ - `validation_fail_fast_mode`: whether fail-fast was enabled for this run
61
+ - `validation_stopped_early`: whether validation stopped at first failure
62
+ - `validation_commands_attempted`: how many validation commands actually ran
63
+
64
+ Contributors should be aware of fail-fast behavior when designing validation commands; avoid side effects that depend on the full command sequence running.
65
+
66
+ ## 3) TypeScript Development Setup
67
+
68
+ This repo is written in **TypeScript 5.7** and compiles to CommonJS in the `dist/` directory. Source files are in `src/` and must be compiled before use.
69
+
70
+ ### Building and Type-Checking
71
+
72
+ ```bash
73
+ npm run build # Compile TypeScript to dist/
74
+ npm run type-check # Full-project type-check (informational while debt is tracked)
75
+ npm run type-check:full # Alias for full-project type-check
76
+ npm run type-check:changed # Changed-file gate used for PR blocking
77
+ ```
78
+
79
+ ### Key directories and files
80
+
81
+ - **`src/`** — TypeScript source files (utilities, CLI, test files)
82
+ - **`dist/`** — Compiled JavaScript output (generated by `npm run build`)
83
+ - **`tsconfig.json`** — TypeScript compiler configuration with strict mode enabled
84
+ - **`.eslintignore`** — ESLint excludes `dist/` (check compiled output separately if needed)
85
+
86
+ ### Development workflow
87
+
88
+ 1. Edit `.ts` files in `src/`
89
+ 2. Run `npm run type-check:changed` to verify changed-file type safety (PR gate)
90
+ 3. Optionally run `npm run type-check` (or `npm run type-check:full`) to view full-project debt status
91
+ 4. Run `npm run build` to compile (or let `npm test` do it as part of the pre-test check)
92
+ 5. Run focused unit tests while iterating (for example `npm run test:unit -- src/result-cache.test.ts` or `npm run test:unit -- -t "cache"`)
93
+ 6. Run `npm run test:ci` before submitting to execute full CI-style validation (build + type-check + Jest + bash integration tests)
94
+
95
+ ### Running a single test file
96
+
97
+ When you only need to run one unit test file, prefer the unit-test script (or direct Jest invocation) instead of `npm test`.
98
+
99
+ ```bash
100
+ npm run test:unit -- src/result-cache.test.ts
101
+ npx jest src/result-cache.test.ts
102
+ ```
103
+
104
+ Use `npm test` when you want the full validation pipeline (build + type-check + jest + integration scripts).
105
+
106
+ ```bash
107
+ npm test
108
+ ```
109
+
110
+ ### Type Safety Standards
111
+
112
+ - **Strict mode enabled** — All files compile with `"strict": true`
113
+ - **No implicit any** — Function parameters and return types must be explicit
114
+ - **ESM modules** — Source uses ES2024 syntax; CommonJS output for Node compatibility
115
+ - **Declaration files** — TypeScript generates `.d.ts` for CLI library exports
116
+
117
+ ## 4) Code Quality: Linting and Style
118
+
119
+ All TypeScript and shell scripts must pass linting before submission, and changed-file type-checking must pass before merge. Full-project type-checking remains informational while debt is burned down. This repo uses **ESLint** for TypeScript code and **ShellCheck** for shell scripts to enforce consistent code style and catch common errors.
120
+
121
+ ### Running linting locally
122
+
123
+ Before pushing, ensure your code passes all linting checks:
124
+
125
+ ```bash
126
+ npm install # Install dependencies (one-time)
127
+ npm run type-check:changed # Verify changed-file TypeScript types (PR gate)
128
+ npm run type-check # Optional: full-project debt snapshot (non-blocking)
129
+ npm run lint # Check all TS and shell scripts
130
+ npm run lint:fix # Auto-fix formatting and common issues
131
+ ```
132
+
133
+ Specific linting commands:
134
+
135
+ - `npm run lint:ts` — Check only TypeScript files
136
+ - `npm run lint:ts:fix` — Auto-fix TypeScript issues
137
+ - `npm run lint:sh` — Check only shell scripts
138
+
139
+ ### What gets linted
140
+
141
+ - **TypeScript files:** All `.ts` files in `src/`
142
+ - **Shell scripts:** `run-kaseki.sh`, `kaseki-agent.sh`, `cleanup-kaseki.sh`
143
+ - **Excluded:** `node_modules/`, `.git/`, `docker/`, `dist/` (compiled output), CI artifacts
144
+
145
+ ### Style expectations
146
+
147
+ See [STYLE.md](STYLE.md) for detailed code style guidelines. In summary:
148
+
149
+ - **Indentation:** 2 spaces (enforced)
150
+ - **Line endings:** Unix (LF) only
151
+ - **Quotes:** Single quotes, except where escaping is needed
152
+ - **Semicolons:** Required at end of statements
153
+ - **Console usage:** Allowed (not flagged as error; this is a CLI tool)
154
+ - **No trailing whitespace**
155
+ - **Types:** Always explicit in function signatures, no implicit `any`
156
+
157
+ ### PR checklist for code quality
158
+
159
+ Before opening a pull request:
160
+
161
+ - [ ] Run `npm run type-check:changed` locally and confirm 0 errors (PR gate).
162
+ - [ ] Optionally run `npm run type-check` (or `npm run type-check:full`) to assess tracked full-project TypeScript debt (non-blocking).
163
+ - [ ] Run `npm run lint` locally and confirm 0 errors.
164
+ - [ ] If linting issues were found, run `npm run lint:fix` and review the changes.
165
+ - [ ] Ensure no unintended auto-fixes were applied (review git diff).
166
+ - [ ] Run `npm run build` to verify compilation succeeds.
167
+ - [ ] If you disagree with a lint rule, discuss in the PR description.
168
+
169
+ ## 5) Running the local containerized flow
170
+
171
+ Use either the published image or a local build, then run `./run-kaseki.sh` from this repo root.
172
+
173
+ ### Option A: pull published image
174
+
175
+ ```bash
176
+ docker pull docker.io/cyanautomation/kaseki-agent:latest
177
+ OPENROUTER_API_KEY=<your_openrouter_api_key> ./run-kaseki.sh
178
+ ```
179
+
180
+ Use stable version tags such as `0.1.0` for reproducible runs. Reserve `latest`
181
+ for smoke testing a freshly published image before a stable release tag is cut.
182
+
183
+ ### Option B: build locally, then run
184
+
185
+ ```bash
186
+ docker build -t kaseki-template:latest .
187
+ KASEKI_IMAGE=kaseki-template:latest OPENROUTER_API_KEY=<your_openrouter_api_key> ./run-kaseki.sh
188
+ ```
189
+
190
+ Optional: pass a specific instance name (for example `kaseki-7`) as the first arg.
191
+
192
+ ## 6) Release Process and Conventional Commits
193
+
194
+ Kaseki Agent releases are **automated via semantic-release**. Version bumps, changelog updates, and GitHub Releases are generated automatically from commit messages using the **conventional commits** format.
195
+
196
+ ### Conventional Commit Format
197
+
198
+ All commits should follow the format:
199
+
200
+ ```
201
+ type(scope): description
202
+
203
+ [optional body]
204
+
205
+ [optional footer]
206
+ ```
207
+
208
+ **Types that trigger version bumps:**
209
+
210
+ - `feat:` — New feature (bumps **minor** version: 0.1.0 → 0.2.0)
211
+ - `fix:` — Bug fix (bumps **patch** version: 0.1.0 → 0.1.1)
212
+ - `perf:` — Performance improvement (bumps **patch** version)
213
+ - `revert:` — Revert a previous commit (bumps **patch** version)
214
+
215
+ **Types that do NOT trigger version bumps** (included in CHANGELOG as documentation only):
216
+
217
+ - `docs:` — Documentation changes
218
+ - `style:` — Code style/formatting (no logic changes)
219
+ - `refactor:` — Code refactoring (no behavior changes)
220
+ - `test:` — Test additions/updates
221
+ - `chore:` — Dependency updates, build config, etc.
222
+
223
+ **Examples:**
224
+
225
+ ```
226
+ feat(api): add retry logic to GitHub App token exchange
227
+
228
+ Implements exponential backoff for transient network failures.
229
+
230
+ Fixes #123
231
+ ```
232
+
233
+ ```
234
+ fix(docker): resolve cache miss in npm ci layer
235
+
236
+ The workspace cache key was missing lock hash; rebuilt as sha256($lock).
237
+ ```
238
+
239
+ ```
240
+ chore(deps): upgrade semantic-release to v24
241
+ ```
242
+
243
+ ### Making a Release
244
+
245
+ **Workflow Options:**
246
+
247
+ You can create a release in two ways:
248
+
249
+ **Option A: Via GitHub Actions (Recommended)**
250
+
251
+ 1. Go to the repository's [Actions](https://github.com/CyanAutomation/kaseki-agent/actions) tab
252
+ 2. Select the **Release** workflow from the left sidebar
253
+ 3. Click **Run workflow** and choose your options:
254
+ - **Dry-run (optional)**: Check to preview the release without creating tags/releases
255
+ - Click **Run workflow**
256
+ 4. The workflow will:
257
+ - Analyze commits since last release
258
+ - Automatically determine version (major/minor/patch)
259
+ - Update CHANGELOG.md, package.json, and create GitHub Release
260
+ - Automatically trigger Docker multi-arch build and publish images
261
+ 5. Monitor the workflow progress in the Actions tab
262
+ 6. Verify the release in the [Releases](https://github.com/CyanAutomation/kaseki-agent/releases) tab
263
+
264
+ **Option B: Via Local Command (Advanced)**
265
+
266
+ 1. Ensure your local git is clean: `git status`
267
+ 2. **Test locally (recommended):**
268
+
269
+ ```bash
270
+ npm run release:dry
271
+ ```
272
+
273
+ 3. **Create release:**
274
+
275
+ ```bash
276
+ npm run release
277
+ ```
278
+
279
+ 4. This requires:
280
+ - Write access to the repository
281
+ - Valid `GITHUB_TOKEN` in environment (or git credentials)
282
+ - Ability to push tags to GitHub
283
+ 5. The command will automatically trigger the Docker build workflow on GitHub
284
+
285
+ Both options use **semantic-release** to automate all versioning and changelog tasks. The GitHub Actions workflow is recommended for team releases to ensure consistency and visibility.
286
+
287
+ ### Commit Message Best Practices
288
+
289
+ - **Be descriptive:** Include *why* the change was made, not just *what* changed
290
+ - **Use body for details:** If the title is short, explain the impact in the commit body
291
+ - **Reference issues:** Link to related issues with `Fixes #123` or `Relates to #456`
292
+ - **One logical change per commit:** Avoid mixing features with refactoring in a single commit
293
+ - **Squash before merge:** Use PR squash-and-rebase to clean up history if needed, then ensure the final squashed message follows conventional format
294
+
295
+ ### Non-Conventional Commits
296
+
297
+ If a commit message doesn't follow the format, it will **not trigger a version bump** but will still be included in the CHANGELOG. This allows for organic adoption—your PR reviewers can suggest better commit messages without blocking merges.
298
+
299
+ Once you're comfortable with the format, encourage your team to adopt it systematically (optional: use `commitlint` + `husky` hooks for enforcement in future phases).
300
+
301
+ ## 7) Validating changed-file allowlist and max diff limits
302
+
303
+ The container runner enforces quality gates using:
304
+
305
+ - `KASEKI_CHANGED_FILES_ALLOWLIST`
306
+ - `KASEKI_MAX_DIFF_BYTES`
307
+
308
+ Contributors must validate that any change to defaults or behavior preserves these constraints:
309
+
310
+ - Changed files remain within the configured allowlist for the intended task.
311
+ - `git.diff` size remains under the configured max diff bytes.
312
+ - If you intentionally broaden scope, update defaults/documentation and clearly explain operator impact.
313
+
314
+ A failed allowlist or diff-size check should be treated as a real regression unless intentionally changed and documented.
315
+
316
+ ## 8) Diagnosing failures with `/agents/kaseki-results/kaseki-N`
317
+
318
+ When a run fails, inspect artifacts in this order:
319
+
320
+ 1. `kaseki-report /agents/kaseki-results/kaseki-N` for a compact status, failed command, exit-code, model, timing, changed-file, and next-diagnostic summary.
321
+ 2. `result-summary.md` for top-level status, failed command, and changed files.
322
+ 3. `metadata.json` for exit codes (`pi`, validation, quality, secret scan), model details, and timing.
323
+ 4. `stdout.log` / `stderr.log` for execution flow and shell-level failures.
324
+ 5. `pi-summary.json` and `pi-events.jsonl` for agent/model behavior.
325
+ 6. `validation.log` and `validation-timings.tsv` for command failures and duration outliers.
326
+ 7. `quality.log`, `changed-files.txt`, and `git.diff` for allowlist/diff-limit failures.
327
+ 8. `secret-scan.log` for credential-detection issues.
328
+ 9. `host-start.json`, `host_docker_exit_code`, and `resource.time` for host/container startup context.
329
+
330
+ Tip: If quality or validation failures are ambiguous, compare `git.status` + `git.diff` with `TASK_PROMPT` constraints first.
331
+
332
+ ## PR checklist
333
+
334
+ Before opening/merging, include:
335
+
336
+ - [ ] Prompt rationale for any `TASK_PROMPT` default or guardrail change.
337
+ - [ ] Test evidence (commands + output summary), including focused Vitest updates when behavior changed.
338
+ - [ ] Confirmation that changed-file allowlist and max diff checks still pass (or documented rationale for updates).
339
+ - [ ] Any operator-impacting env var, default, or runbook/documentation updates.
package/Dockerfile ADDED
@@ -0,0 +1,217 @@
1
+ # Bump the pinned Node base image monthly with a security review.
2
+ # Node v24 base image: Updated May 2026 for improved performance and security.
3
+ # Using ARG for DRY principle - base image used in both stages
4
+ ARG NODE_IMAGE=node:24-bookworm-slim
5
+
6
+ FROM ${NODE_IMAGE} AS deps
7
+
8
+ # Phase 1: System dependencies + user setup (consolidated)
9
+ RUN apt-get update \
10
+ && apt-get install -y --no-install-recommends bash ca-certificates git procps \
11
+ && rm -rf /var/lib/apt/lists/* \
12
+ && groupadd --system --gid 10001 kaseki \
13
+ && useradd --system --uid 10001 --gid kaseki --create-home --home-dir /home/kaseki --shell /usr/sbin/nologin kaseki \
14
+ && mkdir -p /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent \
15
+ && chown -R kaseki:kaseki /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent
16
+
17
+ ENV HOME=/tmp/kaseki-home \
18
+ NPM_CONFIG_CACHE=/tmp/npm-cache \
19
+ npm_config_cache=/tmp/npm-cache \
20
+ PI_CODING_AGENT_DIR=/tmp/pi-agent \
21
+ PI_TELEMETRY=0 \
22
+ PI_SKIP_VERSION_CHECK=1 \
23
+ CI=true
24
+
25
+ # Phase 2: Workspace cache seed for Layer 3 runtime fallback
26
+ WORKDIR /opt/kaseki/workspace-cache-seed
27
+ COPY docker/workspace-cache/package.json docker/workspace-cache/package-lock.json ./
28
+ RUN npm ci --no-audit --prefer-offline --ignore-scripts \
29
+ && mkdir -p node_modules
30
+
31
+ # Phase 3: Global Pi CLI installation (Layer 3 fallback for image seed cache)
32
+ RUN npm install -g --no-audit @earendil-works/pi-coding-agent@0.74.0
33
+
34
+
35
+ FROM ${NODE_IMAGE} AS runtime
36
+
37
+ # System dependencies + user setup (consolidated)
38
+ RUN apt-get update \
39
+ && apt-get install -y --no-install-recommends bash ca-certificates curl docker.io git procps \
40
+ && rm -rf /var/lib/apt/lists/* \
41
+ && groupadd --system --gid 10001 kaseki \
42
+ && useradd --system --uid 10001 --gid kaseki --create-home --home-dir /home/kaseki --shell /usr/sbin/nologin kaseki \
43
+ && mkdir -p /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent /opt/kaseki/workspace-cache/default \
44
+ && chown -R kaseki:kaseki /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent /opt/kaseki
45
+
46
+ ENV HOME=/tmp/kaseki-home \
47
+ NPM_CONFIG_CACHE=/tmp/npm-cache \
48
+ npm_config_cache=/tmp/npm-cache \
49
+ PI_CODING_AGENT_DIR=/tmp/pi-agent \
50
+ PI_TELEMETRY=0 \
51
+ PI_SKIP_VERSION_CHECK=1 \
52
+ CI=true
53
+
54
+ # Copy Pi CLI and workspace cache seed from deps stage
55
+ COPY --from=deps /usr/local/lib/node_modules /usr/local/lib/node_modules
56
+ RUN ln -sf ../lib/node_modules/@earendil-works/pi-coding-agent/dist/cli.js /usr/local/bin/pi
57
+ COPY --from=deps /opt/kaseki/workspace-cache-seed/node_modules /opt/kaseki/workspace-cache/default/node_modules
58
+
59
+ # Build kaseki application (cache-optimal: dependencies first, then source code)
60
+ WORKDIR /app
61
+ COPY package.json package-lock.json tsconfig.json ./
62
+ COPY src ./src
63
+ RUN npm ci --no-audit --prefer-offline --ignore-scripts && npm run build
64
+ RUN test -f /app/dist/kaseki-api-service.js
65
+
66
+ # Copy all application files (after build, so layer invalidation is minimal)
67
+ COPY Dockerfile .dockerignore README.md CLAUDE.md CONTRIBUTING.md STYLE.md ./
68
+ COPY kaseki run-kaseki.sh kaseki-agent.sh ./
69
+ COPY docs ./docs
70
+ COPY ops ./ops
71
+ COPY scripts ./scripts
72
+ COPY docker ./docker
73
+ COPY test ./test
74
+
75
+ # Copy entrypoints to /usr/local/bin
76
+ COPY kaseki-agent.sh /usr/local/bin/kaseki-agent
77
+ COPY scripts/docker-entrypoint.sh /usr/local/bin/kaseki-entrypoint
78
+
79
+ # Setup and install binaries (consolidated: container scripts, lib copies, permissions, and global installs)
80
+ RUN chmod +x \
81
+ /app/scripts/kaseki-container-setup.sh \
82
+ /app/scripts/kaseki-container-setup-remote.sh \
83
+ /app/scripts/kaseki-container-entrypoint-wrapper.sh \
84
+ /app/kaseki /app/run-kaseki.sh /app/kaseki-agent.sh \
85
+ && mkdir -p /scripts \
86
+ && ln -sf /app/scripts/kaseki-container-setup.sh /scripts/kaseki-container-setup.sh \
87
+ && ln -sf /app/scripts/kaseki-container-setup-remote.sh /scripts/kaseki-container-setup-remote.sh \
88
+ && ln -sf /app/scripts/kaseki-container-entrypoint-wrapper.sh /scripts/kaseki-container-entrypoint-wrapper.sh \
89
+ && mkdir -p /app/lib \
90
+ && cp dist/pi-event-filter.js /app/lib/pi-event-filter.js \
91
+ && cp dist/event-aggregator.js /app/lib/event-aggregator.js \
92
+ && cp dist/timestamp-tracker.js /app/lib/timestamp-tracker.js \
93
+ && cp dist/pi-progress-stream.js /app/lib/pi-progress-stream.js \
94
+ && cp dist/progress-stream-utils.js /app/lib/progress-stream-utils.js \
95
+ && cp dist/kaseki-report.js /app/lib/kaseki-report.js \
96
+ && cp dist/instance-state-derivation.js /app/lib/instance-state-derivation.js \
97
+ && cp dist/instance-metadata-reader.js /app/lib/instance-metadata-reader.js \
98
+ && cp dist/kaseki-cli.js /app/kaseki-cli.js \
99
+ && cp dist/kaseki-cli-lib.js /app/kaseki-cli-lib.js \
100
+ && cp dist/github-app-token.js /app/lib/github-app-token.js \
101
+ && chmod 0755 /app/dist/*.js \
102
+ && install -m 0755 /app/lib/pi-event-filter.js /usr/local/bin/kaseki-pi-event-filter \
103
+ && install -m 0755 /app/lib/pi-progress-stream.js /usr/local/bin/kaseki-pi-progress-stream \
104
+ && install -m 0755 /app/lib/event-aggregator.js /usr/local/bin/event-aggregator.js \
105
+ && install -m 0755 /app/lib/timestamp-tracker.js /usr/local/bin/timestamp-tracker.js \
106
+ && install -m 0755 /app/lib/progress-stream-utils.js /usr/local/bin/progress-stream-utils.js \
107
+ && install -m 0755 /app/lib/instance-state-derivation.js /usr/local/bin/instance-state-derivation.js \
108
+ && install -m 0755 /app/lib/instance-metadata-reader.js /usr/local/bin/instance-metadata-reader.js \
109
+ && install -m 0755 /app/lib/kaseki-report.js /usr/local/bin/kaseki-report \
110
+ && install -m 0755 /app/lib/github-app-token.js /usr/local/bin/github-app-token \
111
+ && ln -sf github-app-token /usr/local/bin/github-app-token.js \
112
+ && chmod 0755 \
113
+ /usr/local/bin/kaseki-entrypoint \
114
+ /usr/local/bin/kaseki-pi-event-filter \
115
+ /usr/local/bin/kaseki-pi-progress-stream \
116
+ /usr/local/bin/kaseki-report \
117
+ /usr/local/bin/github-app-token \
118
+ /usr/local/bin/github-app-token.js \
119
+ /usr/local/lib/node_modules/@earendil-works/pi-coding-agent/dist/cli.js \
120
+ /app/scripts/*.sh
121
+
122
+ WORKDIR /workspace
123
+ USER kaseki
124
+ ENTRYPOINT ["/usr/local/bin/kaseki-entrypoint"]
125
+ CMD ["agent"]
126
+
127
+ # The runner initializes these logs before long-running work starts.
128
+ HEALTHCHECK --interval=30s --timeout=5s --start-period=10s --retries=3 \
129
+ CMD test -f /results/stdout.log && test -f /results/stderr.log
130
+
131
+
132
+ # ===== FINAL STAGE: Artifact-Stripped Production Image =====
133
+ # This stage removes build-time artifacts (test/, docs/, src/) and devDependencies,
134
+ # reducing image size by ~80-150 MB while preserving all runtime functionality.
135
+ # Trade-off: Cannot rebuild code in container (not needed—build happens in CI before image creation).
136
+ #
137
+ # Impact:
138
+ # - Size: 15–25% reduction (80 MB prune + 50 MB docs/test/src)
139
+ # - Build time: negligible (final stage only copies needed files)
140
+ # - Runtime: unaffected (all runtime binaries, scripts, and dependencies included)
141
+ #
142
+ FROM ${NODE_IMAGE} AS final
143
+
144
+ # Minimal setup: only runtime requirements (no build tools or package managers beyond npm for app startup check)
145
+ RUN apt-get update \
146
+ && apt-get install -y --no-install-recommends bash ca-certificates curl docker.io git procps \
147
+ && rm -rf /var/lib/apt/lists/* \
148
+ && groupadd --system --gid 10001 kaseki \
149
+ && useradd --system --uid 10001 --gid kaseki --create-home --home-dir /home/kaseki --shell /usr/sbin/nologin kaseki \
150
+ && mkdir -p /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent /opt/kaseki/workspace-cache/default \
151
+ && chown -R kaseki:kaseki /workspace /results /tmp/kaseki-home /tmp/npm-cache /tmp/pi-agent /opt/kaseki
152
+
153
+ ENV HOME=/tmp/kaseki-home \
154
+ NPM_CONFIG_CACHE=/tmp/npm-cache \
155
+ npm_config_cache=/tmp/npm-cache \
156
+ PI_CODING_AGENT_DIR=/tmp/pi-agent \
157
+ PI_TELEMETRY=0 \
158
+ PI_SKIP_VERSION_CHECK=1 \
159
+ CI=true
160
+
161
+ # Copy runtime essentials from runtime stage (skip test/, docs/, src/)
162
+ COPY --from=runtime /usr/local/lib/node_modules /usr/local/lib/node_modules
163
+ COPY --from=runtime /usr/local/bin/pi /usr/local/bin/pi
164
+ COPY --from=runtime /opt/kaseki/workspace-cache/default/node_modules /opt/kaseki/workspace-cache/default/node_modules
165
+
166
+ # Copy application files (excluding build artifacts)
167
+ WORKDIR /app
168
+ COPY --from=runtime /app/package.json /app/package-lock.json /app/
169
+ COPY --from=runtime /app/Dockerfile /app/.dockerignore /app/README.md /app/CLAUDE.md /app/CONTRIBUTING.md /app/STYLE.md ./
170
+ COPY --from=runtime /app/kaseki /app/run-kaseki.sh /app/kaseki-agent.sh ./
171
+ COPY --from=runtime /app/ops ./ops
172
+ COPY --from=runtime /app/scripts ./scripts
173
+ COPY --from=runtime /app/docker ./docker
174
+ COPY --from=runtime /app/dist ./dist
175
+ COPY --from=runtime /app/lib ./lib
176
+ COPY --from=runtime /app/node_modules ./node_modules
177
+
178
+ # Copy only production dependencies (remove devDependencies)
179
+ # Note: This only affects kaseki-agent's own dependencies; Pi CLI and workspace cache remain untouched.
180
+ RUN npm prune --production
181
+
182
+ # Install global binaries and set up scripts (from runtime stage)
183
+ RUN mkdir -p /scripts \
184
+ && ln -sf /app/scripts/kaseki-container-setup.sh /scripts/kaseki-container-setup.sh \
185
+ && ln -sf /app/scripts/kaseki-container-setup-remote.sh /scripts/kaseki-container-setup-remote.sh \
186
+ && ln -sf /app/scripts/kaseki-container-entrypoint-wrapper.sh /scripts/kaseki-container-entrypoint-wrapper.sh \
187
+ && install -m 0755 /app/lib/pi-event-filter.js /usr/local/bin/kaseki-pi-event-filter \
188
+ && install -m 0755 /app/lib/pi-progress-stream.js /usr/local/bin/kaseki-pi-progress-stream \
189
+ && install -m 0755 /app/lib/event-aggregator.js /usr/local/bin/event-aggregator.js \
190
+ && install -m 0755 /app/lib/timestamp-tracker.js /usr/local/bin/timestamp-tracker.js \
191
+ && install -m 0755 /app/lib/progress-stream-utils.js /usr/local/bin/progress-stream-utils.js \
192
+ && install -m 0755 /app/lib/instance-state-derivation.js /usr/local/bin/instance-state-derivation.js \
193
+ && install -m 0755 /app/lib/instance-metadata-reader.js /usr/local/bin/instance-metadata-reader.js \
194
+ && install -m 0755 /app/lib/kaseki-report.js /usr/local/bin/kaseki-report \
195
+ && install -m 0755 /app/lib/github-app-token.js /usr/local/bin/github-app-token \
196
+ && ln -sf github-app-token /usr/local/bin/github-app-token.js \
197
+ && install -m 0755 /app/kaseki-agent.sh /usr/local/bin/kaseki-agent \
198
+ && install -m 0755 /app/scripts/docker-entrypoint.sh /usr/local/bin/kaseki-entrypoint \
199
+ && chmod 0755 \
200
+ /usr/local/bin/kaseki-entrypoint \
201
+ /usr/local/bin/kaseki-pi-event-filter \
202
+ /usr/local/bin/kaseki-pi-progress-stream \
203
+ /usr/local/bin/kaseki-report \
204
+ /usr/local/bin/github-app-token \
205
+ /usr/local/bin/github-app-token.js \
206
+ /usr/local/lib/node_modules/@earendil-works/pi-coding-agent/dist/cli.js \
207
+ /app/kaseki /app/run-kaseki.sh /app/kaseki-agent.sh \
208
+ /app/scripts/*.sh
209
+
210
+ WORKDIR /workspace
211
+ USER kaseki
212
+ ENTRYPOINT ["/usr/local/bin/kaseki-entrypoint"]
213
+ CMD ["agent"]
214
+
215
+ # The runner initializes these logs before long-running work starts.
216
+ HEALTHCHECK --interval=30s --timeout=5s --start-period=10s --retries=3 \
217
+ CMD test -f /results/stdout.log && test -f /results/stderr.log