iec-cli 0.6.6

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 (443) hide show
  1. package/README.md +159 -0
  2. package/dist/commands/backup.d.ts +11 -0
  3. package/dist/commands/backup.d.ts.map +1 -0
  4. package/dist/commands/backup.js +112 -0
  5. package/dist/commands/backup.js.map +1 -0
  6. package/dist/commands/config.d.ts +28 -0
  7. package/dist/commands/config.d.ts.map +1 -0
  8. package/dist/commands/config.js +190 -0
  9. package/dist/commands/config.js.map +1 -0
  10. package/dist/commands/deploy.d.ts +16 -0
  11. package/dist/commands/deploy.d.ts.map +1 -0
  12. package/dist/commands/deploy.js +235 -0
  13. package/dist/commands/deploy.js.map +1 -0
  14. package/dist/commands/destroy.d.ts +12 -0
  15. package/dist/commands/destroy.d.ts.map +1 -0
  16. package/dist/commands/destroy.js +62 -0
  17. package/dist/commands/destroy.js.map +1 -0
  18. package/dist/commands/domains.d.ts +36 -0
  19. package/dist/commands/domains.d.ts.map +1 -0
  20. package/dist/commands/domains.js +323 -0
  21. package/dist/commands/domains.js.map +1 -0
  22. package/dist/commands/env.d.ts +7 -0
  23. package/dist/commands/env.d.ts.map +1 -0
  24. package/dist/commands/env.js +42 -0
  25. package/dist/commands/env.js.map +1 -0
  26. package/dist/commands/git.d.ts +32 -0
  27. package/dist/commands/git.d.ts.map +1 -0
  28. package/dist/commands/git.js +340 -0
  29. package/dist/commands/git.js.map +1 -0
  30. package/dist/commands/init-ai.d.ts +7 -0
  31. package/dist/commands/init-ai.d.ts.map +1 -0
  32. package/dist/commands/init-ai.js +257 -0
  33. package/dist/commands/init-ai.js.map +1 -0
  34. package/dist/commands/init.d.ts +8 -0
  35. package/dist/commands/init.d.ts.map +1 -0
  36. package/dist/commands/init.js +228 -0
  37. package/dist/commands/init.js.map +1 -0
  38. package/dist/commands/link.d.ts +10 -0
  39. package/dist/commands/link.d.ts.map +1 -0
  40. package/dist/commands/link.js +193 -0
  41. package/dist/commands/link.js.map +1 -0
  42. package/dist/commands/login.d.ts +16 -0
  43. package/dist/commands/login.d.ts.map +1 -0
  44. package/dist/commands/login.js +468 -0
  45. package/dist/commands/login.js.map +1 -0
  46. package/dist/commands/logs.d.ts +16 -0
  47. package/dist/commands/logs.d.ts.map +1 -0
  48. package/dist/commands/logs.js +362 -0
  49. package/dist/commands/logs.js.map +1 -0
  50. package/dist/commands/oauth.d.ts +33 -0
  51. package/dist/commands/oauth.d.ts.map +1 -0
  52. package/dist/commands/oauth.js +181 -0
  53. package/dist/commands/oauth.js.map +1 -0
  54. package/dist/commands/preflight.d.ts +8 -0
  55. package/dist/commands/preflight.d.ts.map +1 -0
  56. package/dist/commands/preflight.js +190 -0
  57. package/dist/commands/preflight.js.map +1 -0
  58. package/dist/commands/program.d.ts +7 -0
  59. package/dist/commands/program.d.ts.map +1 -0
  60. package/dist/commands/program.js +59 -0
  61. package/dist/commands/program.js.map +1 -0
  62. package/dist/commands/programs.d.ts +7 -0
  63. package/dist/commands/programs.d.ts.map +1 -0
  64. package/dist/commands/programs.js +42 -0
  65. package/dist/commands/programs.js.map +1 -0
  66. package/dist/commands/push.d.ts +12 -0
  67. package/dist/commands/push.d.ts.map +1 -0
  68. package/dist/commands/push.js +166 -0
  69. package/dist/commands/push.js.map +1 -0
  70. package/dist/commands/register-scaffold.test.d.ts +2 -0
  71. package/dist/commands/register-scaffold.test.d.ts.map +1 -0
  72. package/dist/commands/register-scaffold.test.js +291 -0
  73. package/dist/commands/register-scaffold.test.js.map +1 -0
  74. package/dist/commands/register.d.ts +7 -0
  75. package/dist/commands/register.d.ts.map +1 -0
  76. package/dist/commands/register.js +304 -0
  77. package/dist/commands/register.js.map +1 -0
  78. package/dist/commands/rollback.d.ts +11 -0
  79. package/dist/commands/rollback.d.ts.map +1 -0
  80. package/dist/commands/rollback.js +147 -0
  81. package/dist/commands/rollback.js.map +1 -0
  82. package/dist/commands/sample.d.ts +15 -0
  83. package/dist/commands/sample.d.ts.map +1 -0
  84. package/dist/commands/sample.js +312 -0
  85. package/dist/commands/sample.js.map +1 -0
  86. package/dist/commands/scopes.d.ts +29 -0
  87. package/dist/commands/scopes.d.ts.map +1 -0
  88. package/dist/commands/scopes.js +203 -0
  89. package/dist/commands/scopes.js.map +1 -0
  90. package/dist/commands/services.d.ts +13 -0
  91. package/dist/commands/services.d.ts.map +1 -0
  92. package/dist/commands/services.js +95 -0
  93. package/dist/commands/services.js.map +1 -0
  94. package/dist/commands/settings.d.ts +10 -0
  95. package/dist/commands/settings.d.ts.map +1 -0
  96. package/dist/commands/settings.js +41 -0
  97. package/dist/commands/settings.js.map +1 -0
  98. package/dist/commands/signup.d.ts +9 -0
  99. package/dist/commands/signup.d.ts.map +1 -0
  100. package/dist/commands/signup.js +192 -0
  101. package/dist/commands/signup.js.map +1 -0
  102. package/dist/commands/status.d.ts +9 -0
  103. package/dist/commands/status.d.ts.map +1 -0
  104. package/dist/commands/status.js +170 -0
  105. package/dist/commands/status.js.map +1 -0
  106. package/dist/commands/troubleshoot.d.ts +19 -0
  107. package/dist/commands/troubleshoot.d.ts.map +1 -0
  108. package/dist/commands/troubleshoot.js +465 -0
  109. package/dist/commands/troubleshoot.js.map +1 -0
  110. package/dist/commands/update.d.ts +6 -0
  111. package/dist/commands/update.d.ts.map +1 -0
  112. package/dist/commands/update.js +64 -0
  113. package/dist/commands/update.js.map +1 -0
  114. package/dist/commands/user.d.ts +17 -0
  115. package/dist/commands/user.d.ts.map +1 -0
  116. package/dist/commands/user.js +126 -0
  117. package/dist/commands/user.js.map +1 -0
  118. package/dist/commands/versions.d.ts +16 -0
  119. package/dist/commands/versions.d.ts.map +1 -0
  120. package/dist/commands/versions.js +116 -0
  121. package/dist/commands/versions.js.map +1 -0
  122. package/dist/index.d.ts +3 -0
  123. package/dist/index.d.ts.map +1 -0
  124. package/dist/index.js +556 -0
  125. package/dist/index.js.map +1 -0
  126. package/dist/lib/__tests__/scaffold-integration.test.d.ts +2 -0
  127. package/dist/lib/__tests__/scaffold-integration.test.d.ts.map +1 -0
  128. package/dist/lib/__tests__/scaffold-integration.test.js +321 -0
  129. package/dist/lib/__tests__/scaffold-integration.test.js.map +1 -0
  130. package/dist/lib/ai/client.d.ts +39 -0
  131. package/dist/lib/ai/client.d.ts.map +1 -0
  132. package/dist/lib/ai/client.js +236 -0
  133. package/dist/lib/ai/client.js.map +1 -0
  134. package/dist/lib/ai/generator.d.ts +17 -0
  135. package/dist/lib/ai/generator.d.ts.map +1 -0
  136. package/dist/lib/ai/generator.js +338 -0
  137. package/dist/lib/ai/generator.js.map +1 -0
  138. package/dist/lib/ai/prompts.d.ts +47 -0
  139. package/dist/lib/ai/prompts.d.ts.map +1 -0
  140. package/dist/lib/ai/prompts.js +247 -0
  141. package/dist/lib/ai/prompts.js.map +1 -0
  142. package/dist/lib/ai/scanner.d.ts +50 -0
  143. package/dist/lib/ai/scanner.d.ts.map +1 -0
  144. package/dist/lib/ai/scanner.js +237 -0
  145. package/dist/lib/ai/scanner.js.map +1 -0
  146. package/dist/lib/api.d.ts +18 -0
  147. package/dist/lib/api.d.ts.map +1 -0
  148. package/dist/lib/api.js +67 -0
  149. package/dist/lib/api.js.map +1 -0
  150. package/dist/lib/auto-register.d.ts +12 -0
  151. package/dist/lib/auto-register.d.ts.map +1 -0
  152. package/dist/lib/auto-register.js +42 -0
  153. package/dist/lib/auto-register.js.map +1 -0
  154. package/dist/lib/bio.d.ts +90 -0
  155. package/dist/lib/bio.d.ts.map +1 -0
  156. package/dist/lib/bio.js +247 -0
  157. package/dist/lib/bio.js.map +1 -0
  158. package/dist/lib/builder.d.ts +65 -0
  159. package/dist/lib/builder.d.ts.map +1 -0
  160. package/dist/lib/builder.js +192 -0
  161. package/dist/lib/builder.js.map +1 -0
  162. package/dist/lib/catalog.d.ts +3 -0
  163. package/dist/lib/catalog.d.ts.map +1 -0
  164. package/dist/lib/catalog.js +17 -0
  165. package/dist/lib/catalog.js.map +1 -0
  166. package/dist/lib/config.d.ts +20 -0
  167. package/dist/lib/config.d.ts.map +1 -0
  168. package/dist/lib/config.js +124 -0
  169. package/dist/lib/config.js.map +1 -0
  170. package/dist/lib/forgejo.d.ts +188 -0
  171. package/dist/lib/forgejo.d.ts.map +1 -0
  172. package/dist/lib/forgejo.js +305 -0
  173. package/dist/lib/forgejo.js.map +1 -0
  174. package/dist/lib/output.d.ts +12 -0
  175. package/dist/lib/output.d.ts.map +1 -0
  176. package/dist/lib/output.js +39 -0
  177. package/dist/lib/output.js.map +1 -0
  178. package/dist/lib/scaffold.d.ts +30 -0
  179. package/dist/lib/scaffold.d.ts.map +1 -0
  180. package/dist/lib/scaffold.js +180 -0
  181. package/dist/lib/scaffold.js.map +1 -0
  182. package/dist/lib/scope-requests.d.ts +17 -0
  183. package/dist/lib/scope-requests.d.ts.map +1 -0
  184. package/dist/lib/scope-requests.js +78 -0
  185. package/dist/lib/scope-requests.js.map +1 -0
  186. package/dist/lib/scope-requests.test.d.ts +2 -0
  187. package/dist/lib/scope-requests.test.d.ts.map +1 -0
  188. package/dist/lib/scope-requests.test.js +239 -0
  189. package/dist/lib/scope-requests.test.js.map +1 -0
  190. package/dist/lib/troubleshoot/analyzer.d.ts +14 -0
  191. package/dist/lib/troubleshoot/analyzer.d.ts.map +1 -0
  192. package/dist/lib/troubleshoot/analyzer.js +541 -0
  193. package/dist/lib/troubleshoot/analyzer.js.map +1 -0
  194. package/dist/lib/troubleshoot/auto-fix.d.ts +29 -0
  195. package/dist/lib/troubleshoot/auto-fix.d.ts.map +1 -0
  196. package/dist/lib/troubleshoot/auto-fix.js +373 -0
  197. package/dist/lib/troubleshoot/auto-fix.js.map +1 -0
  198. package/dist/lib/troubleshoot/index.d.ts +5 -0
  199. package/dist/lib/troubleshoot/index.d.ts.map +1 -0
  200. package/dist/lib/troubleshoot/index.js +6 -0
  201. package/dist/lib/troubleshoot/index.js.map +1 -0
  202. package/dist/lib/troubleshoot/log-fetcher.d.ts +43 -0
  203. package/dist/lib/troubleshoot/log-fetcher.d.ts.map +1 -0
  204. package/dist/lib/troubleshoot/log-fetcher.js +431 -0
  205. package/dist/lib/troubleshoot/log-fetcher.js.map +1 -0
  206. package/dist/lib/troubleshoot/redactor.d.ts +35 -0
  207. package/dist/lib/troubleshoot/redactor.d.ts.map +1 -0
  208. package/dist/lib/troubleshoot/redactor.js +208 -0
  209. package/dist/lib/troubleshoot/redactor.js.map +1 -0
  210. package/dist/lib/validators/catalog-schemas.d.ts +59 -0
  211. package/dist/lib/validators/catalog-schemas.d.ts.map +1 -0
  212. package/dist/lib/validators/catalog-schemas.js +32 -0
  213. package/dist/lib/validators/catalog-schemas.js.map +1 -0
  214. package/dist/lib/validators/catalog-validator.d.ts +3 -0
  215. package/dist/lib/validators/catalog-validator.d.ts.map +1 -0
  216. package/dist/lib/validators/catalog-validator.js +247 -0
  217. package/dist/lib/validators/catalog-validator.js.map +1 -0
  218. package/dist/lib/validators/catalog-validator.test.d.ts +2 -0
  219. package/dist/lib/validators/catalog-validator.test.d.ts.map +1 -0
  220. package/dist/lib/validators/catalog-validator.test.js +420 -0
  221. package/dist/lib/validators/catalog-validator.test.js.map +1 -0
  222. package/dist/lib/validators/dockerfile-validator.d.ts +5 -0
  223. package/dist/lib/validators/dockerfile-validator.d.ts.map +1 -0
  224. package/dist/lib/validators/dockerfile-validator.js +295 -0
  225. package/dist/lib/validators/dockerfile-validator.js.map +1 -0
  226. package/dist/lib/validators/dockerfile-validator.test.d.ts +2 -0
  227. package/dist/lib/validators/dockerfile-validator.test.d.ts.map +1 -0
  228. package/dist/lib/validators/dockerfile-validator.test.js +161 -0
  229. package/dist/lib/validators/dockerfile-validator.test.js.map +1 -0
  230. package/dist/lib/validators/env-validator.d.ts +3 -0
  231. package/dist/lib/validators/env-validator.d.ts.map +1 -0
  232. package/dist/lib/validators/env-validator.js +268 -0
  233. package/dist/lib/validators/env-validator.js.map +1 -0
  234. package/dist/lib/validators/git-validator.d.ts +3 -0
  235. package/dist/lib/validators/git-validator.d.ts.map +1 -0
  236. package/dist/lib/validators/git-validator.js +236 -0
  237. package/dist/lib/validators/git-validator.js.map +1 -0
  238. package/dist/lib/validators/health-detector.d.ts +4 -0
  239. package/dist/lib/validators/health-detector.d.ts.map +1 -0
  240. package/dist/lib/validators/health-detector.js +172 -0
  241. package/dist/lib/validators/health-detector.js.map +1 -0
  242. package/dist/lib/validators/health-detector.test.d.ts +2 -0
  243. package/dist/lib/validators/health-detector.test.d.ts.map +1 -0
  244. package/dist/lib/validators/health-detector.test.js +118 -0
  245. package/dist/lib/validators/health-detector.test.js.map +1 -0
  246. package/dist/lib/validators/index.d.ts +8 -0
  247. package/dist/lib/validators/index.d.ts.map +1 -0
  248. package/dist/lib/validators/index.js +8 -0
  249. package/dist/lib/validators/index.js.map +1 -0
  250. package/dist/lib/validators/route-validator.d.ts +3 -0
  251. package/dist/lib/validators/route-validator.d.ts.map +1 -0
  252. package/dist/lib/validators/route-validator.js +238 -0
  253. package/dist/lib/validators/route-validator.js.map +1 -0
  254. package/dist/lib/validators/scope-validator.d.ts +3 -0
  255. package/dist/lib/validators/scope-validator.d.ts.map +1 -0
  256. package/dist/lib/validators/scope-validator.js +141 -0
  257. package/dist/lib/validators/scope-validator.js.map +1 -0
  258. package/dist/lib/watch.d.ts +35 -0
  259. package/dist/lib/watch.d.ts.map +1 -0
  260. package/dist/lib/watch.js +171 -0
  261. package/dist/lib/watch.js.map +1 -0
  262. package/dist/templates/api/.env.example +15 -0
  263. package/dist/templates/api/Dockerfile +45 -0
  264. package/dist/templates/api/README.md +85 -0
  265. package/dist/templates/api/catalog-info.yaml +22 -0
  266. package/dist/templates/api/gitignore +31 -0
  267. package/dist/templates/api/helm/{{name}}/Chart.yaml +9 -0
  268. package/dist/templates/api/helm/{{name}}/templates/deployment.yaml +72 -0
  269. package/dist/templates/api/helm/{{name}}/templates/ingress.yaml +43 -0
  270. package/dist/templates/api/helm/{{name}}/templates/service.yaml +17 -0
  271. package/dist/templates/api/helm/{{name}}/values.yaml +64 -0
  272. package/dist/templates/api/package.json +33 -0
  273. package/dist/templates/api/src/index.ts +61 -0
  274. package/dist/templates/api/src/routes/example.ts +165 -0
  275. package/dist/templates/api/tsconfig.json +18 -0
  276. package/dist/templates/crosspod/README.md +87 -0
  277. package/dist/templates/crosspod/service-a/Dockerfile +27 -0
  278. package/dist/templates/crosspod/service-a/catalog-info.yaml +54 -0
  279. package/dist/templates/crosspod/service-a/gitignore +5 -0
  280. package/dist/templates/crosspod/service-a/helm/{{name}}-service-a/Chart.yaml +6 -0
  281. package/dist/templates/crosspod/service-a/helm/{{name}}-service-a/templates/deployment.yaml +72 -0
  282. package/dist/templates/crosspod/service-a/helm/{{name}}-service-a/templates/ingress.yaml +43 -0
  283. package/dist/templates/crosspod/service-a/helm/{{name}}-service-a/templates/service.yaml +17 -0
  284. package/dist/templates/crosspod/service-a/helm/{{name}}-service-a/values.yaml +44 -0
  285. package/dist/templates/crosspod/service-a/package.json +29 -0
  286. package/dist/templates/crosspod/service-a/src/index.ts +89 -0
  287. package/dist/templates/crosspod/service-a/tsconfig.json +14 -0
  288. package/dist/templates/crosspod/service-b/Dockerfile +27 -0
  289. package/dist/templates/crosspod/service-b/catalog-info.yaml +27 -0
  290. package/dist/templates/crosspod/service-b/gitignore +5 -0
  291. package/dist/templates/crosspod/service-b/helm/{{name}}-service-b/Chart.yaml +6 -0
  292. package/dist/templates/crosspod/service-b/helm/{{name}}-service-b/templates/deployment.yaml +72 -0
  293. package/dist/templates/crosspod/service-b/helm/{{name}}-service-b/templates/ingress.yaml +43 -0
  294. package/dist/templates/crosspod/service-b/helm/{{name}}-service-b/templates/service.yaml +17 -0
  295. package/dist/templates/crosspod/service-b/helm/{{name}}-service-b/values.yaml +47 -0
  296. package/dist/templates/crosspod/service-b/package.json +26 -0
  297. package/dist/templates/crosspod/service-b/src/index.ts +143 -0
  298. package/dist/templates/crosspod/service-b/tsconfig.json +14 -0
  299. package/dist/templates/mga/{{name}}-api/.env.example +5 -0
  300. package/dist/templates/mga/{{name}}-api/Dockerfile +45 -0
  301. package/dist/templates/mga/{{name}}-api/catalog-info.yaml +44 -0
  302. package/dist/templates/mga/{{name}}-api/gitignore +31 -0
  303. package/dist/templates/mga/{{name}}-api/helm/{{name}}-api/Chart.yaml +9 -0
  304. package/dist/templates/mga/{{name}}-api/helm/{{name}}-api/templates/deployment.yaml +72 -0
  305. package/dist/templates/mga/{{name}}-api/helm/{{name}}-api/templates/ingress.yaml +43 -0
  306. package/dist/templates/mga/{{name}}-api/helm/{{name}}-api/templates/service.yaml +17 -0
  307. package/dist/templates/mga/{{name}}-api/helm/{{name}}-api/values.yaml +65 -0
  308. package/dist/templates/mga/{{name}}-api/package.json +37 -0
  309. package/dist/templates/mga/{{name}}-api/src/index.ts +82 -0
  310. package/dist/templates/mga/{{name}}-api/src/lib/mongo.ts +19 -0
  311. package/dist/templates/mga/{{name}}-api/src/middleware/auth.ts +133 -0
  312. package/dist/templates/mga/{{name}}-api/src/models/agent.ts +45 -0
  313. package/dist/templates/mga/{{name}}-api/src/models/application.ts +58 -0
  314. package/dist/templates/mga/{{name}}-api/src/models/invite.ts +39 -0
  315. package/dist/templates/mga/{{name}}-api/src/models/policy.ts +59 -0
  316. package/dist/templates/mga/{{name}}-api/src/models/product.ts +51 -0
  317. package/dist/templates/mga/{{name}}-api/src/models/quote.ts +68 -0
  318. package/dist/templates/mga/{{name}}-api/src/routes/agents.ts +98 -0
  319. package/dist/templates/mga/{{name}}-api/src/routes/applications.ts +170 -0
  320. package/dist/templates/mga/{{name}}-api/src/routes/invites.ts +146 -0
  321. package/dist/templates/mga/{{name}}-api/src/routes/policies.ts +70 -0
  322. package/dist/templates/mga/{{name}}-api/src/routes/products.ts +154 -0
  323. package/dist/templates/mga/{{name}}-api/src/routes/quotes.ts +263 -0
  324. package/dist/templates/mga/{{name}}-api/src/routes/reports.ts +199 -0
  325. package/dist/templates/mga/{{name}}-api/tsconfig.json +18 -0
  326. package/dist/templates/mga/{{name}}-web/.dockerignore +6 -0
  327. package/dist/templates/mga/{{name}}-web/.env.example +6 -0
  328. package/dist/templates/mga/{{name}}-web/Dockerfile +51 -0
  329. package/dist/templates/mga/{{name}}-web/catalog-info.yaml +24 -0
  330. package/dist/templates/mga/{{name}}-web/dockerignore +6 -0
  331. package/dist/templates/mga/{{name}}-web/gitignore +36 -0
  332. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/Chart.yaml +9 -0
  333. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/templates/_helpers.tpl +49 -0
  334. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/templates/configmap.yaml +10 -0
  335. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/templates/deployment.yaml +56 -0
  336. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/templates/ingress.yaml +41 -0
  337. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/templates/service.yaml +15 -0
  338. package/dist/templates/mga/{{name}}-web/helm/{{name}}-web/values.yaml +70 -0
  339. package/dist/templates/mga/{{name}}-web/next.config.js +8 -0
  340. package/dist/templates/mga/{{name}}-web/package.json +30 -0
  341. package/dist/templates/mga/{{name}}-web/public/.gitkeep +0 -0
  342. package/dist/templates/mga/{{name}}-web/public/gitkeep +0 -0
  343. package/dist/templates/mga/{{name}}-web/src/app/api/auth/callback/route.ts +77 -0
  344. package/dist/templates/mga/{{name}}-web/src/app/api/auth/login/route.ts +16 -0
  345. package/dist/templates/mga/{{name}}-web/src/app/api/auth/logout/route.ts +7 -0
  346. package/dist/templates/mga/{{name}}-web/src/app/api/auth/session/route.ts +42 -0
  347. package/dist/templates/mga/{{name}}-web/src/app/api/health/route.ts +10 -0
  348. package/dist/templates/mga/{{name}}-web/src/app/api/proxy/applications/route.ts +47 -0
  349. package/dist/templates/mga/{{name}}-web/src/app/applications/layout.tsx +17 -0
  350. package/dist/templates/mga/{{name}}-web/src/app/applications/new/page.tsx +374 -0
  351. package/dist/templates/mga/{{name}}-web/src/app/applications/page.tsx +109 -0
  352. package/dist/templates/mga/{{name}}-web/src/app/dashboard/admin/page.tsx +179 -0
  353. package/dist/templates/mga/{{name}}-web/src/app/dashboard/agent/page.tsx +125 -0
  354. package/dist/templates/mga/{{name}}-web/src/app/dashboard/insured/page.tsx +145 -0
  355. package/dist/templates/mga/{{name}}-web/src/app/dashboard/layout.tsx +17 -0
  356. package/dist/templates/mga/{{name}}-web/src/app/dashboard/page.tsx +27 -0
  357. package/dist/templates/mga/{{name}}-web/src/app/dashboard/shell.tsx +89 -0
  358. package/dist/templates/mga/{{name}}-web/src/app/globals.css +477 -0
  359. package/dist/templates/mga/{{name}}-web/src/app/layout.tsx +19 -0
  360. package/dist/templates/mga/{{name}}-web/src/app/page.tsx +74 -0
  361. package/dist/templates/mga/{{name}}-web/src/app/reports/layout.tsx +21 -0
  362. package/dist/templates/mga/{{name}}-web/src/app/reports/page.tsx +231 -0
  363. package/dist/templates/mga/{{name}}-web/src/lib/api.ts +79 -0
  364. package/dist/templates/mga/{{name}}-web/src/lib/auth.ts +285 -0
  365. package/dist/templates/mga/{{name}}-web/src/middleware.ts +71 -0
  366. package/dist/templates/mga/{{name}}-web/tsconfig.json +26 -0
  367. package/dist/templates/nextjs/.env.example +11 -0
  368. package/dist/templates/nextjs/Dockerfile +51 -0
  369. package/dist/templates/nextjs/README.md +87 -0
  370. package/dist/templates/nextjs/catalog-info.yaml +16 -0
  371. package/dist/templates/nextjs/gitignore +36 -0
  372. package/dist/templates/nextjs/helm/{{name}}/Chart.yaml +9 -0
  373. package/dist/templates/nextjs/helm/{{name}}/templates/deployment.yaml +72 -0
  374. package/dist/templates/nextjs/helm/{{name}}/templates/ingress.yaml +43 -0
  375. package/dist/templates/nextjs/helm/{{name}}/templates/service.yaml +17 -0
  376. package/dist/templates/nextjs/helm/{{name}}/values.yaml +60 -0
  377. package/dist/templates/nextjs/next.config.js +23 -0
  378. package/dist/templates/nextjs/package.json +29 -0
  379. package/dist/templates/nextjs/public/.gitkeep +0 -0
  380. package/dist/templates/nextjs/public/gitkeep +0 -0
  381. package/dist/templates/nextjs/src/app/api/example/route.ts +63 -0
  382. package/dist/templates/nextjs/src/app/api/health/route.ts +10 -0
  383. package/dist/templates/nextjs/src/app/layout.tsx +18 -0
  384. package/dist/templates/nextjs/src/app/page.tsx +49 -0
  385. package/dist/templates/nextjs/tsconfig.json +26 -0
  386. package/dist/templates/nextjs-oauth/.dockerignore +6 -0
  387. package/dist/templates/nextjs-oauth/.env.example +12 -0
  388. package/dist/templates/nextjs-oauth/Dockerfile +51 -0
  389. package/dist/templates/nextjs-oauth/README.md +115 -0
  390. package/dist/templates/nextjs-oauth/catalog-info.yaml +17 -0
  391. package/dist/templates/nextjs-oauth/dockerignore +6 -0
  392. package/dist/templates/nextjs-oauth/gitignore +36 -0
  393. package/dist/templates/nextjs-oauth/helm/Chart.yaml +6 -0
  394. package/dist/templates/nextjs-oauth/helm/templates/_helpers.tpl +49 -0
  395. package/dist/templates/nextjs-oauth/helm/templates/configmap.yaml +10 -0
  396. package/dist/templates/nextjs-oauth/helm/templates/deployment.yaml +56 -0
  397. package/dist/templates/nextjs-oauth/helm/templates/ingress.yaml +41 -0
  398. package/dist/templates/nextjs-oauth/helm/templates/service.yaml +15 -0
  399. package/dist/templates/nextjs-oauth/helm/values.yaml +69 -0
  400. package/dist/templates/nextjs-oauth/helm/{{name}}/Chart.yaml +9 -0
  401. package/dist/templates/nextjs-oauth/helm/{{name}}/templates/deployment.yaml +68 -0
  402. package/dist/templates/nextjs-oauth/helm/{{name}}/templates/service.yaml +17 -0
  403. package/dist/templates/nextjs-oauth/helm/{{name}}/values.yaml +51 -0
  404. package/dist/templates/nextjs-oauth/next.config.js +23 -0
  405. package/dist/templates/nextjs-oauth/package.json +30 -0
  406. package/dist/templates/nextjs-oauth/public/.gitkeep +0 -0
  407. package/dist/templates/nextjs-oauth/public/gitkeep +0 -0
  408. package/dist/templates/nextjs-oauth/src/app/api/auth/callback/route.ts +77 -0
  409. package/dist/templates/nextjs-oauth/src/app/api/auth/login/route.ts +16 -0
  410. package/dist/templates/nextjs-oauth/src/app/api/auth/logout/route.ts +7 -0
  411. package/dist/templates/nextjs-oauth/src/app/api/auth/session/route.ts +42 -0
  412. package/dist/templates/nextjs-oauth/src/app/api/example/route.ts +63 -0
  413. package/dist/templates/nextjs-oauth/src/app/api/health/route.ts +10 -0
  414. package/dist/templates/nextjs-oauth/src/app/dashboard/page.tsx +92 -0
  415. package/dist/templates/nextjs-oauth/src/app/layout.tsx +18 -0
  416. package/dist/templates/nextjs-oauth/src/app/page.tsx +110 -0
  417. package/dist/templates/nextjs-oauth/src/lib/auth.ts +285 -0
  418. package/dist/templates/nextjs-oauth/src/middleware.ts +71 -0
  419. package/dist/templates/nextjs-oauth/tsconfig.json +26 -0
  420. package/dist/templates/static/catalog-info.yaml +14 -0
  421. package/dist/templates/static/index.html +16 -0
  422. package/dist/templates/static/styles.css +39 -0
  423. package/dist/templates/worker/.env.example +13 -0
  424. package/dist/templates/worker/Dockerfile +26 -0
  425. package/dist/templates/worker/README.md +106 -0
  426. package/dist/templates/worker/catalog-info.yaml +19 -0
  427. package/dist/templates/worker/gitignore +5 -0
  428. package/dist/templates/worker/helm/{{name}}/Chart.yaml +9 -0
  429. package/dist/templates/worker/helm/{{name}}/templates/deployment.yaml +68 -0
  430. package/dist/templates/worker/helm/{{name}}/templates/ingress.yaml +43 -0
  431. package/dist/templates/worker/helm/{{name}}/values.yaml +64 -0
  432. package/dist/templates/worker/package.json +26 -0
  433. package/dist/templates/worker/src/index.ts +185 -0
  434. package/dist/templates/worker/tsconfig.json +14 -0
  435. package/dist/types/index.d.ts +596 -0
  436. package/dist/types/index.d.ts.map +1 -0
  437. package/dist/types/index.js +41 -0
  438. package/dist/types/index.js.map +1 -0
  439. package/dist/types/platform.d.ts +191 -0
  440. package/dist/types/platform.d.ts.map +1 -0
  441. package/dist/types/platform.js +17 -0
  442. package/dist/types/platform.js.map +1 -0
  443. package/package.json +62 -0
@@ -0,0 +1,285 @@
1
+ import { cookies } from 'next/headers'
2
+ import { SignJWT, jwtVerify } from 'jose'
3
+ import crypto from 'crypto'
4
+
5
+ // Configuration — read lazily so `next build` doesn't fail when env vars are
6
+ // absent (they are injected at runtime via ConfigMap / Secret in K8s).
7
+ function getBioIdUrl(): string {
8
+ return process.env.BIO_ID_URL || 'http://localhost:6100'
9
+ }
10
+ function getAppUrl(): string {
11
+ return process.env.APP_URL || 'http://localhost:3000'
12
+ }
13
+ function getClientId(): string {
14
+ const id = process.env.OAUTH_CLIENT_ID
15
+ if (!id) throw new Error('OAUTH_CLIENT_ID is not configured')
16
+ return id
17
+ }
18
+ function getClientSecret(): string {
19
+ const secret = process.env.OAUTH_CLIENT_SECRET
20
+ if (!secret) throw new Error('OAUTH_CLIENT_SECRET is not configured')
21
+ return secret
22
+ }
23
+ function getJwtSecret(): Uint8Array {
24
+ const secret = process.env.JWT_SECRET
25
+ if (!secret && process.env.NODE_ENV === 'production') {
26
+ throw new Error('JWT_SECRET environment variable is required in production')
27
+ }
28
+ return new TextEncoder().encode(secret || 'dev-only-secret-do-not-use-in-production')
29
+ }
30
+
31
+ const COOKIE_PREFIX = '{{name}}'
32
+ const SESSION_MAX_AGE = 60 * 60 // 1 hour
33
+ const REFRESH_TOKEN_MAX_AGE = 60 * 60 * 24 * 30 // 30 days
34
+ const OAUTH_FLOW_MAX_AGE = 60 * 10 // 10 minutes
35
+
36
+ export interface User {
37
+ id: string
38
+ email: string
39
+ name: string
40
+ roles: string[]
41
+ }
42
+
43
+ // ---------------------------------------------------------------------------
44
+ // Helpers
45
+ // ---------------------------------------------------------------------------
46
+
47
+ export function sanitizeReturnTo(returnTo: string | undefined, fallback = '/dashboard'): string {
48
+ if (!returnTo || !returnTo.startsWith('/') || returnTo.startsWith('//')) {
49
+ return fallback
50
+ }
51
+ return returnTo
52
+ }
53
+
54
+ export function generatePKCE(): { codeVerifier: string; codeChallenge: string } {
55
+ const codeVerifier = crypto.randomBytes(32).toString('base64url')
56
+ const codeChallenge = crypto
57
+ .createHash('sha256')
58
+ .update(codeVerifier)
59
+ .digest('base64url')
60
+ return { codeVerifier, codeChallenge }
61
+ }
62
+
63
+ export function getAuthorizationUrl(state: string, codeChallenge: string): string {
64
+ const params = new URLSearchParams({
65
+ client_id: getClientId(),
66
+ redirect_uri: `${getAppUrl()}/api/auth/callback`,
67
+ response_type: 'code',
68
+ scope: 'openid profile email',
69
+ state,
70
+ code_challenge: codeChallenge,
71
+ code_challenge_method: 'S256',
72
+ })
73
+ return `${getBioIdUrl()}/oauth/authorize?${params.toString()}`
74
+ }
75
+
76
+ async function parseErrorResponse(response: Response, fallbackMessage: string): Promise<string> {
77
+ try {
78
+ const error = await response.json()
79
+ return error.error_description || error.error || fallbackMessage
80
+ } catch {
81
+ return fallbackMessage
82
+ }
83
+ }
84
+
85
+ // ---------------------------------------------------------------------------
86
+ // Bio-id API calls
87
+ // ---------------------------------------------------------------------------
88
+
89
+ export async function exchangeCodeForTokens(
90
+ code: string,
91
+ codeVerifier: string
92
+ ): Promise<{
93
+ access_token: string
94
+ token_type: string
95
+ expires_in: number
96
+ refresh_token: string
97
+ scope: string
98
+ id_token?: string
99
+ }> {
100
+ const response = await fetch(`${getBioIdUrl()}/api/oauth/token`, {
101
+ method: 'POST',
102
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
103
+ body: new URLSearchParams({
104
+ grant_type: 'authorization_code',
105
+ code,
106
+ redirect_uri: `${getAppUrl()}/api/auth/callback`,
107
+ client_id: getClientId(),
108
+ client_secret: getClientSecret(),
109
+ code_verifier: codeVerifier,
110
+ }).toString(),
111
+ })
112
+
113
+ if (!response.ok) {
114
+ throw new Error(await parseErrorResponse(response, 'Token exchange failed'))
115
+ }
116
+
117
+ return response.json()
118
+ }
119
+
120
+ export async function refreshAccessToken(refreshToken: string): Promise<{
121
+ access_token: string
122
+ token_type: string
123
+ expires_in: number
124
+ refresh_token: string
125
+ scope: string
126
+ }> {
127
+ const response = await fetch(`${getBioIdUrl()}/api/oauth/token`, {
128
+ method: 'POST',
129
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
130
+ body: new URLSearchParams({
131
+ grant_type: 'refresh_token',
132
+ refresh_token: refreshToken,
133
+ client_id: getClientId(),
134
+ client_secret: getClientSecret(),
135
+ }).toString(),
136
+ })
137
+
138
+ if (!response.ok) {
139
+ throw new Error(await parseErrorResponse(response, 'Token refresh failed'))
140
+ }
141
+
142
+ return response.json()
143
+ }
144
+
145
+ export async function fetchUserInfo(accessToken: string): Promise<User> {
146
+ const response = await fetch(`${getBioIdUrl()}/api/oauth/userinfo`, {
147
+ headers: { Authorization: `Bearer ${accessToken}` },
148
+ })
149
+
150
+ if (!response.ok) {
151
+ throw new Error('Failed to fetch user info')
152
+ }
153
+
154
+ const data = await response.json()
155
+
156
+ return {
157
+ id: data.bio_id || data.sub,
158
+ email: data.email,
159
+ name: data.name,
160
+ roles: data.roles || [],
161
+ }
162
+ }
163
+
164
+ // ---------------------------------------------------------------------------
165
+ // Session management
166
+ //
167
+ // After the OAuth callback, we create OUR OWN session JWT signed with
168
+ // JWT_SECRET. This avoids needing to verify bio-id's access token locally
169
+ // (bio-id uses HS256 signed with its own server secret).
170
+ // ---------------------------------------------------------------------------
171
+
172
+ export async function createSessionToken(user: User): Promise<string> {
173
+ return new SignJWT({
174
+ sub: user.id,
175
+ email: user.email,
176
+ name: user.name,
177
+ roles: user.roles,
178
+ })
179
+ .setProtectedHeader({ alg: 'HS256' })
180
+ .setIssuedAt()
181
+ .setExpirationTime(`${SESSION_MAX_AGE}s`)
182
+ .setIssuer(getAppUrl())
183
+ .sign(getJwtSecret())
184
+ }
185
+
186
+ export async function setSessionCookies(
187
+ sessionToken: string,
188
+ bioRefreshToken: string
189
+ ): Promise<void> {
190
+ const cookieStore = await cookies()
191
+ const secure = getAppUrl().startsWith('https://')
192
+
193
+ cookieStore.set(`${COOKIE_PREFIX}_session`, sessionToken, {
194
+ httpOnly: true,
195
+ secure,
196
+ sameSite: 'lax',
197
+ maxAge: SESSION_MAX_AGE,
198
+ path: '/',
199
+ })
200
+
201
+ cookieStore.set(`${COOKIE_PREFIX}_refresh_token`, bioRefreshToken, {
202
+ httpOnly: true,
203
+ secure,
204
+ sameSite: 'lax',
205
+ maxAge: REFRESH_TOKEN_MAX_AGE,
206
+ path: '/',
207
+ })
208
+ }
209
+
210
+ export async function clearAuthCookies(): Promise<void> {
211
+ const cookieStore = await cookies()
212
+ cookieStore.delete(`${COOKIE_PREFIX}_session`)
213
+ cookieStore.delete(`${COOKIE_PREFIX}_refresh_token`)
214
+ cookieStore.delete('oauth_state')
215
+ cookieStore.delete('oauth_code_verifier')
216
+ cookieStore.delete('oauth_return_to')
217
+ }
218
+
219
+ /**
220
+ * Get the current user from the session cookie (no network call).
221
+ * Verifies OUR session JWT — not bio-id's access token.
222
+ */
223
+ export async function getCurrentUser(): Promise<User | null> {
224
+ const cookieStore = await cookies()
225
+ const sessionToken = cookieStore.get(`${COOKIE_PREFIX}_session`)?.value
226
+
227
+ if (!sessionToken) {
228
+ return null
229
+ }
230
+
231
+ try {
232
+ const { payload } = await jwtVerify(sessionToken, getJwtSecret(), {
233
+ issuer: getAppUrl(),
234
+ })
235
+
236
+ return {
237
+ id: payload.sub || '',
238
+ email: payload.email as string,
239
+ name: payload.name as string,
240
+ roles: (payload.roles as string[]) || [],
241
+ }
242
+ } catch {
243
+ return null
244
+ }
245
+ }
246
+
247
+ /**
248
+ * Generate a login URL with PKCE and state stored in cookies
249
+ */
250
+ export async function getLoginUrl(returnTo?: string): Promise<string> {
251
+ const cookieStore = await cookies()
252
+ const secure = getAppUrl().startsWith('https://')
253
+
254
+ const state = crypto.randomBytes(16).toString('hex')
255
+ const { codeVerifier, codeChallenge } = generatePKCE()
256
+
257
+ cookieStore.set('oauth_state', state, {
258
+ httpOnly: true,
259
+ secure,
260
+ sameSite: 'lax',
261
+ maxAge: OAUTH_FLOW_MAX_AGE,
262
+ path: '/',
263
+ })
264
+
265
+ cookieStore.set('oauth_code_verifier', codeVerifier, {
266
+ httpOnly: true,
267
+ secure,
268
+ sameSite: 'lax',
269
+ maxAge: OAUTH_FLOW_MAX_AGE,
270
+ path: '/',
271
+ })
272
+
273
+ const safeReturnTo = sanitizeReturnTo(returnTo)
274
+ cookieStore.set('oauth_return_to', safeReturnTo, {
275
+ httpOnly: true,
276
+ secure,
277
+ sameSite: 'lax',
278
+ maxAge: OAUTH_FLOW_MAX_AGE,
279
+ path: '/',
280
+ })
281
+
282
+ return getAuthorizationUrl(state, codeChallenge)
283
+ }
284
+
285
+ export { COOKIE_PREFIX, getBioIdUrl, getAppUrl }
@@ -0,0 +1,71 @@
1
+ import { NextRequest, NextResponse } from 'next/server'
2
+ import { jwtVerify } from 'jose'
3
+
4
+ const COOKIE_PREFIX = '{{name}}'
5
+
6
+ // Routes that require authentication
7
+ const PROTECTED_PATHS = ['/dashboard']
8
+
9
+ // Routes that should never be blocked
10
+ const PUBLIC_PATHS = [
11
+ '/',
12
+ '/api/auth',
13
+ '/api/health',
14
+ ]
15
+
16
+ function isPublicPath(pathname: string): boolean {
17
+ return PUBLIC_PATHS.some(
18
+ (path) => pathname === path || pathname.startsWith(`${path}/`)
19
+ )
20
+ }
21
+
22
+ function isProtectedPath(pathname: string): boolean {
23
+ return PROTECTED_PATHS.some(
24
+ (path) => pathname === path || pathname.startsWith(`${path}/`)
25
+ )
26
+ }
27
+
28
+ export async function middleware(request: NextRequest) {
29
+ const { pathname } = request.nextUrl
30
+
31
+ if (isPublicPath(pathname)) {
32
+ return NextResponse.next()
33
+ }
34
+
35
+ if (!isProtectedPath(pathname)) {
36
+ return NextResponse.next()
37
+ }
38
+
39
+ // Check for our session cookie (not bio-id's access token)
40
+ const sessionToken = request.cookies.get(`${COOKIE_PREFIX}_session`)?.value
41
+
42
+ if (!sessionToken) {
43
+ const loginUrl = new URL('/api/auth/login', request.url)
44
+ loginUrl.searchParams.set('returnTo', pathname)
45
+ return NextResponse.redirect(loginUrl)
46
+ }
47
+
48
+ // Verify our own session JWT (signed with JWT_SECRET, issued by APP_URL)
49
+ try {
50
+ const secret = new TextEncoder().encode(
51
+ process.env.JWT_SECRET || 'dev-only-secret-do-not-use-in-production'
52
+ )
53
+ await jwtVerify(sessionToken, secret, {
54
+ issuer: process.env.APP_URL || 'http://localhost:3000',
55
+ })
56
+ } catch {
57
+ // Session expired or invalid — redirect to login
58
+ const loginUrl = new URL('/api/auth/login', request.url)
59
+ loginUrl.searchParams.set('returnTo', pathname)
60
+ return NextResponse.redirect(loginUrl)
61
+ }
62
+
63
+ return NextResponse.next()
64
+ }
65
+
66
+ export const config = {
67
+ matcher: [
68
+ // Match all paths except static files and Next.js internals
69
+ '/((?!_next/static|_next/image|favicon.ico|.*\\.(?:svg|png|jpg|jpeg|gif|webp)$).*)',
70
+ ],
71
+ }
@@ -0,0 +1,26 @@
1
+ {
2
+ "compilerOptions": {
3
+ "lib": ["dom", "dom.iterable", "esnext"],
4
+ "allowJs": true,
5
+ "skipLibCheck": true,
6
+ "strict": true,
7
+ "noEmit": true,
8
+ "esModuleInterop": true,
9
+ "module": "esnext",
10
+ "moduleResolution": "bundler",
11
+ "resolveJsonModule": true,
12
+ "isolatedModules": true,
13
+ "jsx": "preserve",
14
+ "incremental": true,
15
+ "plugins": [
16
+ {
17
+ "name": "next"
18
+ }
19
+ ],
20
+ "paths": {
21
+ "@/*": ["./src/*"]
22
+ }
23
+ },
24
+ "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
25
+ "exclude": ["node_modules"]
26
+ }
@@ -0,0 +1,14 @@
1
+ apiVersion: backstage.io/v1alpha1
2
+ kind: Component
3
+ metadata:
4
+ name: {{name}}
5
+ description: {{description}}
6
+ tags:
7
+ - tawa
8
+ - static
9
+ annotations:
10
+ insureco.io/framework: static
11
+ spec:
12
+ type: service
13
+ lifecycle: production
14
+ owner: {{owner}}
@@ -0,0 +1,16 @@
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
6
+ <title>{{name}}</title>
7
+ <link rel="stylesheet" href="styles.css">
8
+ </head>
9
+ <body>
10
+ <main>
11
+ <h1>{{name}}</h1>
12
+ <p>{{description}}</p>
13
+ <p>Deployed on <a href="https://tawa.insureco.io">Tawa</a></p>
14
+ </main>
15
+ </body>
16
+ </html>
@@ -0,0 +1,39 @@
1
+ * {
2
+ margin: 0;
3
+ padding: 0;
4
+ box-sizing: border-box;
5
+ }
6
+
7
+ body {
8
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
9
+ min-height: 100vh;
10
+ display: flex;
11
+ align-items: center;
12
+ justify-content: center;
13
+ background: #0a0a0a;
14
+ color: #fafafa;
15
+ }
16
+
17
+ main {
18
+ text-align: center;
19
+ padding: 2rem;
20
+ }
21
+
22
+ h1 {
23
+ font-size: 2.5rem;
24
+ margin-bottom: 1rem;
25
+ }
26
+
27
+ p {
28
+ color: #888;
29
+ margin-bottom: 0.5rem;
30
+ }
31
+
32
+ a {
33
+ color: #3b82f6;
34
+ text-decoration: none;
35
+ }
36
+
37
+ a:hover {
38
+ text-decoration: underline;
39
+ }
@@ -0,0 +1,13 @@
1
+ # Redis Configuration
2
+ REDIS_HOST=localhost
3
+ REDIS_PORT=6379
4
+ REDIS_PASSWORD=
5
+
6
+ # Queue Configuration
7
+ QUEUE_NAME={{name}}-jobs
8
+
9
+ # Worker Configuration
10
+ WORKER_CONCURRENCY=5
11
+
12
+ # Environment
13
+ NODE_ENV=development
@@ -0,0 +1,26 @@
1
+ FROM node:22-alpine AS builder
2
+ WORKDIR /app
3
+ COPY package*.json ./
4
+ RUN npm ci
5
+ COPY . .
6
+ RUN npm run build
7
+
8
+ FROM node:22-alpine
9
+ WORKDIR /app
10
+ COPY package*.json ./
11
+ RUN npm ci --production && npm cache clean --force
12
+ COPY --from=builder /app/dist ./dist
13
+
14
+ ENV NODE_ENV=production
15
+
16
+ RUN addgroup -g 1001 -S nodejs && \
17
+ adduser -S nodejs -u 1001 && \
18
+ chown -R nodejs:nodejs /app
19
+
20
+ USER nodejs
21
+
22
+ # Health check via file existence
23
+ HEALTHCHECK --interval=30s --timeout=3s --start-period=10s --retries=3 \
24
+ CMD test -f /tmp/healthy || exit 1
25
+
26
+ CMD ["node", "dist/index.js"]
@@ -0,0 +1,106 @@
1
+ # {{name}}
2
+
3
+ {{description}}
4
+
5
+ A background job processor using BullMQ and Redis.
6
+
7
+ ## Getting Started
8
+
9
+ ### Prerequisites
10
+
11
+ - Node.js 20+
12
+ - Redis server
13
+
14
+ ### Installation
15
+
16
+ ```bash
17
+ npm install
18
+ ```
19
+
20
+ ### Development
21
+
22
+ Start Redis locally:
23
+
24
+ ```bash
25
+ docker run -d -p 6379:6379 redis:alpine
26
+ ```
27
+
28
+ Run the worker:
29
+
30
+ ```bash
31
+ npm run dev
32
+ ```
33
+
34
+ ## Job Types
35
+
36
+ The worker processes these job types:
37
+
38
+ - `email` - Send email notifications
39
+ - `report` - Generate reports
40
+ - `sync` - Synchronize data
41
+ - `cleanup` - Clean up resources
42
+
43
+ ## Adding Jobs to the Queue
44
+
45
+ From another service:
46
+
47
+ ```typescript
48
+ import { Queue } from 'bullmq'
49
+
50
+ const queue = new Queue('{{name}}-jobs', {
51
+ connection: {
52
+ host: 'redis',
53
+ port: 6379,
54
+ },
55
+ })
56
+
57
+ // Add a job
58
+ await queue.add('my-job', {
59
+ type: 'email',
60
+ payload: {
61
+ to: 'user@example.com',
62
+ subject: 'Hello',
63
+ body: 'World',
64
+ },
65
+ priority: 5,
66
+ })
67
+ ```
68
+
69
+ ## Health Checks
70
+
71
+ The worker uses file-based health checks:
72
+
73
+ - Creates `/tmp/healthy` when ready
74
+ - Removes the file on error or shutdown
75
+ - Kubernetes checks file existence for liveness
76
+
77
+ ## Configuration
78
+
79
+ Environment variables:
80
+
81
+ | Variable | Default | Description |
82
+ |----------|---------|-------------|
83
+ | `REDIS_HOST` | localhost | Redis server host |
84
+ | `REDIS_PORT` | 6379 | Redis server port |
85
+ | `REDIS_PASSWORD` | - | Redis password |
86
+ | `QUEUE_NAME` | {{name}}-jobs | Queue name |
87
+ | `WORKER_CONCURRENCY` | 5 | Max concurrent jobs |
88
+
89
+ ## Deployment
90
+
91
+ ```bash
92
+ iec link
93
+ iec deploy
94
+ ```
95
+
96
+ ## Project Structure
97
+
98
+ ```
99
+ {{name}}/
100
+ ├── src/
101
+ │ └── index.ts # Worker entry point
102
+ ├── helm/
103
+ │ └── {{name}}/ # Kubernetes Helm chart
104
+ ├── Dockerfile
105
+ └── catalog-info.yaml
106
+ ```
@@ -0,0 +1,19 @@
1
+ apiVersion: backstage.io/v1alpha1
2
+ kind: Component
3
+ metadata:
4
+ name: {{name}}
5
+ description: {{description}}
6
+ tags:
7
+ - tawa
8
+ - worker
9
+ - background-job
10
+ annotations:
11
+ insureco.io/framework: bullmq
12
+ insureco.io/language: typescript
13
+ insureco.io/type: worker
14
+ spec:
15
+ type: service
16
+ lifecycle: experimental
17
+ owner: {{owner}}
18
+ # Workers typically don't expose HTTP routes
19
+ # Health is monitored via TCP probe or file-based health check
@@ -0,0 +1,5 @@
1
+ node_modules/
2
+ dist/
3
+ .env
4
+ .env.local
5
+ *.log
@@ -0,0 +1,9 @@
1
+ apiVersion: v2
2
+ name: {{name}}
3
+ description: Helm chart for {{name}} background worker
4
+ type: application
5
+ version: 0.1.0
6
+ appVersion: "0.1.0"
7
+ maintainers:
8
+ - name: team-platform
9
+ email: platform@insureco.io
@@ -0,0 +1,68 @@
1
+ apiVersion: apps/v1
2
+ kind: Deployment
3
+ metadata:
4
+ name: {{ .Release.Name }}
5
+ labels:
6
+ app: {{ .Release.Name }}
7
+ app.kubernetes.io/name: {{ .Release.Name }}
8
+ app.kubernetes.io/instance: {{ .Release.Name }}
9
+ spec:
10
+ replicas: {{ .Values.replicaCount }}
11
+ selector:
12
+ matchLabels:
13
+ app: {{ .Release.Name }}
14
+ template:
15
+ metadata:
16
+ labels:
17
+ app: {{ .Release.Name }}
18
+ app.kubernetes.io/name: {{ .Release.Name }}
19
+ app.kubernetes.io/instance: {{ .Release.Name }}
20
+ spec:
21
+ {{- with .Values.imagePullSecrets }}
22
+ imagePullSecrets:
23
+ {{- toYaml . | nindent 8 }}
24
+ {{- end }}
25
+ containers:
26
+ - name: {{ .Chart.Name }}
27
+ image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}"
28
+ imagePullPolicy: {{ .Values.image.pullPolicy }}
29
+ envFrom:
30
+ - configMapRef:
31
+ name: {{ .Release.Name }}-config
32
+ optional: true
33
+ - secretRef:
34
+ name: {{ .Release.Name }}-secrets
35
+ optional: true
36
+ {{- if .Values.secretRef }}
37
+ - secretRef:
38
+ name: {{ .Values.secretRef }}
39
+ {{- end }}
40
+ {{- with .Values.env }}
41
+ env:
42
+ {{- range $key, $value := . }}
43
+ - name: {{ $key }}
44
+ value: {{ $value | quote }}
45
+ {{- end }}
46
+ {{- end }}
47
+ {{- with .Values.livenessProbe }}
48
+ livenessProbe:
49
+ {{- toYaml . | nindent 12 }}
50
+ {{- end }}
51
+ {{- with .Values.readinessProbe }}
52
+ readinessProbe:
53
+ {{- toYaml . | nindent 12 }}
54
+ {{- end }}
55
+ resources:
56
+ {{- toYaml .Values.resources | nindent 12 }}
57
+ {{- with .Values.nodeSelector }}
58
+ nodeSelector:
59
+ {{- toYaml . | nindent 8 }}
60
+ {{- end }}
61
+ {{- with .Values.affinity }}
62
+ affinity:
63
+ {{- toYaml . | nindent 8 }}
64
+ {{- end }}
65
+ {{- with .Values.tolerations }}
66
+ tolerations:
67
+ {{- toYaml . | nindent 8 }}
68
+ {{- end }}