@agent-native/core 0.164.4 → 0.164.12

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 (268) hide show
  1. package/corpus/README.md +1 -1
  2. package/corpus/templates/calendar/.agents/skills/event-management/SKILL.md +84 -0
  3. package/corpus/templates/calendar/AGENTS.md +5 -0
  4. package/corpus/templates/calendar/actions/delete-event.ts +1 -1
  5. package/corpus/templates/calendar/actions/delete-events.ts +508 -0
  6. package/corpus/templates/calendar/actions/event-action-helpers.ts +1 -1
  7. package/corpus/templates/calendar/actions/list-events.ts +53 -0
  8. package/corpus/templates/calendar/app/components/calendar/CreateEventDialog.tsx +36 -47
  9. package/corpus/templates/calendar/app/components/calendar/DayView.tsx +3 -0
  10. package/corpus/templates/calendar/app/components/calendar/EventDetailPopover.tsx +18 -1
  11. package/corpus/templates/calendar/app/components/calendar/InlineEventPickers.tsx +256 -38
  12. package/corpus/templates/calendar/app/hooks/use-google-auth.ts +43 -3
  13. package/corpus/templates/calendar/app/i18n-data.ts +120 -0
  14. package/corpus/templates/calendar/app/lib/event-form-utils.ts +113 -0
  15. package/corpus/templates/calendar/changelog/2026-08-18-the-agent-can-now-remove-many-meetings-at-once-such-as-every.md +6 -0
  16. package/corpus/templates/calendar/server/handlers/google-auth.ts +119 -3
  17. package/corpus/templates/calendar/server/lib/event-weekday.ts +112 -0
  18. package/corpus/templates/calendar/server/routes/[base]/_agent-native/google/add-account/auth-url.post.ts +1 -0
  19. package/corpus/templates/calendar/server/routes/[base]/_agent-native/google/auth-url.post.ts +1 -0
  20. package/corpus/templates/calendar/server/routes/_agent-native/google/add-account/auth-url.post.ts +1 -0
  21. package/corpus/templates/calendar/server/routes/_agent-native/google/auth-url.post.ts +1 -0
  22. package/corpus/templates/clips/app/components/player/video-player.tsx +12 -0
  23. package/corpus/templates/clips/app/routes/_app.dictate.tsx +18 -4
  24. package/corpus/templates/clips/app/routes/r.$recordingId.tsx +114 -20
  25. package/corpus/templates/clips/app/routes/share.$shareId.tsx +83 -78
  26. package/corpus/templates/clips/changelog/2026-08-19-clips-nightly-builds-are-available-for-trying-the-latest-upd.md +6 -0
  27. package/corpus/templates/clips/changelog/2026-08-19-social-preview-video-frames.md +1 -0
  28. package/corpus/templates/clips/desktop/README.md +19 -4
  29. package/corpus/templates/clips/desktop/src/app.tsx +78 -16
  30. package/corpus/templates/clips/desktop/src-tauri/Cargo.toml +3 -2
  31. package/corpus/templates/clips/desktop/src-tauri/tauri.conf.json +1 -0
  32. package/corpus/templates/clips/server/routes/[base]/_agent-native/google/auth-url.post.ts +1 -0
  33. package/corpus/templates/clips/server/routes/_agent-native/google/auth-url.get.ts +41 -3
  34. package/corpus/templates/clips/server/routes/_agent-native/google/auth-url.post.ts +1 -0
  35. package/corpus/templates/clips/server/routes/_agent-native/google/callback.get.ts +22 -1
  36. package/corpus/templates/clips/server/routes/api/clips-updater.json.get.ts +41 -22
  37. package/corpus/templates/factory/AGENTS.md +3 -2
  38. package/corpus/templates/factory/actions/get-factory-graph-version.ts +69 -0
  39. package/corpus/templates/factory/actions/list-factory-automations.ts +4 -0
  40. package/corpus/templates/factory/actions/list-factory-graph-versions.ts +82 -0
  41. package/corpus/templates/factory/actions/restore-factory-graph-version.ts +163 -0
  42. package/corpus/templates/factory/actions/save-factory-graph.ts +93 -60
  43. package/corpus/templates/factory/actions/start-builder-for-item.ts +19 -17
  44. package/corpus/templates/factory/app/components/factory/FactoryAuditView.tsx +100 -36
  45. package/corpus/templates/factory/app/components/factory/FactoryHistoryView.tsx +709 -0
  46. package/corpus/templates/factory/app/components/factory/FactoryInspector.tsx +62 -2
  47. package/corpus/templates/factory/app/components/ui/alert-dialog.tsx +1 -0
  48. package/corpus/templates/factory/app/i18n/en-US.ts +47 -0
  49. package/corpus/templates/factory/app/routes/factory.tsx +324 -61
  50. package/corpus/templates/factory/server/connectors/slack.ts +44 -2
  51. package/corpus/templates/factory/server/plugins/agent-chat.ts +12 -8
  52. package/corpus/templates/factory/server/plugins/factory-scheduler-job.ts +13 -0
  53. package/corpus/templates/factory/server/triage/slack-client.ts +5 -0
  54. package/corpus/templates/factory/server/triage/slack-poller.ts +72 -4
  55. package/corpus/templates/mail/actions/view-screen.ts +1 -1
  56. package/corpus/templates/mail/app/components/GoogleConnectBanner.tsx +100 -18
  57. package/corpus/templates/mail/server/handlers/google-auth.ts +125 -24
  58. package/corpus/templates/mail/server/lib/gmail-query.ts +5 -2
  59. package/corpus/templates/mail/server/routes/[base]/_agent-native/google/add-account/auth-url.post.ts +1 -0
  60. package/corpus/templates/mail/server/routes/[base]/_agent-native/google/auth-url.post.ts +1 -0
  61. package/corpus/templates/mail/server/routes/_agent-native/google/add-account/auth-url.post.ts +1 -0
  62. package/corpus/templates/mail/server/routes/_agent-native/google/auth-url.post.ts +1 -0
  63. package/corpus/templates/plan/app/pages/PlansPage.tsx +0 -12
  64. package/corpus/templates/plan/changelog/2026-08-19-plan-prompts-now-guide-you-to-connect-ai-before-sending-and-.md +6 -0
  65. package/corpus/templates/slides/actions/approve-deck-access-request.ts +234 -0
  66. package/corpus/templates/slides/actions/get-deck-access-status.ts +35 -2
  67. package/corpus/templates/slides/actions/request-deck-access.ts +263 -64
  68. package/corpus/templates/slides/app/components/editor/MissingDeckAccessPane.tsx +196 -0
  69. package/corpus/templates/slides/app/components/editor/RequestDeckAccessDialog.tsx +101 -0
  70. package/corpus/templates/slides/app/hooks/use-deck-access.ts +7 -4
  71. package/corpus/templates/slides/app/i18n/en-US.ts +29 -6
  72. package/corpus/templates/slides/app/pages/DeckEditor.tsx +147 -169
  73. package/corpus/templates/slides/app/routes/access-request.approve.tsx +250 -0
  74. package/corpus/templates/slides/server/db/schema.ts +8 -0
  75. package/corpus/templates/slides/server/lib/access-request-email.ts +36 -0
  76. package/corpus/templates/slides/server/lib/emails.ts +26 -0
  77. package/corpus/templates/slides/server/plugins/agent-chat.ts +7 -0
  78. package/corpus/templates/slides/server/plugins/db.ts +50 -0
  79. package/corpus/templates/slides/shared/deck-access.ts +31 -0
  80. package/dist/a2a/task-store.d.ts +1 -0
  81. package/dist/a2a/task-store.js +1 -1
  82. package/dist/agent/observational-memory/store.d.ts +1 -0
  83. package/dist/agent/observational-memory/store.js +1 -1
  84. package/dist/agent/run-store.d.ts +1 -0
  85. package/dist/agent/run-store.js +1 -1
  86. package/dist/agent/tool-approval-store.d.ts +1 -0
  87. package/dist/agent/tool-approval-store.js +1 -1
  88. package/dist/application-state/store.d.ts +1 -0
  89. package/dist/application-state/store.js +1 -1
  90. package/dist/browser-sessions/store.d.ts +1 -0
  91. package/dist/browser-sessions/store.js +1 -1
  92. package/dist/checkpoints/store.d.ts +1 -0
  93. package/dist/checkpoints/store.js +1 -1
  94. package/dist/cli/code-agent-schedules.d.ts +11 -0
  95. package/dist/cli/code-agent-schedules.js +44 -5
  96. package/dist/client/AgentPanel.d.ts +5 -1
  97. package/dist/client/AgentPanel.js +2 -2
  98. package/dist/client/AssistantChat.d.ts +5 -1
  99. package/dist/client/AssistantChat.js +40 -6
  100. package/dist/client/EnvironmentBadge.d.ts +7 -13
  101. package/dist/client/EnvironmentBadge.js +43 -92
  102. package/dist/client/agent-chat/index.d.ts +1 -0
  103. package/dist/client/agent-chat/index.js +1 -0
  104. package/dist/client/agent-chat-adapter.js +76 -50
  105. package/dist/client/app-providers.js +4 -4
  106. package/dist/client/chat/message-components.d.ts +4 -0
  107. package/dist/client/chat/message-components.js +28 -1
  108. package/dist/client/chat/run-recovery.js +26 -0
  109. package/dist/client/chat-first/apps-rail.d.ts +1 -0
  110. package/dist/client/chat-first/apps-rail.js +28 -2
  111. package/dist/client/sse-event-processor.js +13 -8
  112. package/dist/client/use-active-agent-chat-run.d.ts +2 -0
  113. package/dist/client/use-active-agent-chat-run.js +22 -0
  114. package/dist/coding-tools/sandbox/executions-store.d.ts +1 -0
  115. package/dist/coding-tools/sandbox/executions-store.js +1 -1
  116. package/dist/collab/awareness-store.d.ts +1 -0
  117. package/dist/collab/awareness-store.js +1 -1
  118. package/dist/collab/routes.d.ts +1 -1
  119. package/dist/collab/storage.d.ts +1 -0
  120. package/dist/collab/storage.js +1 -1
  121. package/dist/collab/struct-routes.d.ts +1 -1
  122. package/dist/db/client.js +3 -3
  123. package/dist/db/ddl-guard.js +8 -0
  124. package/dist/db/migration-runtime.d.ts +23 -0
  125. package/dist/db/migration-runtime.js +41 -0
  126. package/dist/db/migrations.d.ts +1 -2
  127. package/dist/db/migrations.js +2 -24
  128. package/dist/email-catalog/log.d.ts +1 -0
  129. package/dist/email-catalog/log.js +1 -1
  130. package/dist/guards/index.d.ts +1 -0
  131. package/dist/guards/index.js +1 -0
  132. package/dist/guards/release-schema-complete.d.ts +22 -0
  133. package/dist/guards/release-schema-complete.js +144 -0
  134. package/dist/integrations/a2a-continuations-store.d.ts +1 -0
  135. package/dist/integrations/a2a-continuations-store.js +1 -1
  136. package/dist/integrations/awaiting-input-store.d.ts +1 -0
  137. package/dist/integrations/awaiting-input-store.js +1 -1
  138. package/dist/integrations/config-store.d.ts +1 -0
  139. package/dist/integrations/config-store.js +1 -1
  140. package/dist/integrations/controls-store.d.ts +1 -0
  141. package/dist/integrations/controls-store.js +1 -1
  142. package/dist/integrations/identity-links-store.d.ts +1 -0
  143. package/dist/integrations/identity-links-store.js +1 -1
  144. package/dist/integrations/installations-store.d.ts +1 -0
  145. package/dist/integrations/installations-store.js +1 -1
  146. package/dist/integrations/remote-commands-store.d.ts +1 -0
  147. package/dist/integrations/remote-commands-store.js +1 -1
  148. package/dist/integrations/remote-devices-store.d.ts +1 -0
  149. package/dist/integrations/remote-devices-store.js +1 -1
  150. package/dist/integrations/remote-push-store.d.ts +1 -0
  151. package/dist/integrations/remote-push-store.js +1 -1
  152. package/dist/integrations/remote-run-events-store.d.ts +1 -0
  153. package/dist/integrations/remote-run-events-store.js +1 -1
  154. package/dist/integrations/scope-store.d.ts +1 -0
  155. package/dist/integrations/scope-store.js +1 -1
  156. package/dist/integrations/thread-mapping-store.d.ts +1 -0
  157. package/dist/integrations/thread-mapping-store.js +1 -1
  158. package/dist/integrations/usage-budget-store.d.ts +1 -0
  159. package/dist/integrations/usage-budget-store.js +1 -1
  160. package/dist/jobs/background-automation-runner.js +111 -9
  161. package/dist/jobs/run-history.d.ts +1 -0
  162. package/dist/jobs/run-history.js +1 -1
  163. package/dist/jobs/scheduler-health.d.ts +1 -0
  164. package/dist/jobs/scheduler-health.js +1 -1
  165. package/dist/mcp/approval-store.d.ts +1 -0
  166. package/dist/mcp/approval-store.js +1 -1
  167. package/dist/mcp/connect-store.d.ts +1 -0
  168. package/dist/mcp/connect-store.js +1 -1
  169. package/dist/mcp/oauth-store.d.ts +1 -0
  170. package/dist/mcp/oauth-store.js +1 -1
  171. package/dist/notifications/store.d.ts +1 -0
  172. package/dist/notifications/store.js +1 -1
  173. package/dist/oauth-tokens/store.d.ts +1 -0
  174. package/dist/oauth-tokens/store.js +1 -1
  175. package/dist/observability/routes.d.ts +5 -5
  176. package/dist/progress/routes.d.ts +1 -1
  177. package/dist/progress/store.d.ts +1 -0
  178. package/dist/progress/store.js +1 -1
  179. package/dist/provider-api/actions/custom-provider-registration.d.ts +5 -5
  180. package/dist/provider-api/actions/provider-api.d.ts +4 -4
  181. package/dist/provider-api/corpus-jobs-store.d.ts +1 -0
  182. package/dist/provider-api/corpus-jobs-store.js +1 -1
  183. package/dist/provider-api/custom-registry.d.ts +1 -0
  184. package/dist/provider-api/custom-registry.js +1 -1
  185. package/dist/provider-api/quota-governor.d.ts +1 -0
  186. package/dist/provider-api/quota-governor.js +1 -1
  187. package/dist/provider-api/staged-datasets-store.d.ts +1 -0
  188. package/dist/provider-api/staged-datasets-store.js +1 -1
  189. package/dist/resources/handlers.d.ts +3 -3
  190. package/dist/resources/store.d.ts +1 -0
  191. package/dist/resources/store.js +1 -1
  192. package/dist/scripts/dev/index.js +15 -1
  193. package/dist/search/index.js +3 -0
  194. package/dist/secrets/routes.d.ts +9 -9
  195. package/dist/secrets/storage.d.ts +1 -0
  196. package/dist/secrets/storage.js +1 -1
  197. package/dist/server/agent-chat-plugin.js +38 -9
  198. package/dist/server/agent-engine-api-key-route.d.ts +1 -1
  199. package/dist/server/agent-teams-run-queue.d.ts +1 -0
  200. package/dist/server/agent-teams-run-queue.js +1 -1
  201. package/dist/server/auth-marketing.js +3 -1
  202. package/dist/server/auth.d.ts +18 -1
  203. package/dist/server/auth.js +370 -154
  204. package/dist/server/embed-session.d.ts +1 -0
  205. package/dist/server/embed-session.js +1 -1
  206. package/dist/server/google-auth-plugin.js +3 -1
  207. package/dist/server/google-oauth.d.ts +10 -0
  208. package/dist/server/google-oauth.js +25 -1
  209. package/dist/server/identity-sso-store.d.ts +1 -0
  210. package/dist/server/identity-sso-store.js +1 -1
  211. package/dist/server/index.d.ts +1 -1
  212. package/dist/server/index.js +1 -1
  213. package/dist/server/onboarding-html.js +200 -31
  214. package/dist/server/poll.d.ts +2 -0
  215. package/dist/server/poll.js +19 -1
  216. package/dist/server/realtime-token.d.ts +1 -1
  217. package/dist/server/release-migrations.js +5 -0
  218. package/dist/server/release-schema.d.ts +46 -0
  219. package/dist/server/release-schema.js +307 -0
  220. package/dist/settings/store.d.ts +1 -0
  221. package/dist/settings/store.js +1 -1
  222. package/dist/shared/environment-lanes.d.ts +28 -0
  223. package/dist/shared/environment-lanes.js +61 -0
  224. package/dist/sharing/actions/share-resource.js +22 -2
  225. package/dist/styles/agent-native.css +17 -15
  226. package/dist/triggers/routes.d.ts +11 -0
  227. package/dist/triggers/routes.js +10 -0
  228. package/dist/usage/alerts-store.d.ts +1 -0
  229. package/dist/usage/alerts-store.js +1 -1
  230. package/dist/usage/store.d.ts +1 -0
  231. package/dist/usage/store.js +1 -1
  232. package/docs/content/actions-access-control.mdx +136 -2
  233. package/docs/content/actions-agent-tools.mdx +101 -0
  234. package/docs/content/actions-defining.mdx +2 -2
  235. package/docs/content/audit-log.mdx +1 -1
  236. package/docs/content/authentication.mdx +1 -1
  237. package/docs/content/cloudflare.mdx +43 -0
  238. package/docs/content/creating-templates.mdx +1 -1
  239. package/docs/content/deploy-an-app.mdx +109 -0
  240. package/docs/content/deployment-environment-variables.mdx +101 -0
  241. package/docs/content/deployment.mdx +125 -792
  242. package/docs/content/docs-components.mdx +2 -2
  243. package/docs/content/environment-variables.mdx +41 -41
  244. package/docs/content/file-uploads.mdx +74 -40
  245. package/docs/content/harness-agents.mdx +2 -2
  246. package/docs/content/internationalization.mdx +61 -65
  247. package/docs/content/key-concepts.mdx +3 -3
  248. package/docs/content/multi-app-workspace.mdx +2 -2
  249. package/docs/content/netlify.mdx +47 -0
  250. package/docs/content/node-docker.mdx +138 -0
  251. package/docs/content/organizations-teams-permissions.mdx +5 -5
  252. package/docs/content/other-platforms.mdx +27 -0
  253. package/docs/content/ssr-caching.mdx +45 -0
  254. package/docs/content/template-assets-developers.mdx +2 -2
  255. package/docs/content/template-chat-developers.mdx +2 -2
  256. package/docs/content/template-content-developers.mdx +2 -2
  257. package/docs/content/{local-file-mode.mdx → template-content-local-files.mdx} +2 -1
  258. package/docs/content/template-content-sync.mdx +2 -2
  259. package/docs/content/toolkit-agent-ux.mdx +1 -1
  260. package/docs/content/toolkit-resources.mdx +2 -2
  261. package/docs/content/updating-ui-in-production.mdx +35 -0
  262. package/docs/content/vercel.mdx +38 -0
  263. package/docs/content/what-is-agent-native.mdx +1 -1
  264. package/docs/content/workspace-deployment.mdx +350 -0
  265. package/package.json +2 -2
  266. package/docs/content/agents.mdx +0 -9
  267. package/docs/content/database.mdx +0 -317
  268. package/docs/content/human-approval.mdx +0 -156
@@ -0,0 +1,350 @@
1
+ ---
2
+ title: "Workspace Deployment"
3
+ description: "Ship every app in an agent-native workspace to one origin with a single command, or self-host a workspace with Docker Compose."
4
+ ---
5
+
6
+ # Workspace Deployment
7
+
8
+ If your project is a [workspace](/docs/multi-app-workspace) with more than one app, you can deploy every app to a single origin instead of managing separate deployments per app. This page covers the managed one-command path and a self-hosted Docker Compose alternative. See [Deployment](/docs/deployment) for picking a database, a preset, and a platform first.
9
+
10
+ ## One Origin, Many Apps {#workspace-deploy}
11
+
12
+ Ship every app in a workspace to a single origin with one command:
13
+
14
+ ```bash
15
+ npx @agent-native/core@latest deploy
16
+ # https://your-agents.com/mail/* → apps/mail
17
+ # https://your-agents.com/calendar/* → apps/calendar
18
+ # https://your-agents.com/forms/* → apps/forms
19
+ ```
20
+
21
+ <Diagram id="doc-block-1aw1umr" title="One origin, many apps" summary={"Each workspace app is built with its own base path and mounted under a path prefix on a single origin. Login and cross-app A2A are same-origin and free as a result."}>
22
+
23
+ ```html
24
+ <div class="diagram-ws">
25
+ <div class="diagram-panel" data-rough>
26
+ <strong>https://your-agents.com</strong>
27
+ <div class="diagram-row">
28
+ <span class="diagram-pill accent">/mail/*</span
29
+ ><small class="diagram-muted">apps/mail</small>
30
+ </div>
31
+ <div class="diagram-row">
32
+ <span class="diagram-pill accent">/calendar/*</span
33
+ ><small class="diagram-muted">apps/calendar</small>
34
+ </div>
35
+ <div class="diagram-row">
36
+ <span class="diagram-pill accent">/forms/*</span
37
+ ><small class="diagram-muted">apps/forms</small>
38
+ </div>
39
+ </div>
40
+ <div class="diagram-col wins">
41
+ <span class="diagram-pill ok">shared login session</span
42
+ ><span class="diagram-pill ok">zero-config cross-app A2A</span>
43
+ </div>
44
+ </div>
45
+ ```
46
+
47
+ ```css
48
+ .diagram-ws {
49
+ display: flex;
50
+ align-items: center;
51
+ gap: 16px;
52
+ flex-wrap: wrap;
53
+ }
54
+ .diagram-ws .diagram-panel {
55
+ display: flex;
56
+ flex-direction: column;
57
+ gap: 6px;
58
+ padding: 14px 16px;
59
+ }
60
+ .diagram-ws .diagram-row {
61
+ display: flex;
62
+ align-items: center;
63
+ gap: 8px;
64
+ }
65
+ .diagram-ws .wins {
66
+ display: flex;
67
+ flex-direction: column;
68
+ gap: 8px;
69
+ align-items: flex-start;
70
+ }
71
+ ```
72
+
73
+ </Diagram>
74
+
75
+ **Same-origin** means every app looks like part of the same website to the browser. That gives you two big wins for free:
76
+
77
+ - **Shared login session**. Log into any app, and every app is logged in.
78
+ - **Zero-config cross-app A2A**. Tagging `@calendar` from mail is a same-origin fetch. There's no CORS and no JWT signing between siblings.
79
+
80
+ <Callout tone="info">
81
+
82
+ Under the hood, each app is built with its own **base path**, a URL prefix like `/mail` set via `APP_BASE_PATH`/`VITE_APP_BASE_PATH`, then packaged for the target Nitro preset. Cloudflare Pages routes through a generated **dispatcher worker**, a small script at `dist/_worker.js` that reads the incoming path and forwards the request to the matching app. Netlify uses one function per app plus generated redirects. Vercel writes a workspace-level `.vercel/output` using the Build Output API.
83
+
84
+ </Callout>
85
+
86
+ Publish the build for your platform:
87
+
88
+ <TabsBlock
89
+ id="doc-block-wsdeploytabs1"
90
+ tabs={[
91
+ {
92
+ id: "cloudflare",
93
+ label: "Cloudflare (default)",
94
+ blocks: [
95
+ {
96
+ type: "code",
97
+ id: "wf-cf",
98
+ data: { code: "wrangler pages deploy dist", language: "bash" },
99
+ },
100
+ ],
101
+ },
102
+ {
103
+ id: "netlify",
104
+ label: "Netlify",
105
+ blocks: [
106
+ {
107
+ type: "code",
108
+ id: "wf-nl",
109
+ data: {
110
+ code: "npx @agent-native/core@latest deploy --preset netlify",
111
+ language: "bash",
112
+ },
113
+ },
114
+ ],
115
+ },
116
+ {
117
+ id: "vercel",
118
+ label: "Vercel",
119
+ blocks: [
120
+ {
121
+ type: "code",
122
+ id: "wf-vc",
123
+ data: {
124
+ code: "npx @agent-native/core@latest deploy --preset vercel",
125
+ language: "bash",
126
+ },
127
+ },
128
+ ],
129
+ },
130
+ ]}
131
+ />
132
+
133
+ <Callout tone="warning">
134
+
135
+ Hosted workspace builds require `A2A_SECRET` in the deploy provider environment. Without it, Slack, inbound webhooks, and cross-app A2A resume don't work, since those all go through signed background processors. Local `--build-only` artifact checks still run without it.
136
+
137
+ </Callout>
138
+
139
+ <Callout tone="info">
140
+
141
+ Wiring up a provider build command instead of deploying by hand? Add `--build-only` to the same command, for example `npx @agent-native/core@latest deploy --preset vercel --build-only`. It writes the output directly, so no `vercel.json` is required for workspace routing.
142
+
143
+ Prefer a separate domain per app instead of one shared origin? Every app in the workspace is still independently deployable. Run `cd apps/<name> && npx @agent-native/core@latest build` like a standalone scaffold.
144
+
145
+ </Callout>
146
+
147
+ ## Self-hosted Workspace with Docker Compose {#workspace-docker-compose}
148
+
149
+ A workspace is not one Nitro server process today. Each app still builds to its own `.output/` directory and runs its own Node/Nitro server, so self-hosting a workspace means running several servers behind a single entry point.
150
+
151
+ <Diagram id="doc-block-3selfhost1" title="Self-hosted workspace shape" summary={"One reverse proxy in front of one container per app, all pointing at the same Postgres database."}>
152
+
153
+ ```html
154
+ <div class="diagram-selfhost">
155
+ <div class="diagram-box" data-rough>Internet</div>
156
+ <div class="diagram-arrow diagram-muted" aria-hidden="true">&rarr;</div>
157
+ <div class="diagram-panel center" data-rough>
158
+ <span class="diagram-pill accent">proxy</span
159
+ ><small class="diagram-muted">routes by path prefix</small>
160
+ </div>
161
+ <div class="diagram-arrow diagram-muted" aria-hidden="true">&rarr;</div>
162
+ <div class="diagram-col">
163
+ <div class="diagram-row">
164
+ <span class="diagram-pill">/mail</span
165
+ ><small class="diagram-muted">mail container</small>
166
+ </div>
167
+ <div class="diagram-row">
168
+ <span class="diagram-pill">/calendar</span
169
+ ><small class="diagram-muted">calendar container</small>
170
+ </div>
171
+ </div>
172
+ <div class="diagram-arrow diagram-muted" aria-hidden="true">&harr;</div>
173
+ <div class="diagram-box" data-rough>
174
+ Shared Postgres<br /><small class="diagram-muted">one DATABASE_URL</small>
175
+ </div>
176
+ </div>
177
+ ```
178
+
179
+ ```css
180
+ .diagram-selfhost {
181
+ display: flex;
182
+ align-items: center;
183
+ gap: 12px;
184
+ flex-wrap: wrap;
185
+ }
186
+ .diagram-selfhost .diagram-panel.center {
187
+ display: flex;
188
+ flex-direction: column;
189
+ align-items: center;
190
+ gap: 4px;
191
+ padding: 14px 16px;
192
+ }
193
+ .diagram-selfhost .diagram-col {
194
+ display: flex;
195
+ flex-direction: column;
196
+ gap: 8px;
197
+ }
198
+ .diagram-selfhost .diagram-row {
199
+ display: flex;
200
+ align-items: center;
201
+ gap: 8px;
202
+ }
203
+ .diagram-selfhost .diagram-arrow {
204
+ font-size: 22px;
205
+ line-height: 1;
206
+ }
207
+ ```
208
+
209
+ </Diagram>
210
+
211
+ A **reverse proxy** is that single entry point in the picture above: it receives every request and forwards it to the right container based on the URL path, the same job Cloudflare's dispatcher worker does for a managed deploy. On a VPS, that means one container per workspace app, all pointing at the same Postgres database and shared production secrets, with the proxy in front.
212
+
213
+ <Steps>
214
+
215
+ ### Build each app with a matching base path
216
+
217
+ The base path is a build-time input for the client bundle and a runtime input for the server. Build each app with the same path the proxy will route to it:
218
+
219
+ ```bash maxLines=8
220
+ APP_BASE_PATH=/mail VITE_APP_BASE_PATH=/mail npx @agent-native/core@latest build
221
+ node .output/server/index.mjs
222
+ ```
223
+
224
+ ### Write a reusable Dockerfile
225
+
226
+ Take the app name and path prefix as build arguments, so one Dockerfile serves every app in the workspace:
227
+
228
+ ```dockerfile filename="Dockerfile.workspace-app" maxLines=12
229
+ FROM node:24-slim AS build
230
+ WORKDIR /workspace
231
+ RUN corepack enable
232
+ COPY package.json pnpm-lock.yaml pnpm-workspace.yaml ./
233
+ COPY packages ./packages
234
+ COPY apps ./apps
235
+ ARG APP_NAME
236
+ ARG APP_BASE_PATH
237
+ ENV APP_BASE_PATH=$APP_BASE_PATH
238
+ ENV VITE_APP_BASE_PATH=$APP_BASE_PATH
239
+ RUN pnpm install --frozen-lockfile
240
+ RUN pnpm --dir apps/$APP_NAME build
241
+
242
+ FROM node:24-slim
243
+ WORKDIR /app
244
+ ARG APP_NAME
245
+ ARG APP_BASE_PATH
246
+ ENV NODE_ENV=production
247
+ ENV PORT=3000
248
+ ENV APP_BASE_PATH=$APP_BASE_PATH
249
+ COPY --from=build /workspace/apps/$APP_NAME/.output .output
250
+ EXPOSE 3000
251
+ CMD ["node", ".output/server/index.mjs"]
252
+ ```
253
+
254
+ ### Compose Postgres, the apps, and the proxy
255
+
256
+ This example uses Caddy because it can terminate HTTP locally or sit behind Cloudflare's SSL proxy, but the important part is the path-prefix routing:
257
+
258
+ ```yaml filename="docker-compose.yml" maxLines=30
259
+ services:
260
+ postgres:
261
+ image: postgres:17
262
+ restart: unless-stopped
263
+ environment:
264
+ POSTGRES_DB: agent_native
265
+ POSTGRES_USER: agent_native
266
+ POSTGRES_PASSWORD: change-me
267
+ volumes:
268
+ - postgres-data:/var/lib/postgresql/data
269
+
270
+ mail:
271
+ build:
272
+ context: .
273
+ dockerfile: Dockerfile.workspace-app
274
+ args:
275
+ APP_NAME: mail
276
+ APP_BASE_PATH: /mail
277
+ restart: unless-stopped
278
+ environment:
279
+ DATABASE_URL: postgres://agent_native:change-me@postgres:5432/agent_native
280
+ BETTER_AUTH_URL: https://agents.example.com/mail
281
+ BETTER_AUTH_SECRET: ${BETTER_AUTH_SECRET}
282
+ A2A_SECRET: ${A2A_SECRET}
283
+ ANTHROPIC_API_KEY: ${ANTHROPIC_API_KEY}
284
+ depends_on:
285
+ - postgres
286
+
287
+ calendar:
288
+ build:
289
+ context: .
290
+ dockerfile: Dockerfile.workspace-app
291
+ args:
292
+ APP_NAME: calendar
293
+ APP_BASE_PATH: /calendar
294
+ restart: unless-stopped
295
+ environment:
296
+ DATABASE_URL: postgres://agent_native:change-me@postgres:5432/agent_native
297
+ BETTER_AUTH_URL: https://agents.example.com/calendar
298
+ BETTER_AUTH_SECRET: ${BETTER_AUTH_SECRET}
299
+ A2A_SECRET: ${A2A_SECRET}
300
+ ANTHROPIC_API_KEY: ${ANTHROPIC_API_KEY}
301
+ depends_on:
302
+ - postgres
303
+
304
+ proxy:
305
+ image: caddy:2
306
+ restart: unless-stopped
307
+ ports:
308
+ - "80:80"
309
+ - "443:443"
310
+ volumes:
311
+ - ./Caddyfile:/etc/caddy/Caddyfile:ro
312
+ depends_on:
313
+ - mail
314
+ - calendar
315
+
316
+ volumes:
317
+ postgres-data:
318
+ ```
319
+
320
+ ### Configure the proxy
321
+
322
+ ```caddyfile filename="Caddyfile"
323
+ agents.example.com {
324
+ reverse_proxy /mail* mail:3000
325
+ reverse_proxy /calendar* calendar:3000
326
+ }
327
+ ```
328
+
329
+ </Steps>
330
+
331
+ <Callout tone="info">
332
+
333
+ - Keep `DATABASE_URL`, `BETTER_AUTH_SECRET`, `A2A_SECRET`, and other production
334
+ secrets identical across app containers when you want shared auth, shared
335
+ credentials, and cross-app A2A.
336
+ - Set `BETTER_AUTH_URL` to the public URL for that app path. OAuth callback URLs
337
+ should use the same public URL.
338
+ - Do not rely on the container filesystem for production data. Use Postgres (or
339
+ another persistent SQL backend) for `DATABASE_URL`.
340
+ - If Cloudflare terminates TLS in front of the VPS, configure Cloudflare to send
341
+ normal `X-Forwarded-Proto` / `X-Forwarded-Host` headers and route the public
342
+ host to the proxy container.
343
+
344
+ </Callout>
345
+
346
+ ## What's next
347
+
348
+ - [**Deployment**](/docs/deployment) — pick a persistent database, a Nitro preset, and a platform before deploying a workspace
349
+ - [**Multi-App Workspace**](/docs/multi-app-workspace) — the workspace model this page's `deploy` command builds on
350
+ - [**Security**](/docs/security) — the production checklist and opt-in flags for a hosted deployment
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@agent-native/core",
3
- "version": "0.164.4",
3
+ "version": "0.164.12",
4
4
  "description": "Framework for agent-native application development — where AI agents and UI share SQL state, actions, and context",
5
5
  "homepage": "https://github.com/BuilderIO/agent-native#readme",
6
6
  "bugs": {
@@ -428,7 +428,7 @@
428
428
  "yjs": "^13.6.32",
429
429
  "zod": "^4.3.6",
430
430
  "@agent-native/recap-cli": "0.5.5",
431
- "@agent-native/toolkit": "^0.16.6"
431
+ "@agent-native/toolkit": "^0.16.7"
432
432
  },
433
433
  "devDependencies": {
434
434
  "@ai-sdk/anthropic": "^3.0.71",
@@ -1,9 +0,0 @@
1
- ---
2
- title: "Agents"
3
- description: "Agent configuration, instructions, and the surfaces agents operate through."
4
- draft: true
5
- ---
6
-
7
- # Agents
8
-
9
- This section is coming soon. In the meantime, see [Writing Agent Instructions](/docs/writing-agent-instructions), [Skills](/docs/skills-guide), and [Agent Surfaces](/docs/agent-surfaces) for existing coverage.
@@ -1,317 +0,0 @@
1
- ---
2
- title: "Database"
3
- description: "Connect a portable SQL database to your agent-native app and write provider-agnostic Drizzle code."
4
- ---
5
-
6
- # Database
7
-
8
- Agent-native apps use [Drizzle ORM](https://orm.drizzle.team) and support portable SQL backends. For anything beyond local development, connect a persistent SQL database — Postgres, libSQL/Turso, or another Drizzle-compatible backend — by setting `DATABASE_URL`. When that variable is unset, the app falls back to a zero-config local SQLite file so you can start developing immediately. For local development that should behave like Postgres without running a separate database server, opt into PGlite with `DATABASE_URL=pglite:./data/pglite`.
9
-
10
- <Diagram id="doc-block-vykcz4" title="One schema, many backends" summary={"App code uses the framework's dialect-agnostic helpers. The dialect is auto-detected from DATABASE_URL at runtime; unset means a local SQLite file."}>
11
-
12
- ```html
13
- <div class="diagram-db">
14
- <div class="diagram-panel center" data-rough>
15
- <span class="diagram-pill accent">@agent-native/core/db/schema</span
16
- ><small class="diagram-muted">table · text · integer · real · now</small
17
- ><small class="diagram-muted">+ Drizzle query DSL</small>
18
- </div>
19
- <div class="diagram-arrow diagram-muted" aria-hidden="true">&rarr;</div>
20
- <div class="diagram-box" data-rough>
21
- DATABASE_URL<br /><small class="diagram-muted">dialect auto-detected</small>
22
- </div>
23
- <div class="diagram-arrow diagram-muted" aria-hidden="true">&rarr;</div>
24
- <div class="diagram-grid">
25
- <span class="diagram-pill"
26
- >Postgres<br /><small class="diagram-muted">Neon · Supabase</small></span
27
- ><span class="diagram-pill">libSQL / Turso</span
28
- ><span class="diagram-pill">Cloudflare D1</span
29
- ><span class="diagram-pill warn"
30
- >SQLite file<br /><small class="diagram-muted"
31
- >unset = local dev only</small
32
- ></span
33
- ><span class="diagram-pill warn"
34
- >PGlite<br /><small class="diagram-muted"
35
- >local Postgres opt-in</small
36
- ></span
37
- >
38
- </div>
39
- </div>
40
- ```
41
-
42
- ```css
43
- .diagram-db {
44
- display: flex;
45
- align-items: center;
46
- gap: 12px;
47
- flex-wrap: wrap;
48
- }
49
- .diagram-db .center {
50
- display: flex;
51
- flex-direction: column;
52
- align-items: center;
53
- gap: 4px;
54
- padding: 14px 16px;
55
- }
56
- .diagram-db .diagram-arrow {
57
- font-size: 22px;
58
- line-height: 1;
59
- }
60
- .diagram-db .diagram-grid {
61
- display: grid;
62
- grid-template-columns: repeat(2, minmax(0, 1fr));
63
- gap: 8px;
64
- }
65
- ```
66
-
67
- </Diagram>
68
-
69
- ## Local default: SQLite file {#default-sqlite}
70
-
71
- When `DATABASE_URL` is not set, the app creates a SQLite database at `data/app.db`. This is the zero-config default for local development — no setup required. It is meant for development only; for production, set `DATABASE_URL` to a persistent SQL database.
72
-
73
- Do not rely on that local file for deployed apps. Containers, serverless functions, and preview environments may reset their filesystem, which means a local SQLite file can disappear between restarts. Set `DATABASE_URL` to a persistent hosted database before production use.
74
-
75
- ## Local Postgres Opt-In: PGlite {#local-pglite}
76
-
77
- Install the optional PGlite package, then set `DATABASE_URL=pglite:./data/pglite` to run the app against [PGlite](https://pglite.dev/), a local WASM Postgres database:
78
-
79
- ```bash
80
- pnpm add @electric-sql/pglite@^0.5.3
81
- ```
82
-
83
- This keeps local development on the Postgres dialect, including Postgres schema helpers and migrations, without requiring Docker or a hosted database.
84
-
85
- PGlite is still local development storage. Treat it like the SQLite fallback for durability and sharing: use it to test Postgres-shaped behavior on your machine, then set `DATABASE_URL` to a persistent hosted database for production, previews, or any shared environment.
86
-
87
- ## Connecting a Production Database {#production}
88
-
89
- Set `DATABASE_URL` in your `.env` file or deploy-provider environment to connect a hosted database. Turso is not required; use whichever Drizzle-compatible SQL backend fits your deployment:
90
-
91
- ```bash
92
- # Neon Postgres
93
- DATABASE_URL=postgres://user:pass@ep-cool-name-123456.us-east-2.aws.neon.tech/mydb?sslmode=require
94
-
95
- # Supabase Postgres
96
- DATABASE_URL=postgres://postgres.xxxx:pass@aws-0-us-east-1.pooler.supabase.com:6543/postgres
97
-
98
- # Plain Postgres
99
- DATABASE_URL=postgres://user:pass@localhost:5432/mydb
100
-
101
- # Local PGlite (Postgres dialect, local development only)
102
- DATABASE_URL=pglite:./data/pglite
103
-
104
- # Turso (libSQL)
105
- DATABASE_URL=libsql://my-db-org.turso.io
106
- DATABASE_AUTH_TOKEN=your-token
107
- ```
108
-
109
- The framework auto-detects the dialect from the URL and configures Drizzle accordingly. The built-in adapters cover Postgres URLs, local PGlite URLs, libSQL/Turso URLs, SQLite file URLs, and Cloudflare D1 bindings. Common production choices include Neon, Supabase, Turso/libSQL, plain Postgres, durable SQLite, and Builder.io-managed environments when available.
110
-
111
- ## Builder.io Managed Database {#builder-managed}
112
-
113
- _Planned (not yet available):_ when connected to Builder.io, your app will be able to use a managed database provisioned automatically, with no connection strings required.
114
-
115
- ## Where the DB Client Lives {#db-client}
116
-
117
- Each template creates a lazy, singleton Drizzle client by calling `createGetDb(schema)` from `@agent-native/core/db`. The canonical location is `server/db/index.ts`:
118
-
119
- ```ts filename="server/db/index.ts"
120
- import { createGetDb } from "@agent-native/core/db";
121
- import * as schema from "./schema.js";
122
-
123
- export const getDb = createGetDb(schema);
124
- ```
125
-
126
- Import `getDb` from this template-local path — `../../server/db/index.js` in routes, `../server/db/index.js` in actions — rather than from `@agent-native/core` directly. The core export returns a generic untyped instance; the template's `getDb()` carries your schema types. See [Server](/docs/server-routes#request-context) for how actions and custom routes each import it.
127
-
128
- ## Dialect-Agnostic Schema And Queries {#schema}
129
-
130
- App database code should use Drizzle's schema and query DSL so it can run across providers. Never write SQLite-only syntax (`INSERT OR REPLACE`, `AUTOINCREMENT`, `datetime('now')`) or Postgres-only syntax in product code.
131
-
132
- Use the framework's schema helpers from `@agent-native/core/db/schema`:
133
-
134
- ```ts
135
- import { table, text, integer, real, now } from "@agent-native/core/db/schema";
136
-
137
- export const tasks = table("tasks", {
138
- id: text("id").primaryKey(),
139
- title: text("title").notNull(),
140
- priority: integer("priority").notNull().default(0),
141
- weight: real("weight"),
142
- done: integer("done", { mode: "boolean" }).notNull().default(false),
143
- ownerEmail: text("owner_email").notNull(),
144
- createdAt: text("created_at").notNull().default(now()),
145
- });
146
- ```
147
-
148
- | Helper | Purpose |
149
- | --------- | --------------------------------------------------------------- |
150
- | `table` | Define a table — delegates to `pgTable` or `sqliteTable` |
151
- | `text` | Text column, supports `{ enum: [...] }` |
152
- | `integer` | Integer column, `{ mode: "boolean" }` maps to Postgres boolean |
153
- | `real` | Float column — `real` on SQLite, `double precision` on Postgres |
154
- | `now` | Dialect-agnostic current timestamp for `.default(now())` |
155
-
156
- The `tasks` table above defines the same columns on every backend:
157
-
158
- <DataModel
159
- id="doc-block-14e70da"
160
- title="The tasks table"
161
- summary={
162
- "Defined once with the framework helpers; the dialect is chosen at runtime from DATABASE_URL."
163
- }
164
- entities={[
165
- {
166
- id: "tasks",
167
- name: "tasks",
168
- note: "Domain table. Add owner_email (or ...ownableColumns()) so SQL-level scoping can filter rows to the authenticated user.",
169
- fields: [
170
- {
171
- name: "id",
172
- type: "text",
173
- pk: true,
174
- nullable: false,
175
- },
176
- {
177
- name: "title",
178
- type: "text",
179
- nullable: false,
180
- },
181
- {
182
- name: "priority",
183
- type: "integer",
184
- nullable: false,
185
- note: "default 0",
186
- },
187
- {
188
- name: "weight",
189
- type: "real",
190
- nullable: true,
191
- },
192
- {
193
- name: "done",
194
- type: "integer (boolean mode)",
195
- nullable: false,
196
- note: "default false; maps to a Postgres boolean",
197
- },
198
- {
199
- name: "owner_email",
200
- type: "text",
201
- nullable: false,
202
- note: "enables data scoping",
203
- },
204
- {
205
- name: "created_at",
206
- type: "text",
207
- nullable: false,
208
- note: "default now()",
209
- },
210
- ],
211
- },
212
- ]}
213
- />
214
-
215
- Never import from `drizzle-orm/sqlite-core` or `drizzle-orm/pg-core` directly. Always use `@agent-native/core/db/schema`.
216
-
217
- Tables that store user-facing data must include an `owner_email` column so the framework's SQL-level scoping can filter rows to the authenticated user — see [Security](/docs/security#data-scoping). Tables that also support sharing with other users or orgs should spread `...ownableColumns()` instead, which adds `owner_email`, `org_id`, and `visibility` in one call — see [Sharing](/docs/sharing#building).
218
-
219
- For reads and writes, use Drizzle's query builder and portable operators from `drizzle-orm`:
220
-
221
- ```ts
222
- import { and, desc, eq } from "drizzle-orm";
223
- import { getDb } from "../server/db/index.js";
224
- import { tasks } from "../server/db/schema.js";
225
-
226
- const db = getDb();
227
-
228
- const openTasks = await db
229
- .select()
230
- .from(tasks)
231
- .where(and(eq(tasks.ownerEmail, userEmail), eq(tasks.done, false)))
232
- .orderBy(desc(tasks.createdAt));
233
-
234
- await db.update(tasks).set({ done: true }).where(eq(tasks.id, taskId));
235
- ```
236
-
237
- ## Raw SQL Escape Hatches {#raw-sql}
238
-
239
- Raw SQL is not the default app-code API. Use it only for additive migrations, health checks, carefully reviewed advanced queries that Drizzle cannot express, or one-off maintenance. Keep it parameterized and dialect-agnostic. For timestamps in Drizzle schemas, prefer `.default(now())`; for migration SQL, use `runMigrations()` so framework-supported compatibility rewrites and dialect-gated statements stay centralized.
240
-
241
- For cases where you truly need raw SQL outside of Drizzle queries:
242
-
243
- - `getDbExec()` — auto-converts `?` params to `$1` for Postgres
244
- - `isPostgres()` — runtime dialect check
245
- - `intType()` — returns the correct integer type for the current dialect
246
-
247
- ## Migrations and Schema Updates {#migrations}
248
-
249
- In hosted environments, multiple deployment previews, branches, and the production server share the same underlying database. Therefore, database schema updates must follow strict constraints to avoid data loss and service disruption.
250
-
251
- ### The "Zero Destructive Changes" Rule
252
-
253
- All database schema updates must be **strictly additive**.
254
-
255
- - **Do not drop tables or columns.**
256
- - **Do not rename tables or columns.** Renaming a column or table looks like a drop + create sequence to Drizzle, which will permanently delete your existing production data.
257
- - If a column needs to be renamed or replaced, add the new column alongside the old one, update your application code to read from/write to both, migrate the data, and only retire the old column in a later release once no active deployments are referencing it.
258
-
259
- <Callout tone="risk">
260
- **Never run `drizzle-kit push` against a production database.** Template
261
- database schemas only define app-specific domain tables; they do not define
262
- central framework tables (`user`, `session`, `application_state`, etc.). If
263
- you run `drizzle-kit push` against production, Drizzle will detect these
264
- framework tables as "not in schema" and attempt to drop them, causing
265
- immediate system-wide failure and data loss.
266
- </Callout>
267
-
268
- ### Safe Migration Path
269
-
270
- Instead of pushing directly, schema changes should be applied via additive SQL
271
- migrations. For local development, implement them in a server plugin (e.g.
272
- `server/plugins/db.ts`) by invoking the framework's `runMigrations()` helper.
273
- For production or serverless deployments, run migrations in a release or deploy
274
- step instead of on the first request. The Chat template provides
275
- `pnpm migrate:production` for this.
276
-
277
- <AnnotatedCode
278
- id="doc-block-zaaj7e"
279
- title="An additive migration plugin"
280
- filename="server/plugins/db.ts"
281
- language="ts"
282
- code={
283
- 'import { runMigrations } from "@agent-native/core/db";\n\nexport default runMigrations(\n [\n {\n version: 1,\n sql: `ALTER TABLE projects ADD COLUMN IF NOT EXISTS sort_order INTEGER NOT NULL DEFAULT 0`,\n },\n {\n // Dialect-gated: runs only on the matching backend. Omit the other key\n // to make it a no-op on that dialect.\n version: 2,\n sql: {\n postgres: `ALTER TABLE projects ADD COLUMN IF NOT EXISTS tsv tsvector`,\n sqlite: `SELECT 1`, // no-op; tsvector is Postgres-only\n },\n },\n ],\n { table: "my_app_migrations" },\n);'
284
- }
285
- annotations={[
286
- {
287
- lines: "6-7",
288
- label: "Additive only",
289
- note: "`ADD COLUMN IF NOT EXISTS` is safe to re-run and never drops data. Renames look like drop+create to Drizzle, so add-then-migrate instead.",
290
- },
291
- {
292
- lines: "13-16",
293
- label: "Dialect gating",
294
- note: "Pass an object keyed by dialect to run different SQL per backend. Make the other key a no-op (`SELECT 1`) for Postgres-only or SQLite-only features.",
295
- },
296
- {
297
- lines: "19",
298
- label: "Per-app version table",
299
- note: "Each app tracks its own applied versions so migrations are idempotent across restarts and instances.",
300
- },
301
- ]}
302
- />
303
-
304
- ## Environment Variables {#environment-variables}
305
-
306
- | Variable | Purpose |
307
- | --------------------- | ------------------------------------------------------------------------------------------------------- |
308
- | `DATABASE_URL` | Persistent SQL connection string (unset = local SQLite; `pglite:./data/pglite` = local Postgres opt-in) |
309
- | `DATABASE_AUTH_TOKEN` | Auth token for providers that require a separate token, such as Turso/libSQL |
310
-
311
- ## What's next
312
-
313
- - [**Security — Data Scoping**](/docs/security#data-scoping) — how `owner_email` and access helpers scope reads and writes
314
- - [**Sharing**](/docs/sharing#building) — `ownableColumns()` and the visibility model for shared resources
315
- - [**Server**](/docs/server-routes#request-context) — how actions and custom routes each import `getDb`
316
- - [**Deployment**](/docs/deployment#persistent-database) — connecting a persistent database per deploy target
317
- - [**Actions**](/docs/actions-access-control#access-control) — a complete, paste-ready action that reads and writes through `getDb`/`schema`