@geekmidas/cli 10.0.0-alpha.12 → 10.0.0-alpha.121

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 (517) hide show
  1. package/README.md +310 -377
  2. package/bin/adjacent-tsconfig.mjs +46 -8
  3. package/bin/gkm.mjs +11 -3
  4. package/bin/owning-tsconfig-jsx-register.mjs +18 -0
  5. package/bin/owning-tsconfig-jsx.mjs +108 -0
  6. package/dist/EndpointGenerator-BDa6pPgE.cjs +1090 -0
  7. package/dist/EndpointGenerator-BDa6pPgE.cjs.map +1 -0
  8. package/dist/EndpointGenerator-CP_z_E3e.mjs +1031 -0
  9. package/dist/EndpointGenerator-CP_z_E3e.mjs.map +1 -0
  10. package/dist/GoDaddyProvider-3C8U_tVu.cjs +388 -0
  11. package/dist/GoDaddyProvider-3C8U_tVu.cjs.map +1 -0
  12. package/dist/GoDaddyProvider-D0MQoOM4.mjs +388 -0
  13. package/dist/GoDaddyProvider-D0MQoOM4.mjs.map +1 -0
  14. package/dist/{HostingerProvider-BcyFRbqV.mjs → HostingerProvider-BNpS9aRJ.mjs} +29 -25
  15. package/dist/HostingerProvider-BNpS9aRJ.mjs.map +1 -0
  16. package/dist/{HostingerProvider-BOvsgATO.cjs → HostingerProvider-DR1iws1P.cjs} +29 -25
  17. package/dist/HostingerProvider-DR1iws1P.cjs.map +1 -0
  18. package/dist/LegacyStateStore-CRi7TosX.mjs +124 -0
  19. package/dist/LegacyStateStore-CRi7TosX.mjs.map +1 -0
  20. package/dist/LegacyStateStore-DHsoQGOo.cjs +124 -0
  21. package/dist/LegacyStateStore-DHsoQGOo.cjs.map +1 -0
  22. package/dist/LocalStateStore-BQXTkeoS.cjs +178 -0
  23. package/dist/LocalStateStore-BQXTkeoS.cjs.map +1 -0
  24. package/dist/LocalStateStore-Dkth0jXX.mjs +167 -0
  25. package/dist/LocalStateStore-Dkth0jXX.mjs.map +1 -0
  26. package/dist/OpenApiTsGenerator-CsrukCE-.mjs +536 -0
  27. package/dist/OpenApiTsGenerator-CsrukCE-.mjs.map +1 -0
  28. package/dist/OpenApiTsGenerator-FNhY7Ssz.cjs +541 -0
  29. package/dist/OpenApiTsGenerator-FNhY7Ssz.cjs.map +1 -0
  30. package/dist/{Route53Provider-CH9XH7bz.cjs → Route53Provider-Bllus2NR.cjs} +21 -22
  31. package/dist/Route53Provider-Bllus2NR.cjs.map +1 -0
  32. package/dist/{Route53Provider-C0xmer8U.mjs → Route53Provider-QXxjkZO1.mjs} +13 -13
  33. package/dist/Route53Provider-QXxjkZO1.mjs.map +1 -0
  34. package/dist/S3StateStore-DGKZgyKz.cjs +222 -0
  35. package/dist/S3StateStore-DGKZgyKz.cjs.map +1 -0
  36. package/dist/S3StateStore-pZZnLLBd.mjs +223 -0
  37. package/dist/S3StateStore-pZZnLLBd.mjs.map +1 -0
  38. package/dist/SSMStateStore-CZRMERDA.mjs +205 -0
  39. package/dist/SSMStateStore-CZRMERDA.mjs.map +1 -0
  40. package/dist/SSMStateStore-DzkyjQ5D.cjs +204 -0
  41. package/dist/SSMStateStore-DzkyjQ5D.cjs.map +1 -0
  42. package/dist/SubscriberGenerator-C8CPxrCK.cjs +592 -0
  43. package/dist/SubscriberGenerator-C8CPxrCK.cjs.map +1 -0
  44. package/dist/SubscriberGenerator-y3pncae_.mjs +533 -0
  45. package/dist/SubscriberGenerator-y3pncae_.mjs.map +1 -0
  46. package/dist/add-C0kXOsWS.mjs +717 -0
  47. package/dist/add-C0kXOsWS.mjs.map +1 -0
  48. package/dist/add-Df8cmz0H.cjs +719 -0
  49. package/dist/add-Df8cmz0H.cjs.map +1 -0
  50. package/dist/appPorts-BoXMwolc.mjs +249 -0
  51. package/dist/appPorts-BoXMwolc.mjs.map +1 -0
  52. package/dist/appPorts-IW-OZmRi.cjs +296 -0
  53. package/dist/appPorts-IW-OZmRi.cjs.map +1 -0
  54. package/dist/aws-8QQ8n-t6.mjs +89 -0
  55. package/dist/aws-8QQ8n-t6.mjs.map +1 -0
  56. package/dist/aws-DY9NqQIT.cjs +100 -0
  57. package/dist/aws-DY9NqQIT.cjs.map +1 -0
  58. package/dist/awsStore-Bx5nCFnS.mjs +121 -0
  59. package/dist/awsStore-Bx5nCFnS.mjs.map +1 -0
  60. package/dist/awsStore-u3ehhMoY.cjs +138 -0
  61. package/dist/awsStore-u3ehhMoY.cjs.map +1 -0
  62. package/dist/{backup-provisioner-DXXg6FIL.mjs → backup-provisioner-C8DnCmxK.mjs} +11 -8
  63. package/dist/backup-provisioner-C8DnCmxK.mjs.map +1 -0
  64. package/dist/{backup-provisioner-cE2PuCTb.cjs → backup-provisioner-oDEsPj02.cjs} +22 -20
  65. package/dist/backup-provisioner-oDEsPj02.cjs.map +1 -0
  66. package/dist/backups/runner.cjs +519 -0
  67. package/dist/backups/runner.cjs.map +1 -0
  68. package/dist/backups/runner.d.cts +102 -0
  69. package/dist/backups/runner.d.cts.map +1 -0
  70. package/dist/backups/runner.d.mts +102 -0
  71. package/dist/backups/runner.d.mts.map +1 -0
  72. package/dist/backups/runner.mjs +506 -0
  73. package/dist/backups/runner.mjs.map +1 -0
  74. package/dist/{bundler-Bux2iF-v.mjs → bundler-B-I4Du99.mjs} +35 -16
  75. package/dist/bundler-B-I4Du99.mjs.map +1 -0
  76. package/dist/{bundler-BMekgx7a.cjs → bundler-Dx_grUmc.cjs} +37 -19
  77. package/dist/bundler-Dx_grUmc.cjs.map +1 -0
  78. package/dist/cli-Cd9exatJ.cjs +71 -0
  79. package/dist/cli-Cd9exatJ.cjs.map +1 -0
  80. package/dist/cli-DL7GxGAe.mjs +71 -0
  81. package/dist/cli-DL7GxGAe.mjs.map +1 -0
  82. package/dist/compose-C43c03WZ.mjs +3284 -0
  83. package/dist/compose-C43c03WZ.mjs.map +1 -0
  84. package/dist/compose-Mdgea4Yt.cjs +3427 -0
  85. package/dist/compose-Mdgea4Yt.cjs.map +1 -0
  86. package/dist/config-D48erO2j.d.mts +269 -0
  87. package/dist/config-D48erO2j.d.mts.map +1 -0
  88. package/dist/config-DHDtsQrB.d.cts +269 -0
  89. package/dist/config-DHDtsQrB.d.cts.map +1 -0
  90. package/dist/config.cjs +421 -11
  91. package/dist/config.cjs.map +1 -0
  92. package/dist/config.d.cts +4 -120
  93. package/dist/config.d.mts +4 -120
  94. package/dist/config.mjs +405 -4
  95. package/dist/config.mjs.map +1 -0
  96. package/dist/credentialSchemas-B67WJOOm.cjs +272 -0
  97. package/dist/credentialSchemas-B67WJOOm.cjs.map +1 -0
  98. package/dist/credentialSchemas-DDOLRCLF.mjs +237 -0
  99. package/dist/credentialSchemas-DDOLRCLF.mjs.map +1 -0
  100. package/dist/credentials-B5N5yKk6.mjs +267 -0
  101. package/dist/credentials-B5N5yKk6.mjs.map +1 -0
  102. package/dist/credentials-Zqr3QQYB.cjs +350 -0
  103. package/dist/credentials-Zqr3QQYB.cjs.map +1 -0
  104. package/dist/databases-BPOgTn1u.mjs +522 -0
  105. package/dist/databases-BPOgTn1u.mjs.map +1 -0
  106. package/dist/databases-fOaoBInm.cjs +625 -0
  107. package/dist/databases-fOaoBInm.cjs.map +1 -0
  108. package/dist/define-6poNqm5O.mjs +106 -0
  109. package/dist/define-6poNqm5O.mjs.map +1 -0
  110. package/dist/define-crmMcXFS.cjs +153 -0
  111. package/dist/define-crmMcXFS.cjs.map +1 -0
  112. package/dist/deploy/public.cjs +212 -0
  113. package/dist/deploy/public.cjs.map +1 -0
  114. package/dist/deploy/public.d.cts +654 -0
  115. package/dist/deploy/public.d.cts.map +1 -0
  116. package/dist/deploy/public.d.mts +654 -0
  117. package/dist/deploy/public.d.mts.map +1 -0
  118. package/dist/deploy/public.mjs +145 -0
  119. package/dist/deploy/public.mjs.map +1 -0
  120. package/dist/deploy/sniffer-envkit-patch.cjs +18 -10
  121. package/dist/deploy/sniffer-envkit-patch.cjs.map +1 -1
  122. package/dist/deploy/sniffer-envkit-patch.d.cts +0 -2
  123. package/dist/deploy/sniffer-envkit-patch.d.cts.map +1 -1
  124. package/dist/deploy/sniffer-envkit-patch.d.mts +0 -2
  125. package/dist/deploy/sniffer-envkit-patch.d.mts.map +1 -1
  126. package/dist/deploy/sniffer-envkit-patch.mjs +10 -2
  127. package/dist/deploy/sniffer-envkit-patch.mjs.map +1 -1
  128. package/dist/deploy/sniffer-envparser-worker.cjs +54 -0
  129. package/dist/deploy/sniffer-envparser-worker.cjs.map +1 -0
  130. package/dist/deploy/sniffer-envparser-worker.d.cts +1 -0
  131. package/dist/deploy/sniffer-envparser-worker.d.mts +1 -0
  132. package/dist/deploy/sniffer-envparser-worker.mjs +55 -0
  133. package/dist/deploy/sniffer-envparser-worker.mjs.map +1 -0
  134. package/dist/deploy/sniffer-hooks.cjs +13 -7
  135. package/dist/deploy/sniffer-hooks.cjs.map +1 -1
  136. package/dist/deploy/sniffer-hooks.d.cts +1 -2
  137. package/dist/deploy/sniffer-hooks.d.cts.map +1 -1
  138. package/dist/deploy/sniffer-hooks.d.mts +1 -2
  139. package/dist/deploy/sniffer-hooks.d.mts.map +1 -1
  140. package/dist/deploy/sniffer-hooks.mjs +10 -3
  141. package/dist/deploy/sniffer-hooks.mjs.map +1 -1
  142. package/dist/deploy/sniffer-loader.cjs +16 -7
  143. package/dist/deploy/sniffer-loader.cjs.map +1 -1
  144. package/dist/deploy/sniffer-loader.d.cts +1 -1
  145. package/dist/deploy/sniffer-loader.d.mts +1 -1
  146. package/dist/deploy/sniffer-loader.mjs +14 -3
  147. package/dist/deploy/sniffer-loader.mjs.map +1 -1
  148. package/dist/deploy/sniffer-routes-worker.cjs +11 -11
  149. package/dist/deploy/sniffer-routes-worker.cjs.map +1 -1
  150. package/dist/deploy/sniffer-routes-worker.d.cts +1 -1
  151. package/dist/deploy/sniffer-routes-worker.d.mts +1 -1
  152. package/dist/deploy/sniffer-routes-worker.mjs +4 -4
  153. package/dist/deploy/sniffer-routes-worker.mjs.map +1 -1
  154. package/dist/deploy/sniffer-worker.cjs +15 -6
  155. package/dist/deploy/sniffer-worker.cjs.map +1 -1
  156. package/dist/deploy/sniffer-worker.d.cts +1 -3
  157. package/dist/deploy/sniffer-worker.d.cts.map +1 -1
  158. package/dist/deploy/sniffer-worker.d.mts +1 -3
  159. package/dist/deploy/sniffer-worker.d.mts.map +1 -1
  160. package/dist/deploy/sniffer-worker.mjs +15 -4
  161. package/dist/deploy/sniffer-worker.mjs.map +1 -1
  162. package/dist/deploy-BMM2hx-K.cjs +2401 -0
  163. package/dist/deploy-BMM2hx-K.cjs.map +1 -0
  164. package/dist/deploy-D5YhwDng.mjs +2328 -0
  165. package/dist/deploy-D5YhwDng.mjs.map +1 -0
  166. package/dist/derive-B4vDpzgP.mjs +150 -0
  167. package/dist/derive-B4vDpzgP.mjs.map +1 -0
  168. package/dist/derive-DAbo49sm.cjs +161 -0
  169. package/dist/derive-DAbo49sm.cjs.map +1 -0
  170. package/dist/discover-C5roJuc9.mjs +560 -0
  171. package/dist/discover-C5roJuc9.mjs.map +1 -0
  172. package/dist/discover-CSW_BMWa.d.cts +125 -0
  173. package/dist/discover-CSW_BMWa.d.cts.map +1 -0
  174. package/dist/discover-DozUKs8f.cjs +639 -0
  175. package/dist/discover-DozUKs8f.cjs.map +1 -0
  176. package/dist/discover-xtT7fgWg.d.mts +125 -0
  177. package/dist/discover-xtT7fgWg.d.mts.map +1 -0
  178. package/dist/dns-BIYf20p7.cjs +1057 -0
  179. package/dist/dns-BIYf20p7.cjs.map +1 -0
  180. package/dist/dns-agf2VCdV.mjs +926 -0
  181. package/dist/dns-agf2VCdV.mjs.map +1 -0
  182. package/dist/dokploy-2p4PK6ej.mjs +38 -0
  183. package/dist/dokploy-2p4PK6ej.mjs.map +1 -0
  184. package/dist/dokploy-BANMTroy.cjs +38 -0
  185. package/dist/dokploy-BANMTroy.cjs.map +1 -0
  186. package/dist/drivers-BjGDYfnC.mjs +195 -0
  187. package/dist/drivers-BjGDYfnC.mjs.map +1 -0
  188. package/dist/drivers-DbjiYpW6.cjs +224 -0
  189. package/dist/drivers-DbjiYpW6.cjs.map +1 -0
  190. package/dist/eas-CNi16SoO.cjs +337 -0
  191. package/dist/eas-CNi16SoO.cjs.map +1 -0
  192. package/dist/eas-iT2JDHCh.mjs +334 -0
  193. package/dist/eas-iT2JDHCh.mjs.map +1 -0
  194. package/dist/{emit-CIlvnDvV.mjs → emit-C1e8qD08.mjs} +13 -26
  195. package/dist/emit-C1e8qD08.mjs.map +1 -0
  196. package/dist/{emit-CUD1BWls.cjs → emit-Dmc1nvdS.cjs} +31 -57
  197. package/dist/emit-Dmc1nvdS.cjs.map +1 -0
  198. package/dist/encryption-DkXVbyZc.mjs +89 -0
  199. package/dist/encryption-DkXVbyZc.mjs.map +1 -0
  200. package/dist/encryption-d2lLtkYx.cjs +90 -0
  201. package/dist/encryption-d2lLtkYx.cjs.map +1 -0
  202. package/dist/engine-CatKW6E-.mjs +3089 -0
  203. package/dist/engine-CatKW6E-.mjs.map +1 -0
  204. package/dist/engine-DlEHexED.cjs +3202 -0
  205. package/dist/engine-DlEHexED.cjs.map +1 -0
  206. package/dist/errors-D8Gwp5kU.mjs +23 -0
  207. package/dist/errors-D8Gwp5kU.mjs.map +1 -0
  208. package/dist/errors-DMC4Umsb.cjs +34 -0
  209. package/dist/errors-DMC4Umsb.cjs.map +1 -0
  210. package/dist/github-BAeaC1Pl.cjs +833 -0
  211. package/dist/github-BAeaC1Pl.cjs.map +1 -0
  212. package/dist/github-DErsqKGN.mjs +832 -0
  213. package/dist/github-DErsqKGN.mjs.map +1 -0
  214. package/dist/googlePlay-BVcfFWRO.cjs +931 -0
  215. package/dist/googlePlay-BVcfFWRO.cjs.map +1 -0
  216. package/dist/googlePlay-BXJ5ZjMK.mjs +931 -0
  217. package/dist/googlePlay-BXJ5ZjMK.mjs.map +1 -0
  218. package/dist/identity-CBXr4wNi.mjs +129 -0
  219. package/dist/identity-CBXr4wNi.mjs.map +1 -0
  220. package/dist/identity-CbLfgQNT.cjs +182 -0
  221. package/dist/identity-CbLfgQNT.cjs.map +1 -0
  222. package/dist/{index-BzJ7QJ9c.d.mts → index-8OfpOtSI.d.cts} +39 -20
  223. package/dist/index-8OfpOtSI.d.cts.map +1 -0
  224. package/dist/{index-CfMjtdVC.d.cts → index-Dpji6Bxq.d.mts} +39 -20
  225. package/dist/index-Dpji6Bxq.d.mts.map +1 -0
  226. package/dist/index.cjs +14291 -11898
  227. package/dist/index.cjs.map +1 -1
  228. package/dist/index.d.cts +1 -1
  229. package/dist/index.d.mts +1 -1
  230. package/dist/index.mjs +13938 -11560
  231. package/dist/index.mjs.map +1 -1
  232. package/dist/local-BwC2v2Y8.mjs +224 -0
  233. package/dist/local-BwC2v2Y8.mjs.map +1 -0
  234. package/dist/local-DNhnkugT.cjs +241 -0
  235. package/dist/local-DNhnkugT.cjs.map +1 -0
  236. package/dist/migrate-Bb1MmGHl.mjs +181 -0
  237. package/dist/migrate-Bb1MmGHl.mjs.map +1 -0
  238. package/dist/migrate-D79GI0XM.cjs +271 -0
  239. package/dist/migrate-D79GI0XM.cjs.map +1 -0
  240. package/dist/migrate-L4a273dY.cjs +181 -0
  241. package/dist/migrate-L4a273dY.cjs.map +1 -0
  242. package/dist/migrate-s4QizIoM.mjs +266 -0
  243. package/dist/migrate-s4QizIoM.mjs.map +1 -0
  244. package/dist/openapi.cjs +214 -10
  245. package/dist/openapi.cjs.map +1 -0
  246. package/dist/openapi.d.cts +38 -17
  247. package/dist/openapi.d.cts.map +1 -1
  248. package/dist/openapi.d.mts +38 -17
  249. package/dist/openapi.d.mts.map +1 -1
  250. package/dist/openapi.mjs +208 -5
  251. package/dist/openapi.mjs.map +1 -0
  252. package/dist/projectBucket-BBbQ1lHF.cjs +263 -0
  253. package/dist/projectBucket-BBbQ1lHF.cjs.map +1 -0
  254. package/dist/projectBucket-C_DN4WzF.mjs +222 -0
  255. package/dist/projectBucket-C_DN4WzF.mjs.map +1 -0
  256. package/dist/provider-BqpjG9QM.cjs +57 -0
  257. package/dist/provider-BqpjG9QM.cjs.map +1 -0
  258. package/dist/provider-CEOKk8NS.mjs +46 -0
  259. package/dist/provider-CEOKk8NS.mjs.map +1 -0
  260. package/dist/publish-CcTlmJT6.mjs +123 -0
  261. package/dist/publish-CcTlmJT6.mjs.map +1 -0
  262. package/dist/publish-ydscCYsW.cjs +124 -0
  263. package/dist/publish-ydscCYsW.cjs.map +1 -0
  264. package/dist/ready-BFFP838V.cjs +404 -0
  265. package/dist/ready-BFFP838V.cjs.map +1 -0
  266. package/dist/ready-BOfogqzr.mjs +375 -0
  267. package/dist/ready-BOfogqzr.mjs.map +1 -0
  268. package/dist/reconcile/public.cjs +3 -5
  269. package/dist/reconcile/public.d.cts +11 -87
  270. package/dist/reconcile/public.d.cts.map +1 -1
  271. package/dist/reconcile/public.d.mts +11 -87
  272. package/dist/reconcile/public.d.mts.map +1 -1
  273. package/dist/reconcile/public.mjs +3 -4
  274. package/dist/{reconcile-BI0tWkwz.mjs → reconcile--I7V4Klj.mjs} +4 -7
  275. package/dist/reconcile--I7V4Klj.mjs.map +1 -0
  276. package/dist/{reconcile-Bhw5fmKu.cjs → reconcile-CuCQBa5-.cjs} +5 -8
  277. package/dist/reconcile-CuCQBa5-.cjs.map +1 -0
  278. package/dist/resolve-BLp2trep.mjs +263 -0
  279. package/dist/resolve-BLp2trep.mjs.map +1 -0
  280. package/dist/resolve-BgL-brF9.cjs +316 -0
  281. package/dist/resolve-BgL-brF9.cjs.map +1 -0
  282. package/dist/rollback-2cyLXEH1.cjs +165 -0
  283. package/dist/rollback-2cyLXEH1.cjs.map +1 -0
  284. package/dist/rollback-DwqZ8zzj.mjs +136 -0
  285. package/dist/rollback-DwqZ8zzj.mjs.map +1 -0
  286. package/dist/rolldown-runtime-BhDjJH2R.mjs +15 -0
  287. package/dist/{chunk-CUT6urMc.cjs → rolldown-runtime-C0BPl7ul.cjs} +23 -10
  288. package/dist/run-BJLIerMM.mjs +133 -0
  289. package/dist/run-BJLIerMM.mjs.map +1 -0
  290. package/dist/run-fVZ-rLnc.cjs +174 -0
  291. package/dist/run-fVZ-rLnc.cjs.map +1 -0
  292. package/dist/runtime-ACdfK59n.d.cts +82 -0
  293. package/dist/runtime-ACdfK59n.d.cts.map +1 -0
  294. package/dist/runtime-YyQuekxi.d.mts +82 -0
  295. package/dist/runtime-YyQuekxi.d.mts.map +1 -0
  296. package/dist/s3-CrPoA89T.cjs +215 -0
  297. package/dist/s3-CrPoA89T.cjs.map +1 -0
  298. package/dist/s3-DQXZdmCM.mjs +215 -0
  299. package/dist/s3-DQXZdmCM.mjs.map +1 -0
  300. package/dist/sandbox/config-worker.cjs +43 -0
  301. package/dist/sandbox/config-worker.cjs.map +1 -0
  302. package/dist/sandbox/config-worker.d.cts +1 -0
  303. package/dist/sandbox/config-worker.d.mts +1 -0
  304. package/dist/sandbox/config-worker.mjs +44 -0
  305. package/dist/sandbox/config-worker.mjs.map +1 -0
  306. package/dist/sandbox/credentials-worker.cjs +54 -0
  307. package/dist/sandbox/credentials-worker.cjs.map +1 -0
  308. package/dist/sandbox/credentials-worker.d.cts +1 -0
  309. package/dist/sandbox/credentials-worker.d.mts +1 -0
  310. package/dist/sandbox/credentials-worker.mjs +55 -0
  311. package/dist/sandbox/credentials-worker.mjs.map +1 -0
  312. package/dist/sandbox/discover-worker.cjs +50 -0
  313. package/dist/sandbox/discover-worker.cjs.map +1 -0
  314. package/dist/sandbox/discover-worker.d.cts +1 -0
  315. package/dist/sandbox/discover-worker.d.mts +1 -0
  316. package/dist/sandbox/discover-worker.mjs +51 -0
  317. package/dist/sandbox/discover-worker.mjs.map +1 -0
  318. package/dist/sandbox/migrate-worker.cjs +75 -0
  319. package/dist/sandbox/migrate-worker.cjs.map +1 -0
  320. package/dist/sandbox/migrate-worker.d.cts +1 -0
  321. package/dist/sandbox/migrate-worker.d.mts +1 -0
  322. package/dist/sandbox/migrate-worker.mjs +76 -0
  323. package/dist/sandbox/migrate-worker.mjs.map +1 -0
  324. package/dist/sandbox-C4g1eG31.d.mts +104 -0
  325. package/dist/sandbox-C4g1eG31.d.mts.map +1 -0
  326. package/dist/sandbox-CHv3OYXg.cjs +165 -0
  327. package/dist/sandbox-CHv3OYXg.cjs.map +1 -0
  328. package/dist/sandbox-CbVB7uOD.mjs +118 -0
  329. package/dist/sandbox-CbVB7uOD.mjs.map +1 -0
  330. package/dist/sandbox-CdKgQ3XU.d.cts +104 -0
  331. package/dist/sandbox-CdKgQ3XU.d.cts.map +1 -0
  332. package/dist/{workspace-DPV7FtAv.cjs → schemas-BCwKKA42.mjs} +958 -1816
  333. package/dist/schemas-BCwKKA42.mjs.map +1 -0
  334. package/dist/{workspace-CtnZnWsa.mjs → schemas-BQ_v0lEX.cjs} +1048 -1626
  335. package/dist/schemas-BQ_v0lEX.cjs.map +1 -0
  336. package/dist/secretsManager-CQORubp9.mjs +97 -0
  337. package/dist/secretsManager-CQORubp9.mjs.map +1 -0
  338. package/dist/secretsManager-RAGcEDX1.cjs +108 -0
  339. package/dist/secretsManager-RAGcEDX1.cjs.map +1 -0
  340. package/dist/seeds-C2w4UqVP.cjs +9347 -0
  341. package/dist/seeds-C2w4UqVP.cjs.map +1 -0
  342. package/dist/seeds-Cwtv-U9-.mjs +8350 -0
  343. package/dist/seeds-Cwtv-U9-.mjs.map +1 -0
  344. package/dist/serverSetup-BdFOD93s.cjs +631 -0
  345. package/dist/serverSetup-BdFOD93s.cjs.map +1 -0
  346. package/dist/serverSetup-utKsoyGH.mjs +631 -0
  347. package/dist/serverSetup-utKsoyGH.mjs.map +1 -0
  348. package/dist/sniffer-8C4q6Szd.mjs +1825 -0
  349. package/dist/sniffer-8C4q6Szd.mjs.map +1 -0
  350. package/dist/sniffer-CF7wNxMo.cjs +1998 -0
  351. package/dist/sniffer-CF7wNxMo.cjs.map +1 -0
  352. package/dist/sst-B-Uz4cvm.cjs +464 -0
  353. package/dist/sst-B-Uz4cvm.cjs.map +1 -0
  354. package/dist/sst-C1pxbFEd.mjs +441 -0
  355. package/dist/sst-C1pxbFEd.mjs.map +1 -0
  356. package/dist/stage-BvM_u2z4.mjs +302 -0
  357. package/dist/stage-BvM_u2z4.mjs.map +1 -0
  358. package/dist/stage-DEQJGW3r.cjs +313 -0
  359. package/dist/stage-DEQJGW3r.cjs.map +1 -0
  360. package/dist/stages-Cb9rqRbN.mjs +190 -0
  361. package/dist/stages-Cb9rqRbN.mjs.map +1 -0
  362. package/dist/stages-D4SnG5yl.cjs +190 -0
  363. package/dist/stages-D4SnG5yl.cjs.map +1 -0
  364. package/dist/target/public.cjs +15 -0
  365. package/dist/target/public.d.cts +28 -0
  366. package/dist/target/public.d.cts.map +1 -0
  367. package/dist/target/public.d.mts +28 -0
  368. package/dist/target/public.d.mts.map +1 -0
  369. package/dist/target/public.mjs +4 -0
  370. package/dist/terminal-CW_dWeTe.mjs +85 -0
  371. package/dist/terminal-CW_dWeTe.mjs.map +1 -0
  372. package/dist/terminal-DJlqcW_U.cjs +85 -0
  373. package/dist/terminal-DJlqcW_U.cjs.map +1 -0
  374. package/dist/types-B6UXlEkf.d.cts +7650 -0
  375. package/dist/types-B6UXlEkf.d.cts.map +1 -0
  376. package/dist/types-HqVPddRK.d.mts +7649 -0
  377. package/dist/types-HqVPddRK.d.mts.map +1 -0
  378. package/dist/utils-D2Nk1Nv2.cjs +205 -0
  379. package/dist/utils-D2Nk1Nv2.cjs.map +1 -0
  380. package/dist/utils-D_fxUqvU.mjs +156 -0
  381. package/dist/utils-D_fxUqvU.mjs.map +1 -0
  382. package/dist/vitest.cjs +65 -0
  383. package/dist/vitest.cjs.map +1 -0
  384. package/dist/vitest.d.cts +29 -0
  385. package/dist/vitest.d.cts.map +1 -0
  386. package/dist/vitest.d.mts +29 -0
  387. package/dist/vitest.d.mts.map +1 -0
  388. package/dist/vitest.mjs +65 -0
  389. package/dist/vitest.mjs.map +1 -0
  390. package/dist/workerRuntime-BXfhbe13.cjs +108 -0
  391. package/dist/workerRuntime-BXfhbe13.cjs.map +1 -0
  392. package/dist/workerRuntime-CsOyBRx2.mjs +79 -0
  393. package/dist/workerRuntime-CsOyBRx2.mjs.map +1 -0
  394. package/dist/workspace/index.cjs +8 -4
  395. package/dist/workspace/index.d.cts +3 -3
  396. package/dist/workspace/index.d.mts +3 -3
  397. package/dist/workspace/index.mjs +2 -3
  398. package/dist/workspace-BwqQnool.cjs +2806 -0
  399. package/dist/workspace-BwqQnool.cjs.map +1 -0
  400. package/dist/workspace-D1QbNd55.mjs +2394 -0
  401. package/dist/workspace-D1QbNd55.mjs.map +1 -0
  402. package/package.json +54 -22
  403. package/dist/CachedStateProvider-BEBl2wQT.cjs +0 -60
  404. package/dist/CachedStateProvider-BEBl2wQT.cjs.map +0 -1
  405. package/dist/CachedStateProvider-C-8wtlto.mjs +0 -3
  406. package/dist/CachedStateProvider-Co4n5Wvs.mjs +0 -54
  407. package/dist/CachedStateProvider-Co4n5Wvs.mjs.map +0 -1
  408. package/dist/CachedStateProvider-DqhGpzsm.cjs +0 -3
  409. package/dist/HostingerProvider-BOvsgATO.cjs.map +0 -1
  410. package/dist/HostingerProvider-BcyFRbqV.mjs.map +0 -1
  411. package/dist/LocalStateProvider-Bq-0C0sg.mjs +0 -42
  412. package/dist/LocalStateProvider-Bq-0C0sg.mjs.map +0 -1
  413. package/dist/LocalStateProvider-yjXZXZDM.cjs +0 -43
  414. package/dist/LocalStateProvider-yjXZXZDM.cjs.map +0 -1
  415. package/dist/Route53Provider-C0xmer8U.mjs.map +0 -1
  416. package/dist/Route53Provider-CH9XH7bz.cjs.map +0 -1
  417. package/dist/SSMStateProvider-CXtNgPfy.cjs +0 -66
  418. package/dist/SSMStateProvider-CXtNgPfy.cjs.map +0 -1
  419. package/dist/SSMStateProvider-DOZifZfE.mjs +0 -66
  420. package/dist/SSMStateProvider-DOZifZfE.mjs.map +0 -1
  421. package/dist/backup-provisioner-DXXg6FIL.mjs.map +0 -1
  422. package/dist/backup-provisioner-cE2PuCTb.cjs.map +0 -1
  423. package/dist/bundler-BMekgx7a.cjs.map +0 -1
  424. package/dist/bundler-Bux2iF-v.mjs.map +0 -1
  425. package/dist/chunk-Duj1WY3L.mjs +0 -7
  426. package/dist/config-DTsVjKZD.mjs +0 -402
  427. package/dist/config-DTsVjKZD.mjs.map +0 -1
  428. package/dist/config-RYR9j6EF.cjs +0 -462
  429. package/dist/config-RYR9j6EF.cjs.map +0 -1
  430. package/dist/config.d.cts.map +0 -1
  431. package/dist/config.d.mts.map +0 -1
  432. package/dist/credentials-B5zRHdAl.mjs +0 -141
  433. package/dist/credentials-B5zRHdAl.mjs.map +0 -1
  434. package/dist/credentials-BapzjyV5.cjs +0 -195
  435. package/dist/credentials-BapzjyV5.cjs.map +0 -1
  436. package/dist/credentials-DQRvPz2S.cjs +0 -2769
  437. package/dist/credentials-DQRvPz2S.cjs.map +0 -1
  438. package/dist/credentials-jMJC63qs.mjs +0 -2625
  439. package/dist/credentials-jMJC63qs.mjs.map +0 -1
  440. package/dist/discover-BYHQwQqu.mjs +0 -242
  441. package/dist/discover-BYHQwQqu.mjs.map +0 -1
  442. package/dist/discover-DmW9Bscc.cjs +0 -290
  443. package/dist/discover-DmW9Bscc.cjs.map +0 -1
  444. package/dist/dokploy-api-5cK2InBm.cjs +0 -3
  445. package/dist/dokploy-api-D2Ny4Jrc.mjs +0 -3
  446. package/dist/dokploy-api-pdaBryoY.mjs +0 -706
  447. package/dist/dokploy-api-pdaBryoY.mjs.map +0 -1
  448. package/dist/dokploy-api-zqKe9lHH.cjs +0 -718
  449. package/dist/dokploy-api-zqKe9lHH.cjs.map +0 -1
  450. package/dist/emit-CIlvnDvV.mjs.map +0 -1
  451. package/dist/emit-CUD1BWls.cjs.map +0 -1
  452. package/dist/encryption-D2pL3tHH.cjs +0 -54
  453. package/dist/encryption-D2pL3tHH.cjs.map +0 -1
  454. package/dist/encryption-YDsXXi6w.mjs +0 -3
  455. package/dist/encryption-_4zwjOAR.mjs +0 -42
  456. package/dist/encryption-_4zwjOAR.mjs.map +0 -1
  457. package/dist/encryption-sQ2Oxx0d.cjs +0 -4
  458. package/dist/fullstack-secrets-B6KBHf-g.mjs +0 -87
  459. package/dist/fullstack-secrets-B6KBHf-g.mjs.map +0 -1
  460. package/dist/fullstack-secrets-DL8v0y4D.cjs +0 -99
  461. package/dist/fullstack-secrets-DL8v0y4D.cjs.map +0 -1
  462. package/dist/generator-CNzBw7g5.cjs +0 -289
  463. package/dist/generator-CNzBw7g5.cjs.map +0 -1
  464. package/dist/generator-VE2JrFlY.mjs +0 -253
  465. package/dist/generator-VE2JrFlY.mjs.map +0 -1
  466. package/dist/github-BThvbf2W.cjs +0 -197
  467. package/dist/github-BThvbf2W.cjs.map +0 -1
  468. package/dist/github-DpMZurEK.mjs +0 -196
  469. package/dist/github-DpMZurEK.mjs.map +0 -1
  470. package/dist/index-BzJ7QJ9c.d.mts.map +0 -1
  471. package/dist/index-CfMjtdVC.d.cts.map +0 -1
  472. package/dist/keystore-C9rint2E.cjs +0 -101
  473. package/dist/keystore-C9rint2E.cjs.map +0 -1
  474. package/dist/keystore-TxeYM7an.mjs +0 -83
  475. package/dist/keystore-TxeYM7an.mjs.map +0 -1
  476. package/dist/openapi-Bs3-5q_r.mjs +0 -2021
  477. package/dist/openapi-Bs3-5q_r.mjs.map +0 -1
  478. package/dist/openapi-DWLTsYLL.cjs +0 -2075
  479. package/dist/openapi-DWLTsYLL.cjs.map +0 -1
  480. package/dist/openapi-react-query-Byltvm_7.mjs +0 -167
  481. package/dist/openapi-react-query-Byltvm_7.mjs.map +0 -1
  482. package/dist/openapi-react-query-CmJ1xDbn.cjs +0 -173
  483. package/dist/openapi-react-query-CmJ1xDbn.cjs.map +0 -1
  484. package/dist/openapi-react-query.cjs +0 -4
  485. package/dist/openapi-react-query.d.cts +0 -11
  486. package/dist/openapi-react-query.d.cts.map +0 -1
  487. package/dist/openapi-react-query.d.mts +0 -11
  488. package/dist/openapi-react-query.d.mts.map +0 -1
  489. package/dist/openapi-react-query.mjs +0 -4
  490. package/dist/reconcile-BI0tWkwz.mjs.map +0 -1
  491. package/dist/reconcile-Bhw5fmKu.cjs.map +0 -1
  492. package/dist/setup-BmLoNrDX.mjs +0 -12
  493. package/dist/setup-BrR1_xGy.cjs +0 -12
  494. package/dist/setup-BsNR2LBG.cjs +0 -467
  495. package/dist/setup-BsNR2LBG.cjs.map +0 -1
  496. package/dist/setup-D5-JMknk.mjs +0 -437
  497. package/dist/setup-D5-JMknk.mjs.map +0 -1
  498. package/dist/storage-B020InPW.mjs +0 -222
  499. package/dist/storage-B020InPW.mjs.map +0 -1
  500. package/dist/storage-CSNplaJn.cjs +0 -282
  501. package/dist/storage-CSNplaJn.cjs.map +0 -1
  502. package/dist/storage-DGBzMLZa.mjs +0 -4
  503. package/dist/storage-DlVol_oj.cjs +0 -8
  504. package/dist/sync-0ILCb-1S.cjs +0 -93
  505. package/dist/sync-0ILCb-1S.cjs.map +0 -1
  506. package/dist/sync-CzHXiR9c.mjs +0 -76
  507. package/dist/sync-CzHXiR9c.mjs.map +0 -1
  508. package/dist/sync-DYENfOt4.cjs +0 -4
  509. package/dist/sync-HAau6h_R.mjs +0 -3
  510. package/dist/types-DVIx8I1N.d.mts +0 -1950
  511. package/dist/types-DVIx8I1N.d.mts.map +0 -1
  512. package/dist/types-PMP_qXRY.d.cts +0 -1950
  513. package/dist/types-PMP_qXRY.d.cts.map +0 -1
  514. package/dist/workspace-Cji6lE8E.cjs +0 -10
  515. package/dist/workspace-CkJAtRIX.mjs +0 -9
  516. package/dist/workspace-CtnZnWsa.mjs.map +0 -1
  517. package/dist/workspace-DPV7FtAv.cjs.map +0 -1
package/README.md CHANGED
@@ -7,7 +7,7 @@ A powerful CLI tool for building and managing TypeScript-based backend APIs with
7
7
  - **Project Scaffolding**: Interactive `init` command to bootstrap new projects with templates
8
8
  - **Multi-Provider Support**: Generate handlers for AWS Lambda (API Gateway v1/v2) and server applications
9
9
  - **Development Server**: Hot-reload development server with file watching
10
- - **Telescope Integration**: Laravel-style debugging dashboard for inspecting requests, logs, and exceptions
10
+ - **Telescope Integration**: Laravel-style recording of requests, logs and exceptions, served as JSON
11
11
  - **OpenAPI Generation**: Auto-generate OpenAPI 3.0 specifications from your endpoints
12
12
  - **Docker Support**: Generate optimized Dockerfiles with multi-stage builds, turbo prune for monorepos
13
13
  - **Secrets Management**: Secure credential generation, encryption, and stage-based secrets storage
@@ -73,7 +73,7 @@ export default defineConfig({
73
73
  // Logger configuration
74
74
  logger: './src/logger.ts#logger',
75
75
 
76
- // Optional: Telescope debugging dashboard (enabled by default in dev)
76
+ // Optional: Telescope request recording (enabled by default in dev)
77
77
  telescope: {
78
78
  enabled: true,
79
79
  path: '/__telescope',
@@ -143,36 +143,32 @@ export const createUser = api
143
143
 
144
144
  ### 5. Create Subscribers (Optional)
145
145
 
146
- Create event subscribers in `src/subscribers/`:
146
+ Declare the topic once, and a worker to run what has no port; a subscriber is
147
+ built from the worker and binds to the topic:
147
148
 
148
149
  ```typescript
150
+ // src/constructs/topics.ts
151
+ import { Topic } from '@geekmidas/constructs/topic';
152
+ import { z } from 'zod';
153
+
154
+ export const users = new Topic('Users', {
155
+ events: {
156
+ 'user.created': z.object({ userId: z.string(), email: z.email() }),
157
+ 'user.updated': z.object({ userId: z.string() }),
158
+ },
159
+ });
160
+
161
+ // src/constructs/worker.ts
162
+ import { Worker } from '@geekmidas/constructs/worker';
163
+
164
+ export const worker = new Worker('Jobs', { logger });
165
+
149
166
  // src/subscribers/userSubscriber.ts
150
- import { SubscriberBuilder } from '@geekmidas/constructs/subscribers';
151
- import type { Service } from '@geekmidas/services';
152
- import type { EventPublisher, PublishableMessage } from '@geekmidas/events';
153
- import type { EnvironmentParser } from '@geekmidas/envkit';
154
-
155
- // Define event types
156
- type UserEvents =
157
- | PublishableMessage<'user.created', { userId: string; email: string }>
158
- | PublishableMessage<'user.updated', { userId: string }>;
159
-
160
- // Create event publisher service
161
- const userEventPublisher = {
162
- serviceName: 'userEventPublisher' as const,
163
- async register(envParser: EnvironmentParser<{}>) {
164
- const config = envParser.create((get) => ({
165
- publisherUrl: get('EVENT_PUBLISHER_URL').string()
166
- })).parse();
167
-
168
- const { Publisher } = await import('@geekmidas/events');
169
- return Publisher.fromConnectionString<UserEvents>(config.publisherUrl);
170
- }
171
- } satisfies Service<'userEventPublisher', EventPublisher<UserEvents>>;
167
+ import { users } from '../constructs/topics';
168
+ import { worker } from '../constructs/worker';
172
169
 
173
- // Create subscriber
174
- export const userCreatedSubscriber = new SubscriberBuilder()
175
- .publisher(userEventPublisher)
170
+ export const userCreatedSubscriber = worker
171
+ .topic(users)
176
172
  .subscribe(['user.created'])
177
173
  .handle(async ({ events, logger }) => {
178
174
  for (const event of events) {
@@ -182,11 +178,16 @@ export const userCreatedSubscriber = new SubscriberBuilder()
182
178
  });
183
179
  ```
184
180
 
181
+ An endpoint publishes to the topic with `.event(users, { type: 'user.created',
182
+ payload: (user) => ({ userId: user.id, email: user.email }) })`. Declaring the
183
+ topic is what puts a broker in the local plan and resolves
184
+ `USERS_PUBLISHER_CONNECTION_STRING` for whatever publishes to it.
185
+
185
186
  ### 6. Build Handlers
186
187
 
187
188
  ```bash
188
- # Generate AWS Lambda handlers
189
- npx gkm build --provider aws-apigatewayv1
189
+ # Build for where gkm.config.ts deploys (AWS for `deploy: { default: 'sst' }`)
190
+ npx gkm build
190
191
 
191
192
  # Generate server application
192
193
  npx gkm build --provider server
@@ -225,7 +226,7 @@ When run without `--yes`, the command will ask:
225
226
  - `api` - Full API with auth, database, services
226
227
  - `serverless` - AWS Lambda handlers
227
228
  - `worker` - Background job processing
228
- 3. **Telescope** - Include debugging dashboard (default: yes)
229
+ 3. **Telescope** - Include request, exception and log recording (default: yes)
229
230
  4. **Database** - Include Kysely database support (default: yes)
230
231
  5. **Logger** - Choose logger implementation:
231
232
  - `pino` - Fast JSON logger for production (recommended)
@@ -310,17 +311,20 @@ Generate handlers from your endpoints.
310
311
  gkm build [options]
311
312
  ```
312
313
 
314
+ By default it builds for where the project deploys: `deploy: { default: 'sst' }`
315
+ builds for AWS, one Lambda per construct; `dokploy` (the default when nothing
316
+ is declared) builds a server.
317
+
313
318
  **Options:**
314
- - `--provider <provider>`: Target provider (default: `aws-apigatewayv1`)
315
- - `aws-apigatewayv1`: AWS API Gateway v1 Lambda handlers
316
- - `aws-apigatewayv2`: AWS API Gateway v2 Lambda handlers
319
+ - `--provider <provider>`: Override the deploy target
320
+ - `aws`: One Lambda handler per construct (API Gateway v2 for endpoints)
317
321
  - `server`: Server application with Hono
318
322
  - `--production`: Generate production-optimized bundle (server provider only)
319
323
 
320
324
  **Example:**
321
325
  ```bash
322
- # Generate AWS Lambda handlers
323
- gkm build --provider aws-apigatewayv1
326
+ # Build for where gkm.config.ts deploys
327
+ gkm build
324
328
 
325
329
  # Generate server application
326
330
  gkm build --provider server
@@ -334,7 +338,7 @@ gkm build --provider server --production
334
338
  When using `--production` with the server provider, the CLI generates an optimized bundle at `.gkm/server/dist/server.mjs`. This bundle:
335
339
  - Is minified and tree-shaken for smaller size
336
340
  - Includes all dependencies (single-file deployment)
337
- - Can be used with `gkm docker --slim` for minimal Docker images
341
+ - Is what `gkm docker`'s images run — built inside the image, never copied in from the host
338
342
 
339
343
  ### `gkm openapi`
340
344
 
@@ -434,54 +438,44 @@ gkm docker [options]
434
438
  ```
435
439
 
436
440
  **Options:**
437
- - `--build`: Build Docker image after generating files
438
- - `--push`: Push image to registry after building
441
+ - `--build`: Build each app's image after generating files
442
+ - `--push`: Push the images to the registry after building
439
443
  - `--tag <tag>`: Image tag (default: `latest`)
440
444
  - `--registry <url>`: Container registry URL
441
- - `--slim`: Use slim Dockerfile (requires pre-built bundle from `gkm build --production`)
442
- - `--turbo`: Enable turbo prune for monorepo optimization
443
- - `--turbo-package <name>`: Package name for turbo prune (defaults to package.json name)
444
445
 
445
446
  **Generated Files:**
446
- - `.gkm/docker/Dockerfile` - Multi-stage or slim Dockerfile
447
- - `docker-compose.constructs.yml` - the containers the constructs imply, and the app (project root)
448
- - `.gkm/docker/docker-entrypoint.sh` - Entrypoint script
449
- - `.dockerignore` - Docker ignore file (project root)
447
+ - `.gkm/docker/Dockerfile.<app>` - one per app (`Dockerfile` for an app at the root)
448
+ - `docker-compose.constructs.yml` - the containers the constructs imply, and the apps (project root)
449
+ - `.dockerignore` - at the build root, created or completed
450
450
 
451
- **Dockerfile Types:**
451
+ **How an image is built:**
452
452
 
453
- | Type | Flag | Description |
454
- |------|------|-------------|
455
- | Multi-stage | (default) | Builds from source inside Docker, most reproducible |
456
- | Turbo | `--turbo` | Optimized for monorepos with turbo prune |
457
- | Slim | `--slim` | Uses pre-built bundle, requires prior `gkm build --production` |
453
+ Every image is built inside Docker — `docker build` on a clean checkout is all
454
+ it takes. The context is the build root (the directory holding the lockfile or
455
+ `pnpm-workspace.yaml`, at or above the workspace); `turbo prune` cuts the app's
456
+ slice of it; the image installs it, builds the workspace packages the app
457
+ depends on, and builds the app (`gkm build --provider server --production` for
458
+ a backend, the framework's build for a site). The runner holds `server.mjs`, a
459
+ Next.js standalone server, or a Vite site's files served by Caddy.
458
460
 
459
461
  **Example:**
460
462
  ```bash
461
- # Generate multi-stage Dockerfile (default, recommended)
463
+ # Generate the Dockerfiles
462
464
  gkm docker
463
465
 
464
- # Generate and build image
466
+ # Generate and build the images
465
467
  gkm docker --build --tag v1.0.0
466
468
 
467
469
  # Build and push to registry
468
470
  gkm docker --build --push --registry ghcr.io/myorg --tag v1.0.0
469
-
470
- # Use turbo prune for monorepo
471
- gkm docker --turbo --turbo-package my-api
472
-
473
- # Use slim Dockerfile (after running gkm build --production)
474
- gkm build --provider server --production
475
- gkm docker --slim
476
471
  ```
477
472
 
478
473
  **Package Manager Support:**
479
474
 
480
- The CLI auto-detects your package manager from lockfiles and generates optimized Dockerfiles:
481
- - **pnpm**: Uses `pnpm fetch` for better layer caching
482
- - **npm**: Uses `npm ci` with cache mounts
483
- - **yarn**: Uses `yarn install --frozen-lockfile`
484
- - **bun**: Uses `bun install --frozen-lockfile`
475
+ The package manager is detected from the lockfile and pinned to the build
476
+ root's `packageManager` field; turbo is pinned to the version the build root
477
+ resolves. Dependencies install with a BuildKit cache mount for the package
478
+ manager's store.
485
479
 
486
480
  **Configuration:**
487
481
 
@@ -517,10 +511,15 @@ constructs; an image pin or an extra service goes in your own
517
511
  ```yaml
518
512
  # docker-compose.yml
519
513
  services:
520
- postgres:
521
- image: postgis/postgis:16-3.4-alpine
514
+ mailpit:
515
+ image: axllent/mailpit:v1.27
522
516
  ```
523
517
 
518
+ A database's own image is named on the database rather than pinned here —
519
+ `new KyselyDatabase('Geo', { image: 'postgis/postgis:18-3.6-alpine', extensions: ['postgis'] })`
520
+ — so a deploy runs it too, and the extension is created in that database
521
+ only.
522
+
524
523
  **Service Configuration Options:**
525
524
 
526
525
  | Property | Description |
@@ -541,7 +540,7 @@ services:
541
540
 
542
541
  ### `gkm dev`
543
542
 
544
- Start a development server with hot-reload and optional Telescope debugging dashboard.
543
+ Start a development server with hot-reload and optional Telescope recording.
545
544
 
546
545
  ```bash
547
546
  gkm dev [options]
@@ -553,7 +552,8 @@ gkm dev [options]
553
552
  **Features:**
554
553
  - Hot-reload on file changes (endpoints, functions, crons, subscribers)
555
554
  - Automatic port switching if requested port is in use
556
- - Telescope debugging dashboard (enabled by default)
555
+ - Telescope JSON API at `/__telescope/api` (enabled by default)
556
+ - The declared database, read-only, as JSON at `/__gkm/db`
557
557
  - Real-time WebSocket updates in Telescope
558
558
 
559
559
  **Example:**
@@ -781,7 +781,7 @@ Store credentials locally to avoid setting environment variables for every comma
781
781
 
782
782
  ### `gkm login`
783
783
 
784
- Authenticate with a deployment service. Credentials are stored in `~/.gkm/credentials.json`.
784
+ Authenticate with a deployment service. Credentials are stored in `~/.gkm/credentials.json` (`$GKM_HOME/credentials.json` when `GKM_HOME` is set).
785
785
 
786
786
  ```bash
787
787
  gkm login [options]
@@ -809,7 +809,7 @@ gkm login --endpoint https://dokploy.example.com
809
809
  # These commands no longer need DOKPLOY_API_TOKEN
810
810
  gkm deploy:list
811
811
  gkm deploy:init --project my-project --app api
812
- gkm deploy --provider dokploy --stage production
812
+ gkm deploy --stage production
813
813
  ```
814
814
 
815
815
  ### `gkm logout`
@@ -855,92 +855,99 @@ gkm whoami
855
855
 
856
856
  ### `gkm deploy`
857
857
 
858
- Deploy application to a provider. Builds for production, injects encrypted secrets, and deploys.
858
+ Deploy a stage through its **target**: `deploy.default` in `gkm.config.ts`
859
+ (`dokploy` when unset), or `--target` for one run. `dokploy`, `compose` and
860
+ `sst` ship with the CLI; any other target is a package the project installs and
861
+ names in `deploy.targets`.
859
862
 
860
863
  ```bash
861
- gkm deploy --provider <provider> --stage <stage> [options]
864
+ gkm deploy --stage <stage> [options]
862
865
  ```
863
866
 
864
867
  **Options:**
865
- - `--provider <provider>`: Deploy provider (`docker`, `dokploy`, `aws-lambda`)
866
- - `--stage <stage>`: Deployment stage
867
- - `--tag <tag>`: Image tag (default: `stage-timestamp`)
868
- - `--skip-push`: Skip pushing image to registry
869
- - `--skip-build`: Skip build step (use existing build)
868
+ - `--stage <stage>`: Deployment stage (required): one of `stages.deployed`, or the local stage through `compose`
869
+ - `--target <name>`: `dokploy`, `compose`, `sst`, or a name in `deploy.targets` (default: `deploy.default`)
870
+ - `--tag <tag>`: Image tag (default: `<stage>-<timestamp>`; compose: the commit). Through compose, a given tag is pulled
871
+ - `--json`: Write the deploy's events as JSON lines on stdout instead of progress; never prompts
872
+ - `--dry-run`: Show what would be created or reused, and change, build and push nothing
873
+ - `--atomic`: If the release fails, roll back every app it released, not only the ones that failed
874
+ - `--provider <provider>`: Deprecated. `dokploy` means `--target dokploy`; `docker` and `aws-lambda` fail with `ProviderRemoved`
875
+ - `--skip-push`, `--skip-build`: Deprecated and ignored
870
876
 
871
877
  **Examples:**
872
878
  ```bash
873
- # Docker: build and push image
874
- gkm deploy --provider docker --stage production
879
+ # deploy.default (dokploy unless configured otherwise)
880
+ DOKPLOY_API_TOKEN=xxx gkm deploy --stage production
875
881
 
876
- # Dokploy: build, push, and trigger deployment
877
- DOKPLOY_API_TOKEN=xxx gkm deploy --provider dokploy --stage production
882
+ # Plan only
883
+ gkm deploy --stage production --dry-run
878
884
 
879
- # Custom tag
880
- gkm deploy --provider docker --stage production --tag v1.0.0
881
- ```
882
-
883
- **Workflow:**
884
- 1. **Sniffs environment variables** - Automatically detects which env vars each app needs
885
- 2. Builds production bundle with `gkm build --provider server --production --stage <stage>`
886
- 3. Encrypts secrets from `.gkm/secrets/<stage>.json` into the bundle
887
- 4. Generates Docker files with `gkm docker`
888
- 5. Builds and pushes Docker image
889
- 6. (Dokploy) Triggers deployment via API with `GKM_MASTER_KEY`
885
+ # One Docker Compose stack behind Caddy, on this machine, from images CI pushed
886
+ gkm deploy --target compose --stage production --tag v1.4.0
890
887
 
891
- **Environment Variable Detection:**
888
+ # AWS, with deploy: { default: 'sst' }: gkm build --provider aws, then sst deploy
889
+ AWS_PROFILE=acme-prod gkm deploy --stage production
892
890
 
893
- The deploy command automatically detects required environment variables for each app using different strategies based on app configuration:
891
+ # Events for another program
892
+ gkm deploy --stage production --json | jq -c 'select(.type == "app.deployed")'
893
+ ```
894
894
 
895
- | App Type | Detection Strategy |
896
- |----------|-------------------|
897
- | Frontend apps | Returns empty (no server secrets) |
898
- | Apps with `requiredEnv` | Uses explicit list from config |
899
- | Entry-based apps | Imports entry file in subprocess to capture `config.parse()` calls |
900
- | Route-based apps | Loads routes and calls `getEnvironment()` on each construct |
901
- | Apps with `envParser` only | Runs SnifferEnvironmentParser to detect usage |
895
+ **What every deploy does:** loads the config and discovers the constructs in a
896
+ sandbox, takes the stage's lock (a second run gets `StateLocked`; a crashed
897
+ run's lock is released with `gkm state:unlock`), checks every credential and
898
+ secret before anything changes, then runs the target's phases
899
+ (`provision`, `build`, `release`, `verify`) and reports each as events.
902
900
 
903
- For route-based apps, the sniffer loads each endpoint/function/cron/subscriber and collects environment variables from:
904
- - All services attached to the construct (via `service.register()`)
905
- - Publisher service (if any)
906
- - Auditor storage service (if any)
907
- - Database service (if any)
901
+ **Verified, or rolled back (Dokploy).** An app counts as released once Dokploy's deployment has finished and the app has answered its health route 2xx three times in a row (`/health` for a backend, `/` for a site; an app without a domain gets the deployment check only). Backends are released and checked before any site is released, and a failed backend stops the run. Whatever fails is pointed back at the image it ran before. Pending migrations are applied before any app is switched, in the deploy's sandbox, with each database URL handed over as a secret file. Tune the checks with `deploy.dokploy.verify: { deploymentTimeoutMs, healthCheckPath, healthyAfter, intervalMs, healthTimeoutMs }`.
908
902
 
909
- This allows the CLI to validate that all required secrets are configured before deployment, preventing runtime errors from missing environment variables.
903
+ At a terminal a missing Dokploy or registry login is asked for (and the Dokploy one stored). With `--json` or without a terminal nothing is asked: the deploy stops with `MissingCredential` and exits 1.
910
904
 
911
- **Configuration:**
905
+ **From a program:** the same deploy is `deploy()` from `@geekmidas/cli/deploy` — explicit `cwd`, an injected `CredentialProvider`, a logger and an `AbortSignal`; it returns a run you iterate for JSON events, plus a `result` promise. It never prompts, prints or exits.
912
906
 
913
907
  ```typescript
914
- // gkm.config.ts
915
- export default defineConfig({
916
- stages: { local: 'dev', deployed: ['prod'] },
917
- routes: 'src/endpoints/**/*.ts',
918
- envParser: './src/env.ts',
919
- logger: './src/logger.ts',
920
-
921
- docker: {
922
- registry: 'ghcr.io/myorg',
923
- imageName: 'my-api',
924
- },
908
+ import { deploy } from '@geekmidas/cli/deploy';
925
909
 
926
- // For Dokploy deployments
927
- providers: {
928
- dokploy: {
929
- endpoint: 'https://dokploy.example.com',
930
- projectId: 'proj_xxx',
931
- applicationId: 'app_xxx',
932
- },
933
- },
934
- });
910
+ const run = deploy({ cwd: '/srv/shop', stage: 'production', signal });
911
+ for await (const event of run) console.log(event.type);
912
+ const result = await run.result;
935
913
  ```
936
914
 
915
+ The project's own code — loading `gkm.config.ts`, discovering constructs, sniffing each app's environment, running migrations — runs in a `Sandbox`, never in the host process and never with the deploy's credentials. The default `LocalSandbox` is a child process with an allowlisted environment and a timeout per step; a host building repositories it does not trust passes its own isolating one (`sandbox`), and a config holding live objects then fails with `ConfigObjectNotSerializable`.
916
+
917
+ **Writing a target:** `defineTarget` from `@geekmidas/cli/target`, with the package's runtime declared in its `package.json` (`"gkm": { "runtime": "server" }`).
918
+
937
919
  **Environment Variables:**
938
920
  - `DOKPLOY_API_TOKEN`: API token for Dokploy (not needed if logged in via `gkm login`)
939
- - `GKM_MASTER_KEY`: Automatically set by Dokploy, or manually for Docker deployments
921
+ - `DOKPLOY_ENDPOINT`: Dokploy URL, if neither the stored login nor `deploy.dokploy.endpoint` gives one
922
+ - `DOCKER_REGISTRY_USERNAME` / `DOCKER_REGISTRY_PASSWORD`: a registry login, used only when Dokploy has no registry for `deploy.registry` and one has to be created
923
+ - `AWS_PROFILE`, or `AWS_ACCESS_KEY_ID` / `AWS_SECRET_ACCESS_KEY` / `AWS_SESSION_TOKEN`: the `sst` target's AWS credentials, handed to `sst deploy` only (the profile wins when both are set)
924
+ - `GKM_HOME`: where stage keys and stored logins live (default `~/.gkm`)
925
+ - `GKM_MASTER_KEY`: set in each container's runtime environment by the deploy; for an image you run yourself, from `.gkm/server/master.key`, which `gkm build --stage` writes (the key is never printed; output shows its fingerprint)
926
+
927
+ **Guides:**
928
+ [Deploy targets](https://geekmidas.github.io/toolbox/next/guide/deploy-targets) ·
929
+ [Writing a target](https://geekmidas.github.io/toolbox/next/guide/writing-a-target) ·
930
+ [Deploying from a program](https://geekmidas.github.io/toolbox/next/guide/deploy-api) ·
931
+ [The sandbox](https://geekmidas.github.io/toolbox/next/guide/sandbox) ·
932
+ [Deploy state](https://geekmidas.github.io/toolbox/next/guide/state) ·
933
+ [Running in production](https://geekmidas.github.io/toolbox/next/guide/production) ·
934
+ [Upgrading to 10.0.0-alpha](https://geekmidas.github.io/toolbox/next/guide/upgrading) ·
935
+ [Deprecated deploy APIs](https://geekmidas.github.io/toolbox/next/guide/deploy-deprecations)
936
+
937
+ ### `gkm deploy:rollback`
938
+
939
+ Put a stage's app back on the release before the one it runs (Dokploy). One app by default; `--atomic` rolls back every app that has an earlier release, for apps that only work together. It restores images only: migrations are forward-only.
940
+
941
+ ```bash
942
+ gkm deploy:rollback --stage production --app api
943
+ gkm deploy:rollback --stage production --atomic
944
+ ```
945
+
946
+ From a program: `rollbackStage({ cwd, stage, app })` from `@geekmidas/cli/deploy`.
940
947
 
941
948
  ### `gkm deploy:init`
942
949
 
943
- Initialize a new Dokploy deployment by creating a project and application via the Dokploy API. Automatically updates `gkm.config.ts` with the configuration.
950
+ Initialize a new Dokploy deployment by creating a project and application via the Dokploy API. Nothing is written to `gkm.config.ts`: the ids are rediscovered by name on each run and kept in the deploy state file.
944
951
 
945
952
  ```bash
946
953
  gkm deploy:init --project <name> --app <name> [options]
@@ -975,8 +982,7 @@ gkm deploy:init \
975
982
  1. Searches for existing project by name, or creates a new one
976
983
  2. Creates a new application in the project
977
984
  3. Configures registry if `--registry-id` is provided
978
- 4. Updates `gkm.config.ts` with the Dokploy configuration
979
- 5. Shows next steps for secrets and deployment
985
+ 4. Shows next steps for secrets and deployment
980
986
 
981
987
  ### `gkm deploy:list`
982
988
 
@@ -1002,6 +1008,24 @@ gkm deploy:list --registries
1002
1008
  gkm deploy:list --endpoint https://dokploy.example.com
1003
1009
  ```
1004
1010
 
1011
+ ### `gkm state:*`
1012
+
1013
+ Deploy state records what a stage's deploys created, so the next deploy finds
1014
+ it again. It lives where `state` in `gkm.config.ts` says: `.gkm/deploy-<stage>.json`
1015
+ by default, or SSM (`{ provider: 'ssm', region }`) or S3
1016
+ (`{ provider: 's3', bucket, region }`) for teams and CI. Every deploy holds the
1017
+ stage's lock and writes conditionally.
1018
+
1019
+ ```bash
1020
+ gkm state:show --stage production [--json] # ids, releases, pending resources; secrets masked
1021
+ gkm state:pull --stage production # remote → .gkm/
1022
+ gkm state:push --stage production # .gkm/ → remote, under the remote lock
1023
+ gkm state:diff --stage production
1024
+ gkm state:unlock --stage production # release a crashed deploy's lock
1025
+ ```
1026
+
1027
+ See [Deploy state](https://geekmidas.github.io/toolbox/next/guide/state).
1028
+
1005
1029
  ### Using Encrypted Credentials
1006
1030
 
1007
1031
  After deploying with secrets, your application decrypts credentials at runtime:
@@ -1025,7 +1049,7 @@ export const envParser = new EnvironmentParser({...process.env, ...Credentials})
1025
1049
 
1026
1050
  **How it works:**
1027
1051
  - At build time, secrets are encrypted with AES-256-GCM and embedded in the bundle
1028
- - An ephemeral master key is generated per build
1052
+ - An ephemeral master key is generated per build and written to `.gkm/server/master.key` (mode `0600`); the build prints its path and fingerprint, never the key
1029
1053
  - At runtime, `Credentials` decrypts using `GKM_MASTER_KEY` environment variable
1030
1054
  - In development (no embedded secrets), `Credentials` returns `{}`
1031
1055
 
@@ -1044,28 +1068,23 @@ The following commands are planned for future releases:
1044
1068
  The `gkm.config.ts` file defines how the CLI discovers and processes your endpoints:
1045
1069
 
1046
1070
  ```typescript
1047
- // Construct types accept a string, string[], or partitioned config
1048
- type Routes = string | string[] | PartitionedRoutes;
1049
-
1050
- interface PartitionedRoutes {
1051
- paths: string | string[];
1052
- partition: (filepath: string) => string;
1053
- }
1071
+ // Construct types accept a glob string or an array of them
1072
+ type Routes = string | string[];
1054
1073
 
1055
1074
  interface GkmConfig {
1056
- routes: Routes; // Glob patterns or partitioned config
1075
+ routes: Routes; // Glob patterns
1057
1076
  envParser: string; // Path to environment parser
1058
1077
  logger: string; // Path to logger configuration
1059
- functions?: Routes; // Glob patterns or partitioned config
1060
- crons?: Routes; // Glob patterns or partitioned config
1061
- subscribers?: Routes; // Glob patterns or partitioned config
1078
+ functions?: Routes; // Glob patterns
1079
+ crons?: Routes; // Glob patterns
1080
+ subscribers?: Routes; // Glob patterns
1062
1081
  runtime?: 'node' | 'bun'; // Runtime environment (default: 'node')
1063
1082
  telescope?: boolean | TelescopeConfig; // Telescope debugging config
1064
1083
  }
1065
1084
 
1066
1085
  interface TelescopeConfig {
1067
1086
  enabled?: boolean; // Enable/disable (default: true in dev)
1068
- path?: string; // Dashboard path (default: '/__telescope')
1087
+ path?: string; // Where the JSON API is mounted (default: '/__telescope')
1069
1088
  ignore?: string[]; // URL patterns to ignore
1070
1089
  recordBody?: boolean; // Record request/response bodies (default: true)
1071
1090
  maxEntries?: number; // Max entries to keep (default: 1000)
@@ -1077,7 +1096,7 @@ interface TelescopeConfig {
1077
1096
 
1078
1097
  #### `routes`
1079
1098
 
1080
- Glob pattern(s) to discover endpoint files. Can be a single pattern, array of patterns, or a partitioned config:
1099
+ Glob pattern(s) to discover endpoint files. Can be a single pattern or an array of patterns:
1081
1100
 
1082
1101
  ```typescript
1083
1102
  // Single pattern
@@ -1089,19 +1108,8 @@ routes: [
1089
1108
  'src/api/**/*.ts',
1090
1109
  'src/handlers/**/*.ts'
1091
1110
  ]
1092
-
1093
- // Partitioned — groups constructs in the generated manifest
1094
- routes: {
1095
- paths: './src/endpoints/**/*.ts',
1096
- partition: (filepath) => {
1097
- const match = filepath.match(/endpoints\/([^/]+)\//);
1098
- return match?.[1] ?? 'default';
1099
- },
1100
- }
1101
1111
  ```
1102
1112
 
1103
- The same partitioned format works for `functions`, `crons`, and `subscribers`. When a `partition` callback is provided, the generated manifest groups constructs by partition name (e.g., `manifest.routes.admin`). Without it, manifest fields remain flat arrays.
1104
-
1105
1113
  #### `envParser`
1106
1114
 
1107
1115
  Path to your environment parser configuration. Supports both default and named exports.
@@ -1134,7 +1142,7 @@ logger: './src/utils.ts#appLogger'
1134
1142
 
1135
1143
  #### `telescope`
1136
1144
 
1137
- Configuration for the Telescope debugging dashboard. Telescope is enabled by default when using `gkm dev`.
1145
+ Configuration for Telescope, which records requests, logs and exceptions and serves them as JSON. Telescope is enabled by default when using `gkm dev`.
1138
1146
 
1139
1147
  ```typescript
1140
1148
  // Disable telescope
@@ -1159,7 +1167,7 @@ telescope: {
1159
1167
  | Option | Type | Default | Description |
1160
1168
  |--------|------|---------|-------------|
1161
1169
  | `enabled` | `boolean` | `true` | Enable/disable Telescope |
1162
- | `path` | `string` | `/__telescope` | Dashboard URL path |
1170
+ | `path` | `string` | `/__telescope` | Where the JSON API is mounted |
1163
1171
  | `ignore` | `string[]` | `[]` | URL patterns to exclude from recording |
1164
1172
  | `recordBody` | `boolean` | `true` | Record request/response bodies |
1165
1173
  | `maxEntries` | `number` | `1000` | Maximum entries per type to keep |
@@ -1356,42 +1364,24 @@ interface AppSpec {
1356
1364
  }
1357
1365
  ```
1358
1366
 
1359
- ## Providers
1367
+ ## Build Targets
1360
1368
 
1361
- ### AWS API Gateway v1
1369
+ ### AWS
1362
1370
 
1363
- Generates Lambda handlers compatible with AWS API Gateway v1 (REST API).
1371
+ Generates one Lambda handler per construct. Endpoints get an API Gateway v2
1372
+ (HTTP API) adapter.
1364
1373
 
1365
1374
  ```bash
1366
- gkm build --provider aws-apigatewayv1
1367
- ```
1368
-
1369
- **Generated Handler:**
1370
- ```typescript
1371
- import { AmazonApiGatewayV1Endpoint } from '@geekmidas/constructs/aws';
1372
- import { myEndpoint } from '../src/routes/example.js';
1373
- import { envParser } from '../src/env.js';
1374
-
1375
- const adapter = new AmazonApiGatewayV1Endpoint(envParser, myEndpoint);
1376
-
1377
- export const handler = adapter.handler;
1378
- ```
1379
-
1380
- ### AWS API Gateway v2
1381
-
1382
- Generates Lambda handlers compatible with AWS API Gateway v2 (HTTP API).
1383
-
1384
- ```bash
1385
- gkm build --provider aws-apigatewayv2
1375
+ gkm build # with deploy: { default: 'sst' }
1376
+ gkm build --provider aws # whatever the deploy target
1386
1377
  ```
1387
1378
 
1388
1379
  **Generated Handler:**
1389
1380
  ```typescript
1390
1381
  import { AmazonApiGatewayV2Endpoint } from '@geekmidas/constructs/aws';
1391
- import { myEndpoint } from '../src/routes/example.js';
1392
- import { envParser } from '../src/env.js';
1382
+ import { myEndpoint } from '../../../src/routes/example.js';
1393
1383
 
1394
- const adapter = new AmazonApiGatewayV2Endpoint(envParser, myEndpoint);
1384
+ const adapter = new AmazonApiGatewayV2Endpoint(myEndpoint);
1395
1385
 
1396
1386
  export const handler = adapter.handler;
1397
1387
  ```
@@ -1433,139 +1423,141 @@ export default createApp;
1433
1423
 
1434
1424
  ## Output Structure
1435
1425
 
1436
- The CLI generates files in the `.gkm/<provider>` directory:
1426
+ Handlers are generated beside the app, in `<app>/.gkm/<target>`; the manifest
1427
+ at the workspace root, where `sst.config.ts` runs:
1437
1428
 
1438
1429
  ```
1439
- .gkm/
1440
- ├── aws-apigatewayv1/
1441
- │ ├── getUsers.ts # Individual Lambda handler
1442
- │ ├── createUser.ts # Individual Lambda handler
1443
- ├── server/
1444
- │ ├── app.ts # Server application
1445
- │ ├── endpoints.ts # Endpoint exports
1446
- ├── manifest/
1447
- │ ├── aws.ts # AWS manifest with types
1448
- │ └── server.ts # Server manifest with types
1449
- └── openapi.json # OpenAPI specification
1430
+ <root>/
1431
+ ├── .gkm/manifest/
1432
+ │ ├── aws.ts # AWS manifest with types
1433
+ │ └── server.ts # Server manifest with types
1434
+ └── apps/api/.gkm/
1435
+ ├── aws/
1436
+ │ ├── routes/getUsers.ts # One Lambda handler per endpoint
1437
+ │ ├── functions/
1438
+ │ ├── crons/
1439
+ │ ├── queues/
1440
+ │ └── subscribers/
1441
+ └── server/
1442
+ ├── app.ts # Server application
1443
+ └── endpoints.ts # Endpoint exports
1450
1444
  ```
1451
1445
 
1452
1446
  ### Build Manifest
1453
1447
 
1454
- The CLI generates TypeScript manifests with full type information in the `.gkm/manifest/` directory. These manifests export both the data and derived types for type-safe usage.
1448
+ The manifest is the application's, not an app's: the root `gkm build` builds
1449
+ every backend and writes it once, to `.gkm/manifest/aws.ts` or
1450
+ `.gkm/manifest/server.ts` at the workspace root. An app's own build writes no
1451
+ manifest. Every handler path in it is relative to the workspace root. `gkm init`
1452
+ adds a root tsconfig alias for the manifest, `@<project>/manifest`.
1455
1453
 
1456
- #### AWS Manifest (`.gkm/manifest/aws.ts`)
1454
+ It exports two values — every declared construct keyed by id, and the backends
1455
+ the build resolved — and the types derived from them:
1457
1456
 
1458
1457
  ```typescript
1459
- export const manifest = {
1460
- routes: [
1461
- {
1462
- path: '/users',
1463
- method: 'GET',
1464
- handler: '.gkm/aws-apigatewayv1/getUsers.handler',
1465
- authorizer: 'jwt',
1466
- },
1467
- {
1468
- path: '/users',
1469
- method: 'POST',
1470
- handler: '.gkm/aws-apigatewayv1/createUser.handler',
1471
- authorizer: 'jwt',
1472
- },
1473
- ],
1474
- functions: [
1475
- {
1476
- name: 'processData',
1477
- handler: '.gkm/aws-lambda/functions/processData.handler',
1478
- timeout: 60,
1479
- memorySize: 256,
1480
- },
1481
- ],
1482
- crons: [
1483
- {
1484
- name: 'dailyCleanup',
1485
- handler: '.gkm/aws-lambda/crons/dailyCleanup.handler',
1486
- schedule: 'rate(1 day)',
1487
- timeout: 300,
1488
- memorySize: 512,
1458
+ export const constructs = {
1459
+ Database: { id: 'Database', kind: 'database' },
1460
+ Api: {
1461
+ id: 'Api',
1462
+ kind: 'rest-api',
1463
+ path: 'apps/api',
1464
+ endpoints: [
1465
+ {
1466
+ id: 'ApiGET/users',
1467
+ method: 'GET',
1468
+ path: '/users',
1469
+ handler: 'apps/api/.gkm/aws/routes/getUsers.handler',
1470
+ dependencies: [{ target: 'Database', kind: 'database' }],
1471
+ authorizer: 'iam',
1472
+ },
1473
+ ],
1474
+ },
1475
+ ProcessData: {
1476
+ id: 'ProcessData',
1477
+ kind: 'function',
1478
+ handler: 'apps/api/.gkm/aws/functions/processData.handler',
1479
+ dependencies: [],
1480
+ },
1481
+ DailyCleanup: {
1482
+ id: 'DailyCleanup',
1483
+ kind: 'cron',
1484
+ handler: 'apps/api/.gkm/aws/crons/dailyCleanup.handler',
1485
+ schedule: 'rate(1 day)',
1486
+ dependencies: [{ target: 'Database', kind: 'database' }],
1487
+ },
1488
+ Emails: {
1489
+ id: 'Emails',
1490
+ kind: 'queue',
1491
+ // The queue's consumer is nested in it
1492
+ worker: {
1493
+ id: 'emails',
1494
+ handler: 'apps/api/.gkm/aws/queues/emails.handler',
1495
+ dependencies: [],
1489
1496
  },
1490
- ],
1491
- subscribers: [],
1492
- } as const;
1497
+ },
1498
+ Users: {
1499
+ id: 'Users',
1500
+ kind: 'topic',
1501
+ events: ['user.created'],
1502
+ // As are a topic's subscribers
1503
+ subscribers: [
1504
+ {
1505
+ id: 'onUser',
1506
+ handler: 'apps/api/.gkm/aws/subscribers/onUser.handler',
1507
+ events: ['user.created'],
1508
+ dependencies: [],
1509
+ },
1510
+ ],
1511
+ },
1512
+ } as const satisfies ConstructManifest;
1513
+
1514
+ export const backends = { cache: 'upstash', email: 'ses' } as const;
1493
1515
 
1494
1516
  // Derived types
1495
- export type Route = (typeof manifest.routes)[number];
1496
- export type Function = (typeof manifest.functions)[number];
1497
- export type Cron = (typeof manifest.crons)[number];
1498
- export type Subscriber = (typeof manifest.subscribers)[number];
1517
+ export type Ids = IdsOf<typeof constructs>;
1518
+ export type Construct<Id extends Ids> = DeclarationOf<typeof constructs, Id>;
1519
+ export type Kind = Construct<Ids>['kind'];
1499
1520
 
1500
1521
  // Useful union types
1501
- export type Authorizer = Route['authorizer'];
1502
- export type HttpMethod = Route['method'];
1503
- export type RoutePath = Route['path'];
1522
+ export type ProvidedKeys = AllProvidedKeys<typeof constructs>;
1523
+ export type Surfaces = IdsOfKind<typeof constructs, 'rest-api'>;
1524
+ export type CacheBackend = (typeof backends)['cache'];
1525
+ export type EmailBackend = (typeof backends)['email'];
1504
1526
  ```
1505
1527
 
1506
- When routes are partitioned, the manifest groups them by partition name and generates partition-aware types:
1528
+ A `RestApi` carries its endpoints, each with its method, path, handler, the
1529
+ dependencies it declared and its authorizer. On AWS the handler is the
1530
+ endpoint's own Lambda (`apps/api/.gkm/aws/routes/<export>.handler`); in the
1531
+ server manifest every endpoint's handler is the app entry
1532
+ (`apps/api/.gkm/server/app.ts`). Functions and crons are top-level
1533
+ declarations; a queue's worker and a topic's subscribers are nested in the
1534
+ queue or topic.
1507
1535
 
1508
- ```typescript
1509
- export const manifest = {
1510
- routes: {
1511
- "admin": [{ path: '/admin/users', method: 'GET', handler: '...', authorizer: 'jwt' }],
1512
- "default": [{ path: '/users', method: 'GET', handler: '...', authorizer: 'jwt' }],
1513
- },
1514
- functions: [...], // flat if not partitioned
1515
- } as const;
1536
+ #### Using the Manifest
1516
1537
 
1517
- // Partition-aware derived types
1518
- export type RoutePartition = keyof typeof manifest.routes;
1519
- export type Route<P extends RoutePartition = RoutePartition> =
1520
- (typeof manifest.routes)[P][number];
1521
- ```
1522
-
1523
- #### Server Manifest (`.gkm/manifest/server.ts`)
1538
+ On AWS, `fromManifest` from `@geekmidas/cloud/sst` provisions all of it —
1539
+ resources, each API's endpoints, queue consumers, functions and crons:
1524
1540
 
1525
1541
  ```typescript
1526
- export const manifest = {
1527
- app: {
1528
- handler: '.gkm/server/app.ts',
1529
- endpoints: '.gkm/server/endpoints.ts',
1530
- },
1531
- routes: [
1532
- { path: '/users', method: 'GET', authorizer: 'jwt' },
1533
- { path: '/users', method: 'POST', authorizer: 'jwt' },
1534
- ],
1535
- subscribers: [
1536
- { name: 'orderHandler', subscribedEvents: ['order.created'] },
1537
- ],
1538
- } as const;
1542
+ // sst.config.ts
1543
+ const { App, fromManifest, Stack } = await import('@geekmidas/cloud/sst');
1544
+ const { backends, constructs } = await import('./.gkm/manifest/aws.js');
1539
1545
 
1540
- // Derived types
1541
- export type Route = (typeof manifest.routes)[number];
1542
- export type Subscriber = (typeof manifest.subscribers)[number];
1543
-
1544
- // Useful union types
1545
- export type Authorizer = Route['authorizer'];
1546
- export type HttpMethod = Route['method'];
1547
- export type RoutePath = Route['path'];
1546
+ fromManifest(new Stack(app, 'Shop'), constructs, { Database: { vpc } }, backends);
1548
1547
  ```
1549
1548
 
1550
- #### Using Manifest Types
1551
-
1552
- Import the manifest types for type-safe infrastructure configuration:
1549
+ The types narrow to what was declared:
1553
1550
 
1554
1551
  ```typescript
1555
- import { manifest, type Route, type Authorizer } from './.gkm/manifest/aws';
1552
+ import { constructs, type Construct, type Surfaces } from './.gkm/manifest/aws';
1556
1553
 
1557
- // Type-safe route iteration
1558
- for (const route of manifest.routes) {
1559
- console.log(`${route.method} ${route.path} -> ${route.handler}`);
1560
- }
1554
+ const api: Construct<'Api'> = constructs.Api;
1561
1555
 
1562
- // Use union types for validation
1563
- function isValidMethod(method: string): method is HttpMethod {
1564
- return manifest.routes.some((r) => r.method === method);
1556
+ for (const endpoint of api.endpoints) {
1557
+ console.log(`${endpoint.method} ${endpoint.path} -> ${endpoint.handler}`);
1565
1558
  }
1566
1559
 
1567
- // Access authorizer names
1568
- const authorizers = new Set(manifest.routes.map((r) => r.authorizer));
1560
+ const surface: Surfaces = 'Api'; // any other id is a type error
1569
1561
  ```
1570
1562
 
1571
1563
  ## OpenAPI Generation
@@ -1648,62 +1640,25 @@ gkm openapi --output api-docs.json --json
1648
1640
 
1649
1641
  ## Deployment Examples
1650
1642
 
1651
- ### AWS Lambda with Serverless Framework
1643
+ Deploying goes through `gkm deploy` and a target, rather than through a
1644
+ hand-written server file or framework config:
1652
1645
 
1653
- ```yaml
1654
- # serverless.yml
1655
- service: my-api
1656
-
1657
- provider:
1658
- name: aws
1659
- runtime: nodejs18.x
1660
-
1661
- functions:
1662
- getUsers:
1663
- handler: .gkm/aws-apigatewayv1/getUsers.handler
1664
- events:
1665
- - http:
1666
- path: users
1667
- method: get
1668
-
1669
- createUser:
1670
- handler: .gkm/aws-apigatewayv1/createUser.handler
1671
- events:
1672
- - http:
1673
- path: users
1674
- method: post
1675
- ```
1676
-
1677
- ### Server Deployment
1646
+ ```bash
1647
+ # Dokploy (the default target)
1648
+ gkm deploy --stage production
1678
1649
 
1679
- ```typescript
1680
- // server.ts
1681
- import { createApp } from './.gkm/server/app.js';
1650
+ # One Docker Compose stack behind Caddy, on this machine
1651
+ gkm compose --stage production --tag v1.4.0
1682
1652
 
1683
- const app = createApp();
1653
+ # AWS through SST, with deploy: { default: 'sst' }
1654
+ gkm deploy --stage production
1684
1655
 
1685
- const port = process.env.PORT || 3000;
1686
- app.listen(port, () => {
1687
- console.log(`Server running on port ${port}`);
1688
- });
1656
+ # Only the Docker files, to build and run images yourself
1657
+ gkm docker --build --tag v1.4.0
1689
1658
  ```
1690
1659
 
1691
- ### Docker Deployment
1692
-
1693
- ```dockerfile
1694
- FROM node:18-alpine
1695
-
1696
- WORKDIR /app
1697
- COPY package*.json ./
1698
- RUN npm ci --only=production
1699
-
1700
- COPY . .
1701
- RUN npm run build
1702
-
1703
- EXPOSE 3000
1704
-
1705
- CMD ["node", "server.js"]
1706
- ```
1660
+ See [Deploy targets](https://geekmidas.github.io/toolbox/next/guide/deploy-targets) and the
1661
+ [deployment guide](https://geekmidas.github.io/toolbox/next/guide/deployment).
1707
1662
 
1708
1663
  ## Advanced Usage
1709
1664
 
@@ -1900,8 +1855,8 @@ Error: Failed to load gkm.config.ts: Invalid configuration
1900
1855
  # No endpoints found
1901
1856
  No endpoints found to process
1902
1857
 
1903
- # Invalid provider
1904
- Error: Unsupported provider: invalid-provider
1858
+ # Unknown deploy target
1859
+ Unknown deploy target "fly". Use one of dokploy, compose, sst, or name the package that provides it in gkm.config.ts: deploy: { targets: { "fly": '<package>' } }.
1905
1860
  ```
1906
1861
 
1907
1862
  ### OpenAPI Errors
@@ -1921,44 +1876,22 @@ Error: OpenAPI generation failed: Invalid endpoint schema
1921
1876
  "dev": "gkm dev",
1922
1877
  "dev:port": "gkm dev --port 8080",
1923
1878
  "build": "gkm build",
1924
- "build:lambda": "gkm build --provider aws-apigatewayv1",
1879
+ "build:lambda": "gkm build --provider aws",
1925
1880
  "build:server": "gkm build --provider server",
1926
- "docs": "gkm openapi --output src/api.ts"
1881
+ "client": "gkm openapi"
1927
1882
  }
1928
1883
  }
1929
1884
  ```
1930
1885
 
1931
1886
  ### CI/CD Pipeline
1932
1887
 
1933
- ```yaml
1934
- # .github/workflows/deploy.yml
1935
- name: Deploy API
1936
-
1937
- on:
1938
- push:
1939
- branches: [main]
1940
-
1941
- jobs:
1942
- deploy:
1943
- runs-on: ubuntu-latest
1944
-
1945
- steps:
1946
- - uses: actions/checkout@v3
1947
-
1948
- - name: Setup Node.js
1949
- uses: actions/setup-node@v3
1950
- with:
1951
- node-version: '18'
1952
-
1953
- - name: Install dependencies
1954
- run: npm ci
1955
-
1956
- - name: Build handlers
1957
- run: npm run build:lambda
1958
-
1959
- - name: Deploy to AWS
1960
- run: npx serverless deploy
1961
- ```
1888
+ `gkm init` writes a GitHub Actions deploy workflow that runs
1889
+ `gkm deploy --stage "$STAGE"` for each stage. Its credentials come from the
1890
+ stage's GitHub environment: `AWS_ROLE_ARN` for SST (set by
1891
+ `gkm deploy:github --stage <stage>`), or `DOKPLOY_API_TOKEN` and
1892
+ `DOKPLOY_ENDPOINT` for Dokploy. In any CI job, `gkm deploy --json` writes the
1893
+ deploy's events as JSON lines and never prompts. See
1894
+ [Deploying from GitHub Actions](https://geekmidas.github.io/toolbox/next/guide/deployment#deploying-from-github-actions).
1962
1895
 
1963
1896
  ## Troubleshooting
1964
1897
 
@@ -2015,8 +1948,8 @@ DEBUG=gkm:* npx gkm build
2015
1948
  ### Types
2016
1949
 
2017
1950
  ```typescript
2018
- // Provider options
2019
- type Provider = 'server' | 'aws-apigatewayv1' | 'aws-apigatewayv2';
1951
+ // Build targets
1952
+ type Provider = 'aws' | 'server';
2020
1953
 
2021
1954
  // Runtime options
2022
1955
  type Runtime = 'node' | 'bun';
@@ -2054,7 +1987,7 @@ interface TelescopeConfig {
2054
1987
 
2055
1988
  // Build options
2056
1989
  interface BuildOptions {
2057
- provider: Provider;
1990
+ provider?: Provider; // default: where gkm.config.ts deploys
2058
1991
  }
2059
1992
 
2060
1993
  // Dev options