void 0.10.12 → 0.20.0

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 (431) hide show
  1. package/AGENTS_TEMPLATE.md +6 -0
  2. package/{skills/void/docs/node_modules/void/node_modules/pglite-server/LICENSE.md → LICENSE} +1 -1
  3. package/README.md +34 -8
  4. package/dist/{auth-qgMlYp7Z.d.mts → auth-DkcFflXV.d.mts} +10 -11
  5. package/dist/auth-W9WII-mN.mjs +630 -0
  6. package/dist/{auth-cmd-BqsdZJp5.mjs → auth-cmd-CYVhSNFy.mjs} +4 -3
  7. package/dist/{auth-migrations-BTZ-ATvQ.mjs → auth-migrations-9vif1uj8.mjs} +53 -12
  8. package/dist/{better-auth-shared-BQooDxbw.mjs → better-auth-shared-CYw1T3k4.mjs} +7 -10
  9. package/dist/{better-auth-shared-DealXecJ.d.mts → better-auth-shared-DSCeohOK.d.mts} +10 -5
  10. package/dist/{build-cmd-Bujrv5q-.mjs → build-cmd-CkVD1uOh.mjs} +6 -4
  11. package/dist/{cache-C11V8Fxq.mjs → cache-QcUfR-ff.mjs} +9 -5
  12. package/dist/{cancel-deploy-fwFYF04b.mjs → cancel-deploy-DsvWKFTe.mjs} +3 -2
  13. package/dist/cf-access-AJ1ehiFR.mjs +42 -0
  14. package/dist/cf-access-DsSsZUPr.mjs +67 -0
  15. package/dist/cli/cli.d.mts +1 -1
  16. package/dist/cli/cli.mjs +1592 -153
  17. package/dist/cli/env-schema-probe.d.mts +48 -61
  18. package/dist/cli/env-schema-probe.mjs +10 -58
  19. package/dist/{client-Gb71-XkG.mjs → client-CyCHWSO_.mjs} +61 -463
  20. package/dist/cloudflare-auth-DRkGe7-s.mjs +170 -0
  21. package/dist/cloudflare-cmd-D3ME2GAe.mjs +62 -0
  22. package/dist/cloudflare-connect-BivMefMA.mjs +56 -0
  23. package/dist/cloudflare-operations-CPTpRW6d.mjs +566 -0
  24. package/dist/{config-BkTvs43g.mjs → config-BQFq7QvD.mjs} +85 -41
  25. package/dist/{config-CutEMNGJ.mjs → config-NOG_U1aK.mjs} +10 -15
  26. package/dist/connect-D9Yr-T5f.mjs +79 -0
  27. package/dist/{create-project-DsYvl3TB.mjs → create-project-DMV-csEm.mjs} +26 -16
  28. package/dist/database-provider.d.mts +21 -0
  29. package/dist/database-provider.mjs +6 -0
  30. package/dist/{db-DOiJMRt2.mjs → db-BxoUWL0F.mjs} +600 -115
  31. package/dist/{delete-mh6p-zkQ.mjs → delete-iJOqxBz1.mjs} +9 -6
  32. package/dist/{deploy-u7Rv9q_q.mjs → deploy-CcDoeBIf.mjs} +3451 -1986
  33. package/dist/dev-inbox-DkgRWLkW.mjs +307 -0
  34. package/dist/{discover-CJHyvYfR.mjs → discover-xvfrgJeo.mjs} +3 -3
  35. package/dist/{magic-string.es-ZQjdJFFn.mjs → dist-BR1quN_w.mjs} +570 -216
  36. package/dist/{dist-DaKKDf8D.mjs → dist-BrsS7cai.mjs} +17 -2
  37. package/dist/{dist-BuiRJkTd.mjs → dist-m40_XgNh.mjs} +48 -33
  38. package/dist/{domain-DiaNQbrl.mjs → domain-gu_iaHmn.mjs} +41 -4
  39. package/dist/dotenv-VQxupEUv.mjs +181 -0
  40. package/dist/edge.d.mts +2 -0
  41. package/dist/edge.mjs +2 -0
  42. package/dist/email-Ce6SQq-i.mjs +182 -0
  43. package/dist/email-r6DHJyAB.mjs +262 -0
  44. package/dist/{entry-D7yy4xVH.mjs → entry-DU3oDoQ3.mjs} +2 -2
  45. package/dist/env-D4Emu-M_.mjs +95 -0
  46. package/dist/env-DmU2To0C.mjs +73 -0
  47. package/dist/env-helpers-CyKtOBpj.d.mts +22 -0
  48. package/dist/env-public-D_6u46fX.d.mts +135 -0
  49. package/dist/{env-types-QBj-ndax.mjs → env-types-BNPhro-M.mjs} +2 -2
  50. package/dist/{env-validation-Dea3v3ej.mjs → env-validation-ENpMy6Ez.mjs} +68 -122
  51. package/dist/{gen-o_w-8yI8.mjs → gen-BKw6qHIg.mjs} +70 -15
  52. package/dist/{github-cmd-DKcGUNsj.mjs → github-cmd-DJS5Ab-H.mjs} +39 -31
  53. package/dist/{handler-Cjh8uM3Y.d.mts → handler-D1hLsObx.d.mts} +124 -122
  54. package/dist/{head-nmvOgFjd.d.mts → head-Do8P4puT.d.mts} +9 -8
  55. package/dist/{headers-nsHIFixA.mjs → headers-D8QfRX9Y.mjs} +12 -10
  56. package/dist/inbound-BJ70in1n.d.mts +354 -0
  57. package/dist/inbound-CNKxb3FY.mjs +694 -0
  58. package/dist/index.d.mts +61 -34
  59. package/dist/index.mjs +1048 -321
  60. package/dist/{init-3rgHKBVi.mjs → init-Dx5cgKqK.mjs} +329 -271
  61. package/dist/link-D_rm5sRH.mjs +52 -0
  62. package/dist/{list-CPwFDZ_c.mjs → list-M8XShti7.mjs} +37 -5
  63. package/dist/{runner-kapo9aPs.mjs → local-d1-BE8KBbMy.mjs} +116 -6
  64. package/dist/{login-BT3H8PN3.mjs → login-C8-UuLnp.mjs} +17 -15
  65. package/dist/{logs-Bt313ax7.mjs → logs-DwFU7dMW.mjs} +16 -2
  66. package/dist/mime-BJD7d_qL.mjs +1216 -0
  67. package/dist/neon-DHwd2zvC.mjs +54 -0
  68. package/dist/{node-Da0UcsGA.mjs → node-BkaXcpAc.mjs} +29 -8
  69. package/dist/operator-cmd-DYWRbWUA.mjs +348 -0
  70. package/dist/{agents-CtgBYqld.mjs → output-tFQLLj26.mjs} +676 -211
  71. package/dist/{package-json-Cx1osYo6.mjs → package-json-CPoWX79C.mjs} +1 -1
  72. package/dist/pages/client.d.mts +43 -41
  73. package/dist/pages/client.mjs +40 -33
  74. package/dist/pages/head-client.d.mts +10 -12
  75. package/dist/pages/head.d.mts +1 -1
  76. package/dist/pages/index.d.mts +37 -14
  77. package/dist/pages/index.mjs +5 -5
  78. package/dist/pages/islands-plugin.d.mts +25 -27
  79. package/dist/pages/islands-plugin.mjs +6 -4
  80. package/dist/pages/prefetch.d.mts +6 -7
  81. package/dist/pages/protocol.d.mts +2 -2
  82. package/dist/pages/protocol.mjs +2 -1
  83. package/dist/pages/serialize.d.mts +7 -8
  84. package/dist/platform-cmd-BEOVv1PN.mjs +123 -0
  85. package/dist/platform-domain-BszUfiS8.mjs +228 -0
  86. package/dist/platform-lifecycle-CjSr6xf0.mjs +4450 -0
  87. package/dist/platform-management-W30iCaTL.mjs +698 -0
  88. package/dist/platform-recovery-pHHv4ZSg.mjs +99 -0
  89. package/dist/{plugin-inference-DMeavIJ6.mjs → plugin-inference-BDRfZngg.mjs} +35 -19
  90. package/dist/prepare-BfJvFUtJ.mjs +14 -0
  91. package/dist/{prepare-BoKHgMNx.mjs → prepare-CBetXvsN.mjs} +15 -24
  92. package/dist/{preset-BjyR3lzz.mjs → preset-lAy0B0BQ.mjs} +25 -212
  93. package/dist/{project-cmd-D_w-4w5B.mjs → project-cmd-DCpk1cDt.mjs} +25 -12
  94. package/dist/{project-paths-BQd7OmIo.mjs → project-paths-SK8nMHPp.mjs} +3 -1
  95. package/dist/{project-tsconfig-B-QtXjLQ.mjs → project-tsconfig-Ql2XsSQp.mjs} +2 -2
  96. package/dist/{protocol-Bnb0LFp3.d.mts → protocol-C-pqYJjE.d.mts} +3 -4
  97. package/dist/{provision-rShh6MKY.mjs → provision-Blnstcm2.mjs} +78 -45
  98. package/dist/r2-conditions-D1Wk8i7b.mjs +30 -0
  99. package/dist/{requests-B8sZxaFM.mjs → requests-Dn8Vheh1.mjs} +5 -3
  100. package/dist/{resolve-project-BBMtLLV9.mjs → resolve-project--Vxawf7z.mjs} +2 -2
  101. package/dist/rollback-CtlPXEBi.mjs +166 -0
  102. package/dist/{rolldown-runtime-DJK8HYOj.mjs → rolldown-runtime-rQ84J-ij.mjs} +1 -1
  103. package/dist/{route-types-COI2DsZv.mjs → route-types-Da-DpyUp.mjs} +85 -26
  104. package/dist/routes-stub.d.mts +22 -23
  105. package/dist/runner-mysql-CgRFl3s6.mjs +61 -0
  106. package/dist/{runner-pg-CHM76xuC.mjs → runner-pg-DCkWPsWS.mjs} +18 -6
  107. package/dist/runtime/ai.d.mts +21 -14
  108. package/dist/runtime/ai.mjs +5 -4
  109. package/dist/runtime/auth-client-react.d.mts +3 -5
  110. package/dist/runtime/auth-client-solid.d.mts +3 -5
  111. package/dist/runtime/auth-client-svelte.d.mts +3 -5
  112. package/dist/runtime/auth-client-vue.d.mts +3 -5
  113. package/dist/runtime/auth-client.d.mts +3 -5
  114. package/dist/runtime/auth.d.mts +1 -1
  115. package/dist/runtime/better-auth-mysql.d.mts +10 -0
  116. package/dist/runtime/better-auth-mysql.mjs +49 -0
  117. package/dist/runtime/better-auth-pg.d.mts +8 -9
  118. package/dist/runtime/better-auth-pg.mjs +2 -2
  119. package/dist/runtime/better-auth.d.mts +8 -9
  120. package/dist/runtime/better-auth.mjs +2 -2
  121. package/dist/runtime/client-react.d.mts +1 -1
  122. package/dist/runtime/client-solid.d.mts +1 -1
  123. package/dist/runtime/client-svelte.d.mts +1 -1
  124. package/dist/runtime/client-vue.d.mts +1 -1
  125. package/dist/runtime/client.d.mts +1 -1
  126. package/dist/runtime/db-mysql.d.mts +2 -0
  127. package/dist/runtime/db-mysql.mjs +1 -0
  128. package/dist/runtime/db.d.mts +10 -11
  129. package/dist/runtime/durable.d.mts +47 -0
  130. package/dist/runtime/durable.mjs +146 -0
  131. package/dist/runtime/email/testing.d.mts +112 -0
  132. package/dist/runtime/email/testing.mjs +283 -0
  133. package/dist/runtime/email.d.mts +30 -0
  134. package/dist/runtime/email.mjs +573 -0
  135. package/dist/runtime/env-helpers.d.mts +2 -2
  136. package/dist/runtime/env-helpers.mjs +5 -42
  137. package/dist/runtime/env-public-client.d.mts +10 -11
  138. package/dist/runtime/env-public-client.mjs +1 -1
  139. package/dist/runtime/env-public.d.mts +2 -2
  140. package/dist/runtime/env-public.mjs +104 -49
  141. package/dist/runtime/env.d.mts +19 -18
  142. package/dist/runtime/env.mjs +15 -2
  143. package/dist/runtime/fetch-stream.d.mts +20 -21
  144. package/dist/runtime/fetch.d.mts +15 -16
  145. package/dist/runtime/handler.d.mts +1 -1
  146. package/dist/runtime/isr.d.mts +21 -22
  147. package/dist/runtime/isr.mjs +26 -8
  148. package/dist/runtime/kv.d.mts +9 -10
  149. package/dist/runtime/live-client.d.mts +5 -7
  150. package/dist/runtime/live-client.mjs +9 -7
  151. package/dist/runtime/live-server.d.mts +4 -5
  152. package/dist/runtime/live.d.mts +22 -24
  153. package/dist/runtime/live.mjs +1 -1
  154. package/dist/runtime/log.d.mts +16 -17
  155. package/dist/runtime/migration-handler-mysql.d.mts +4 -0
  156. package/dist/runtime/migration-handler-mysql.mjs +81 -0
  157. package/dist/runtime/migration-handler-pg.d.mts +2 -4
  158. package/dist/runtime/migration-handler.d.mts +5 -6
  159. package/dist/runtime/migration-handler.mjs +4 -3
  160. package/dist/runtime/queues.d.mts +3 -4
  161. package/dist/runtime/queues.mjs +2 -1
  162. package/dist/runtime/remote/binding-handler.d.mts +10 -12
  163. package/dist/runtime/remote/binding-handler.mjs +24 -3
  164. package/dist/runtime/remote/index.d.mts +5 -6
  165. package/dist/runtime/remote/index.mjs +21 -18
  166. package/dist/runtime/response.d.mts +10 -11
  167. package/dist/runtime/sandbox.d.mts +56 -55
  168. package/dist/runtime/sandbox.mjs +57 -49
  169. package/dist/runtime/schema-mysql.d.mts +1 -0
  170. package/dist/runtime/schema-mysql.mjs +2 -0
  171. package/dist/runtime/seed.d.mts +14 -9
  172. package/dist/runtime/sse-client.d.mts +6 -7
  173. package/dist/runtime/sse.d.mts +11 -12
  174. package/dist/runtime/storage.d.mts +3 -4
  175. package/dist/runtime/validator.d.mts +1 -1
  176. package/dist/runtime/ws-server.d.mts +12 -12
  177. package/dist/runtime/ws-server.mjs +32 -4
  178. package/dist/runtime/ws.d.mts +19 -21
  179. package/dist/{scan-DYXkrasO.mjs → scan-BMH4rzlv.mjs} +53 -31
  180. package/dist/{scan-DEwlM_Xy.mjs → scan-CpK-57ug.mjs} +9 -5
  181. package/dist/{secret-Dt32J6RI.mjs → secret-BqTxGqki.mjs} +62 -5
  182. package/dist/{skills-CLjN0uUO.mjs → skills-Q46GZMO-.mjs} +6 -4
  183. package/dist/{standard-schema-DJ0HW7QP.d.mts → standard-schema-Fo_vCAZh.d.mts} +6 -6
  184. package/dist/{subcommand-prompt-BzV8iQZo.mjs → subcommand-prompt-WfySCQ7S.mjs} +67 -48
  185. package/dist/sveltekit.d.mts +12 -11
  186. package/dist/sveltekit.mjs +1 -1
  187. package/dist/types-BAp5AEBU.d.mts +79 -0
  188. package/dist/types-CKWnYgfy.d.mts +1 -0
  189. package/dist/{validate-Cw_RLeTj.mjs → validate-Bihr8WBi.mjs} +3 -3
  190. package/dist/wrangler--imS8n0d.mjs +1796 -0
  191. package/dist/{yarn-pnp-DJn3SAHF.mjs → yarn-pnp-DxSInkzL.mjs} +1 -1
  192. package/package.json +79 -65
  193. package/schema.json +35 -3
  194. package/skills/migrate-vite-cloudflare-to-void/SKILL.md +1 -1
  195. package/skills/void/SKILL.md +59 -2
  196. package/skills/void/docs/guide/ai.md +32 -14
  197. package/skills/void/docs/guide/app-types.md +6 -6
  198. package/skills/void/docs/guide/auth.md +14 -16
  199. package/skills/void/docs/guide/database/d1.md +6 -0
  200. package/skills/void/docs/guide/database/mysql.md +60 -0
  201. package/skills/void/docs/guide/database/postgresql.md +14 -9
  202. package/skills/void/docs/guide/database.md +39 -26
  203. package/skills/void/docs/guide/deployment.md +163 -22
  204. package/skills/void/docs/guide/durable-state.md +140 -0
  205. package/skills/void/docs/guide/edge/headers.md +5 -5
  206. package/skills/void/docs/guide/edge/prerendering.md +2 -0
  207. package/skills/void/docs/guide/edge/revalidation.md +21 -6
  208. package/skills/void/docs/guide/edge/rewrites.md +18 -14
  209. package/skills/void/docs/guide/edge/static-assets.md +23 -8
  210. package/skills/void/docs/guide/email.md +609 -0
  211. package/skills/void/docs/guide/env-migration.md +109 -0
  212. package/skills/void/docs/guide/env-vars.md +70 -248
  213. package/skills/void/docs/guide/index.md +15 -17
  214. package/skills/void/docs/guide/jobs.md +8 -5
  215. package/skills/void/docs/guide/live.md +7 -15
  216. package/skills/void/docs/guide/pages-routing/actions-and-forms.md +8 -4
  217. package/skills/void/docs/guide/pages-routing/islands.md +3 -3
  218. package/skills/void/docs/guide/pages-routing/loaders.md +6 -4
  219. package/skills/void/docs/guide/pages-routing/overview.md +7 -7
  220. package/skills/void/docs/guide/platform-administration.md +212 -0
  221. package/skills/void/docs/guide/platform-development.md +235 -0
  222. package/skills/void/docs/guide/queues.md +10 -10
  223. package/skills/void/docs/guide/quickstart.md +46 -67
  224. package/skills/void/docs/guide/remote-dev.md +8 -6
  225. package/skills/void/docs/guide/sandboxes.md +33 -16
  226. package/skills/void/docs/guide/self-hosted-platform.md +553 -0
  227. package/skills/void/docs/guide/server-routing.md +25 -5
  228. package/skills/void/docs/guide/sse.md +4 -4
  229. package/skills/void/docs/guide/ssg.md +5 -3
  230. package/skills/void/docs/guide/storage.md +2 -2
  231. package/skills/void/docs/guide/websockets.md +18 -7
  232. package/skills/void/docs/index.md +3 -3
  233. package/skills/void/docs/integrations/agents.md +6 -64
  234. package/skills/void/docs/integrations/cloudflare.md +165 -146
  235. package/skills/void/docs/integrations/frameworks/analog.md +4 -4
  236. package/skills/void/docs/integrations/frameworks/astro.md +5 -5
  237. package/skills/void/docs/integrations/frameworks/nuxt.md +5 -5
  238. package/skills/void/docs/integrations/frameworks/overview.md +3 -3
  239. package/skills/void/docs/integrations/frameworks/react-router.md +3 -3
  240. package/skills/void/docs/integrations/frameworks/sveltekit.md +3 -3
  241. package/skills/void/docs/integrations/frameworks/tanstack-start.md +2 -2
  242. package/skills/void/docs/integrations/nodejs-bun-deno.md +11 -4
  243. package/skills/void/docs/reference/api.md +42 -6
  244. package/skills/void/docs/reference/cli.md +637 -159
  245. package/skills/void/docs/reference/config.md +80 -25
  246. package/skills/void/docs/reference/resource-inference.md +13 -9
  247. package/skills/void/docs/reference/structure.md +10 -11
  248. package/AGENT_PROMPT.md +0 -19
  249. package/dist/cf-access-Bqw81xAf.mjs +0 -22
  250. package/dist/env-CZy5MorI.mjs +0 -299
  251. package/dist/env-helpers-z4stu8uc.d.mts +0 -52
  252. package/dist/env-mask-Dd47NbR6.mjs +0 -90
  253. package/dist/env-public-BfiLcMBk.d.mts +0 -140
  254. package/dist/link-CdGHSIy-.mjs +0 -45
  255. package/dist/mcp-DoM3_nhd.mjs +0 -377
  256. package/dist/project-paths-GpziKeQQ.d.mts +0 -25
  257. package/dist/providers-BNKRacMr.d.mts +0 -7
  258. package/dist/proxy-D-3_D-Gl.mjs +0 -5
  259. package/dist/rollback-CkvTFXx5.mjs +0 -90
  260. package/dist/runtime/isr-cache.d.mts +0 -207
  261. package/dist/runtime/isr-cache.mjs +0 -523
  262. package/dist/types-lLjNE9Qp.d.mts +0 -51
  263. package/getting-started-prompt.txt +0 -28
  264. package/skills/void/command/void.md +0 -7
  265. package/skills/void/docs/integrations/auth-providers.md +0 -0
  266. package/skills/void/docs/integrations/payment-processors.md +0 -0
  267. package/skills/void/docs/node_modules/@iconify/vue/README.md +0 -408
  268. package/skills/void/docs/node_modules/@iconify/vue/offline/readme.md +0 -5
  269. package/skills/void/docs/node_modules/@voidzero-dev/vitepress-theme/README.md +0 -103
  270. package/skills/void/docs/node_modules/oxc-minify/README.md +0 -78
  271. package/skills/void/docs/node_modules/reka-ui/README.md +0 -80
  272. package/skills/void/docs/node_modules/vitepress/README.md +0 -28
  273. package/skills/void/docs/node_modules/vitepress/template/api-examples.md +0 -49
  274. package/skills/void/docs/node_modules/vitepress/template/index.md +0 -28
  275. package/skills/void/docs/node_modules/vitepress/template/markdown-examples.md +0 -85
  276. package/skills/void/docs/node_modules/vitepress-plugin-group-icons/README.md +0 -101
  277. package/skills/void/docs/node_modules/void/AGENT_PROMPT.md +0 -19
  278. package/skills/void/docs/node_modules/void/CLAUDE.md +0 -219
  279. package/skills/void/docs/node_modules/void/README.md +0 -90
  280. package/skills/void/docs/node_modules/void/node_modules/@clack/prompts/CHANGELOG.md +0 -685
  281. package/skills/void/docs/node_modules/void/node_modules/@clack/prompts/README.md +0 -396
  282. package/skills/void/docs/node_modules/void/node_modules/@cloudflare/sandbox/README.md +0 -219
  283. package/skills/void/docs/node_modules/void/node_modules/@cloudflare/vite-plugin/README.md +0 -37
  284. package/skills/void/docs/node_modules/void/node_modules/@cloudflare/workers-types/README.md +0 -135
  285. package/skills/void/docs/node_modules/void/node_modules/@electric-sql/pglite/README.md +0 -189
  286. package/skills/void/docs/node_modules/void/node_modules/@hono/oauth-providers/CHANGELOG.md +0 -143
  287. package/skills/void/docs/node_modules/void/node_modules/@hono/oauth-providers/README.md +0 -1272
  288. package/skills/void/docs/node_modules/void/node_modules/@napi-rs/keyring/README.md +0 -19
  289. package/skills/void/docs/node_modules/void/node_modules/@types/better-sqlite3/README.md +0 -15
  290. package/skills/void/docs/node_modules/void/node_modules/@types/node/README.md +0 -15
  291. package/skills/void/docs/node_modules/void/node_modules/@types/pg/README.md +0 -15
  292. package/skills/void/docs/node_modules/void/node_modules/@types/proper-lockfile/README.md +0 -51
  293. package/skills/void/docs/node_modules/void/node_modules/@typescript/native-preview/README.md +0 -22
  294. package/skills/void/docs/node_modules/void/node_modules/@typescript/native-preview/vendor/vscode-jsonrpc/README.md +0 -69
  295. package/skills/void/docs/node_modules/void/node_modules/@void/md/README.md +0 -153
  296. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/@shikijs/engine-javascript/README.md +0 -9
  297. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/@shikijs/transformers/README.md +0 -9
  298. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/@types/node/README.md +0 -15
  299. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/gray-matter/CHANGELOG.md +0 -24
  300. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/gray-matter/README.md +0 -565
  301. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-exit/README.md +0 -127
  302. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-it-anchor/README.md +0 -600
  303. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-it-attrs/README.md +0 -386
  304. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-it-container/README.md +0 -95
  305. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-it-emoji/README.md +0 -101
  306. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/markdown-it-footnote/README.md +0 -135
  307. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/pathslash/README.md +0 -64
  308. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/shiki/README.md +0 -15
  309. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/tinyglobby/README.md +0 -25
  310. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/AGENTS.md +0 -16
  311. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/README.md +0 -220
  312. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/build.md +0 -21
  313. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/check.md +0 -35
  314. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/create.md +0 -70
  315. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/fmt.md +0 -20
  316. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/index.md +0 -35
  317. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/lint.md +0 -26
  318. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/pack.md +0 -17
  319. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/run.md +0 -364
  320. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/staged.md +0 -15
  321. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/config/test.md +0 -18
  322. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/automatic-data-tracking.md +0 -145
  323. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/build.md +0 -40
  324. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/cache.md +0 -107
  325. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/check.md +0 -60
  326. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/ci.md +0 -62
  327. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/commit-hooks.md +0 -60
  328. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/create.md +0 -341
  329. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/dev.md +0 -24
  330. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/docker.md +0 -175
  331. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/env.md +0 -167
  332. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/fmt.md +0 -41
  333. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/github-actions-cache.md +0 -165
  334. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/ide-integration.md +0 -101
  335. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/implode.md +0 -23
  336. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/index.md +0 -134
  337. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/install.md +0 -199
  338. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/lint.md +0 -50
  339. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/migrate-rules.md +0 -347
  340. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/migrate.md +0 -197
  341. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/monorepo.md +0 -176
  342. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/pack.md +0 -69
  343. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/run.md +0 -356
  344. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/test.md +0 -35
  345. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/troubleshooting.md +0 -108
  346. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/upgrade.md +0 -101
  347. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/vpx.md +0 -66
  348. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/guide/why.md +0 -39
  349. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/index.md +0 -12
  350. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/docs/team.md +0 -35
  351. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/templates/generator/README.md +0 -35
  352. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vite-plus/templates/monorepo/README.md +0 -29
  353. package/skills/void/docs/node_modules/void/node_modules/@void/md/node_modules/vue/README.md +0 -58
  354. package/skills/void/docs/node_modules/void/node_modules/arktype/README.md +0 -165
  355. package/skills/void/docs/node_modules/void/node_modules/better-auth/LICENSE.md +0 -20
  356. package/skills/void/docs/node_modules/void/node_modules/better-auth/README.md +0 -32
  357. package/skills/void/docs/node_modules/void/node_modules/better-sqlite3/README.md +0 -99
  358. package/skills/void/docs/node_modules/void/node_modules/blake3-jit/README.md +0 -108
  359. package/skills/void/docs/node_modules/void/node_modules/drizzle-arktype/README.md +0 -51
  360. package/skills/void/docs/node_modules/void/node_modules/drizzle-kit/README.md +0 -79
  361. package/skills/void/docs/node_modules/void/node_modules/drizzle-orm/README.md +0 -44
  362. package/skills/void/docs/node_modules/void/node_modules/drizzle-valibot/README.md +0 -51
  363. package/skills/void/docs/node_modules/void/node_modules/drizzle-zod/README.md +0 -65
  364. package/skills/void/docs/node_modules/void/node_modules/es-module-lexer/README.md +0 -403
  365. package/skills/void/docs/node_modules/void/node_modules/estree-walker/README.md +0 -48
  366. package/skills/void/docs/node_modules/void/node_modules/hono/README.md +0 -85
  367. package/skills/void/docs/node_modules/void/node_modules/ignore/README.md +0 -452
  368. package/skills/void/docs/node_modules/void/node_modules/jsonc-parser/CHANGELOG.md +0 -76
  369. package/skills/void/docs/node_modules/void/node_modules/jsonc-parser/LICENSE.md +0 -21
  370. package/skills/void/docs/node_modules/void/node_modules/jsonc-parser/README.md +0 -364
  371. package/skills/void/docs/node_modules/void/node_modules/jsonc-parser/SECURITY.md +0 -41
  372. package/skills/void/docs/node_modules/void/node_modules/magic-string/README.md +0 -325
  373. package/skills/void/docs/node_modules/void/node_modules/ofetch/README.md +0 -398
  374. package/skills/void/docs/node_modules/void/node_modules/pathslash/README.md +0 -64
  375. package/skills/void/docs/node_modules/void/node_modules/pg/README.md +0 -96
  376. package/skills/void/docs/node_modules/void/node_modules/pglite-server/README.md +0 -135
  377. package/skills/void/docs/node_modules/void/node_modules/picocolors/README.md +0 -21
  378. package/skills/void/docs/node_modules/void/node_modules/proper-lockfile/CHANGELOG.md +0 -108
  379. package/skills/void/docs/node_modules/void/node_modules/proper-lockfile/README.md +0 -183
  380. package/skills/void/docs/node_modules/void/node_modules/tinyglobby/README.md +0 -25
  381. package/skills/void/docs/node_modules/void/node_modules/valibot/LICENSE.md +0 -9
  382. package/skills/void/docs/node_modules/void/node_modules/valibot/README.md +0 -94
  383. package/skills/void/docs/node_modules/void/node_modules/vite-plus/AGENTS.md +0 -16
  384. package/skills/void/docs/node_modules/void/node_modules/vite-plus/README.md +0 -220
  385. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/build.md +0 -21
  386. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/check.md +0 -35
  387. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/create.md +0 -70
  388. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/fmt.md +0 -20
  389. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/index.md +0 -35
  390. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/lint.md +0 -26
  391. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/pack.md +0 -17
  392. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/run.md +0 -364
  393. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/staged.md +0 -15
  394. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/config/test.md +0 -18
  395. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/automatic-data-tracking.md +0 -145
  396. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/build.md +0 -40
  397. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/cache.md +0 -107
  398. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/check.md +0 -60
  399. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/ci.md +0 -62
  400. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/commit-hooks.md +0 -60
  401. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/create.md +0 -341
  402. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/dev.md +0 -24
  403. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/docker.md +0 -175
  404. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/env.md +0 -167
  405. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/fmt.md +0 -41
  406. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/github-actions-cache.md +0 -165
  407. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/ide-integration.md +0 -101
  408. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/implode.md +0 -23
  409. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/index.md +0 -134
  410. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/install.md +0 -199
  411. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/lint.md +0 -50
  412. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/migrate-rules.md +0 -347
  413. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/migrate.md +0 -197
  414. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/monorepo.md +0 -176
  415. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/pack.md +0 -69
  416. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/run.md +0 -356
  417. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/test.md +0 -35
  418. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/troubleshooting.md +0 -108
  419. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/upgrade.md +0 -101
  420. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/vpx.md +0 -66
  421. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/guide/why.md +0 -39
  422. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/index.md +0 -12
  423. package/skills/void/docs/node_modules/void/node_modules/vite-plus/docs/team.md +0 -35
  424. package/skills/void/docs/node_modules/void/node_modules/vite-plus/templates/generator/README.md +0 -35
  425. package/skills/void/docs/node_modules/void/node_modules/vite-plus/templates/monorepo/README.md +0 -29
  426. package/skills/void/docs/node_modules/void/node_modules/wrangler/README.md +0 -63
  427. package/skills/void/docs/node_modules/void/node_modules/zod/README.md +0 -191
  428. package/skills/void/docs/node_modules/void/skills/migrate-vite-cloudflare-to-void/SKILL.md +0 -175
  429. package/skills/void/docs/node_modules/void/skills/void/SKILL.md +0 -76
  430. package/skills/void/docs/node_modules/void/skills/void/command/void.md +0 -7
  431. package/skills/void/docs/node_modules/void/test/e2e/README.md +0 -85
@@ -4,7 +4,7 @@ outline: deep
4
4
 
5
5
  # Cloudflare
6
6
 
7
- Void runs on Cloudflare Workers. This page covers how bindings work, how the plugin merges your wrangler config, and how to deploy directly to your own Cloudflare account.
7
+ Void runs on Cloudflare Workers. This page covers how bindings work, how the plugin merges Cloudflare configuration, and how to deploy directly to your own Cloudflare account.
8
8
 
9
9
  ## Bindings
10
10
 
@@ -34,7 +34,7 @@ export const GET = defineHandler(async (c) => {
34
34
  });
35
35
  ```
36
36
 
37
- `c.env` is fully typed via `CloudContext` -- no manual type declarations needed.
37
+ `CloudContext` provides the types for `c.env`, so you don't need to declare them yourself.
38
38
 
39
39
  ### Via `cloudflare:workers` import
40
40
 
@@ -85,31 +85,32 @@ This augments the `Cloudflare.Env` interface with `DB`, `KV`, `STORAGE`, `AI`, a
85
85
 
86
86
  ### Available bindings
87
87
 
88
- | Binding | Type | Trigger |
89
- | --------- | ------------- | --------------------------------------------------------------- |
90
- | `DB` | `D1Database` | `env.DB` / `c.env.DB` or `import from "void/db"` |
91
- | `KV` | `KVNamespace` | `env.KV` / `c.env.KV` or `import from "void/kv"` |
92
- | `STORAGE` | `R2Bucket` | `env.STORAGE` / `c.env.STORAGE` or `import from "void/storage"` |
93
- | `AI` | `Ai` | `env.AI` / `c.env.AI` or `import from "void/ai"` |
94
- | `QUEUE_*` | `Queue<T>` | `defineQueue()` or `import { queues } from "void/queues"` |
88
+ | Binding | Type | Trigger |
89
+ | ---------------- | ------------------------ | --------------------------------------------------------------- |
90
+ | `DB` | `D1Database` | `env.DB` / `c.env.DB` or `import from "void/db"` |
91
+ | `KV` | `KVNamespace` | `env.KV` / `c.env.KV` or `import from "void/kv"` |
92
+ | `STORAGE` | `R2Bucket` | `env.STORAGE` / `c.env.STORAGE` or `import from "void/storage"` |
93
+ | `AI` | `Ai` | `env.AI` / `c.env.AI` or `import from "void/ai"` |
94
+ | `QUEUE_*` | `Queue<T>` | `defineQueue()` or `import { queues } from "void/queues"` |
95
+ | filename-derived | `DurableObjectNamespace` | module in `durable-objects/` |
95
96
 
96
97
  Bindings are [inferred automatically](../reference/resource-inference.md) by scanning your source files for import and access patterns. You can also set them explicitly in `void.json`:
97
98
 
98
99
  ```json
99
100
  {
100
101
  "inference": {
101
- "bindings": { "db": true, "kv": true, "storage": false, "ai": true }
102
+ "bindings": { "db": true, "kv": true, "storage": false, "ai": "MY_AI" }
102
103
  }
103
104
  }
104
105
  ```
105
106
 
106
- `db`, `kv`, and `storage` accept a string to customize the binding name (e.g. `"db": "MY_DB"`). `ai` only accepts a boolean.
107
+ `db`, `kv`, `storage`, and `ai` accept a string to customize the binding name (for example, `"db": "MY_DB"` or `"ai": "MY_AI"`). `email` is a boolean feature switch.
107
108
 
108
109
  See [Configuration](../reference/config.md) for details.
109
110
 
110
- ### Wrangler passthrough
111
+ ### Cloudflare configuration passthrough
111
112
 
112
- You can set non-binding wrangler fields like `compatibility_date` and `compatibility_flags` in `void.json`:
113
+ You can set non-binding Cloudflare fields like `compatibility_date` and `compatibility_flags` in `void.json`:
113
114
 
114
115
  ```json
115
116
  {
@@ -120,18 +121,18 @@ You can set non-binding wrangler fields like `compatibility_date` and `compatibi
120
121
  }
121
122
  ```
122
123
 
123
- For environment variables, use `.env` files for local values and secrets. Void automatically loads `.env` files through Vite's `loadEnv` and merges them into the worker's `vars` bindings:
124
+ For environment variables, declare the schema in `env.ts` and put local values in the single root `.env` file. Void loads `.env` into local development bindings only; it never becomes production configuration:
124
125
 
125
126
  ```bash
126
127
  # .env
127
128
  API_URL=https://api.example.com
128
129
  ```
129
130
 
130
- Binding arrays such as `d1_databases`, `kv_namespaces`, and `r2_buckets` are not allowed in the `worker` field because Void manages bindings for you. If you need custom bindings with real resource IDs, add a `wrangler.jsonc` to the project root instead. See [Wrangler config merging](#wrangler-config-merging) for details.
131
+ Binding arrays such as `d1_databases`, `kv_namespaces`, and `r2_buckets` are not allowed in the `worker` field because Void manages bindings for you. If you need custom bindings with real resource IDs, add a `wrangler.jsonc` to the project root instead. See [Cloudflare config merging](#cloudflare-config-merging) for details.
131
132
 
132
- For non-secret plain-text defaults, you can also set `worker.vars` in `void.json`. Values from `.env` files override `worker.vars`.
133
+ For non-secret plain-text defaults, you can also set `worker.vars` in `void.json`. Local `.env` values override `worker.vars` during development. Production builds reject any `worker.vars` name that is declared as a server key in `env.ts`; store those values remotely with `void secret put` instead.
133
134
 
134
- ## Wrangler config merging
135
+ ## Cloudflare config merging
135
136
 
136
137
  By default, Void configures the Cloudflare plugin programmatically, so you don't need a `wrangler.jsonc` for bindings. Void pins a Workers compatibility date in `void.json` `worker.compatibility_date`; if no date is already configured in `void.json` or `wrangler.jsonc`/`wrangler.json`, Void writes the latest known-good date to `void.json`. Bindings are inferred from your source code and provisioned with local placeholder IDs for development.
137
138
 
@@ -148,9 +149,9 @@ In Void's default mode and when using frameworks where Void controls the Cloudfl
148
149
 
149
150
  All other fields in your `wrangler.jsonc` -- `name`, `routes`, `services`, `vars`, `env`, `compatibility_date`, etc. -- are preserved in the resolved config and flow through to the build output.
150
151
 
151
- Fields that Void always sets (`main`, `triggers`, `assets`) don't need to be in your wrangler config -- they're added programmatically based on your project structure.
152
+ Fields that Void always sets (`main`, `triggers`, `assets`) don't need to be in your Cloudflare config -- they're added programmatically based on your project structure.
152
153
 
153
- In this mode, Void does **not** modify your `wrangler.jsonc` file on disk. The merge is purely in-memory.
154
+ In this mode, normal inferred bindings are merged purely in memory. Typed state modules in `durable-objects/` are the exception: Void persists their bindings and `new_sqlite_classes` entries to `wrangler.jsonc` because Cloudflare Durable Object migration history must remain append-only across builds. Commit those entries.
154
155
 
155
156
  ### Adapter-based frameworks (SvelteKit, Nuxt, Astro)
156
157
 
@@ -159,11 +160,11 @@ When using SvelteKit, Nuxt, or Astro, the framework's own Cloudflare adapter own
159
160
  Because Void doesn't control the CF plugin in this mode, it can't merge bindings via a config callback. Instead, on dev startup Void syncs inferred bindings directly to your `wrangler.jsonc` file on disk:
160
161
 
161
162
  - Only adds bindings that are **missing** by name -- existing bindings are never modified or removed.
162
- - If `worker.compatibility_date` is set in `void.json`, syncs that date into wrangler config so the framework adapter reads the same value.
163
+ - If `worker.compatibility_date` is set in `void.json`, syncs that date into the Cloudflare config so the framework adapter reads the same value.
163
164
  - Also ensures the `nodejs_als` compatibility flag is present.
164
165
  - The framework adapter then reads this `wrangler.jsonc` normally.
165
166
 
166
- This means your `wrangler.jsonc` is the single source of truth for bindings in this mode. Void keeps it up to date as you add new resource imports to your code, but you're responsible for replacing placeholder IDs with real ones before deploying.
167
+ The framework adapter reads bindings from `wrangler.jsonc`. Void adds them as you import resources, and `void deploy --platform cloudflare` replaces local placeholder IDs when it provisions production resources.
167
168
 
168
169
  ### Merge precedence
169
170
 
@@ -173,7 +174,7 @@ This means your `wrangler.jsonc` is the single source of truth for bindings in t
173
174
  | `void.json` `worker` field | Highest for compat | `compatibility_date`, `compatibility_flags`, `vars` |
174
175
  | Void inference | Fills gaps only | Adds placeholder bindings for inferred resources not in your config |
175
176
 
176
- If no date is found in `void.json`, project wrangler config, or the supported generated build wrangler fallback during deploy, Void pins the latest known-good date to `void.json` and uses it for that run.
177
+ If no date is found in `void.json`, the project Cloudflare config, or the supported generated build fallback during deploy, Void pins the latest known-good date to `void.json` and uses it for that run.
177
178
 
178
179
  ### Example
179
180
 
@@ -196,160 +197,194 @@ If your code uses `c.env.DB` and `c.env.KV`, and your `wrangler.jsonc` only defi
196
197
 
197
198
  Void sees that `DB` is already configured and leaves it alone (including your real `database_id`), but adds a local placeholder for `KV` since it's missing. The `services` array passes through unchanged.
198
199
 
199
- This means `pnpm dev` works out of the box (Miniflare creates local instances of all bindings), while `wrangler deploy` uses your real D1 database ID and service bindings.
200
+ This means `pnpm dev` works out of the box (Miniflare creates local instances of all bindings), while `void deploy --platform cloudflare` uses your real D1 database ID and service bindings.
200
201
 
201
202
  ### What ends up in the build output
202
203
 
203
204
  After `vite build`, the Cloudflare Vite plugin writes a merged `wrangler.json` to the `dist/` directory. This file contains:
204
205
 
205
206
  - All fields from your `wrangler.jsonc` (bindings with real IDs, routes, services, vars, environments)
206
- - Any inferred bindings Void added (with placeholder IDs -- replace these before deploying)
207
+ - Any inferred bindings Void added (local placeholders during development; provisioned IDs during deploy)
207
208
  - Fields set by Void (`main`, `assets`, `triggers`)
208
209
 
209
- When you run `wrangler deploy`, it picks up this generated `wrangler.json` and deploys everything.
210
+ When you run `void deploy --platform cloudflare`, Void validates this generated `wrangler.json` and deploys it safely.
210
211
 
211
212
  ::: tip
212
- When deploying via `void deploy` (to the Void platform), the `wrangler.json` in the build output is **skipped** -- the platform manages worker configuration via its own deploy manifest. The merge behavior described here only applies to direct `wrangler deploy`.
213
+ When deploying to a Void platform, the `wrangler.json` in the build output is **skipped** because the platform manages Worker configuration through its own deploy manifest. The merge behavior described here applies to direct Cloudflare deployment.
213
214
  :::
214
215
 
215
216
  ## Deploy to your own Cloudflare account
216
217
 
217
- Void's default deployment path is `void deploy`, which uploads to the Void platform. But the generated worker is a standard Cloudflare Worker -- you can deploy it directly to your own account. Two paths get you there:
218
+ Choose Cloudflare during `void init`, then deploy:
218
219
 
219
- - **[`void deploy --backend cloudflare`](#one-command-void-deploy-backend-cloudflare)** -- a first-class flow that provisions bindings, applies remote migrations, checks secrets, builds, and runs `wrangler deploy` for you.
220
- - **[Manual `vite build && wrangler deploy`](#manual-build-and-deploy-with-wrangler)** -- create resources and edit `wrangler.jsonc` yourself, then build and deploy with wrangler directly.
220
+ ```sh
221
+ void deploy
222
+ ```
221
223
 
222
- Either way, the [Local development](#local-development), [AI](#ai-self-host), and [ISR](#isr-self-host) notes below apply.
224
+ Void opens your browser to sign in when needed. If you have access to several accounts, it asks which one to use and saves the account in your root `wrangler.jsonc`. Credentials are stored in your operating system's keychain. Press Ctrl+C to cancel login, or manage your session with `void cloudflare login`, `status`, and `logout`.
223
225
 
224
- ### One command: `void deploy --backend cloudflare`
226
+ To configure deployment separately from project setup, run `void connect --platform cloudflare`. It uses the same browser login and account selection as `void init`, and saves Cloudflare as the target for subsequent `void deploy` commands.
225
227
 
226
- `void deploy --backend cloudflare` deploys the built worker to **your own** Cloudflare account. It uses your local wrangler auth and your root `wrangler.jsonc` -- there is no Void login or linked project.
228
+ ### One command: `void deploy --platform cloudflare`
227
229
 
228
- ```bash
229
- # Deploy using the resources already declared in wrangler.jsonc
230
- void deploy --backend cloudflare
230
+ You can also choose Cloudflare for a single deploy:
231
231
 
232
- # Create any missing resources first, then deploy
233
- void deploy --backend cloudflare --provision
232
+ ```sh
233
+ void deploy --platform cloudflare
234
234
  ```
235
235
 
236
- **Prerequisites**
236
+ This deploys directly to your account. You don't need a Void platform connection or project. Once Cloudflare is saved in `.void/project.json`, `void deploy` uses it automatically.
237
237
 
238
- - **Pin an account.** Set `account_id` in your root `wrangler.jsonc`, or export `CLOUDFLARE_ACCOUNT_ID`. A multi-account token otherwise makes wrangler prompt (or error in CI), which Void cannot intercept -- so the account must be pinned first.
239
- - **Authenticate wrangler.** Run `wrangler login`, or set `CLOUDFLARE_API_TOKEN`. Deploy needs a token with `Workers Scripts:Edit` plus read on the resources you bind. `--provision` additionally needs per-product `*:Edit` (D1, KV, R2, Queues, Hyperdrive).
240
- - **`CLOUDFLARE_API_TOKEN` is required to provision a Hyperdrive config for the first time.** `wrangler login` covers every other resource, but wrangler exposes no machine-readable Hyperdrive list, so Void checks whether the config already exists over the Cloudflare REST API -- which an OAuth session cannot authenticate. Without a token `--provision` stops **before** touching your account rather than risk minting a duplicate config. Either export `CLOUDFLARE_API_TOKEN` (with Hyperdrive edit permission), or create the Hyperdrive config yourself and add its id to the `hyperdrive` binding in `wrangler.jsonc` -- deploying an **already-provisioned** Hyperdrive app needs no token and works under `wrangler login` alone.
241
- - **Docker**, if your app uses the sandbox -- the build needs it locally.
238
+ ### Deploy an existing Worker
242
239
 
243
- **What it does** (in order): settles the app class (a full Void app on the Cloudflare Workers target -- see [scope](#scope-and-limitations)) before any account operation; pins the account and confirms wrangler auth; provisions or drift-checks resources; **builds**; then, against the artifact the build actually emitted, warns on plaintext vars, gates on missing required secrets, checks the auth schema, and validates migrations; then applies remote D1 migrations for SQLite apps (and verifies none remain pending); then runs `wrangler deploy` on exactly the artifact it verified.
240
+ This handoff is for the existing source of an app already built with Void and previously deployed directly to Cloudflare. Keep its `wrangler.jsonc` or `wrangler.json`, then run:
244
241
 
245
- Note that **the build runs before the secret, auth-schema, and migration gates** -- those gates read the real emitted worker, so there has to be one to read. A missing production secret or a bad migration is therefore reported _after_ the build has run, which is worth knowing if your build hooks are slow or have side effects. In exchange, nothing remote is touched until every ground-truth gate has passed: remote D1 migrations are applied only afterwards, so a failed gate leaves your account, your database, and your live worker exactly as they were.
242
+ ```sh
243
+ void deploy
244
+ ```
246
245
 
247
- **Trust boundary: the build runs your project's code.** Exactly like the manual `vite build && wrangler deploy` below, this backend runs your project's build -- your config, every Vite plugin, and every build dependency -- with filesystem access before the credentialed deploy. Deploy narrows what that build can quietly change: it runs the build with your Cloudflare credentials scrubbed, verifies the emitted `wrangler.json` against a pre-build snapshot of your account, name, and binding identities, and checks that the wrangler CLI it is about to run with your token was not modified during the build. Those checks catch a build that tampers with the deploy target or the uploader. They do not sandbox the build itself, so a fully-compromised build dependency remains a trust boundary -- the same one you accept running `vite build` by hand. Vet your dependencies as you would for any deploy; stronger build isolation is future work.
246
+ If the project has no deployment destination, Void asks whether to link and deploy to Cloudflare using the existing Worker and resources. Accept to sign in, verify the configured Worker, and deploy in the same command. Your account and Worker name stay the same. The next deployment is just `void deploy`.
248
247
 
249
- Without `--provision`, deploy is a **drift check**: if a binding your source needs is not yet in `wrangler.jsonc` with a real id, deploy stops and names each missing resource, telling you to run `--provision` once. Queues carry no id in the config, so deploy instead checks each one against your account (`wrangler queues info`) at the same point -- a queue that does not exist stops the deploy before anything is built or migrated.
248
+ The first handoff preserves resource bindings, production variables, encrypted secrets, event handlers, and existing routes and schedules. It builds the app, checks the uploaded version's bindings and handler set, and verifies readiness before activating it. Void saves `keep_vars: true` in your config so later deployments retain dashboard-only variables too. The active version must also be the latest uploaded version; activate or remove an unpublished candidate in Cloudflare before retrying so secret inheritance has an unambiguous source.
250
249
 
251
- **`--provision`** creates any D1 database, KV namespace, R2 bucket, Queues, Hyperdrive config, and the ISR cache namespace your source needs, then lets wrangler write the real ids into your root `wrangler.jsonc`. It is **idempotent** -- it reads existing ids first, so re-running creates nothing that already exists.
250
+ Keep this first deployment focused on the existing site. Apart from the explicit ISR cache choice below, new resources, auth setup, runtime features, database migrations, and secret overrides stop the handoff before activation. A later code-only deploy continues to preserve dashboard-managed routes and visibility. Before adding a cron, queue consumer, workflow, or visibility change when those values exist only in the dashboard, add the current `routes`, `workers_dev`, and `preview_urls` values to the root Wrangler config. If the build fails, fix it and rerun `void deploy`; Void remembers the destination and checks the existing Worker again.
252
251
 
253
- #### Scope and limitations
252
+ Pages with `prerender = true` (including automatically prerendered Markdown pages) also request ISR caching. When the existing Worker has no cache, Void asks whether to enable it and saves the choice as `routing.isr` in `void.json`:
254
253
 
255
- - **Supported apps (v1): full Void apps on the Cloudflare Workers target only** -- worker-bearing apps that run Void's routing (`routes/` and/or `pages/`), with D1 (SQLite) and/or KV, R2, Queues, and Hyperdrive, plus auth on D1/SQLite and ISR. Everything else fails closed **before** any account operation, with guidance:
256
- - **Framework SSR is not supported here (yet).** The whole framework path -- TanStack Start, React Router, vinext (and SvelteKit, Nuxt, Analog, Astro) -- is deferred in v1. Deploy them with `void deploy` (the managed platform) or the framework's own Cloudflare adapter. Framework SSR support for this backend is a follow-up.
257
- - **Static-only / SPA / SSG apps are not supported here** -- including unconfigured ones, `output: "static"` in `void.json`, and `--dir` / `--spa` deploys. Deploy those with `void deploy` (the managed platform) or host the built assets on Cloudflare Pages / any static host.
258
- - **WebSocket / Durable Object routes (`*.ws.ts`) are not supported here (yet).** A WebSocket route makes the build emit a key-value-backed Durable Object namespace (a `new_classes` migration), which a fresh Cloudflare account -- and every Workers Free account -- refuses to create. Deploy those with `void deploy`. SQLite-backed WebSocket support for this backend is a follow-up.
259
- - **Custom `migrations_pattern` is not supported here.** v1 deploys only Void's default migration convention -- `db/migrations/*.sql` with wrangler's default pattern (leave `migrations_pattern` unset). Remove a custom `migrations_pattern` from the D1 binding, or deploy with `void deploy`. Supporting custom patterns is a follow-up.
260
- - **Non-Cloudflare targets (`node` / `bun` / `deno`) are not supported here** -- this backend deploys Cloudflare Workers only.
261
- - **`--skip-build` is not supported here.** Every check on this path validates the artifact the build emits -- the worker `vars` in `dist/ssr/wrangler.json` and the generated auth schema -- so skipping the build would leave them reading a stale or missing artifact instead of the worker being uploaded. Drop `--skip-build`, or use `void deploy` (the managed platform), which supports it.
262
- - **PostgreSQL apps with auth enabled are not supported here.** This backend verifies + applies auth tables through remote D1 (SQLite) migrations only, so it cannot provision or verify the Better Auth schema on Postgres/Hyperdrive. Deploy with `void deploy`, or use D1 for the auth app.
263
- - **PostgreSQL apps with checked-in migrations are not supported here.** This backend applies only remote D1 (SQLite) migrations. A PostgreSQL app's `db/migrations/*.sql` are applied over Hyperdrive by the managed platform (`void deploy`) at deploy time; this self-host backend never runs them, so it would deploy against an unmigrated database. Deploy with `void deploy`, or apply the migrations yourself against your Postgres and remove them from `db/migrations/`. (A pg app _without_ auth **and** with an externally-managed schema — no checked-in migrations — still deploys.)
264
- - **Auth requires checked-in migrations that produce the Better Auth schema.** The managed platform creates the Better Auth tables at runtime after deploy; this self-host backend never runs that step. Deploy reads the required Better Auth schema from the one the build itself generated (`.void/better-auth-schema.ts`, so configured renames and plugin tables are already reflected), then verifies the checked-in `db/migrations/*.sql` produce it by applying them to an in-memory SQLite database. Names alone are not enough: it also checks the constraints that carry correctness -- every auth table's `id` must be uniquely constrained (a `PRIMARY KEY` or a `UNIQUE` constraint/index; SQLite refuses a foreign key whose parent key is not unique, failing at runtime with `foreign key mismatch`), every field the schema marks `unique` must be covered by a unique constraint (a column-level `UNIQUE` or a single-column unique index both count, under any index name), and every field with a `references` target must have a matching foreign key. Column types, non-unique indexes and the exact `ON DELETE` action are deliberately not asserted. If a check fails, deploy fails closed naming the offending `table.column` -- fix the schema in `db/schema.ts` (Drizzle's `.primaryKey()`, `.unique()` and `.references()` are opt-in), run `void db generate`, commit the migration, or deploy with `void deploy`.
265
- - **Migrations must apply in the same order Void validated.** Deploy checks that the files wrangler will apply to remote D1 (and the order it applies them, by numeric prefix) exactly match Void's `db/migrations/*.sql` set -- no stray files (e.g. `seed.sql`), same content, same order. Zero-pad your migration prefixes (`0001_`, `0002_`, ...) so numeric and lexicographic order agree; deploy fails closed on a mismatch.
266
- - **Provision is a single-operator, dev-machine action.** The lock guarding it is per local config path only; it does not coordinate across machines or CI hosts. Two people provisioning the same account at once could create duplicate resources.
267
- - **Provision fails closed in CI.** In non-interactive shells, `--provision` is disabled unless your committed `wrangler.jsonc` already covers every resource (a provable no-op). The workflow is: provision **locally**, commit the updated `wrangler.jsonc`, then let CI run `void deploy --backend cloudflare` (deploy itself is CI-safe).
268
- - **Your `wrangler.jsonc` is rewritten on provision.** Wrangler preserves your comments but normalizes the whole file's indentation when it writes the new ids -- expect that in the diff.
269
- - **Your `.env*` values ship as plaintext.** The build bakes them into the worker's `vars`. This backend runs Vite's production env loading, so **all four** of `.env`, `.env.local`, `.env.production` and `.env.production.local` are loaded and shipped -- including the `.local` files, which are gitignored but **not** deploy-excluded here (unlike managed `void deploy`, which reads only `.env` and `.env.production`). The one exception: a value that is also present in the shell environment with the same value is stripped back out, so a var you `export` in CI does not get baked in. Move real secrets to `wrangler secret put <NAME>` so they are never written into `wrangler.json`. Deploy warns on likely-plaintext secrets -- by key name, and by value shape for credential-bearing connection URLs such as `DATABASE_URL` -- and hard-blocks on missing required secrets.
270
- - **First deploy of a new worker.** A worker that has never been deployed has no remote secrets to list yet, so the secret gate prints the still-unset required key names and the `wrangler secret put <NAME>` commands that bootstrap them on the draft worker (or add a value to `.env` / `.env.production` and rerun).
254
+ - **Yes:** provisions the KV cache and enables ISR in this deployment. The uploaded Worker must retain every existing binding and use exactly the approved cache namespace.
255
+ - **No:** saves `routing.isr: false`. Pages render on each request, and later deployments keep ISR disabled until you change that setting.
271
256
 
272
- The manual steps below are the by-hand equivalent -- reach for them when you want to manage resources and `wrangler.jsonc` yourself.
257
+ You can keep your page-level prerender and revalidate exports with either choice. The same saved choice applies to retries, other machines, and CI; completing the handoff does not change it. To choose ahead of time, set `routing.isr` to `true` or `false`. A non-interactive handoff with no saved choice stops with instructions to set it. Existing caches keep their namespace IDs. Commit `void.json` and any updated resource IDs in the root Cloudflare config.
273
258
 
274
- ### Manual: build and deploy with wrangler
259
+ If linking reports other missing inferred resources, the error lists each binding and why the app needs it. Check that the root config uses the existing Worker's binding names and resource IDs, and that `inference.bindings` in `void.json` matches those names. An application KV binding explicitly named `ISR_CACHE` is still required. An existing D1 binding without checked-in migrations can keep its current `migrations_dir`, including an omitted value; linking does not provision a database or change its migration settings. Keep `.void/cloudflare-link.json` when retrying so the handoff checks remain in place.
275
260
 
276
- Prefer to manage everything by hand? Create the resources, write `wrangler.jsonc`, and run `wrangler deploy` yourself.
261
+ Declining the initial link-and-deploy prompt leaves the project unchanged. Explicit platform choices and existing project links take precedence. In CI, select the destination with `--platform cloudflare` and provide Cloudflare credentials.
277
262
 
278
- #### 1. Create your resources
263
+ Direct deployment uses the top-level JSON/JSONC configuration; convert a `wrangler.toml` with the same settings before linking. Named environments need a separate top-level config. If previews are disabled, include the existing production hostname in your config so Void can check the candidate through it.
279
264
 
280
- Create whatever bindings your app uses:
265
+ ### What happens during deploy
281
266
 
282
- ```bash
283
- # D1 database
284
- wrangler d1 create my-app-db
267
+ Void reads your app's configuration and source, then:
285
268
 
286
- # KV namespace
287
- wrangler kv namespace create KV
269
+ 1. Checks the app type, selected account, and Cloudflare credentials.
270
+ 2. If the app uses email (`sendEmail()` or `email/` handlers), reads your zone's email state and, before any project code runs, asks once to set it up. See [Your own Cloudflare account](../guide/email.md#your-own-cloudflare-account) in the email guide.
271
+ 3. Creates missing resources or reuses resources already in your account.
272
+ 4. Builds the app and checks the generated Worker config, secrets, and migration history.
273
+ 5. Preserves or creates the auth secret, verifies required server keys in encrypted remote storage, and applies pending migrations.
274
+ 6. Uploads a Worker Version and checks that it is ready.
275
+ 7. Sends traffic to the new version and applies routes, custom domains, cron schedules, queue consumers, and Email Routing rules.
288
276
 
289
- # R2 bucket
290
- wrangler r2 bucket create my-app-storage
291
- ```
277
+ The secret and migration checks need the built Worker, so they happen after provisioning and building. If a check fails, resources may already exist, but Void has not applied remote D1 migrations or uploaded the application Worker.
292
278
 
293
- #### 2. Add a `wrangler.jsonc`
279
+ Resource IDs are saved in `wrangler.jsonc` for the next deploy. Void preserves comments, though it may adjust indentation when writing the file. Commit the updated config so other machines and CI can reuse the same resources. The old `--provision` flag is still accepted, but provisioning is now automatic.
294
280
 
295
- Create `wrangler.jsonc` in your project root with the resource IDs from step 1:
281
+ Run the first deploy from one machine at a time. The provisioning lock protects a local config file; it cannot coordinate two fresh CI runners, which could create duplicate resources.
296
282
 
297
- ```jsonc
298
- {
299
- "name": "my-app",
300
- "compatibility_date": "2026-02-24",
301
- "d1_databases": [
302
- {
303
- "binding": "DB",
304
- "database_name": "my-app-db",
305
- "database_id": "<your-database-id>",
306
- "migrations_dir": "./db/migrations",
307
- },
308
- ],
309
- "kv_namespaces": [
310
- {
311
- "binding": "KV",
312
- "id": "<your-namespace-id>",
313
- },
314
- ],
315
- "r2_buckets": [
316
- {
317
- "binding": "STORAGE",
318
- "bucket_name": "my-app-storage",
319
- },
320
- ],
321
- }
322
- ```
283
+ ### Deploying from CI
323
284
 
324
- Only include the bindings your app actually uses. You can also add service bindings, custom routes, environment overrides, and any other standard wrangler fields -- they all flow through to the build output. You don't need `main` or `assets` -- those are set by the plugin.
285
+ Set `CLOUDFLARE_API_TOKEN` in your CI secrets. The token needs Workers Scripts: Edit and read access to bound resources, plus edit permission for each product Void needs to provision. Set `CLOUDFLARE_ACCOUNT_ID` if the token can access more than one account.
325
286
 
326
- #### 3. Run migrations
287
+ Email setup needs a browser session from `void cloudflare login`, which carries the Email Routing and Email Sending scopes, or a `CLOUDFLARE_API_TOKEN` that also has Email Routing Edit and Email Sending Edit. A Global API Key pair is refused. In CI the email step never prompts: run `void email setup --platform cloudflare` once locally, commit `wrangler.jsonc`, then deploy with `--require-email`.
327
288
 
328
- If your app uses D1, apply migrations before deploying:
289
+ When a Worker has no version preview URL, such as a Worker with Durable Objects, also set `CLOUDFLARE_WORKERS_SUBDOMAIN`. Use the account subdomain, for example `my-team` or `my-team.workers.dev`. Local deploys cache this value in ignored `.void/cloudflare.json` after Cloudflare reports a deployment URL; a fresh CI checkout has no such cache.
329
290
 
330
- ```bash
331
- wrangler d1 migrations apply my-app-db --remote
291
+ #### Cloudflare Access
292
+
293
+ If Cloudflare Access protects the Worker's `workers.dev` hostname, Void needs credentials to check deployment readiness. In CI, provide an allowed `CF_ACCESS_CLIENT_ID` and `CF_ACCESS_CLIENT_SECRET` pair. For a local deploy, you can use a short-lived user session:
294
+
295
+ ```sh
296
+ export CF_ACCESS_TOKEN="$(cloudflared access token --app=https://<worker>.<account>.workers.dev)"
332
297
  ```
333
298
 
334
- This uses the same `db/migrations/` directory that Void uses locally. `my-app-db` is the database name from your `wrangler.jsonc`; using the database name avoids accidentally applying migrations to the wrong binding.
299
+ Void sends these credentials only to a matching HTTPS readiness URL. It doesn't save them or pass them to your build or deployment tools.
335
300
 
336
- #### 4. Build and deploy
301
+ If Access blocks a version preview but allows the stable Worker hostname, Void checks the new version through that hostname using a version override. If Access still denies the request, Void leaves the upload inactive or restores the previous deployment. A required first-deploy bootstrap is an exception: that Worker is already active behind Access when the check runs.
337
302
 
338
- ```bash
339
- vite build && wrangler deploy
303
+ ### Databases and secrets
304
+
305
+ PostgreSQL and MySQL apps need a production `DATABASE_URL` in the deploy process environment. Void uses it for Hyperdrive provisioning and migrations, and never writes it to generated config. PostgreSQL migrations are transactional; MySQL schema changes may partially apply before an error.
306
+
307
+ Creating a Hyperdrive config for the first time also requires `CLOUDFLARE_API_TOKEN` with Hyperdrive edit permission. Void needs the REST API to find existing configurations, and the current provisioning path can't use browser OAuth for that lookup. Alternatively, create the config in the Cloudflare dashboard and add its ID to the `hyperdrive` binding in `wrangler.jsonc`. An app with an existing Hyperdrive binding can deploy through browser login.
308
+
309
+ For auth-enabled apps, run `void db generate` and commit the migrations. Void includes the production Better Auth schema, including renamed tables and plugin tables, and checks it against your migration history during deploy. D1 also gets an in-memory schema check before remote migration. A mismatch stops deployment and asks you to regenerate the SQL.
310
+
311
+ Custom D1 layouts are supported through `migrations_dir`, `migrations_table`, and `migrations_pattern`. The files Cloudflare will apply must match the files Void validated, including their content and numeric order. Missing, extra, or reordered migrations stop deployment.
312
+
313
+ Root `.env` is local-only and is never emitted into Worker vars. Every non-client key declared in `env.ts` is a server value: store it with `void secret put <NAME>`. Void emits required server names through `secrets.required`, rejects plaintext Worker vars with those names, and preserves existing remote secrets.
314
+
315
+ For apps using auth, Void creates a random 32-byte `BETTER_AUTH_SECRET` only when the remote secret is missing. It reuses that value on later deploys. Both auth secrets and schema-marked secrets can be set up on a new Worker's draft before its first upload.
316
+
317
+ ### Readiness and rollback
318
+
319
+ Void usually checks an uploaded version before sending it traffic. When Cloudflare provides a version preview URL, Void probes that URL. Otherwise, it stages the version at 0% traffic and checks it through `workers.dev` using Cloudflare's version-override header.
320
+
321
+ If readiness or trigger synchronization fails, Void restores the previous deployment. If you already have a gradual rollout splitting traffic across versions, finish or cancel it in Cloudflare before deploying through Void.
322
+
323
+ A new Worker may need one ordinary deployment before version uploads work. This can happen when creating the Worker, establishing its first Durable Object migration history, or enabling preview URLs. Void checks that the Worker did not exist before first-deploy secret setup, deploys it once, then checks the active Worker through `/__void/ready`. It keeps that earlier check even if attaching a secret creates a placeholder version. This bootstrap is never used for an existing application.
324
+
325
+ To inspect versions or roll back:
326
+
327
+ ```sh
328
+ void project status
329
+ void project rollback [version]
340
330
  ```
341
331
 
342
- That's it. The Cloudflare Vite plugin produces a complete build output with a merged `wrangler.json` in the dist directory (containing your real resource IDs and any inferred bindings), and `wrangler deploy` picks it up.
332
+ Versions with a complete trigger snapshot can restore their schedules, queues, workflows, routes, and domains along with the code. For an older version deployed outside Void, or a handoff that preserved existing triggers, rollback keeps the current routes and schedules. You can return to the original Worker Version without redeploying its source.
333
+
334
+ Rollback does not reverse database migrations. Void asks for confirmation when the schema may be newer than the code or migration metadata is missing.
335
+
336
+ #### Scope and limitations
337
+
338
+ Void supports Worker apps, static sites, SPAs, known SSGs, `--dir` deploys, and fully prerenderable Pages apps with `output: "static"`. It also deploys Cloudflare output from TanStack Start, React Router, SvelteKit, Nuxt, Analog, and Astro. The vinext adapters remain experimental and are outside the beta support commitment.
339
+
340
+ Static sites use a small Worker in front of Workers Assets to handle redirects, rewrites, fallbacks, and headers. Hybrid and SSR apps keep their application Worker. A page that opts out of prerendering, a dynamic page without `getPrerenderPaths()`, or another runtime feature keeps the app on a Worker even with `output: "static"`.
341
+
342
+ Native Void applications apply `void.json` routing rules in their Worker.
343
+ Framework-owned Workers do not yet support those Void redirects, rewrites,
344
+ fallbacks, or headers on the direct target. The CLI rejects such configuration
345
+ before provisioning or building; configure the rules in the framework or its
346
+ Worker instead. This restriction does not change an explicit asset policy for
347
+ `routing.notFound`.
348
+
349
+ Worker apps support D1, KV, R2, Queues, typed state, PostgreSQL and MySQL through Hyperdrive, auth, WebSockets, AI, cron jobs, and ISR. The main limits are:
350
+
351
+ - **Sandbox needs Workers Paid and Docker.** Importing `void/sandbox` or enabling `sandbox` in `void.json` adds a Container application. Void checks access before provisioning or building. [Enable Workers Paid](https://dash.cloudflare.com/?to=/:account/workers/plans) and sign in again if needed. API tokens need Account / Containers: Edit and Account / Cloudchamber: Edit. See [Containers pricing](https://developers.cloudflare.com/containers/pricing/). Apps without Sandbox skip this check and remain compatible with Workers Free within its quotas.
352
+ - **Worker apps need a fresh build.** `--skip-build` works for existing static, SPA, and SSG output. Worker validation needs the current build's vars and auth schema.
353
+ - **Named Cloudflare environments aren't supported.** Direct commands use the top-level root config and reject `CLOUDFLARE_ENV`, `CLOUDFLARE_VITE_WRANGLER_CONFIG_PATH`, and project-local name overrides. Use a separate root config per deployment target.
354
+ - **Node.js, Bun, and Deno use a different deployment path.** See their [integration guide](./nodejs-bun-deno.md).
355
+ - **Email is set up on the first deploy, on a zone you own.** Put `email.from` in `void.json`; the deploy reads your account, prints a checklist of what it would change, and asks once. See [Your own Cloudflare account](../guide/email.md#your-own-cloudflare-account). Outside Void's reach: `email/_default.ts` and dynamic local parts (`email/[user].ts`) need a catch-all, which exists only on a zone apex, so on a mail subdomain they get no rule; a mail domain that already has non-Cloudflare MX records is refused, never routed over; `sendEmail()` to arbitrary recipients needs Workers Paid (Email Sending onboarding), otherwise verified destinations only; Void owns the top-level `addresses` array in `wrangler.jsonc`, so hand-written entries there skip the email step; and `void email usage`, `logs`, `allow`, and `destinations` are platform-only.
356
+
357
+ WebSocket routes and typed state use SQLite-backed Durable Objects. Commit the bindings and `new_sqlite_classes` migration history in `wrangler.jsonc`; don't delete or reorder deployed migration steps. Older hosted classes using `new_classes` keep their existing storage.
358
+
359
+ Bare `vite build && wrangler deploy` does not provision schema-declared secrets. Use `wrangler secret bulk` / `wrangler secret put` and list every inherited name under `secrets.required` yourself.
360
+
361
+ ISR uses the shared cache protocol. Entries are scoped to a deployment and hostname, and `routing.revalidateQueryAllowlist` adds bounded query variants. `revalidate()` purges matching entries and variants from KV and the local edge cache. See [ISR](#isr-self-host) below for cache behavior across regions.
362
+
363
+ ### Managing the deployed app
364
+
365
+ With Cloudflare selected, `void secret`, `void domain`, `void project status|list|logs|rollback`, and remote `void db` commands use the saved Worker and account. Database commands operate on the selected D1 database. Logs are a live tail; Void doesn't provide hosted log history for direct deploys.
366
+
367
+ Custom domain changes update routes immediately without rewriting schedules, queues, or workflows. Removing the final custom domain requires `CLOUDFLARE_API_TOKEN` with Workers Scripts: Edit because that operation uses Cloudflare's domain-record API.
368
+
369
+ `void project delete` doesn't remove direct Cloudflare resources, which may be shared. Review their use and remove them explicitly in Cloudflare.
370
+
371
+ ::: details How Void checks the build
372
+
373
+ Your build runs your config, Vite plugins, and dependencies with filesystem access. Void removes Cloudflare credentials from the build environment, checks the generated account, Worker name, and binding IDs against the pre-build configuration, and verifies that the bundled deployment tool hasn't changed.
374
+
375
+ These checks detect changes to the deployment target or uploader, but they don't sandbox arbitrary build code. Build dependencies still need the same trust as other code you run on your machine.
376
+
377
+ :::
343
378
 
344
379
  ### Local development
345
380
 
346
- `pnpm dev` continues to work as before -- Miniflare creates local instances of all bindings regardless of the IDs in your `wrangler.jsonc`. Your real resource IDs are only used when you run `wrangler deploy`.
381
+ `pnpm dev` continues to work as before -- Miniflare creates local instances of all bindings regardless of the IDs in your `wrangler.jsonc`. Your real resource IDs are only used during direct Cloudflare deployment.
347
382
 
348
- ### AI (self-host)
383
+ ### AI on your Cloudflare account {#ai-self-host}
349
384
 
350
385
  `void/ai` works on your own Cloudflare account, along two paths:
351
386
 
352
- - **Workers AI** (`ai.run`, `ai.stream`, `ai.image`) works out of the box. When your app imports `void/ai`, `vite build` infers that you need AI and adds a Workers AI binding (`env.AI`) to the generated `wrangler.json` automatically -- you do **not** add it to `wrangler.jsonc`.
387
+ - **Workers AI** (`ai.run`, `ai.stream`, `ai.image`) works out of the box. When your app imports `void/ai`, `vite build` infers that you need AI and adds a Workers AI binding (`env.AI`) to the generated `wrangler.json` automatically -- you do **not** add it to `wrangler.jsonc`. Set `inference.bindings.ai` to a string to use a custom name.
353
388
  - **Provider models** (`ai.provider("openai").fetch(...)`) route through _your own_ Cloudflare AI Gateway. Set its id in `void.json` and add the provider's API key as a Worker secret.
354
389
 
355
390
  ```jsonc
@@ -363,7 +398,7 @@ That's it. The Cloudflare Vite plugin produces a complete build output with a me
363
398
 
364
399
  ```bash
365
400
  # provider API key, stored as a Worker secret (never committed)
366
- wrangler secret put OPENAI_API_KEY
401
+ void secret put OPENAI_API_KEY
367
402
  ```
368
403
 
369
404
  ```ts
@@ -372,7 +407,7 @@ import { defineHandler } from 'void';
372
407
  import { ai } from 'void/ai';
373
408
 
374
409
  export const POST = defineHandler(async (c) => {
375
- // Workers AI -- uses env.AI directly
410
+ // Workers AI -- uses the inferred or configured AI binding directly
376
411
  const summary = await ai.run('@cf/meta/llama-3.1-8b-instruct', {
377
412
  prompt: 'Summarize the changelog.',
378
413
  });
@@ -388,33 +423,17 @@ export const POST = defineHandler(async (c) => {
388
423
  });
389
424
  ```
390
425
 
391
- `ai.gateway` is required for `ai.provider().fetch()` -- without it, that call returns a `501`. No AI traffic or provider secret passes through Void's shared proxy: requests go directly to _your own_ Cloudflare AI Gateway, authenticated with provider secrets from _your_ Worker's environment. (The request and that secret are of course still sent onward to the AI Gateway and the upstream provider you call.)
426
+ Set `ai.gateway` before calling `ai.provider().fetch()`; otherwise it returns `501`. Requests use the provider secrets in your Worker's environment and go through your AI Gateway to the provider. They don't pass through the Void platform's shared proxy.
392
427
 
393
428
  Notes:
394
429
 
395
- - **No cross-tenant usage metering.** On the Void platform, AI calls are metered and billed through a shared proxy. Self-hosted, there is no metering -- you get your own [Cloudflare AI Gateway analytics](https://developers.cloudflare.com/ai-gateway/) instead.
396
- - **The runtime reads the `env.AI` binding by name** -- a custom-named root AI binding is not supported.
397
- - **`void dev` has no local Workers AI emulation.** In development, AI still routes through Void, so `void dev` AI requires `void auth login` even when you deploy self-hosted.
398
-
399
- ### ISR (self-host)
430
+ - **Account-owned usage.** Direct deployments use your own [Cloudflare AI Gateway analytics](https://developers.cloudflare.com/ai-gateway/). A team platform meters requests through its shared proxy; those usage records do not automatically bill application developers.
431
+ - **Custom AI binding names are supported.** Configure `"inference": { "bindings": { "ai": "MY_AI" } }`, or declare the custom `ai.binding` in your root Wrangler config; the generated worker records the resolved name for `void/ai` automatically.
432
+ - **Workers AI runs remotely during development.** After `void connect --platform cloudflare`, an app importing `void/ai` uses your account's remote AI binding with your Cloudflare login or API token. Development and preview calls consume that account's allowance. Apps without AI imports add no AI binding or authentication probe.
400
433
 
401
- [Revalidation (ISR)](../guide/edge/revalidation.md) works self-hosted, but the cache KV is **not** auto-injected (a KV binding needs a real namespace id). Create a namespace and bind it as `ISR_CACHE`:
434
+ ### ISR on your Cloudflare account {#isr-self-host}
402
435
 
403
- ```bash
404
- wrangler kv namespace create ISR_CACHE
405
- ```
406
-
407
- ```jsonc
408
- // wrangler.jsonc
409
- {
410
- "kv_namespaces": [
411
- {
412
- "binding": "ISR_CACHE",
413
- "id": "<your-namespace-id>",
414
- },
415
- ],
416
- }
417
- ```
436
+ [Revalidation (ISR)](../guide/edge/revalidation.md) works self-hosted. `void deploy --platform cloudflare` automatically creates or reuses the cache KV namespace and persists its `ISR_CACHE` binding in `wrangler.jsonc`, just like the other inferred resources.
418
437
 
419
438
  Configure revalidation exactly as on the platform -- globally or per-path in `void.json`:
420
439
 
@@ -446,8 +465,8 @@ await revalidate({ all: true });
446
465
 
447
466
  Self-hosted, `revalidate()` purges this worker's own KV entries (global, authoritative) plus the current colo's edge cache.
448
467
 
449
- Limits (the single-worker cache ladder can't do everything the platform's dispatch layer does):
468
+ There are a few differences from platform-managed ISR:
450
469
 
451
- - **No fleet-wide / cross-colo edge purge.** `revalidate()` clears KV globally and the _local_ colo's edge cache; other colos keep serving their edge copy until it expires (bounded by the response's `s-maxage`), then re-render on the next edge miss.
452
- - **The pages-protocol JSON variant is not served from a cold colo's KV.** A colo that hasn't rendered the HTML yet re-renders the JSON live; the JSON edge cache is warmed only as a side effect of the HTML render path.
453
- - **The warm cache is dropped on every redeploy.** Each `vite build` bakes a fresh deployment id into the cache keys, so cached HTML never outlives the hashed assets it references -- the first request after a deploy is a cold render.
470
+ - **Edge caches expire independently.** `revalidate()` clears KV and the current data center's edge cache. Other data centers may serve their cached response until its `s-maxage` expires, then render again.
471
+ - **Pages JSON is cached after an HTML render.** A data center that hasn't rendered the HTML yet generates the JSON response live rather than reading it from KV.
472
+ - **Each deploy starts with a fresh cache.** Cache keys include a new deployment ID, so cached HTML can't reference assets from an older build. The first request renders the page again.
@@ -4,7 +4,7 @@ outline: deep
4
4
 
5
5
  # Analog
6
6
 
7
- [Analog](https://analogjs.org/) is a Vite-based Angular meta-framework powered by Nitro. Add `voidPlugin()` to the Vite config for binding inference, typed DB, and migrations during development.
7
+ Use Void with [Analog](https://analogjs.org/) for resource detection, typed database queries, and migrations. Analog keeps its own build and Cloudflare integration; Void plugs into its Vite configuration.
8
8
 
9
9
  ## Setup
10
10
 
@@ -18,10 +18,10 @@ cd my-app
18
18
  ### 2. Install dependencies
19
19
 
20
20
  ```bash
21
- npm install -D void wrangler nitro-cloudflare-dev
21
+ npm install -D void nitro-cloudflare-dev
22
22
  ```
23
23
 
24
- The `wrangler` dependency is needed for local Cloudflare bindings. `nitro-cloudflare-dev` creates a Cloudflare platform proxy during dev so that `void/db`, `void/kv`, and other runtime helpers can access bindings.
24
+ Void provides the local Cloudflare binding runtime. `nitro-cloudflare-dev` creates the platform proxy during development so that `void/db`, `void/kv`, and other runtime helpers can access bindings.
25
25
 
26
26
  ### 3. Configure `vite.config.ts`
27
27
 
@@ -162,7 +162,7 @@ export default defineQueue<{ to: string; subject: string }>(async (batch) => {
162
162
 
163
163
  ### Environment Variables
164
164
 
165
- Void gives you a typed env layer: declare keys in `env.ts`, read them via `import { env } from "void/env"`, and get schema validation at build + deploy time plus a client-leak guard that fails the build if a server-only key reaches the browser. See the [env vars guide](../../guide/env-vars.md) for the full feature set.
165
+ Declare environment variables in `env.ts`, then read them with `import { env } from "void/env"`. Void supplies types, checks values during build and deploy, and stops the build if client code references a server-only key. See [Environment Variables](../../guide/env-vars.md).
166
166
 
167
167
  `void/env` replaces the H3 event context and `import { env } from "cloudflare:workers"` for env-var access. Keep those around when you need raw binding access (D1, KV, R2, etc.).
168
168
 
@@ -4,12 +4,12 @@ outline: deep
4
4
 
5
5
  # Astro
6
6
 
7
- [Astro](https://astro.build/) has its own CLI and Cloudflare adapter (`@astrojs/cloudflare`). Add `voidPlugin()` to Astro's Vite config for binding inference, typed DB, and migrations during development.
7
+ Use Void with [Astro](https://astro.build/) for resource detection, typed database queries, and migrations. Astro keeps its own build and Cloudflare integration; Void plugs into its Vite configuration.
8
8
 
9
9
  ::: warning Astro 6 required
10
10
 
11
11
  - [Astro 6+](https://astro.build/blog/astro-6/) is required to use `import { x } from "void/x"` helpers in Astro apps.
12
- - You also need to enable `"nodejs_als"` under `compatibility_flags` in your wrangler config.
12
+ - You also need to enable `"nodejs_als"` under `compatibility_flags` in your Cloudflare config.
13
13
  :::
14
14
 
15
15
  ## Setup
@@ -40,7 +40,7 @@ export default defineConfig({
40
40
  });
41
41
  ```
42
42
 
43
- By default, Astro Cloudflare runtime and `voidPlugin()` migrations share Wrangler's local state at `.wrangler/state/v3`, so no extra persistence configuration is required.
43
+ By default, Astro's Cloudflare runtime and `voidPlugin()` migrations share local state at `.wrangler/state/v3`, so no extra persistence configuration is required.
44
44
 
45
45
  ### 4. Create `wrangler.jsonc`
46
46
 
@@ -162,9 +162,9 @@ export default defineQueue<{ to: string; subject: string }>(async (batch) => {
162
162
 
163
163
  ### Environment Variables
164
164
 
165
- Void gives you a typed env layer: declare keys in `env.ts`, read them via `import { env } from "void/env"`, and get schema validation at build + deploy time plus a client-leak guard that fails the build if a server-only key reaches the browser. See the [env vars guide](../../guide/env-vars.md) for the full feature set.
165
+ Declare environment variables in `env.ts`, then read them with `import { env } from "void/env"`. Void supplies types, checks values during build and deploy, and stops the build if client code references a server-only key. See [Environment Variables](../../guide/env-vars.md).
166
166
 
167
- Astro-specific note: the client prefix is `PUBLIC_*` (Astro's default `envPrefix`), not `VITE_*` — name client-exposed keys accordingly and the leak guard + constant folding honour the prefix automatically.
167
+ Void always uses `VITE_*` for client-exposed schema keys, including in Astro projects. Astro's separate `PUBLIC_*` convention still applies to direct `import.meta.env` access, but it does not change the `void/env` server/client boundary.
168
168
 
169
169
  `void/env` replaces [`astro:env`](https://docs.astro.build/en/guides/environment-variables/) and `Astro.locals.runtime.env` for env-var access. Keep `Astro.locals.runtime.env` around when you need raw binding access (D1, KV, R2, etc.).
170
170