okengine 0.11.2 → 0.12.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 (1261) hide show
  1. package/manifest.v1.schema.json +1 -1
  2. package/package.json +57 -3
  3. package/site/content/docs/ai/index.mdx +2 -2
  4. package/site/content/docs/ai/llms-txt.mdx +21 -16
  5. package/site/content/docs/ai/mcp.mdx +1 -1
  6. package/site/content/docs/ai/skills.mdx +16 -14
  7. package/site/content/docs/deployment/docker-swarm.mdx +7 -8
  8. package/site/content/docs/deployment/docker.mdx +20 -12
  9. package/site/content/docs/deployment/index.mdx +2 -2
  10. package/site/content/docs/deployment/kubernetes.mdx +2 -2
  11. package/site/content/docs/deployment/reverse-proxy.mdx +39 -21
  12. package/site/content/docs/elements/ai.mdx +25 -15
  13. package/site/content/docs/elements/channel.mdx +2 -2
  14. package/site/content/docs/elements/clock.mdx +11 -1
  15. package/site/content/docs/elements/flow.mdx +66 -16
  16. package/site/content/docs/elements/gate.mdx +47 -39
  17. package/site/content/docs/elements/signal.mdx +2 -2
  18. package/site/content/docs/elements/store.mdx +191 -48
  19. package/site/content/docs/elements/vault.mdx +126 -41
  20. package/site/content/docs/get-started/basic-usage.mdx +14 -6
  21. package/site/content/docs/get-started/installation.mdx +24 -16
  22. package/site/content/docs/plugins/cors.mdx +9 -9
  23. package/site/content/docs/plugins/csrf.mdx +1 -1
  24. package/site/content/docs/providers/cockroachdb.mdx +13 -0
  25. package/site/content/docs/providers/neon.mdx +22 -0
  26. package/site/content/docs/providers/supabase.mdx +17 -0
  27. package/site/content/docs/providers/yugabytedb.mdx +15 -0
  28. package/site/content/docs/recipes/caddy.mdx +3 -3
  29. package/site/content/docs/recipes/cockroachdb.mdx +8 -2
  30. package/site/content/docs/recipes/index.mdx +6 -1
  31. package/site/content/docs/recipes/llama-cpp.mdx +5 -6
  32. package/site/content/docs/recipes/mailpit.mdx +3 -3
  33. package/site/content/docs/recipes/meilisearch.mdx +4 -4
  34. package/site/content/docs/recipes/meta.json +1 -0
  35. package/site/content/docs/recipes/nginx.mdx +117 -0
  36. package/site/content/docs/recipes/ollama.mdx +3 -3
  37. package/site/content/docs/recipes/pgdog.mdx +1 -1
  38. package/site/content/docs/recipes/postgres.mdx +44 -8
  39. package/site/content/docs/recipes/redis.mdx +7 -2
  40. package/site/content/docs/recipes/rustfs.mdx +4 -4
  41. package/site/content/docs/recipes/sglang.mdx +2 -2
  42. package/site/content/docs/recipes/supabase-docker.mdx +24 -0
  43. package/site/content/docs/recipes/timescale.mdx +30 -6
  44. package/site/content/docs/recipes/traefik.mdx +10 -7
  45. package/site/content/docs/recipes/vllm.mdx +2 -2
  46. package/site/content/docs/recipes/yugabytedb.mdx +7 -1
  47. package/site/content/docs/reference/cli.md +67 -34
  48. package/site/content/docs/reference/client.mdx +39 -20
  49. package/site/content/docs/reference/configuration.mdx +31 -24
  50. package/site/content/docs/reference/environment-variables.mdx +23 -20
  51. package/site/content/docs/reference/errors.mdx +25 -20
  52. package/site/content/docs/reference/fx.mdx +19 -12
  53. package/site/content/docs/reference/plugins.mdx +2 -2
  54. package/site/content/docs/reference/security.md +16 -7
  55. package/src/auth/auth.test.ts +2 -2
  56. package/src/auth/bindings.ts +5 -5
  57. package/src/auth/config.ts +8 -0
  58. package/src/auth/gate-auth.test.ts +5 -5
  59. package/src/auth/index.ts +3 -0
  60. package/src/auth/operator.ts +1 -1
  61. package/src/auth/password-policy.test.ts +142 -5
  62. package/src/auth/password-policy.ts +128 -12
  63. package/src/auth/plugin.ts +2 -2
  64. package/src/cli/ai-setup/ai-setup.test.ts +1 -1
  65. package/src/cli/ai-setup/apply.ts +3 -18
  66. package/src/cli/ai-setup/index.ts +4 -4
  67. package/src/cli/ai-setup/prompts.ts +1 -1
  68. package/src/cli/ask-seed.test.ts +27 -0
  69. package/src/cli/ask-seed.ts +11 -7
  70. package/src/cli/attach-host-console.test.ts +134 -0
  71. package/src/cli/attach-host-console.ts +100 -0
  72. package/src/cli/console-cmd.test.ts +81 -0
  73. package/src/cli/console-cmd.ts +107 -0
  74. package/src/cli/db-seed.ts +14 -3
  75. package/src/cli/db.test.ts +37 -2
  76. package/src/cli/db.ts +26 -0
  77. package/src/cli/dev-app-runner.ts +6 -40
  78. package/src/cli/dev-console-vite.test.ts +86 -0
  79. package/src/cli/dev-console-vite.ts +164 -0
  80. package/src/cli/dev-schema-sync.ts +2 -2
  81. package/src/cli/dev.test.ts +78 -2
  82. package/src/cli/dev.ts +170 -56
  83. package/src/cli/docker-cli.test.ts +2 -2
  84. package/src/cli/docker.ts +1 -1
  85. package/src/cli/doctor.ts +2 -1
  86. package/src/cli/drizzle-env.test.ts +4 -9
  87. package/src/cli/drizzle-env.ts +2 -2
  88. package/src/cli/hero-meta.test.ts +37 -0
  89. package/src/cli/hero-meta.ts +30 -9
  90. package/src/cli/index.ts +5 -0
  91. package/src/cli/load-config.images.test.ts +12 -12
  92. package/src/cli/load-config.ts +1 -1
  93. package/src/cli/project-state.test.ts +6 -2
  94. package/src/cli/project-state.ts +27 -11
  95. package/src/cli/registry.ts +11 -0
  96. package/src/cli/replay.ts +7 -2
  97. package/src/cli/vault-cmd.test.ts +2 -0
  98. package/src/cli/vault-cmd.ts +7 -2
  99. package/src/client/create.test.ts +38 -2
  100. package/src/client/create.ts +16 -11
  101. package/src/client/index.ts +6 -0
  102. package/src/client/pager.test.ts +66 -0
  103. package/src/client/pager.ts +138 -0
  104. package/src/client/transport.ts +9 -6
  105. package/src/client/types.ts +58 -10
  106. package/src/compiler/aot.test.ts +12 -2
  107. package/src/compiler/effects-infer.ts +13 -4
  108. package/src/compiler/extract.test.ts +243 -5
  109. package/src/compiler/extract.ts +323 -58
  110. package/src/compiler/fixtures/skyport/src/flows/bookings/index.ts +2 -2
  111. package/src/compiler/fixtures/skyport/src/gates.ts +2 -0
  112. package/src/compiler/fixtures/skyport.expected.json +4 -0
  113. package/src/config/driver-defaults.test.ts +3 -0
  114. package/src/config/driver-defaults.ts +14 -0
  115. package/src/config/index.ts +5 -0
  116. package/src/console/budget.test.ts +27 -37
  117. package/src/console/index.ts +3 -0
  118. package/src/console/password-policy.ts +89 -0
  119. package/src/console/server/app.ts +138 -12
  120. package/src/console/server/auth-rate.test.ts +3 -3
  121. package/src/console/server/auth-store.test.ts +222 -0
  122. package/src/console/server/auth-store.ts +499 -0
  123. package/src/console/server/bind.ts +2 -3
  124. package/src/console/server/channels.test.ts +1 -1
  125. package/src/console/server/claim.test.ts +60 -1
  126. package/src/console/server/claim.ts +137 -2
  127. package/src/console/server/console.test.ts +102 -6
  128. package/src/console/server/dry-run.audit.test.ts +5 -2
  129. package/src/console/server/files-catalog.test.ts +51 -0
  130. package/src/console/server/files-catalog.ts +122 -0
  131. package/src/console/server/flows-invoke.test.ts +655 -38
  132. package/src/console/server/flows.ts +907 -90
  133. package/src/console/server/gates.test.ts +59 -0
  134. package/src/console/server/gates.ts +17 -14
  135. package/src/console/server/i18n.ts +7 -4
  136. package/src/console/server/index-search.test.ts +57 -0
  137. package/src/console/server/index-search.ts +102 -0
  138. package/src/console/server/index.ts +32 -1
  139. package/src/console/server/instances.test.ts +68 -0
  140. package/src/console/server/instances.ts +58 -0
  141. package/src/console/server/invoke-user-flow.test.ts +206 -0
  142. package/src/console/server/invoke-user-flow.ts +367 -0
  143. package/src/console/server/live.test.ts +44 -1
  144. package/src/console/server/live.ts +16 -0
  145. package/src/console/server/operator-db.test.ts +5 -5
  146. package/src/console/server/operator-db.ts +2 -2
  147. package/src/console/server/panel-load.ts +1 -0
  148. package/src/console/server/plugin.ts +12 -2
  149. package/src/console/server/runs-history.test.ts +143 -0
  150. package/src/console/server/runs-ingest.test.ts +379 -0
  151. package/src/console/server/runs-ingest.ts +127 -0
  152. package/src/console/server/runs-list-nesting.test.ts +97 -0
  153. package/src/console/server/runs-pii.test.ts +69 -0
  154. package/src/console/server/runs-pii.ts +50 -4
  155. package/src/console/server/runs-query-guard.test.ts +75 -0
  156. package/src/console/server/runs-query-guard.ts +224 -0
  157. package/src/console/server/runs-query-mask.test.ts +37 -0
  158. package/src/console/server/runs-query-mask.ts +82 -0
  159. package/src/console/server/runs-query.test.ts +287 -0
  160. package/src/console/server/runs-query.ts +107 -0
  161. package/src/console/server/security-headers.ts +21 -2
  162. package/src/console/server/security.gate.test.ts +306 -3
  163. package/src/console/server/serve.ts +138 -9
  164. package/src/console/server/spa-paths.test.ts +36 -0
  165. package/src/console/server/spa-proxy.test.ts +86 -0
  166. package/src/console/server/sql-catalog.ts +572 -0
  167. package/src/console/server/sql-extension.test.ts +19 -0
  168. package/src/console/server/sql-rls.test.ts +44 -0
  169. package/src/console/server/state.ts +445 -7
  170. package/src/console/server/store-kv-stats.test.ts +178 -0
  171. package/src/console/server/store-kv-stats.ts +339 -0
  172. package/src/console/server/store-stats.test.ts +165 -0
  173. package/src/console/server/store-stats.ts +526 -0
  174. package/src/console/server/store.test.ts +930 -0
  175. package/src/console/server/store.ts +859 -76
  176. package/src/console/server/traces-replay.test.ts +212 -0
  177. package/src/console/server/vault-http.test.ts +458 -0
  178. package/src/console/server/vault-overlay.test.ts +49 -0
  179. package/src/console/server/vault-overlay.ts +99 -0
  180. package/src/console/server/vault.test.ts +75 -0
  181. package/src/console/server/vault.ts +443 -27
  182. package/src/console/ui-next/components.json +26 -0
  183. package/src/console/ui-next/dist/assets/bash-CLZ0U2zV.js +1 -0
  184. package/src/console/ui-next/dist/assets/cache-glyph-CLPBqZeb.js +1 -0
  185. package/src/console/ui-next/dist/assets/call-pii-button-bqkxMrJH.js +1 -0
  186. package/src/console/ui-next/dist/assets/collapsible-DYb0xU8C.js +1 -0
  187. package/src/console/ui-next/dist/assets/confirm-sheet-DDCRmG62.js +1 -0
  188. package/src/console/ui-next/dist/assets/dagre.esm-ZwcdTuZZ.js +1 -0
  189. package/src/console/ui-next/dist/assets/duration-tone-oiRxPVsZ.js +9 -0
  190. package/src/console/ui-next/dist/assets/explorer-empty-HjTnVQoR.js +1 -0
  191. package/src/console/ui-next/dist/assets/flows-page-C_Tas1E1.js +1 -0
  192. package/src/console/ui-next/dist/assets/github-dark-C-LZuMrd.js +1 -0
  193. package/src/console/ui-next/dist/assets/github-light-EUqPIrTm.js +1 -0
  194. package/src/console/ui-next/dist/assets/highlighted-json-CvDPvveV.js +154 -0
  195. package/src/console/ui-next/dist/assets/http-method-BJ92Z_ke.js +1 -0
  196. package/src/console/ui-next/dist/assets/index-D4Ldtj79.css +2 -0
  197. package/src/console/ui-next/dist/assets/index-DX248G39.js +66 -0
  198. package/src/console/ui-next/dist/assets/json-qhed-kSA.js +1 -0
  199. package/src/console/ui-next/dist/assets/link-DF7SZ9Ek.js +1 -0
  200. package/src/console/ui-next/dist/assets/observability-page-BwVS5Jvm.js +4 -0
  201. package/src/console/ui-next/dist/assets/preload-helper-oH4irX4C.js +1 -0
  202. package/src/console/ui-next/dist/assets/query-gate-parts-1m8m1iNp.js +2 -0
  203. package/src/console/ui-next/dist/assets/react-B1ML8gxg.js +1 -0
  204. package/src/console/ui-next/dist/assets/react-dom-Bph1y7z7.js +9 -0
  205. package/src/console/ui-next/dist/assets/replica-lag-C8_BRt2x.js +18 -0
  206. package/src/console/ui-next/dist/assets/rolldown-runtime-hePW80VL.js +1 -0
  207. package/src/console/ui-next/dist/assets/sheet-form-D-ata7jy.js +1 -0
  208. package/src/console/ui-next/dist/assets/shortcut-Cgzuv4k1.js +1 -0
  209. package/src/console/ui-next/dist/assets/shortcut-keys-DO4IsVqv.js +1 -0
  210. package/src/console/ui-next/dist/assets/skeleton-CL_X0GCj.js +1 -0
  211. package/src/console/ui-next/dist/assets/sql-BskegiFM.js +1 -0
  212. package/src/console/ui-next/dist/assets/store-page-v3LXdYpr.js +45 -0
  213. package/src/console/ui-next/dist/assets/trace-detail-sheet-D16lWQMt.js +2 -0
  214. package/src/console/ui-next/dist/assets/tsx-udAQXfEw.js +1 -0
  215. package/src/console/ui-next/dist/assets/typescript-bsJCZSQ-.js +1 -0
  216. package/src/console/ui-next/dist/assets/units-page-C5KOI7qG.js +1 -0
  217. package/src/console/ui-next/dist/assets/use-vault-list-Cl79j_ku.js +1 -0
  218. package/src/console/ui-next/dist/assets/vault-page-CSOYMHhO.js +2 -0
  219. package/src/console/ui-next/dist/assets/xyflow-D7n4g6go.js +7 -0
  220. package/src/console/ui-next/dist/assets/xyflow-DZ0Ws1xk.css +1 -0
  221. package/src/console/ui-next/dist/favicon.svg +6 -0
  222. package/src/console/ui-next/dist/index.html +56 -0
  223. package/src/console/ui-next/index.html +45 -0
  224. package/src/console/ui-next/public/favicon.svg +6 -0
  225. package/src/console/ui-next/seed-invoke-host.test.ts +47 -0
  226. package/src/console/ui-next/seed-invoke-host.ts +199 -0
  227. package/src/console/ui-next/seed-invoke-ops.test.ts +280 -0
  228. package/src/console/ui-next/seed-invoke-ops.ts +587 -0
  229. package/src/console/ui-next/src/client-session.test.ts +22 -0
  230. package/src/console/ui-next/src/client.ts +1379 -0
  231. package/src/console/ui-next/src/components/agents/agent-code.tsx +207 -0
  232. package/src/console/ui-next/src/components/agents/agent-disclosure.tsx +63 -0
  233. package/src/console/ui-next/src/components/agents/file-diff.tsx +271 -0
  234. package/src/console/ui-next/src/components/auth-card.tsx +298 -0
  235. package/src/console/ui-next/src/components/charts/animation.ts +36 -0
  236. package/src/console/ui-next/src/components/charts/area-chart-loading.tsx +115 -0
  237. package/src/console/ui-next/src/components/charts/area-chart.tsx +261 -0
  238. package/src/console/ui-next/src/components/charts/area-gradient-defs.tsx +98 -0
  239. package/src/console/ui-next/src/components/charts/area.tsx +349 -0
  240. package/src/console/ui-next/src/components/charts/chart-child-passthrough.ts +110 -0
  241. package/src/console/ui-next/src/components/charts/chart-config-context.tsx +81 -0
  242. package/src/console/ui-next/src/components/charts/chart-context.tsx +414 -0
  243. package/src/console/ui-next/src/components/charts/chart-defs.ts +61 -0
  244. package/src/console/ui-next/src/components/charts/chart-formatters.ts +26 -0
  245. package/src/console/ui-next/src/components/charts/chart-legend-hover.tsx +41 -0
  246. package/src/console/ui-next/src/components/charts/chart-loading-label.tsx +56 -0
  247. package/src/console/ui-next/src/components/charts/chart-phase.ts +52 -0
  248. package/src/console/ui-next/src/components/charts/chart-reveal-clip.tsx +87 -0
  249. package/src/console/ui-next/src/components/charts/composed-chart.tsx +333 -0
  250. package/src/console/ui-next/src/components/charts/dash-tail-stroke.tsx +75 -0
  251. package/src/console/ui-next/src/components/charts/decimate-time-series.ts +134 -0
  252. package/src/console/ui-next/src/components/charts/fade-edges.ts +52 -0
  253. package/src/console/ui-next/src/components/charts/filter-data-by-x-domain.ts +59 -0
  254. package/src/console/ui-next/src/components/charts/generate-chart-skeleton-data.ts +42 -0
  255. package/src/console/ui-next/src/components/charts/grid.tsx +299 -0
  256. package/src/console/ui-next/src/components/charts/highlight-segment-bounds.ts +68 -0
  257. package/src/console/ui-next/src/components/charts/highlight-segment.tsx +65 -0
  258. package/src/console/ui-next/src/components/charts/indicator-fade.ts +62 -0
  259. package/src/console/ui-next/src/components/charts/line-chart-loading.tsx +111 -0
  260. package/src/console/ui-next/src/components/charts/line-chart.tsx +293 -0
  261. package/src/console/ui-next/src/components/charts/line-loading-pulse.tsx +201 -0
  262. package/src/console/ui-next/src/components/charts/line-loading-timing.ts +12 -0
  263. package/src/console/ui-next/src/components/charts/line-series-terminal-marker.tsx +91 -0
  264. package/src/console/ui-next/src/components/charts/line.tsx +384 -0
  265. package/src/console/ui-next/src/components/charts/loading-sweep.tsx +452 -0
  266. package/src/console/ui-next/src/components/charts/motion-utils.ts +47 -0
  267. package/src/console/ui-next/src/components/charts/path-stroke-utils.ts +82 -0
  268. package/src/console/ui-next/src/components/charts/pattern-area.tsx +45 -0
  269. package/src/console/ui-next/src/components/charts/projection-config.ts +112 -0
  270. package/src/console/ui-next/src/components/charts/projection-line-end-marker.tsx +51 -0
  271. package/src/console/ui-next/src/components/charts/projection-line.tsx +208 -0
  272. package/src/console/ui-next/src/components/charts/projection-utils.ts +378 -0
  273. package/src/console/ui-next/src/components/charts/reference-area-config.ts +59 -0
  274. package/src/console/ui-next/src/components/charts/reference-area-geometry.ts +136 -0
  275. package/src/console/ui-next/src/components/charts/reference-area-registration-context.tsx +16 -0
  276. package/src/console/ui-next/src/components/charts/series-bar-layout.ts +60 -0
  277. package/src/console/ui-next/src/components/charts/series-bar.tsx +304 -0
  278. package/src/console/ui-next/src/components/charts/series-dash-tail-overlay.tsx +82 -0
  279. package/src/console/ui-next/src/components/charts/series-highlight-layer.tsx +49 -0
  280. package/src/console/ui-next/src/components/charts/series-hover-dim.tsx +57 -0
  281. package/src/console/ui-next/src/components/charts/series-markers.tsx +267 -0
  282. package/src/console/ui-next/src/components/charts/series-path-utils.ts +103 -0
  283. package/src/console/ui-next/src/components/charts/series-point-marker.tsx +205 -0
  284. package/src/console/ui-next/src/components/charts/static-chart-preview-context.tsx +16 -0
  285. package/src/console/ui-next/src/components/charts/time-series-chart-shell.tsx +644 -0
  286. package/src/console/ui-next/src/components/charts/tooltip/chart-tooltip.tsx +400 -0
  287. package/src/console/ui-next/src/components/charts/tooltip/date-ticker.tsx +140 -0
  288. package/src/console/ui-next/src/components/charts/tooltip/index.ts +10 -0
  289. package/src/console/ui-next/src/components/charts/tooltip/tooltip-box.tsx +227 -0
  290. package/src/console/ui-next/src/components/charts/tooltip/tooltip-content.tsx +58 -0
  291. package/src/console/ui-next/src/components/charts/tooltip/tooltip-dot.tsx +173 -0
  292. package/src/console/ui-next/src/components/charts/tooltip/tooltip-indicator.tsx +191 -0
  293. package/src/console/ui-next/src/components/charts/use-animated-series-path.ts +155 -0
  294. package/src/console/ui-next/src/components/charts/use-animated-y-domains.ts +227 -0
  295. package/src/console/ui-next/src/components/charts/use-chart-interaction.ts +343 -0
  296. package/src/console/ui-next/src/components/charts/use-chart-phase-orchestrator.ts +173 -0
  297. package/src/console/ui-next/src/components/charts/use-enter-complete.ts +28 -0
  298. package/src/console/ui-next/src/components/charts/use-grid-shimmer.ts +101 -0
  299. package/src/console/ui-next/src/components/charts/use-highlight-segment.ts +58 -0
  300. package/src/console/ui-next/src/components/charts/use-mount-progress.ts +29 -0
  301. package/src/console/ui-next/src/components/charts/use-scheduled-tooltip.ts +97 -0
  302. package/src/console/ui-next/src/components/charts/x-axis.tsx +635 -0
  303. package/src/console/ui-next/src/components/charts/y-axis-scales.ts +108 -0
  304. package/src/console/ui-next/src/components/charts/y-axis-ticks.ts +25 -0
  305. package/src/console/ui-next/src/components/charts/y-axis.tsx +151 -0
  306. package/src/console/ui-next/src/components/charts/y-domain-utils.ts +120 -0
  307. package/src/console/ui-next/src/components/console-chrome.tsx +50 -0
  308. package/src/console/ui-next/src/components/document-title.tsx +18 -0
  309. package/src/console/ui-next/src/components/explorer/copy-inline-button.tsx +57 -0
  310. package/src/console/ui-next/src/components/explorer/detail-header.tsx +82 -0
  311. package/src/console/ui-next/src/components/explorer/explorer-chrome.ts +123 -0
  312. package/src/console/ui-next/src/components/explorer/explorer-empty.tsx +67 -0
  313. package/src/console/ui-next/src/components/explorer/explorer-search.tsx +20 -0
  314. package/src/console/ui-next/src/components/explorer/explorer-start-toggle.tsx +52 -0
  315. package/src/console/ui-next/src/components/explorer/section-head.tsx +33 -0
  316. package/src/console/ui-next/src/components/explorer/tree-expand-toggle.tsx +69 -0
  317. package/src/console/ui-next/src/components/explorer/use-explorer-start-panel.ts +34 -0
  318. package/src/console/ui-next/src/components/gate-list.tsx +70 -0
  319. package/src/console/ui-next/src/components/generate-password-button.tsx +76 -0
  320. package/src/console/ui-next/src/components/highlighted-json.tsx +73 -0
  321. package/src/console/ui-next/src/components/http-method-badge.tsx +35 -0
  322. package/src/console/ui-next/src/components/mode-toggle.tsx +84 -0
  323. package/src/console/ui-next/src/components/motion/button/base.tsx +145 -0
  324. package/src/console/ui-next/src/components/motion/button/expanding-arrow.tsx +167 -0
  325. package/src/console/ui-next/src/components/motion/button/index.ts +12 -0
  326. package/src/console/ui-next/src/components/motion/button/stateful.tsx +243 -0
  327. package/src/console/ui-next/src/components/motion/checkbox.tsx +120 -0
  328. package/src/console/ui-next/src/components/motion/select.tsx +436 -0
  329. package/src/console/ui-next/src/components/motion/switch.tsx +108 -0
  330. package/src/console/ui-next/src/components/motion/table/editable-cell.tsx +98 -0
  331. package/src/console/ui-next/src/components/motion/table/index.tsx +404 -0
  332. package/src/console/ui-next/src/components/motion/table/row-handle.tsx +95 -0
  333. package/src/console/ui-next/src/components/motion/table/skeleton-rows.tsx +52 -0
  334. package/src/console/ui-next/src/components/motion/table/table-header.tsx +337 -0
  335. package/src/console/ui-next/src/components/motion/table/table-menu.tsx +130 -0
  336. package/src/console/ui-next/src/components/motion/table/types.ts +109 -0
  337. package/src/console/ui-next/src/components/motion/table/use-cell-range.ts +145 -0
  338. package/src/console/ui-next/src/components/motion/table/use-column-reorder.ts +112 -0
  339. package/src/console/ui-next/src/components/motion/table/use-column-resize.ts +83 -0
  340. package/src/console/ui-next/src/components/motion/table/use-column-sort.ts +73 -0
  341. package/src/console/ui-next/src/components/motion/table/use-row-selection.ts +70 -0
  342. package/src/console/ui-next/src/components/motion/table/utils.ts +138 -0
  343. package/src/console/ui-next/src/components/oke-logo.tsx +65 -0
  344. package/src/console/ui-next/src/components/password-input.tsx +67 -0
  345. package/src/console/ui-next/src/components/password-strength.tsx +160 -0
  346. package/src/console/ui-next/src/components/shell/app-sidebar.tsx +117 -0
  347. package/src/console/ui-next/src/components/shell/command-items.test.ts +30 -0
  348. package/src/console/ui-next/src/components/shell/command-items.ts +144 -0
  349. package/src/console/ui-next/src/components/shell/command-match.test.ts +37 -0
  350. package/src/console/ui-next/src/components/shell/command-match.ts +45 -0
  351. package/src/console/ui-next/src/components/shell/command-palette.tsx +334 -0
  352. package/src/console/ui-next/src/components/shell/nav-footer.tsx +109 -0
  353. package/src/console/ui-next/src/components/shell/section-empty.tsx +42 -0
  354. package/src/console/ui-next/src/components/shell/settings-dialog.tsx +65 -0
  355. package/src/console/ui-next/src/components/shell/shell-layout.tsx +100 -0
  356. package/src/console/ui-next/src/components/shimmering-text.tsx +87 -0
  357. package/src/console/ui-next/src/components/signal-delivery-badge.tsx +38 -0
  358. package/src/console/ui-next/src/components/theme-provider.tsx +86 -0
  359. package/src/console/ui-next/src/components/ui/alert-dialog.tsx +147 -0
  360. package/src/console/ui-next/src/components/ui/avatar.tsx +91 -0
  361. package/src/console/ui-next/src/components/ui/badge.tsx +54 -0
  362. package/src/console/ui-next/src/components/ui/breadcrumb.tsx +104 -0
  363. package/src/console/ui-next/src/components/ui/button.tsx +58 -0
  364. package/src/console/ui-next/src/components/ui/card.tsx +88 -0
  365. package/src/console/ui-next/src/components/ui/collapsible.tsx +15 -0
  366. package/src/console/ui-next/src/components/ui/confirm-sheet.tsx +149 -0
  367. package/src/console/ui-next/src/components/ui/dialog.tsx +144 -0
  368. package/src/console/ui-next/src/components/ui/dropdown-menu.tsx +265 -0
  369. package/src/console/ui-next/src/components/ui/empty.tsx +95 -0
  370. package/src/console/ui-next/src/components/ui/field.tsx +224 -0
  371. package/src/console/ui-next/src/components/ui/input.tsx +30 -0
  372. package/src/console/ui-next/src/components/ui/kbd.tsx +41 -0
  373. package/src/console/ui-next/src/components/ui/label.tsx +20 -0
  374. package/src/console/ui-next/src/components/ui/progress.tsx +66 -0
  375. package/src/console/ui-next/src/components/ui/resizable.tsx +74 -0
  376. package/src/console/ui-next/src/components/ui/select.tsx +230 -0
  377. package/src/console/ui-next/src/components/ui/separator.tsx +21 -0
  378. package/src/console/ui-next/src/components/ui/sheet-form.tsx +337 -0
  379. package/src/console/ui-next/src/components/ui/sheet.tsx +130 -0
  380. package/src/console/ui-next/src/components/ui/sidebar.tsx +691 -0
  381. package/src/console/ui-next/src/components/ui/skeleton.tsx +20 -0
  382. package/src/console/ui-next/src/components/ui/toggle-group.tsx +87 -0
  383. package/src/console/ui-next/src/components/ui/toggle.tsx +46 -0
  384. package/src/console/ui-next/src/components/ui/toolbar-tip.tsx +41 -0
  385. package/src/console/ui-next/src/components/ui/tooltip.tsx +74 -0
  386. package/src/console/ui-next/src/features/auth/auth-redirect.test.ts +119 -0
  387. package/src/console/ui-next/src/features/auth/auth-redirect.ts +153 -0
  388. package/src/console/ui-next/src/features/auth/login-form.tsx +234 -0
  389. package/src/console/ui-next/src/features/auth/logout.ts +17 -0
  390. package/src/console/ui-next/src/features/flows/data/console-live-session.test.ts +329 -0
  391. package/src/console/ui-next/src/features/flows/data/console-live-session.ts +210 -0
  392. package/src/console/ui-next/src/features/flows/data/use-console-live.ts +79 -0
  393. package/src/console/ui-next/src/features/flows/data/use-manifest.ts +23 -0
  394. package/src/console/ui-next/src/features/flows/data/use-runs.ts +24 -0
  395. package/src/console/ui-next/src/features/flows/fixture.ts +81 -0
  396. package/src/console/ui-next/src/features/flows/flows-page.tsx +227 -0
  397. package/src/console/ui-next/src/features/flows/graph/build-flow-graph.test.ts +236 -0
  398. package/src/console/ui-next/src/features/flows/graph/build-flow-graph.ts +530 -0
  399. package/src/console/ui-next/src/features/flows/graph/element-map.test.ts +443 -0
  400. package/src/console/ui-next/src/features/flows/graph/element-map.ts +1077 -0
  401. package/src/console/ui-next/src/features/flows/graph/flow-graph-nodes.tsx +486 -0
  402. package/src/console/ui-next/src/features/flows/graph/flow-graph-theme.ts +143 -0
  403. package/src/console/ui-next/src/features/flows/graph/flow-graph.tsx +268 -0
  404. package/src/console/ui-next/src/features/flows/graph/neighborhood.test.ts +64 -0
  405. package/src/console/ui-next/src/features/flows/graph/neighborhood.ts +82 -0
  406. package/src/console/ui-next/src/features/flows/graph/orchestra.test.ts +97 -0
  407. package/src/console/ui-next/src/features/flows/graph/orchestra.ts +86 -0
  408. package/src/console/ui-next/src/features/flows/graph/use-overview-orchestra.ts +95 -0
  409. package/src/console/ui-next/src/features/flows/state/flows-selection.test.ts +24 -0
  410. package/src/console/ui-next/src/features/flows/state/flows-selection.ts +92 -0
  411. package/src/console/ui-next/src/features/flows/traces/advanced-filters.tsx +222 -0
  412. package/src/console/ui-next/src/features/flows/traces/cache-glyph.tsx +42 -0
  413. package/src/console/ui-next/src/features/flows/traces/cache-icon.test.ts +27 -0
  414. package/src/console/ui-next/src/features/flows/traces/cache-icon.ts +48 -0
  415. package/src/console/ui-next/src/features/flows/traces/dimension-query.test.ts +100 -0
  416. package/src/console/ui-next/src/features/flows/traces/dimension-query.ts +325 -0
  417. package/src/console/ui-next/src/features/flows/traces/duration-tone.test.ts +71 -0
  418. package/src/console/ui-next/src/features/flows/traces/duration-tone.ts +128 -0
  419. package/src/console/ui-next/src/features/flows/traces/effect-kind.ts +106 -0
  420. package/src/console/ui-next/src/features/flows/traces/effect-summary.ts +193 -0
  421. package/src/console/ui-next/src/features/flows/traces/filter-runs.test.ts +98 -0
  422. package/src/console/ui-next/src/features/flows/traces/filter-runs.ts +68 -0
  423. package/src/console/ui-next/src/features/flows/traces/format-duration.test.ts +47 -0
  424. package/src/console/ui-next/src/features/flows/traces/format-duration.ts +25 -0
  425. package/src/console/ui-next/src/features/flows/traces/graph-filter.test.ts +192 -0
  426. package/src/console/ui-next/src/features/flows/traces/graph-filter.ts +175 -0
  427. package/src/console/ui-next/src/features/flows/traces/http-method.ts +134 -0
  428. package/src/console/ui-next/src/features/flows/traces/replay-playback.test.ts +101 -0
  429. package/src/console/ui-next/src/features/flows/traces/replay-playback.ts +107 -0
  430. package/src/console/ui-next/src/features/flows/traces/request-input-view.test.ts +60 -0
  431. package/src/console/ui-next/src/features/flows/traces/request-input-view.ts +108 -0
  432. package/src/console/ui-next/src/features/flows/traces/request-meta.ts +62 -0
  433. package/src/console/ui-next/src/features/flows/traces/scope-runs.test.ts +51 -0
  434. package/src/console/ui-next/src/features/flows/traces/scope-runs.ts +23 -0
  435. package/src/console/ui-next/src/features/flows/traces/trace-actions.test.ts +80 -0
  436. package/src/console/ui-next/src/features/flows/traces/trace-actions.ts +57 -0
  437. package/src/console/ui-next/src/features/flows/traces/trace-chain.test.ts +68 -0
  438. package/src/console/ui-next/src/features/flows/traces/trace-chain.ts +59 -0
  439. package/src/console/ui-next/src/features/flows/traces/trace-detail-sheet.tsx +1003 -0
  440. package/src/console/ui-next/src/features/flows/traces/trace-detail.test.ts +357 -0
  441. package/src/console/ui-next/src/features/flows/traces/trace-gates.ts +90 -0
  442. package/src/console/ui-next/src/features/flows/traces/trace-request-section.tsx +574 -0
  443. package/src/console/ui-next/src/features/flows/traces/trace-row-meta.test.ts +42 -0
  444. package/src/console/ui-next/src/features/flows/traces/trace-row-meta.ts +47 -0
  445. package/src/console/ui-next/src/features/flows/traces/trace-row.tsx +149 -0
  446. package/src/console/ui-next/src/features/flows/traces/traces-pane.tsx +289 -0
  447. package/src/console/ui-next/src/features/flows/traces/trigger-icon.test.ts +42 -0
  448. package/src/console/ui-next/src/features/flows/traces/trigger-icon.ts +53 -0
  449. package/src/console/ui-next/src/features/flows/traces/waterfall-bars.test.ts +93 -0
  450. package/src/console/ui-next/src/features/flows/traces/waterfall-bars.ts +80 -0
  451. package/src/console/ui-next/src/features/flows/traces/waterfall-timeline.test.ts +121 -0
  452. package/src/console/ui-next/src/features/flows/traces/waterfall-timeline.ts +230 -0
  453. package/src/console/ui-next/src/features/flows/traces/waterfall-tooltip.test.ts +51 -0
  454. package/src/console/ui-next/src/features/flows/traces/waterfall-tooltip.ts +20 -0
  455. package/src/console/ui-next/src/features/not-found/not-found-page.tsx +23 -0
  456. package/src/console/ui-next/src/features/observability/data/use-ai-list.ts +26 -0
  457. package/src/console/ui-next/src/features/observability/data/use-clock-list.ts +27 -0
  458. package/src/console/ui-next/src/features/observability/data/use-instances-list.ts +27 -0
  459. package/src/console/ui-next/src/features/observability/data/use-runs-query.ts +39 -0
  460. package/src/console/ui-next/src/features/observability/data/use-signals-list.ts +25 -0
  461. package/src/console/ui-next/src/features/observability/detail/ai-rail.tsx +77 -0
  462. package/src/console/ui-next/src/features/observability/detail/instance-fleet-sheet.tsx +111 -0
  463. package/src/console/ui-next/src/features/observability/detail/metrics-chart.tsx +111 -0
  464. package/src/console/ui-next/src/features/observability/detail/metrics-panel.tsx +154 -0
  465. package/src/console/ui-next/src/features/observability/explorer/error-list.tsx +139 -0
  466. package/src/console/ui-next/src/features/observability/explorer/error-row.tsx +84 -0
  467. package/src/console/ui-next/src/features/observability/explorer/health-strip.tsx +146 -0
  468. package/src/console/ui-next/src/features/observability/lib/ask-count.test.ts +47 -0
  469. package/src/console/ui-next/src/features/observability/lib/ask-count.ts +44 -0
  470. package/src/console/ui-next/src/features/observability/lib/health-cells.test.ts +243 -0
  471. package/src/console/ui-next/src/features/observability/lib/health-cells.ts +207 -0
  472. package/src/console/ui-next/src/features/observability/lib/run-fixture.ts +43 -0
  473. package/src/console/ui-next/src/features/observability/lib/time-buckets.test.ts +61 -0
  474. package/src/console/ui-next/src/features/observability/lib/time-buckets.ts +126 -0
  475. package/src/console/ui-next/src/features/observability/lib/token-count.test.ts +75 -0
  476. package/src/console/ui-next/src/features/observability/lib/token-count.ts +70 -0
  477. package/src/console/ui-next/src/features/observability/lib/top-errors.test.ts +89 -0
  478. package/src/console/ui-next/src/features/observability/lib/top-errors.ts +135 -0
  479. package/src/console/ui-next/src/features/observability/lib/window-stats.test.ts +62 -0
  480. package/src/console/ui-next/src/features/observability/lib/window-stats.ts +124 -0
  481. package/src/console/ui-next/src/features/observability/observability-page.tsx +217 -0
  482. package/src/console/ui-next/src/features/observability/query/runs-query-panel.tsx +91 -0
  483. package/src/console/ui-next/src/features/observability/state/observability-selection.test.ts +27 -0
  484. package/src/console/ui-next/src/features/observability/state/observability-selection.ts +121 -0
  485. package/src/console/ui-next/src/features/setup/auth-gate.test.ts +17 -0
  486. package/src/console/ui-next/src/features/setup/auth-gate.ts +21 -0
  487. package/src/console/ui-next/src/features/setup/claim-page.tsx +418 -0
  488. package/src/console/ui-next/src/features/store/data/use-gates.ts +26 -0
  489. package/src/console/ui-next/src/features/store/data/use-store-edit.ts +92 -0
  490. package/src/console/ui-next/src/features/store/data/use-store-files.ts +96 -0
  491. package/src/console/ui-next/src/features/store/data/use-store-kv-stats.ts +47 -0
  492. package/src/console/ui-next/src/features/store/data/use-store-query.test.ts +42 -0
  493. package/src/console/ui-next/src/features/store/data/use-store-query.ts +68 -0
  494. package/src/console/ui-next/src/features/store/data/use-store-reveal.ts +28 -0
  495. package/src/console/ui-next/src/features/store/data/use-store-sql-advise.ts +39 -0
  496. package/src/console/ui-next/src/features/store/data/use-store-sql-locks.ts +51 -0
  497. package/src/console/ui-next/src/features/store/data/use-store-sql-stats.ts +47 -0
  498. package/src/console/ui-next/src/features/store/data/use-store-sql.ts +39 -0
  499. package/src/console/ui-next/src/features/store/data/use-stores-list.ts +24 -0
  500. package/src/console/ui-next/src/features/store/detail/browse-section.tsx +692 -0
  501. package/src/console/ui-next/src/features/store/detail/json-value-sheet.tsx +470 -0
  502. package/src/console/ui-next/src/features/store/detail/resource-panel.tsx +325 -0
  503. package/src/console/ui-next/src/features/store/detail/reveal-cell.tsx +137 -0
  504. package/src/console/ui-next/src/features/store/detail/store-row-detail-sheet.tsx +225 -0
  505. package/src/console/ui-next/src/features/store/detail/touched-by-section.tsx +101 -0
  506. package/src/console/ui-next/src/features/store/explorer/store-tree.tsx +1044 -0
  507. package/src/console/ui-next/src/features/store/files/file-explorer.tsx +563 -0
  508. package/src/console/ui-next/src/features/store/files/file-kind-icon.tsx +70 -0
  509. package/src/console/ui-next/src/features/store/files/file-preview.tsx +338 -0
  510. package/src/console/ui-next/src/features/store/files/file-upload-sheet.tsx +190 -0
  511. package/src/console/ui-next/src/features/store/grid/catalog-advanced.tsx +80 -0
  512. package/src/console/ui-next/src/features/store/grid/extension-library-sheet.tsx +761 -0
  513. package/src/console/ui-next/src/features/store/grid/kv-add-sheet.tsx +165 -0
  514. package/src/console/ui-next/src/features/store/grid/pending-changes-sheet.tsx +219 -0
  515. package/src/console/ui-next/src/features/store/grid/rls-policy-sheet.tsx +875 -0
  516. package/src/console/ui-next/src/features/store/grid/sql-function-sheet.tsx +473 -0
  517. package/src/console/ui-next/src/features/store/grid/sql-index-sheet.tsx +355 -0
  518. package/src/console/ui-next/src/features/store/grid/sql-insert-sheet.tsx +177 -0
  519. package/src/console/ui-next/src/features/store/grid/sql-trigger-sheet.tsx +445 -0
  520. package/src/console/ui-next/src/features/store/grid/store-confirm-sheet.tsx +73 -0
  521. package/src/console/ui-next/src/features/store/grid/store-data-grid.tsx +1844 -0
  522. package/src/console/ui-next/src/features/store/grid/store-edit-sheet.tsx +329 -0
  523. package/src/console/ui-next/src/features/store/grid/store-grid-context-menu.tsx +111 -0
  524. package/src/console/ui-next/src/features/store/grid/store-grid-shortcuts.tsx +124 -0
  525. package/src/console/ui-next/src/features/store/lib/cell-selection.test.ts +125 -0
  526. package/src/console/ui-next/src/features/store/lib/cell-selection.ts +115 -0
  527. package/src/console/ui-next/src/features/store/lib/confirmation.test.ts +48 -0
  528. package/src/console/ui-next/src/features/store/lib/confirmation.ts +63 -0
  529. package/src/console/ui-next/src/features/store/lib/edit-history.test.ts +60 -0
  530. package/src/console/ui-next/src/features/store/lib/edit-history.ts +64 -0
  531. package/src/console/ui-next/src/features/store/lib/fields-from-table.ts +94 -0
  532. package/src/console/ui-next/src/features/store/lib/files-body.test.ts +16 -0
  533. package/src/console/ui-next/src/features/store/lib/files-body.ts +79 -0
  534. package/src/console/ui-next/src/features/store/lib/files-meta.test.ts +75 -0
  535. package/src/console/ui-next/src/features/store/lib/files-meta.ts +259 -0
  536. package/src/console/ui-next/src/features/store/lib/files-origin.test.ts +69 -0
  537. package/src/console/ui-next/src/features/store/lib/files-origin.ts +53 -0
  538. package/src/console/ui-next/src/features/store/lib/files-tree.test.ts +123 -0
  539. package/src/console/ui-next/src/features/store/lib/files-tree.ts +233 -0
  540. package/src/console/ui-next/src/features/store/lib/grid-model.test.ts +127 -0
  541. package/src/console/ui-next/src/features/store/lib/grid-model.ts +219 -0
  542. package/src/console/ui-next/src/features/store/lib/grid-transfer.test.ts +123 -0
  543. package/src/console/ui-next/src/features/store/lib/grid-transfer.ts +217 -0
  544. package/src/console/ui-next/src/features/store/lib/index-query.test.ts +30 -0
  545. package/src/console/ui-next/src/features/store/lib/index-query.ts +57 -0
  546. package/src/console/ui-next/src/features/store/lib/json-value.test.ts +141 -0
  547. package/src/console/ui-next/src/features/store/lib/json-value.ts +266 -0
  548. package/src/console/ui-next/src/features/store/lib/kv-format.test.ts +44 -0
  549. package/src/console/ui-next/src/features/store/lib/kv-format.ts +103 -0
  550. package/src/console/ui-next/src/features/store/lib/kv-meta.test.ts +43 -0
  551. package/src/console/ui-next/src/features/store/lib/kv-meta.ts +63 -0
  552. package/src/console/ui-next/src/features/store/lib/kv-query.test.ts +128 -0
  553. package/src/console/ui-next/src/features/store/lib/kv-query.ts +303 -0
  554. package/src/console/ui-next/src/features/store/lib/parse-resource-ref.ts +38 -0
  555. package/src/console/ui-next/src/features/store/lib/patch.test.ts +99 -0
  556. package/src/console/ui-next/src/features/store/lib/patch.ts +129 -0
  557. package/src/console/ui-next/src/features/store/lib/pending-edits.test.ts +125 -0
  558. package/src/console/ui-next/src/features/store/lib/pending-edits.ts +150 -0
  559. package/src/console/ui-next/src/features/store/lib/pending-sql.test.ts +108 -0
  560. package/src/console/ui-next/src/features/store/lib/pending-sql.ts +136 -0
  561. package/src/console/ui-next/src/features/store/lib/pg-extension-library.test.ts +117 -0
  562. package/src/console/ui-next/src/features/store/lib/pg-extension-library.ts +277 -0
  563. package/src/console/ui-next/src/features/store/lib/query-defaults.test.ts +78 -0
  564. package/src/console/ui-next/src/features/store/lib/query-defaults.ts +77 -0
  565. package/src/console/ui-next/src/features/store/lib/query-gate.test.ts +132 -0
  566. package/src/console/ui-next/src/features/store/lib/query-gate.ts +187 -0
  567. package/src/console/ui-next/src/features/store/lib/query-highlight.test.ts +103 -0
  568. package/src/console/ui-next/src/features/store/lib/query-highlight.ts +382 -0
  569. package/src/console/ui-next/src/features/store/lib/query-schema.test.ts +139 -0
  570. package/src/console/ui-next/src/features/store/lib/query-schema.ts +128 -0
  571. package/src/console/ui-next/src/features/store/lib/query-session.test.ts +91 -0
  572. package/src/console/ui-next/src/features/store/lib/query-session.ts +330 -0
  573. package/src/console/ui-next/src/features/store/lib/replica-lag.test.ts +101 -0
  574. package/src/console/ui-next/src/features/store/lib/replica-lag.ts +31 -0
  575. package/src/console/ui-next/src/features/store/lib/resource-effects.ts +12 -0
  576. package/src/console/ui-next/src/features/store/lib/rls-gate-catalog.test.ts +131 -0
  577. package/src/console/ui-next/src/features/store/lib/rls-gate-catalog.ts +274 -0
  578. package/src/console/ui-next/src/features/store/lib/rls-policy.test.ts +95 -0
  579. package/src/console/ui-next/src/features/store/lib/rls-policy.ts +290 -0
  580. package/src/console/ui-next/src/features/store/lib/rtl.test.ts +17 -0
  581. package/src/console/ui-next/src/features/store/lib/rtl.ts +15 -0
  582. package/src/console/ui-next/src/features/store/lib/schema-color.test.ts +91 -0
  583. package/src/console/ui-next/src/features/store/lib/schema-color.ts +216 -0
  584. package/src/console/ui-next/src/features/store/lib/schema-graph.test.ts +435 -0
  585. package/src/console/ui-next/src/features/store/lib/schema-graph.ts +566 -0
  586. package/src/console/ui-next/src/features/store/lib/sql-catalog.test.ts +60 -0
  587. package/src/console/ui-next/src/features/store/lib/sql-catalog.ts +98 -0
  588. package/src/console/ui-next/src/features/store/lib/sql-complete.test.ts +109 -0
  589. package/src/console/ui-next/src/features/store/lib/sql-complete.ts +385 -0
  590. package/src/console/ui-next/src/features/store/lib/sql-format.test.ts +35 -0
  591. package/src/console/ui-next/src/features/store/lib/sql-format.ts +85 -0
  592. package/src/console/ui-next/src/features/store/lib/sql-function.test.ts +141 -0
  593. package/src/console/ui-next/src/features/store/lib/sql-function.ts +195 -0
  594. package/src/console/ui-next/src/features/store/lib/sql-index.test.ts +101 -0
  595. package/src/console/ui-next/src/features/store/lib/sql-index.ts +151 -0
  596. package/src/console/ui-next/src/features/store/lib/sql-statements.test.ts +114 -0
  597. package/src/console/ui-next/src/features/store/lib/sql-statements.ts +205 -0
  598. package/src/console/ui-next/src/features/store/lib/sql-trigger.test.ts +125 -0
  599. package/src/console/ui-next/src/features/store/lib/sql-trigger.ts +210 -0
  600. package/src/console/ui-next/src/features/store/lib/store-tree.test.ts +220 -0
  601. package/src/console/ui-next/src/features/store/lib/store-tree.ts +314 -0
  602. package/src/console/ui-next/src/features/store/performance/advisor-enable.test.ts +16 -0
  603. package/src/console/ui-next/src/features/store/performance/advisor-enable.ts +26 -0
  604. package/src/console/ui-next/src/features/store/performance/kv-performance-panel.tsx +223 -0
  605. package/src/console/ui-next/src/features/store/performance/performance-panel.tsx +442 -0
  606. package/src/console/ui-next/src/features/store/query/query-complete.tsx +131 -0
  607. package/src/console/ui-next/src/features/store/query/query-console.tsx +1159 -0
  608. package/src/console/ui-next/src/features/store/query/query-editor.tsx +300 -0
  609. package/src/console/ui-next/src/features/store/query/query-gate-menu.tsx +178 -0
  610. package/src/console/ui-next/src/features/store/query/query-gate-parts.tsx +344 -0
  611. package/src/console/ui-next/src/features/store/query/query-gate-viz.tsx +166 -0
  612. package/src/console/ui-next/src/features/store/query/query-highlight-view.tsx +61 -0
  613. package/src/console/ui-next/src/features/store/query/query-results.tsx +369 -0
  614. package/src/console/ui-next/src/features/store/query/query-schema-panel.tsx +300 -0
  615. package/src/console/ui-next/src/features/store/query/sql-style-editor.tsx +73 -0
  616. package/src/console/ui-next/src/features/store/schema/schema-constraint-icon.tsx +108 -0
  617. package/src/console/ui-next/src/features/store/schema/schema-relation-edge.tsx +76 -0
  618. package/src/console/ui-next/src/features/store/schema/schema-relation-icon.tsx +84 -0
  619. package/src/console/ui-next/src/features/store/schema/schema-table-node.tsx +199 -0
  620. package/src/console/ui-next/src/features/store/schema/schema-visualizer.tsx +273 -0
  621. package/src/console/ui-next/src/features/store/state/store-selection.test.ts +38 -0
  622. package/src/console/ui-next/src/features/store/state/store-selection.ts +154 -0
  623. package/src/console/ui-next/src/features/store/store-page.tsx +180 -0
  624. package/src/console/ui-next/src/features/units/call/call-api-panel.tsx +1247 -0
  625. package/src/console/ui-next/src/features/units/call/call-identity-menu.tsx +226 -0
  626. package/src/console/ui-next/src/features/units/call/call-pii-button.tsx +60 -0
  627. package/src/console/ui-next/src/features/units/data/use-flows-invoke.ts +75 -0
  628. package/src/console/ui-next/src/features/units/detail/effects-summary.tsx +80 -0
  629. package/src/console/ui-next/src/features/units/detail/errors-section.tsx +64 -0
  630. package/src/console/ui-next/src/features/units/detail/flow-activity-strip.tsx +119 -0
  631. package/src/console/ui-next/src/features/units/detail/flow-contract-panel.tsx +335 -0
  632. package/src/console/ui-next/src/features/units/detail/schema-fields.tsx +149 -0
  633. package/src/console/ui-next/src/features/units/detail/validation-section.tsx +66 -0
  634. package/src/console/ui-next/src/features/units/explorer/units-tree.tsx +644 -0
  635. package/src/console/ui-next/src/features/units/lib/call-invoke-as.test.ts +40 -0
  636. package/src/console/ui-next/src/features/units/lib/call-read-safe.test.ts +38 -0
  637. package/src/console/ui-next/src/features/units/lib/call-read-safe.ts +32 -0
  638. package/src/console/ui-next/src/features/units/lib/call-timing.test.ts +28 -0
  639. package/src/console/ui-next/src/features/units/lib/call-timing.ts +34 -0
  640. package/src/console/ui-next/src/features/units/lib/contract-input.test.ts +47 -0
  641. package/src/console/ui-next/src/features/units/lib/contract-input.ts +68 -0
  642. package/src/console/ui-next/src/features/units/lib/fields-from-schema.test.ts +119 -0
  643. package/src/console/ui-next/src/features/units/lib/fields-from-schema.ts +329 -0
  644. package/src/console/ui-next/src/features/units/lib/fk-lookup.test.ts +103 -0
  645. package/src/console/ui-next/src/features/units/lib/fk-lookup.ts +175 -0
  646. package/src/console/ui-next/src/features/units/lib/flow-activity.test.ts +76 -0
  647. package/src/console/ui-next/src/features/units/lib/flow-activity.ts +68 -0
  648. package/src/console/ui-next/src/features/units/lib/flow-trigger.test.ts +63 -0
  649. package/src/console/ui-next/src/features/units/lib/flow-trigger.ts +120 -0
  650. package/src/console/ui-next/src/features/units/lib/invoke-cache.test.ts +31 -0
  651. package/src/console/ui-next/src/features/units/lib/invoke-cache.ts +22 -0
  652. package/src/console/ui-next/src/features/units/lib/invoke-response.test.ts +76 -0
  653. package/src/console/ui-next/src/features/units/lib/invoke-response.ts +70 -0
  654. package/src/console/ui-next/src/features/units/lib/path-params.test.ts +43 -0
  655. package/src/console/ui-next/src/features/units/lib/path-params.ts +75 -0
  656. package/src/console/ui-next/src/features/units/lib/resolve-clock.test.ts +106 -0
  657. package/src/console/ui-next/src/features/units/lib/resolve-clock.ts +79 -0
  658. package/src/console/ui-next/src/features/units/lib/schema-type-visual.ts +28 -0
  659. package/src/console/ui-next/src/features/units/lib/signal-delivery.test.ts +29 -0
  660. package/src/console/ui-next/src/features/units/lib/signal-delivery.ts +67 -0
  661. package/src/console/ui-next/src/features/units/lib/unit-tree.test.ts +289 -0
  662. package/src/console/ui-next/src/features/units/lib/unit-tree.ts +307 -0
  663. package/src/console/ui-next/src/features/units/lib/validate-contract.ts +103 -0
  664. package/src/console/ui-next/src/features/units/state/units-selection.ts +49 -0
  665. package/src/console/ui-next/src/features/units/units-page.tsx +120 -0
  666. package/src/console/ui-next/src/features/vault/data/use-vault-list.ts +27 -0
  667. package/src/console/ui-next/src/features/vault/detail/vault-detail.tsx +831 -0
  668. package/src/console/ui-next/src/features/vault/detail/vault-overview.tsx +71 -0
  669. package/src/console/ui-next/src/features/vault/explorer/vault-list.tsx +291 -0
  670. package/src/console/ui-next/src/features/vault/explorer/vault-posture-strip.tsx +131 -0
  671. package/src/console/ui-next/src/features/vault/explorer/vault-search.tsx +126 -0
  672. package/src/console/ui-next/src/features/vault/lib/backend.test.ts +147 -0
  673. package/src/console/ui-next/src/features/vault/lib/backend.ts +216 -0
  674. package/src/console/ui-next/src/features/vault/lib/blast-radius.ts +53 -0
  675. package/src/console/ui-next/src/features/vault/lib/confirmation.test.ts +41 -0
  676. package/src/console/ui-next/src/features/vault/lib/confirmation.ts +50 -0
  677. package/src/console/ui-next/src/features/vault/lib/contract-ops.test.ts +35 -0
  678. package/src/console/ui-next/src/features/vault/lib/contract-ops.ts +94 -0
  679. package/src/console/ui-next/src/features/vault/lib/dormant.ts +28 -0
  680. package/src/console/ui-next/src/features/vault/lib/export-safe.test.ts +25 -0
  681. package/src/console/ui-next/src/features/vault/lib/export-safe.ts +62 -0
  682. package/src/console/ui-next/src/features/vault/lib/fixture.ts +92 -0
  683. package/src/console/ui-next/src/features/vault/lib/group.test.ts +31 -0
  684. package/src/console/ui-next/src/features/vault/lib/group.ts +43 -0
  685. package/src/console/ui-next/src/features/vault/lib/posture.test.ts +137 -0
  686. package/src/console/ui-next/src/features/vault/lib/posture.ts +275 -0
  687. package/src/console/ui-next/src/features/vault/lib/progress.test.ts +36 -0
  688. package/src/console/ui-next/src/features/vault/lib/progress.ts +51 -0
  689. package/src/console/ui-next/src/features/vault/lib/search.test.ts +139 -0
  690. package/src/console/ui-next/src/features/vault/lib/search.ts +403 -0
  691. package/src/console/ui-next/src/features/vault/lib/theme.ts +14 -0
  692. package/src/console/ui-next/src/features/vault/lib/types.ts +114 -0
  693. package/src/console/ui-next/src/features/vault/lib/write-review.test.ts +139 -0
  694. package/src/console/ui-next/src/features/vault/lib/write-review.ts +115 -0
  695. package/src/console/ui-next/src/features/vault/sheets/vault-create-sheet.tsx +209 -0
  696. package/src/console/ui-next/src/features/vault/sheets/vault-master-key-sheet.tsx +87 -0
  697. package/src/console/ui-next/src/features/vault/sheets/vault-rotate-master-sheet.tsx +43 -0
  698. package/src/console/ui-next/src/features/vault/sheets/vault-security-sheet.tsx +205 -0
  699. package/src/console/ui-next/src/features/vault/sheets/vault-verify-sheet.tsx +103 -0
  700. package/src/console/ui-next/src/features/vault/sheets/vault-write-review-dialog.test.tsx +175 -0
  701. package/src/console/ui-next/src/features/vault/sheets/vault-write-review-dialog.tsx +135 -0
  702. package/src/console/ui-next/src/features/vault/sheets/vault-write-sheet.tsx +224 -0
  703. package/src/console/ui-next/src/features/vault/state/vault-selection.test.ts +20 -0
  704. package/src/console/ui-next/src/features/vault/state/vault-selection.ts +87 -0
  705. package/src/console/ui-next/src/features/vault/vault-page.tsx +439 -0
  706. package/src/console/ui-next/src/hooks/use-mobile.ts +22 -0
  707. package/src/console/ui-next/src/lib/document-meta.test.ts +43 -0
  708. package/src/console/ui-next/src/lib/document-meta.ts +34 -0
  709. package/src/console/ui-next/src/lib/ease.ts +59 -0
  710. package/src/console/ui-next/src/lib/element-icons.test.ts +38 -0
  711. package/src/console/ui-next/src/lib/element-icons.ts +75 -0
  712. package/src/console/ui-next/src/lib/highlight.test.ts +30 -0
  713. package/src/console/ui-next/src/lib/highlight.ts +39 -0
  714. package/src/console/ui-next/src/lib/hooks/use-hover-capable.ts +30 -0
  715. package/src/console/ui-next/src/lib/last-module-search.test.ts +47 -0
  716. package/src/console/ui-next/src/lib/last-module-search.ts +164 -0
  717. package/src/console/ui-next/src/lib/motion.ts +16 -0
  718. package/src/console/ui-next/src/lib/shiki.ts +42 -0
  719. package/src/console/ui-next/src/lib/shortcut-keys.tsx +47 -0
  720. package/src/console/ui-next/src/lib/shortcut.test.ts +70 -0
  721. package/src/console/ui-next/src/lib/shortcut.ts +111 -0
  722. package/src/console/ui-next/src/lib/use-console-shortcuts.ts +56 -0
  723. package/src/console/ui-next/src/lib/use-last-module-search.ts +37 -0
  724. package/src/console/ui-next/src/lib/utils.ts +15 -0
  725. package/src/console/ui-next/src/main.tsx +44 -0
  726. package/src/console/ui-next/src/router.tsx +175 -0
  727. package/src/console/ui-next/src/styles.css +384 -0
  728. package/src/console/ui-next/src/vite-env.d.ts +17 -0
  729. package/src/console/ui-next/tsconfig.json +25 -0
  730. package/src/console/ui-next/ui-next-dev-operator.test.ts +76 -0
  731. package/src/console/ui-next/ui-next-dev-operator.ts +81 -0
  732. package/src/console/ui-next/ui-next-seed-app-schema.ts +526 -0
  733. package/src/console/ui-next/ui-next-seed-manifest-surface.ts +882 -0
  734. package/src/console/ui-next/ui-next-seed-manifest.ts +635 -0
  735. package/src/console/ui-next/ui-next-seed-runs.ts +1429 -0
  736. package/src/console/ui-next/ui-next-seed-store.ts +1125 -0
  737. package/src/console/ui-next/ui-next-seed.test.ts +511 -0
  738. package/src/console/ui-next/ui-next-seed.ts +122 -0
  739. package/src/console/ui-next/vite-console-kernel-plugin.ts +195 -0
  740. package/src/console/ui-next/vite.config.ts +88 -0
  741. package/src/console/xss.gate.test.ts +21 -26
  742. package/src/docker/compose.ts +26 -7
  743. package/src/docker/derive.ts +67 -13
  744. package/src/docker/docker.test.ts +219 -27
  745. package/src/docker/helpers.ts +20 -0
  746. package/src/docker/images-config.test.ts +29 -22
  747. package/src/docker/index.ts +8 -0
  748. package/src/docker/postgres-advisor.integration.test.ts +163 -0
  749. package/src/docker/query-passthrough.integration.test.ts +212 -0
  750. package/src/docker/recipes/index.ts +13 -0
  751. package/src/docker/recipes/llama-cpp.ts +3 -3
  752. package/src/docker/recipes/nginx.ts +61 -0
  753. package/src/docker/recipes/ollama.ts +1 -1
  754. package/src/docker/recipes/postgres-advisor.ts +58 -0
  755. package/src/docker/recipes/postgres.ts +6 -2
  756. package/src/docker/recipes/sglang.ts +1 -1
  757. package/src/docker/recipes/timescale.ts +6 -2
  758. package/src/docker/recipes/traefik.ts +1 -0
  759. package/src/docker/recipes/vllm.ts +1 -1
  760. package/src/docker/stack-id.test.ts +5 -14
  761. package/src/docker/stack-id.ts +15 -35
  762. package/src/docker/stack.integration.test.ts +2 -2
  763. package/src/docker/types.ts +16 -7
  764. package/src/drivers/ai-mock.ts +41 -1
  765. package/src/drivers/ai-openai-compatible.ts +19 -1
  766. package/src/drivers/index.ts +32 -0
  767. package/src/drivers/instances-postgres.ts +154 -0
  768. package/src/drivers/meilisearch.integration.test.ts +9 -0
  769. package/src/drivers/meilisearch.test.ts +134 -6
  770. package/src/drivers/meilisearch.ts +77 -8
  771. package/src/drivers/memory.ts +384 -24
  772. package/src/drivers/pg-extensions.test.ts +50 -0
  773. package/src/drivers/pg-extensions.ts +1054 -0
  774. package/src/drivers/pg-rls.test.ts +71 -0
  775. package/src/drivers/pg-rls.ts +234 -0
  776. package/src/drivers/pgvector.ts +24 -0
  777. package/src/drivers/redis.ts +12 -0
  778. package/src/drivers/s3-ensure-bucket.test.ts +88 -0
  779. package/src/drivers/s3-ensure-bucket.ts +152 -0
  780. package/src/drivers/s3.ts +34 -2
  781. package/src/drivers/types.ts +28 -0
  782. package/src/drivers/vault-1password.test.ts +164 -0
  783. package/src/drivers/vault-1password.ts +351 -0
  784. package/src/drivers/vault-aws-secrets-manager.ts +15 -94
  785. package/src/drivers/vault-azure-key-vault.test.ts +137 -0
  786. package/src/drivers/vault-azure-key-vault.ts +243 -0
  787. package/src/drivers/vault-doppler.test.ts +133 -0
  788. package/src/drivers/vault-doppler.ts +202 -0
  789. package/src/drivers/vault-dotenv-parse.ts +32 -0
  790. package/src/drivers/vault-env.ts +1 -1
  791. package/src/drivers/vault-gcp-secret-manager.test.ts +127 -0
  792. package/src/drivers/vault-gcp-secret-manager.ts +291 -0
  793. package/src/drivers/vault-managed.test.ts +23 -26
  794. package/src/drivers/vault-managed.ts +58 -20
  795. package/src/drivers/vault-remote-bag.ts +242 -0
  796. package/src/drivers/vault-types.ts +9 -7
  797. package/src/elements/ai/runtime.ts +100 -8
  798. package/src/elements/ai/schema.test.ts +133 -0
  799. package/src/elements/ai/schema.ts +156 -11
  800. package/src/elements/ai.test.ts +53 -0
  801. package/src/elements/ai.ts +1 -0
  802. package/src/elements/clock/runtime.ts +31 -13
  803. package/src/elements/clock.test.ts +49 -0
  804. package/src/elements/gate/config.ts +18 -3
  805. package/src/elements/gate/declare.ts +25 -5
  806. package/src/elements/gate/flatten.ts +74 -0
  807. package/src/elements/gate/permissions.ts +1 -0
  808. package/src/elements/gate/runtime.ts +16 -4
  809. package/src/elements/gate.test.ts +32 -0
  810. package/src/elements/gate.ts +9 -1
  811. package/src/elements/store/cache.test.ts +79 -0
  812. package/src/elements/store/cache.ts +176 -0
  813. package/src/elements/store/classify.ts +79 -4
  814. package/src/elements/store/emit-drizzle.ts +3 -1
  815. package/src/elements/store/files-policy.test.ts +36 -1
  816. package/src/elements/store/files-policy.ts +151 -0
  817. package/src/elements/store/resource-list-docs.fixture.ts +0 -2
  818. package/src/elements/store/resource-list-docs.test.ts +3 -0
  819. package/src/elements/store/resource.test.ts +62 -2
  820. package/src/elements/store/resource.ts +279 -62
  821. package/src/elements/store/runtime.ts +53 -2
  822. package/src/elements/store/schema-decl.test.ts +49 -0
  823. package/src/elements/store/schema-decl.ts +29 -9
  824. package/src/elements/store/seed.test.ts +22 -1
  825. package/src/elements/store/seed.ts +46 -1
  826. package/src/elements/store/sql-session.ts +32 -7
  827. package/src/elements/store/table.ts +17 -1
  828. package/src/elements/store/upsert-app.test.ts +1 -1
  829. package/src/elements/store.test.ts +21 -0
  830. package/src/elements/store.ts +26 -3
  831. package/src/elements/vault/boot-chain.test.ts +108 -10
  832. package/src/elements/vault/boot-chain.ts +15 -15
  833. package/src/elements/vault/builtin-adapter.test.ts +1 -0
  834. package/src/elements/vault/builtin-adapter.ts +12 -0
  835. package/src/elements/vault/chain.ts +6 -20
  836. package/src/elements/vault/declare.ts +5 -2
  837. package/src/elements/vault/runtime.ts +47 -13
  838. package/src/elements/vault/storage.ts +35 -4
  839. package/src/elements/vault.test.ts +1 -0
  840. package/src/elements/vault.ts +2 -0
  841. package/src/full.ts +10 -0
  842. package/src/http.ts +1 -1
  843. package/src/index.ts +8 -0
  844. package/src/kernel/adopt-barrel-fresh.test.ts +1 -2
  845. package/src/kernel/app-auth.ts +8 -1
  846. package/src/kernel/app.ts +245 -25
  847. package/src/kernel/auth-resolve.ts +51 -0
  848. package/src/kernel/auto-cache.test.ts +270 -0
  849. package/src/kernel/boot-bind/ai.test.ts +34 -1
  850. package/src/kernel/boot-bind/ai.ts +15 -2
  851. package/src/kernel/boot-bind/channel.test.ts +1 -1
  852. package/src/kernel/boot-bind/channel.ts +1 -1
  853. package/src/kernel/boot-bind/clock.ts +9 -7
  854. package/src/kernel/boot-bind/gate.ts +1 -1
  855. package/src/kernel/boot-bind/honor-config.test.ts +70 -3
  856. package/src/kernel/boot-bind/instances.ts +58 -0
  857. package/src/kernel/boot-bind/journal.ts +3 -2
  858. package/src/kernel/boot-bind/runs.ts +63 -5
  859. package/src/kernel/boot-bind/signal.ts +1 -1
  860. package/src/kernel/boot-bind/store.ts +4 -4
  861. package/src/kernel/boot.test.ts +9 -9
  862. package/src/kernel/boot.ts +115 -16
  863. package/src/kernel/capability.test.ts +42 -0
  864. package/src/kernel/capability.ts +44 -2
  865. package/src/kernel/compensate.test.ts +34 -1
  866. package/src/kernel/compensate.ts +19 -0
  867. package/src/kernel/effect-timing.test.ts +16 -0
  868. package/src/kernel/effects-stamping.test.ts +3 -3
  869. package/src/kernel/effects.test.ts +15 -0
  870. package/src/kernel/effects.ts +39 -5
  871. package/src/kernel/elapsed.test.ts +26 -0
  872. package/src/kernel/elapsed.ts +23 -0
  873. package/src/kernel/errors.ts +26 -3
  874. package/src/kernel/flow.ts +5 -1
  875. package/src/kernel/fx-ask-telemetry.test.ts +114 -0
  876. package/src/kernel/fx.test.ts +143 -2
  877. package/src/kernel/fx.ts +136 -19
  878. package/src/kernel/graceful-shutdown.test.ts +20 -0
  879. package/src/kernel/graceful-shutdown.ts +9 -3
  880. package/src/kernel/horizontal-child.ts +4 -4
  881. package/src/kernel/http-query.test.ts +184 -0
  882. package/src/kernel/http-resource.ts +55 -0
  883. package/src/kernel/index.ts +43 -0
  884. package/src/kernel/instance-id.ts +23 -0
  885. package/src/kernel/instances-chaos-child.ts +73 -0
  886. package/src/kernel/instances.chaos.test.ts +238 -0
  887. package/src/kernel/instances.test.ts +85 -0
  888. package/src/kernel/instances.ts +372 -0
  889. package/src/kernel/lazy-require.ts +20 -0
  890. package/src/kernel/list-page.test.ts +194 -0
  891. package/src/kernel/list-page.ts +515 -0
  892. package/src/kernel/list-query.ts +469 -0
  893. package/src/kernel/pipeline-api-key.test.ts +266 -0
  894. package/src/kernel/pipeline.test.ts +164 -2
  895. package/src/kernel/pipeline.ts +13 -1
  896. package/src/kernel/plugin-elements.test.ts +1 -1
  897. package/src/kernel/plugin-needs.test.ts +1 -1
  898. package/src/kernel/plugin.ts +5 -5
  899. package/src/kernel/ready.test.ts +22 -2
  900. package/src/kernel/registry.ts +8 -4
  901. package/src/kernel/resource-mount.test.ts +75 -0
  902. package/src/kernel/router/index.ts +2 -0
  903. package/src/kernel/router/linear.ts +7 -0
  904. package/src/kernel/router/regexp.ts +8 -0
  905. package/src/kernel/router/smart.ts +7 -3
  906. package/src/kernel/router/trie.ts +7 -0
  907. package/src/kernel/router/types.ts +41 -1
  908. package/src/kernel/router.test.ts +27 -0
  909. package/src/kernel/router.ts +2 -0
  910. package/src/kernel/run-duration.test.ts +92 -0
  911. package/src/kernel/run-telemetry.ts +8 -2
  912. package/src/kernel/triggers.ts +95 -74
  913. package/src/manifest/sql-resource.test.ts +29 -0
  914. package/src/manifest/sql-resource.ts +20 -4
  915. package/src/manifest/types.ts +8 -3
  916. package/src/plugins/auth-delivery.mailpit.integration.test.ts +1 -1
  917. package/src/plugins/auth-methods.security.test.ts +3 -3
  918. package/src/plugins/auth-methods.test.ts +2 -2
  919. package/src/plugins/cors.test.ts +4 -2
  920. package/src/plugins/cors.ts +11 -2
  921. package/src/plugins/csrf.test.ts +17 -0
  922. package/src/plugins/csrf.ts +1 -1
  923. package/src/plugins/username-policy.test.ts +8 -8
  924. package/src/plugins/username.ts +1 -1
  925. package/src/release/build-lib.ts +7 -1
  926. package/src/release/limits.ts +2 -2
  927. package/src/release/measure.ts +7 -10
  928. package/src/runs/bridge-to-console.ts +99 -0
  929. package/src/runs/collect.test.ts +68 -0
  930. package/src/runs/collect.ts +29 -2
  931. package/src/runs/drivers/clickhouse.ts +4 -1
  932. package/src/runs/drivers/files.ts +138 -33
  933. package/src/runs/drivers/memory.ts +46 -7
  934. package/src/runs/drivers/postgres.ts +4 -1
  935. package/src/runs/duckdb.test.ts +33 -0
  936. package/src/runs/duckdb.ts +41 -0
  937. package/src/runs/history.ts +61 -0
  938. package/src/runs/index.ts +29 -1
  939. package/src/runs/parquet.test.ts +110 -0
  940. package/src/runs/parquet.ts +129 -8
  941. package/src/runs/retention.test.ts +24 -0
  942. package/src/runs/retention.ts +42 -0
  943. package/src/runs/runs.test.ts +101 -0
  944. package/src/runs/runtime.ts +5 -3
  945. package/src/runs/types.ts +33 -4
  946. package/src/runtime/bun.ts +61 -4
  947. package/src/runtime/dev-request-log.test.ts +4 -0
  948. package/src/runtime/dev-request-log.ts +19 -2
  949. package/src/runtime/index.ts +8 -1
  950. package/src/runtime/json-code-block.test.ts +355 -0
  951. package/src/runtime/json-code-block.ts +961 -0
  952. package/src/runtime/serve.test.ts +49 -4
  953. package/src/term.test.ts +89 -1
  954. package/src/term.ts +103 -29
  955. package/src/test/create-test-app.ts +3 -1
  956. package/src/console/ui/access/AccessA11yView.tsx +0 -222
  957. package/src/console/ui/access/a11y.test.tsx +0 -113
  958. package/src/console/ui/access/acknowledgement.test.ts +0 -10
  959. package/src/console/ui/access/acknowledgement.ts +0 -33
  960. package/src/console/ui/access/blast-radius.test.ts +0 -26
  961. package/src/console/ui/access/blast-radius.ts +0 -38
  962. package/src/console/ui/access/confirmation.test.ts +0 -34
  963. package/src/console/ui/access/confirmation.ts +0 -33
  964. package/src/console/ui/access/fixture.ts +0 -199
  965. package/src/console/ui/access/grantable.test.ts +0 -15
  966. package/src/console/ui/access/grantable.ts +0 -31
  967. package/src/console/ui/access/hygiene.test.ts +0 -12
  968. package/src/console/ui/access/hygiene.ts +0 -39
  969. package/src/console/ui/access/index.ts +0 -47
  970. package/src/console/ui/access/provenance.test.ts +0 -10
  971. package/src/console/ui/access/provenance.ts +0 -25
  972. package/src/console/ui/access/search.test.ts +0 -13
  973. package/src/console/ui/access/search.ts +0 -68
  974. package/src/console/ui/access/types.ts +0 -111
  975. package/src/console/ui/ai/AiA11yView.tsx +0 -254
  976. package/src/console/ui/ai/a11y.test.tsx +0 -96
  977. package/src/console/ui/ai/findings.ts +0 -41
  978. package/src/console/ui/ai/fixture.ts +0 -177
  979. package/src/console/ui/ai/format.ts +0 -88
  980. package/src/console/ui/ai/group.test.ts +0 -35
  981. package/src/console/ui/ai/group.ts +0 -80
  982. package/src/console/ui/ai/index.ts +0 -59
  983. package/src/console/ui/ai/promotion.test.ts +0 -72
  984. package/src/console/ui/ai/promotion.ts +0 -141
  985. package/src/console/ui/ai/search.test.ts +0 -31
  986. package/src/console/ui/ai/search.ts +0 -79
  987. package/src/console/ui/ai/types.ts +0 -132
  988. package/src/console/ui/architecture/ArchitectureA11yView.tsx +0 -142
  989. package/src/console/ui/architecture/a11y.test.tsx +0 -96
  990. package/src/console/ui/architecture/boundary.ts +0 -42
  991. package/src/console/ui/architecture/declared.ts +0 -161
  992. package/src/console/ui/architecture/fixture.ts +0 -74
  993. package/src/console/ui/architecture/index.ts +0 -56
  994. package/src/console/ui/architecture/layers.ts +0 -64
  995. package/src/console/ui/architecture/layout.ts +0 -66
  996. package/src/console/ui/architecture/pathologies.ts +0 -251
  997. package/src/console/ui/architecture/search.ts +0 -136
  998. package/src/console/ui/architecture/traffic.ts +0 -92
  999. package/src/console/ui/architecture/types.ts +0 -136
  1000. package/src/console/ui/architecture/view.test.ts +0 -153
  1001. package/src/console/ui/architecture/view.ts +0 -489
  1002. package/src/console/ui/channels/ChannelsA11yView.tsx +0 -171
  1003. package/src/console/ui/channels/a11y.test.tsx +0 -95
  1004. package/src/console/ui/channels/confirmation.test.ts +0 -34
  1005. package/src/console/ui/channels/confirmation.ts +0 -24
  1006. package/src/console/ui/channels/fallback.test.ts +0 -15
  1007. package/src/console/ui/channels/fallback.ts +0 -20
  1008. package/src/console/ui/channels/findings.ts +0 -34
  1009. package/src/console/ui/channels/fixture.ts +0 -134
  1010. package/src/console/ui/channels/group.ts +0 -25
  1011. package/src/console/ui/channels/index.ts +0 -51
  1012. package/src/console/ui/channels/locale.test.ts +0 -15
  1013. package/src/console/ui/channels/locale.ts +0 -25
  1014. package/src/console/ui/channels/mask.test.ts +0 -14
  1015. package/src/console/ui/channels/mask.ts +0 -12
  1016. package/src/console/ui/channels/search.ts +0 -49
  1017. package/src/console/ui/channels/taxonomy.test.ts +0 -17
  1018. package/src/console/ui/channels/taxonomy.ts +0 -47
  1019. package/src/console/ui/channels/types.ts +0 -118
  1020. package/src/console/ui/clock/ClockA11yView.tsx +0 -165
  1021. package/src/console/ui/clock/a11y.test.tsx +0 -96
  1022. package/src/console/ui/clock/confirmation.test.ts +0 -30
  1023. package/src/console/ui/clock/confirmation.ts +0 -31
  1024. package/src/console/ui/clock/findings.ts +0 -37
  1025. package/src/console/ui/clock/fixture.ts +0 -111
  1026. package/src/console/ui/clock/health.test.ts +0 -25
  1027. package/src/console/ui/clock/health.ts +0 -56
  1028. package/src/console/ui/clock/index.ts +0 -41
  1029. package/src/console/ui/clock/search.test.ts +0 -37
  1030. package/src/console/ui/clock/search.ts +0 -72
  1031. package/src/console/ui/clock/timeline.test.ts +0 -42
  1032. package/src/console/ui/clock/timeline.ts +0 -41
  1033. package/src/console/ui/clock/types.ts +0 -79
  1034. package/src/console/ui/clock/waiting-on.test.ts +0 -30
  1035. package/src/console/ui/clock/waiting-on.ts +0 -78
  1036. package/src/console/ui/confirmation.unify.test.ts +0 -92
  1037. package/src/console/ui/diff/DiffA11yView.tsx +0 -76
  1038. package/src/console/ui/diff/a11y.test.tsx +0 -96
  1039. package/src/console/ui/diff/fixture.ts +0 -85
  1040. package/src/console/ui/diff/group.test.ts +0 -48
  1041. package/src/console/ui/diff/group.ts +0 -91
  1042. package/src/console/ui/diff/index.ts +0 -32
  1043. package/src/console/ui/diff/search.test.ts +0 -28
  1044. package/src/console/ui/diff/search.ts +0 -63
  1045. package/src/console/ui/diff/summary.ts +0 -73
  1046. package/src/console/ui/diff/types.ts +0 -48
  1047. package/src/console/ui/display.test.ts +0 -14
  1048. package/src/console/ui/display.ts +0 -9
  1049. package/src/console/ui/dist/assets/index--Y0Uaz-m.js +0 -10
  1050. package/src/console/ui/dist/assets/panel-access-ri1X9Otj.js +0 -64
  1051. package/src/console/ui/dist/assets/panel-ai-DLHjRoJk.js +0 -1
  1052. package/src/console/ui/dist/assets/panel-architecture-DI3bQF3J.js +0 -1
  1053. package/src/console/ui/dist/assets/panel-channels-BDYWX29p.js +0 -1
  1054. package/src/console/ui/dist/assets/panel-clock-i-JpTjVB.js +0 -1
  1055. package/src/console/ui/dist/assets/panel-diff-CFuWxiXy.js +0 -1
  1056. package/src/console/ui/dist/assets/panel-flows-B8TRhcoe.js +0 -48
  1057. package/src/console/ui/dist/assets/panel-gates-CfkBgco7.js +0 -1
  1058. package/src/console/ui/dist/assets/panel-overview-CW0CQEc2.js +0 -1
  1059. package/src/console/ui/dist/assets/panel-plugins-DDJwTehL.js +0 -1
  1060. package/src/console/ui/dist/assets/panel-runs-BxuyDI3x.js +0 -1
  1061. package/src/console/ui/dist/assets/panel-signals-BXofbj7v.js +0 -1
  1062. package/src/console/ui/dist/assets/panel-store-B8mH-arU.js +0 -1
  1063. package/src/console/ui/dist/assets/panel-traces-DSA-ZWnf.js +0 -1
  1064. package/src/console/ui/dist/assets/panel-vault-BkZdJPX8.js +0 -1
  1065. package/src/console/ui/dist/assets/rolldown-runtime-B0Z9INg1.js +0 -1
  1066. package/src/console/ui/dist/assets/style-C3L349iZ.css +0 -3
  1067. package/src/console/ui/dist/favicon.svg +0 -7
  1068. package/src/console/ui/dist/index.html +0 -15
  1069. package/src/console/ui/flows/FlowsA11yView.tsx +0 -140
  1070. package/src/console/ui/flows/a11y.test.tsx +0 -99
  1071. package/src/console/ui/flows/buffer.test.ts +0 -83
  1072. package/src/console/ui/flows/buffer.ts +0 -111
  1073. package/src/console/ui/flows/confirmation.ts +0 -129
  1074. package/src/console/ui/flows/contract.test.ts +0 -85
  1075. package/src/console/ui/flows/contract.ts +0 -329
  1076. package/src/console/ui/flows/fixture.ts +0 -81
  1077. package/src/console/ui/flows/graph.test.ts +0 -93
  1078. package/src/console/ui/flows/graph.ts +0 -539
  1079. package/src/console/ui/flows/index.ts +0 -82
  1080. package/src/console/ui/flows/save-as-test.test.ts +0 -47
  1081. package/src/console/ui/flows/save-as-test.ts +0 -97
  1082. package/src/console/ui/flows/search.ts +0 -238
  1083. package/src/console/ui/flows/tiers.ts +0 -133
  1084. package/src/console/ui/gates/GatesA11yView.tsx +0 -183
  1085. package/src/console/ui/gates/a11y.test.tsx +0 -113
  1086. package/src/console/ui/gates/audit.test.ts +0 -40
  1087. package/src/console/ui/gates/audit.ts +0 -61
  1088. package/src/console/ui/gates/denial.test.ts +0 -34
  1089. package/src/console/ui/gates/denial.ts +0 -43
  1090. package/src/console/ui/gates/findings.ts +0 -17
  1091. package/src/console/ui/gates/fixture.ts +0 -193
  1092. package/src/console/ui/gates/group.test.ts +0 -30
  1093. package/src/console/ui/gates/group.ts +0 -94
  1094. package/src/console/ui/gates/index.ts +0 -39
  1095. package/src/console/ui/gates/search.test.ts +0 -49
  1096. package/src/console/ui/gates/search.ts +0 -108
  1097. package/src/console/ui/gates/types.ts +0 -124
  1098. package/src/console/ui/overview/OverviewA11yView.tsx +0 -134
  1099. package/src/console/ui/overview/a11y.test.tsx +0 -112
  1100. package/src/console/ui/overview/busiest.ts +0 -24
  1101. package/src/console/ui/overview/compose.ts +0 -121
  1102. package/src/console/ui/overview/cost.test.ts +0 -39
  1103. package/src/console/ui/overview/cost.ts +0 -134
  1104. package/src/console/ui/overview/fixture.ts +0 -156
  1105. package/src/console/ui/overview/golden.ts +0 -47
  1106. package/src/console/ui/overview/index.ts +0 -52
  1107. package/src/console/ui/overview/rank.test.ts +0 -129
  1108. package/src/console/ui/overview/rank.ts +0 -205
  1109. package/src/console/ui/overview/slo.test.ts +0 -69
  1110. package/src/console/ui/overview/slo.ts +0 -240
  1111. package/src/console/ui/overview/types.ts +0 -127
  1112. package/src/console/ui/overview/verdict.ts +0 -124
  1113. package/src/console/ui/plugins/PluginsA11yView.tsx +0 -217
  1114. package/src/console/ui/plugins/a11y.test.tsx +0 -96
  1115. package/src/console/ui/plugins/command.test.ts +0 -22
  1116. package/src/console/ui/plugins/command.ts +0 -27
  1117. package/src/console/ui/plugins/findings.ts +0 -39
  1118. package/src/console/ui/plugins/fixture.ts +0 -238
  1119. package/src/console/ui/plugins/group.test.ts +0 -36
  1120. package/src/console/ui/plugins/group.ts +0 -62
  1121. package/src/console/ui/plugins/index.ts +0 -30
  1122. package/src/console/ui/plugins/search.ts +0 -55
  1123. package/src/console/ui/plugins/types.ts +0 -118
  1124. package/src/console/ui/runs/RunsA11yView.tsx +0 -252
  1125. package/src/console/ui/runs/a11y.test.tsx +0 -96
  1126. package/src/console/ui/runs/errors.test.ts +0 -53
  1127. package/src/console/ui/runs/errors.ts +0 -88
  1128. package/src/console/ui/runs/explain.test.ts +0 -23
  1129. package/src/console/ui/runs/explain.ts +0 -28
  1130. package/src/console/ui/runs/fixture.ts +0 -189
  1131. package/src/console/ui/runs/group.test.ts +0 -24
  1132. package/src/console/ui/runs/group.ts +0 -76
  1133. package/src/console/ui/runs/histogram.test.ts +0 -22
  1134. package/src/console/ui/runs/histogram.ts +0 -82
  1135. package/src/console/ui/runs/index.ts +0 -69
  1136. package/src/console/ui/runs/project.ts +0 -118
  1137. package/src/console/ui/runs/query.test.ts +0 -48
  1138. package/src/console/ui/runs/query.ts +0 -260
  1139. package/src/console/ui/runs/search.test.ts +0 -45
  1140. package/src/console/ui/runs/search.ts +0 -143
  1141. package/src/console/ui/runs/trace-link.test.ts +0 -26
  1142. package/src/console/ui/runs/trace-link.ts +0 -87
  1143. package/src/console/ui/runs/types.ts +0 -135
  1144. package/src/console/ui/shell/App.tsx +0 -88
  1145. package/src/console/ui/shell/client.ts +0 -1642
  1146. package/src/console/ui/shell/components/oke-logo.tsx +0 -40
  1147. package/src/console/ui/shell/components/ui.tsx +0 -111
  1148. package/src/console/ui/shell/index.html +0 -13
  1149. package/src/console/ui/shell/layout/Shell.tsx +0 -92
  1150. package/src/console/ui/shell/main.tsx +0 -216
  1151. package/src/console/ui/shell/panels/Access.tsx +0 -5
  1152. package/src/console/ui/shell/panels/Ai.tsx +0 -5
  1153. package/src/console/ui/shell/panels/Architecture.tsx +0 -5
  1154. package/src/console/ui/shell/panels/Channels.tsx +0 -5
  1155. package/src/console/ui/shell/panels/Clock.tsx +0 -5
  1156. package/src/console/ui/shell/panels/Diff.tsx +0 -5
  1157. package/src/console/ui/shell/panels/Flows.tsx +0 -5
  1158. package/src/console/ui/shell/panels/Gates.tsx +0 -5
  1159. package/src/console/ui/shell/panels/Overview.tsx +0 -6
  1160. package/src/console/ui/shell/panels/Plugins.tsx +0 -5
  1161. package/src/console/ui/shell/panels/Runs.tsx +0 -5
  1162. package/src/console/ui/shell/panels/Signals.tsx +0 -5
  1163. package/src/console/ui/shell/panels/Store.tsx +0 -5
  1164. package/src/console/ui/shell/panels/Traces.tsx +0 -5
  1165. package/src/console/ui/shell/panels/Vault.tsx +0 -5
  1166. package/src/console/ui/shell/panels/access/AccessPanel.tsx +0 -749
  1167. package/src/console/ui/shell/panels/ai/AiPanel.tsx +0 -492
  1168. package/src/console/ui/shell/panels/architecture/ArchitecturePanel.tsx +0 -329
  1169. package/src/console/ui/shell/panels/channels/ChannelsPanel.tsx +0 -422
  1170. package/src/console/ui/shell/panels/clock/ClockPanel.tsx +0 -454
  1171. package/src/console/ui/shell/panels/diff/DiffPanel.tsx +0 -234
  1172. package/src/console/ui/shell/panels/flows/ContractEditor.tsx +0 -284
  1173. package/src/console/ui/shell/panels/flows/FlowDrawer.tsx +0 -335
  1174. package/src/console/ui/shell/panels/flows/FlowsPanel.tsx +0 -482
  1175. package/src/console/ui/shell/panels/gates/GatesPanel.tsx +0 -433
  1176. package/src/console/ui/shell/panels/overview/OverviewPanel.tsx +0 -398
  1177. package/src/console/ui/shell/panels/plugins/PluginsPanel.tsx +0 -402
  1178. package/src/console/ui/shell/panels/runs/RunsPanel.tsx +0 -652
  1179. package/src/console/ui/shell/panels/signals/SignalsPanel.tsx +0 -788
  1180. package/src/console/ui/shell/panels/store/StorePanel.tsx +0 -755
  1181. package/src/console/ui/shell/panels/traces/TracesPanel.tsx +0 -478
  1182. package/src/console/ui/shell/panels/vault/VaultPanel.tsx +0 -477
  1183. package/src/console/ui/shell/plugin/Sandbox.tsx +0 -29
  1184. package/src/console/ui/shell/public/favicon.svg +0 -7
  1185. package/src/console/ui/shell/setup/Wizard.tsx +0 -211
  1186. package/src/console/ui/shell/styles.css +0 -74
  1187. package/src/console/ui/signals/SignalsA11yView.tsx +0 -252
  1188. package/src/console/ui/signals/a11y.test.tsx +0 -96
  1189. package/src/console/ui/signals/confirmation.test.ts +0 -35
  1190. package/src/console/ui/signals/confirmation.ts +0 -59
  1191. package/src/console/ui/signals/dry-run.test.ts +0 -18
  1192. package/src/console/ui/signals/dry-run.ts +0 -34
  1193. package/src/console/ui/signals/durable.test.ts +0 -22
  1194. package/src/console/ui/signals/durable.ts +0 -39
  1195. package/src/console/ui/signals/findings.ts +0 -31
  1196. package/src/console/ui/signals/fixture.ts +0 -242
  1197. package/src/console/ui/signals/group.test.ts +0 -26
  1198. package/src/console/ui/signals/group.ts +0 -41
  1199. package/src/console/ui/signals/index.ts +0 -49
  1200. package/src/console/ui/signals/monitor.test.ts +0 -30
  1201. package/src/console/ui/signals/monitor.ts +0 -74
  1202. package/src/console/ui/signals/schema-form.test.ts +0 -23
  1203. package/src/console/ui/signals/schema-form.ts +0 -109
  1204. package/src/console/ui/signals/search.ts +0 -93
  1205. package/src/console/ui/signals/types.ts +0 -72
  1206. package/src/console/ui/store/StoreA11yView.tsx +0 -193
  1207. package/src/console/ui/store/a11y.test.tsx +0 -96
  1208. package/src/console/ui/store/cache-view.test.ts +0 -13
  1209. package/src/console/ui/store/cache-view.ts +0 -36
  1210. package/src/console/ui/store/confirmation.test.ts +0 -36
  1211. package/src/console/ui/store/confirmation.ts +0 -52
  1212. package/src/console/ui/store/dry-run.test.ts +0 -15
  1213. package/src/console/ui/store/dry-run.ts +0 -26
  1214. package/src/console/ui/store/fixture.ts +0 -167
  1215. package/src/console/ui/store/group.test.ts +0 -16
  1216. package/src/console/ui/store/group.ts +0 -38
  1217. package/src/console/ui/store/index.ts +0 -36
  1218. package/src/console/ui/store/search.ts +0 -74
  1219. package/src/console/ui/store/types.ts +0 -67
  1220. package/src/console/ui/store/will-not-fire.test.ts +0 -19
  1221. package/src/console/ui/store/will-not-fire.ts +0 -39
  1222. package/src/console/ui/traces/TracesA11yView.tsx +0 -181
  1223. package/src/console/ui/traces/a11y.test.tsx +0 -96
  1224. package/src/console/ui/traces/chain.test.ts +0 -47
  1225. package/src/console/ui/traces/chain.ts +0 -142
  1226. package/src/console/ui/traces/critical-path.test.ts +0 -22
  1227. package/src/console/ui/traces/critical-path.ts +0 -55
  1228. package/src/console/ui/traces/filter.test.ts +0 -74
  1229. package/src/console/ui/traces/filter.ts +0 -104
  1230. package/src/console/ui/traces/fixture.ts +0 -126
  1231. package/src/console/ui/traces/fold.test.ts +0 -59
  1232. package/src/console/ui/traces/fold.ts +0 -168
  1233. package/src/console/ui/traces/index.ts +0 -64
  1234. package/src/console/ui/traces/mini.ts +0 -63
  1235. package/src/console/ui/traces/replay.test.ts +0 -22
  1236. package/src/console/ui/traces/replay.ts +0 -33
  1237. package/src/console/ui/traces/sampling.test.ts +0 -26
  1238. package/src/console/ui/traces/sampling.ts +0 -63
  1239. package/src/console/ui/traces/search.ts +0 -135
  1240. package/src/console/ui/traces/tier.ts +0 -70
  1241. package/src/console/ui/traces/types.ts +0 -125
  1242. package/src/console/ui/tsconfig.json +0 -20
  1243. package/src/console/ui/vault/VaultA11yView.tsx +0 -197
  1244. package/src/console/ui/vault/a11y.test.tsx +0 -96
  1245. package/src/console/ui/vault/backend.test.ts +0 -75
  1246. package/src/console/ui/vault/backend.ts +0 -117
  1247. package/src/console/ui/vault/blast-radius.ts +0 -53
  1248. package/src/console/ui/vault/confirmation.test.ts +0 -37
  1249. package/src/console/ui/vault/confirmation.ts +0 -36
  1250. package/src/console/ui/vault/dormant.ts +0 -28
  1251. package/src/console/ui/vault/export-safe.test.ts +0 -26
  1252. package/src/console/ui/vault/export-safe.ts +0 -62
  1253. package/src/console/ui/vault/fixture.ts +0 -94
  1254. package/src/console/ui/vault/group.test.ts +0 -25
  1255. package/src/console/ui/vault/group.ts +0 -49
  1256. package/src/console/ui/vault/index.ts +0 -47
  1257. package/src/console/ui/vault/search.ts +0 -58
  1258. package/src/console/ui/vault/types.ts +0 -83
  1259. package/src/console/ui/vite.config.ts +0 -84
  1260. /package/src/console/{ui/vault → ui-next/src/features/vault/lib}/blast-radius.test.ts +0 -0
  1261. /package/src/console/{ui/vault → ui-next/src/features/vault/lib}/dormant.test.ts +0 -0
@@ -15,7 +15,10 @@ import {
15
15
  computedCacheKey,
16
16
  createStoreRuntime,
17
17
  files as declareFiles,
18
+ fileKeyWarnings,
18
19
  index as declareIndex,
20
+ coerceSafeFileObjectKey,
21
+ inferFileContentType,
19
22
  isInvalidatedByWrite,
20
23
  kv as declareKv,
21
24
  projectFileKeys,
@@ -27,8 +30,37 @@ import {
27
30
  type StoreRuntime,
28
31
  } from "../../elements/store.ts";
29
32
  import { DryRunWriteIsolationError, withDryRun } from "../../kernel/dry-run.ts";
30
- import type { Effects, Manifest, ResourceRef, StoreFacet } from "../../manifest/types.ts";
33
+ import { addPiiFieldName, piiNameAliases, PII_MASK } from "../../elements/store/classify.ts";
34
+ import { rankIndexHits } from "./index-search.ts";
35
+ import type {
36
+ ColumnClassification,
37
+ Effects,
38
+ Manifest,
39
+ ResourceRef,
40
+ StoreFacet,
41
+ } from "../../manifest/types.ts";
31
42
  import type { WideEvent } from "../../runs/types.ts";
43
+ import { consoleAuthStoreEnabled, projectConsoleAuthStore } from "./auth-store.ts";
44
+ import {
45
+ fileObjectRecord,
46
+ isFilesCatalogKey,
47
+ readFilesCatalog,
48
+ removeFilesCatalogRecords,
49
+ upsertFilesCatalogRecord,
50
+ } from "./files-catalog.ts";
51
+ import {
52
+ alterSqlPolicy,
53
+ createSqlPolicy,
54
+ dropSqlPolicy,
55
+ applySqlTableRls,
56
+ listSqlCatalog,
57
+ listSqlTableRls,
58
+ setSqlExtension,
59
+ setSqlRowSecurity,
60
+ sqlCatalogKind,
61
+ sqlCatalogStoreChildren,
62
+ upgradeSqlExtension,
63
+ } from "./sql-catalog.ts";
32
64
 
33
65
  /** Whether multi-tenancy is declared on the Manifest (off by default). */
34
66
  export function tenancyDeclared(manifest: Manifest | null): boolean {
@@ -64,6 +96,8 @@ export interface ConsoleStoreChild {
64
96
  readonly name: string;
65
97
  /** Effect ref used in Manifest (`sql:bookings`). */
66
98
  readonly effectRef: ResourceRef;
99
+ /** SQL catalog folder when not a table. */
100
+ readonly kind?: "table" | "index" | "function" | "trigger" | "extension" | "policy";
67
101
  readonly writers: readonly string[];
68
102
  readonly readers: readonly string[];
69
103
  readonly cache: ConsoleStoreCacheView;
@@ -71,6 +105,8 @@ export interface ConsoleStoreChild {
71
105
  readonly piiColumns: readonly string[];
72
106
  /** Column key → optional human description (SQL tables). */
73
107
  readonly columnDescriptions: Readonly<Record<string, string>>;
108
+ /** Live RLS (`pg_class.relrowsecurity`) when the engine can report it. */
109
+ readonly rls?: boolean;
74
110
  }
75
111
 
76
112
  /** One row in `console.store.list`. */
@@ -83,6 +119,8 @@ export interface ConsoleStoreRow {
83
119
  readonly replicaLagMs: number | null;
84
120
  readonly migrationDrift: ConsoleMigrationDrift | null;
85
121
  readonly contentAddressed: boolean;
122
+ /** Files driver when the runtime could open the handle (`memory` / `fs` / `s3`). */
123
+ readonly driverId?: "memory" | "fs" | "s3";
86
124
  readonly warnings: ReadonlyArray<{
87
125
  readonly code: string;
88
126
  readonly message: string;
@@ -99,6 +137,11 @@ export interface ProjectStoresOptions {
99
137
  /** Injected fingerprints for tests. */
100
138
  readonly declaredFingerprint?: string;
101
139
  readonly appliedFingerprint?: string | null;
140
+ /**
141
+ * Surface `sql:oke_console` (operator-plane auth). Default: env
142
+ * `OKE_CONSOLE_AUTH_STORE=1`.
143
+ */
144
+ readonly includeAuthStore?: boolean;
102
145
  }
103
146
 
104
147
  /**
@@ -135,17 +178,26 @@ export async function projectStoresList(options: ProjectStoresOptions): Promise<
135
178
  for (const [name, store] of Object.entries(manifest?.stores ?? {})) {
136
179
  const facet = store.facet;
137
180
  const ref = `${facet}:${name}` as ResourceRef;
138
- const children = childrenOf(manifest!, name, facet, store);
181
+ const children = await withSqlTableRls(
182
+ options.runtime,
183
+ ref,
184
+ facet,
185
+ childrenOf(manifest!, name, facet, store),
186
+ );
139
187
  const replicaLagMs = facet === "sql" ? latestReplicaLag(options.runs ?? [], children) : null;
140
188
 
141
189
  let warnings: ConsoleStoreRow["warnings"] = [];
190
+ let filesDriverId: FilesStoreFxHandle["driverId"] | undefined;
142
191
  if (facet === "files" && options.runtime) {
143
192
  try {
144
193
  const handle = (await options.runtime.openRef(ref, {
145
194
  effects: { reads: [ref] },
146
195
  })) as FilesStoreFxHandle;
196
+ filesDriverId = handle.driverId;
147
197
  const keys = await handle.list();
148
- warnings = projectFileKeys(keys).flatMap((k) => k.warnings);
198
+ warnings = projectFileKeys(keys.filter((k) => !isFilesCatalogKey(k))).flatMap(
199
+ (k) => k.warnings,
200
+ );
149
201
  } catch {
150
202
  warnings = [];
151
203
  }
@@ -160,10 +212,15 @@ export async function projectStoresList(options: ProjectStoresOptions): Promise<
160
212
  replicaLagMs,
161
213
  migrationDrift: facet === "sql" ? drift : null,
162
214
  contentAddressed: facet === "files",
215
+ ...(filesDriverId ? { driverId: filesDriverId } : {}),
163
216
  warnings,
164
217
  });
165
218
  }
166
219
 
220
+ if (options.includeAuthStore ?? consoleAuthStoreEnabled()) {
221
+ stores.push(projectConsoleAuthStore());
222
+ }
223
+
167
224
  stores.sort((a, b) => {
168
225
  const order: StoreFacet[] = ["sql", "kv", "files", "index"];
169
226
  const d = order.indexOf(a.facet) - order.indexOf(b.facet);
@@ -200,10 +257,8 @@ function childrenOf(
200
257
  }
201
258
 
202
259
  const unique = [...new Set(names)].sort();
203
- return unique.map((childName) => {
204
- const effectRef = (
205
- facet === "sql" ? `sql:${childName}` : `${facet}:${storeName}`
206
- ) as ResourceRef;
260
+ const tables = unique.map((childName) => {
261
+ const effectRef = `${facet}:${childName}` as ResourceRef;
207
262
  const writers = flowsTouching(manifest, effectRef, "writes");
208
263
  const readers = flowsTouching(manifest, effectRef, "reads");
209
264
  const willNotFire = willNotFireFor(manifest, writers);
@@ -224,8 +279,26 @@ function childrenOf(
224
279
  willNotFire,
225
280
  piiColumns,
226
281
  columnDescriptions: columnDescriptionsFor(store, childName),
282
+ ...(facet === "sql" ? { kind: "table" as const, rls: false } : {}),
227
283
  };
228
284
  });
285
+ if (facet !== "sql") return tables;
286
+ return [...tables, ...sqlCatalogStoreChildren(`${facet}:${storeName}` as ResourceRef)];
287
+ }
288
+
289
+ async function withSqlTableRls(
290
+ runtime: StoreRuntime | null,
291
+ ref: ResourceRef,
292
+ facet: StoreFacet,
293
+ children: readonly ConsoleStoreChild[],
294
+ ): Promise<readonly ConsoleStoreChild[]> {
295
+ if (facet !== "sql" || runtime === null) return children;
296
+ try {
297
+ const sql = (await runtime.openRef(ref, { effects: { reads: [ref] } })) as SqlStoreHandle;
298
+ return applySqlTableRls(children, await listSqlTableRls(sql));
299
+ } catch {
300
+ return children;
301
+ }
229
302
  }
230
303
 
231
304
  function columnDescriptionsFor(
@@ -278,10 +351,16 @@ export function willNotFireFor(
278
351
  }
279
352
 
280
353
  function piiColumnsFor(store: NonNullable<Manifest["stores"]>[string], table: string): string[] {
281
- const cols: string[] = [];
354
+ const cols = new Set<string>();
282
355
  const tableMeta = store.tables?.[table];
283
356
  for (const [col, tags] of Object.entries(tableMeta?.columns ?? {})) {
284
- if (tags?.pii) cols.push(col);
357
+ if (!tags?.pii) continue;
358
+ addPiiFieldName(cols, col);
359
+ const sqlName =
360
+ "sqlName" in tags && typeof (tags as { sqlName?: unknown }).sqlName === "string"
361
+ ? (tags as { sqlName: string }).sqlName
362
+ : undefined;
363
+ if (sqlName) addPiiFieldName(cols, sqlName);
285
364
  }
286
365
  for (const [key, tags] of Object.entries(store.classifications ?? {})) {
287
366
  if (
@@ -292,10 +371,10 @@ function piiColumnsFor(store: NonNullable<Manifest["stores"]>[string], table: st
292
371
  "pii" in tags &&
293
372
  (tags as { pii?: boolean }).pii
294
373
  ) {
295
- cols.push(key.slice(table.length + 1));
374
+ addPiiFieldName(cols, key.slice(table.length + 1));
296
375
  }
297
376
  }
298
- return [...new Set(cols)].sort();
377
+ return [...cols].sort();
299
378
  }
300
379
 
301
380
  function latestReplicaLag(
@@ -341,6 +420,9 @@ export interface StoreQueryResult {
341
420
  readonly keys?: ReadonlyArray<{
342
421
  readonly key: string;
343
422
  readonly value?: unknown;
423
+ readonly ttlMs?: number | null;
424
+ readonly sizeBytes?: number;
425
+ readonly originalName?: string;
344
426
  readonly warnings?: ReadonlyArray<{
345
427
  readonly code: string;
346
428
  readonly message: string;
@@ -356,6 +438,62 @@ export interface StoreQueryResult {
356
438
  readonly routedRole?: "primary" | "replica";
357
439
  }
358
440
 
441
+ const KV_TTL_RE = /^(\d+)(ms|s|m|h|d)$/;
442
+
443
+ /**
444
+ * Prefix for `kv.list` when Console browse does not pass an explicit one.
445
+ *
446
+ * A dedicated `store.kv("drafts")` keeps keys at the namespace root
447
+ * (`ENG-184`). `${child}:` is only for a shared KV store whose children
448
+ * are key prefixes (`kv:cache` / `drafts:…`).
449
+ *
450
+ * @param ref - Store ref (`kv:drafts`)
451
+ * @param child - Selected child / namespace
452
+ * @param explicit - Operator-supplied list prefix
453
+ */
454
+ function kvBrowsePrefix(
455
+ ref: string,
456
+ child: string | undefined,
457
+ explicit: string | undefined,
458
+ ): string {
459
+ if (explicit !== undefined) return explicit;
460
+ if (!child) return "";
461
+ const storeName = ref.split(":")[1] ?? "";
462
+ if (child === storeName) return "";
463
+ return `${child}:`;
464
+ }
465
+
466
+ /**
467
+ * Resolve the TTL argument for `kv.set` from a Console patch.
468
+ * Omitted `ttl` keeps the remaining expiry; `null` / empty clears it.
469
+ *
470
+ * @param patch - Edit patch
471
+ * @param remainingMs - Current remaining TTL, or null
472
+ */
473
+ function kvTtlFromPatch(
474
+ patch: Readonly<Record<string, unknown>>,
475
+ remainingMs: number | null,
476
+ ): string | undefined {
477
+ if (!("ttl" in patch)) {
478
+ return remainingMs !== null && remainingMs > 0 ? `${Math.ceil(remainingMs)}ms` : undefined;
479
+ }
480
+ const raw = patch.ttl;
481
+ if (raw === null || raw === "") return undefined;
482
+ if (typeof raw !== "string" || !KV_TTL_RE.test(raw.trim())) {
483
+ throw new Error("TTL must be a duration like 30m, 1h, or empty to clear");
484
+ }
485
+ return raw.trim();
486
+ }
487
+
488
+ /** UTF-8 byte length of a JSON-serialized KV value. */
489
+ function kvValueSizeBytes(value: unknown): number {
490
+ try {
491
+ return new TextEncoder().encode(JSON.stringify(value ?? null)).length;
492
+ } catch {
493
+ return 0;
494
+ }
495
+ }
496
+
359
497
  /**
360
498
  * Browse a store facet through the runtime (PII masked unless reveal).
361
499
  *
@@ -381,6 +519,12 @@ export async function queryStore(
381
519
  if (!table) {
382
520
  return { facet, rows: [], masked: !input.revealPii, routedRole: sql.routedRole };
383
521
  }
522
+ const catalog = sqlCatalogKind(table);
523
+ if (catalog) {
524
+ const storeName = input.ref.split(":")[1] ?? "";
525
+ const rows = await listSqlCatalog(sql, catalog, manifest, storeName, input.limit ?? 200);
526
+ return { facet, rows, masked: false, routedRole: sql.routedRole };
527
+ }
384
528
  const limit = input.limit ?? 50;
385
529
  let sqlText = `SELECT * FROM "${table}"`;
386
530
  const params: unknown[] = [];
@@ -410,51 +554,203 @@ export async function queryStore(
410
554
 
411
555
  if (facet === "kv") {
412
556
  const kv = handle as KvStoreFxHandle;
413
- const keys = await kv.list(input.prefix ?? "");
557
+ const keys = await kv.list(kvBrowsePrefix(input.ref, input.child, input.prefix));
414
558
  const limited = keys.slice(0, input.limit ?? 100);
415
559
  const entries = await Promise.all(
416
- limited.map(async (key) => ({
417
- key,
418
- value: await kv.get(key),
419
- })),
560
+ limited.map(async (key) => {
561
+ const value = await kv.get(key);
562
+ return {
563
+ key,
564
+ value,
565
+ ttlMs: await kv.ttlMs(key),
566
+ sizeBytes: kvValueSizeBytes(value),
567
+ };
568
+ }),
420
569
  );
421
570
  return { facet, keys: entries, masked: false };
422
571
  }
423
572
 
424
573
  if (facet === "files") {
425
574
  const filesHandle = handle as FilesStoreFxHandle;
426
- const keys = await filesHandle.list(input.prefix ?? "");
575
+ const keys = (await filesHandle.list(input.prefix ?? "")).filter((k) => !isFilesCatalogKey(k));
576
+ const catalog = await readFilesCatalog(filesHandle);
427
577
  const projected = projectFileKeys(keys.slice(0, input.limit ?? 100));
428
- return {
429
- facet,
430
- keys: projected.map((k) => ({
431
- key: k.key,
432
- warnings: k.warnings.map((w) => ({
433
- code: w.code,
434
- message: w.message,
435
- })),
436
- })),
437
- masked: false,
438
- };
578
+ const entries = await Promise.all(
579
+ projected.map(async (k) => {
580
+ const data = await filesHandle.get(k.key);
581
+ const meta = catalog.objects[k.key];
582
+ return {
583
+ key: k.key,
584
+ sizeBytes: data?.byteLength ?? 0,
585
+ ...(meta ? { originalName: meta.originalName } : {}),
586
+ warnings: k.warnings.map((w) => ({
587
+ code: w.code,
588
+ message: w.message,
589
+ })),
590
+ };
591
+ }),
592
+ );
593
+ return { facet, keys: entries, masked: false };
439
594
  }
440
595
 
441
- // index
596
+ // index — text query ranks stored meta; a vector still probes ANN.
442
597
  const idx = handle as IndexStoreFxHandle;
443
598
  void manifest;
599
+ const topK = input.topK ?? 5;
600
+ const listLimit = input.limit ?? 100;
601
+ const q = input.q?.trim() ?? "";
602
+ const vector = input.vector ?? [];
603
+
444
604
  if (idx.driverId === "meilisearch") {
445
- const q = input.q ?? "";
446
- if (q.trim().length === 0) {
447
- return { facet, hits: [], masked: false };
605
+ if (q.length > 0) {
606
+ const result = await idx.search(q, { topK });
607
+ return {
608
+ facet,
609
+ hits: result.hits,
610
+ facetDistribution: result.facetDistribution,
611
+ masked: false,
612
+ };
448
613
  }
449
- const result = await idx.search(q, { topK: input.topK ?? 5 });
450
- return { facet, hits: result.hits, facetDistribution: result.facetDistribution, masked: false };
614
+ return { facet, hits: await idx.list(listLimit), masked: false };
451
615
  }
452
- const vector = input.vector ?? [];
453
- if (vector.length === 0) {
454
- return { facet, hits: [], masked: false };
616
+
617
+ if (vector.length > 0) {
618
+ return { facet, hits: await idx.search(vector, topK), masked: false };
619
+ }
620
+ if (q.length > 0) {
621
+ return {
622
+ facet,
623
+ hits: rankIndexHits(await idx.list(INDEX_TEXT_SCAN), q, topK),
624
+ masked: false,
625
+ };
455
626
  }
456
- const hits = await idx.search(vector, input.topK ?? 5);
457
- return { facet, hits, masked: false };
627
+ return { facet, hits: await idx.list(listLimit), masked: false };
628
+ }
629
+
630
+ /** How many documents a text query scans before ranking. */
631
+ const INDEX_TEXT_SCAN = 2_000;
632
+
633
+ /** Max object body returned by {@link getStoreFile} (2 MiB). */
634
+ export const STORE_FILE_BODY_MAX = 2_000_000;
635
+
636
+ /** Request for {@link getStoreFile}. */
637
+ export interface StoreFileGetInput {
638
+ readonly ref: ResourceRef;
639
+ readonly key: string;
640
+ readonly tenant?: string;
641
+ }
642
+
643
+ /** Object payload for Console preview / download. */
644
+ export interface StoreFileObject {
645
+ readonly key: string;
646
+ readonly sizeBytes: number;
647
+ readonly contentType: string;
648
+ readonly encoding: "utf8" | "base64";
649
+ readonly body: string;
650
+ readonly truncated: boolean;
651
+ readonly originalName?: string;
652
+ readonly warnings: ReadonlyArray<{
653
+ readonly code: string;
654
+ readonly message: string;
655
+ }>;
656
+ }
657
+
658
+ /**
659
+ * Read one files object for Console preview / download.
660
+ *
661
+ * @param runtime - Store runtime
662
+ * @param input - Store ref + object key
663
+ */
664
+ export async function getStoreFile(
665
+ runtime: StoreRuntime,
666
+ input: StoreFileGetInput,
667
+ ): Promise<StoreFileObject> {
668
+ const [facet] = input.ref.split(":") as [StoreFacet, string];
669
+ if (facet !== "files") {
670
+ throw new Error(`store object get requires a files ref, got ${input.ref}`);
671
+ }
672
+ const handle = (await runtime.openRef(input.ref, {
673
+ effects: { reads: [input.ref] },
674
+ })) as FilesStoreFxHandle;
675
+ const data = await handle.get(input.key);
676
+ if (!data) {
677
+ throw new StoreFileNotFoundError(input.ref, input.key);
678
+ }
679
+ const truncated = data.byteLength > STORE_FILE_BODY_MAX;
680
+ const slice = truncated ? data.subarray(0, STORE_FILE_BODY_MAX) : data;
681
+ const catalog = await readFilesCatalog(handle);
682
+ const meta = catalog.objects[input.key];
683
+ const contentType = meta?.contentType ?? inferFileContentType(meta?.originalName ?? input.key);
684
+ const asText = fileBytesAsUtf8(slice, contentType);
685
+ return {
686
+ key: input.key,
687
+ sizeBytes: data.byteLength,
688
+ contentType,
689
+ encoding: asText !== null ? "utf8" : "base64",
690
+ body: asText ?? bytesToBase64(slice),
691
+ truncated,
692
+ ...(meta ? { originalName: meta.originalName } : {}),
693
+ warnings: fileKeyWarnings(input.key).map((w) => ({
694
+ code: w.code,
695
+ message: w.message,
696
+ })),
697
+ };
698
+ }
699
+
700
+ /** Missing object on {@link getStoreFile}. */
701
+ export class StoreFileNotFoundError extends Error {
702
+ readonly ref: string;
703
+ readonly key: string;
704
+
705
+ constructor(ref: string, key: string) {
706
+ super(`object not found: ${key}`);
707
+ this.name = "StoreFileNotFoundError";
708
+ this.ref = ref;
709
+ this.key = key;
710
+ }
711
+ }
712
+
713
+ function fileBytesAsUtf8(bytes: Uint8Array, contentType: string): string | null {
714
+ if (bytes.includes(0)) return null;
715
+ const textual =
716
+ contentType.startsWith("text/") ||
717
+ contentType === "application/json" ||
718
+ contentType === "application/xml" ||
719
+ contentType === "application/javascript";
720
+ if (!textual) return null;
721
+ try {
722
+ return new TextDecoder("utf-8", { fatal: true }).decode(bytes);
723
+ } catch {
724
+ return null;
725
+ }
726
+ }
727
+
728
+ function bytesToBase64(bytes: Uint8Array): string {
729
+ let binary = "";
730
+ const chunk = 0x8000;
731
+ for (let i = 0; i < bytes.length; i += chunk) {
732
+ binary += String.fromCharCode(...bytes.subarray(i, i + chunk));
733
+ }
734
+ return btoa(binary);
735
+ }
736
+
737
+ function decodeFilePatchBody(patch: Readonly<Record<string, unknown>>): Uint8Array {
738
+ const body = patch.body;
739
+ if (typeof body !== "string") {
740
+ throw new Error("files put requires string patch.body");
741
+ }
742
+ if (patch.encoding === "utf8") {
743
+ return new TextEncoder().encode(body);
744
+ }
745
+ if (patch.encoding !== undefined && patch.encoding !== "base64") {
746
+ throw new Error("files put encoding must be utf8 or base64");
747
+ }
748
+ const binary = atob(body);
749
+ const bytes = new Uint8Array(binary.length);
750
+ for (let i = 0; i < binary.length; i++) {
751
+ bytes[i] = binary.charCodeAt(i);
752
+ }
753
+ return bytes;
458
754
  }
459
755
 
460
756
  /** Options for a direct edit (not a flow execution). */
@@ -464,6 +760,7 @@ export interface StoreEditInput {
464
760
  readonly tenant?: string;
465
761
  readonly id?: string;
466
762
  readonly key?: string;
763
+ /** Column values. Omit {@link StoreEditInput.id} to INSERT (requires `patch.id`). */
467
764
  readonly patch: Record<string, unknown>;
468
765
  readonly confirmation?: string;
469
766
  readonly reason?: string;
@@ -512,7 +809,7 @@ export async function editStore(
512
809
  const snapshot = await snapshotEditTarget(runtime, input);
513
810
  try {
514
811
  const { wouldHaveFired } = await withDryRun(async () => {
515
- await applyEdit(runtime, input, { revealPii: false });
812
+ await applyEdit(runtime, input, { revealPii: false, persistMeta: false });
516
813
  });
517
814
  await restoreEditTarget(runtime, snapshot);
518
815
  return {
@@ -531,7 +828,7 @@ export async function editStore(
531
828
  }
532
829
  }
533
830
 
534
- await applyEdit(runtime, input, { revealPii: false });
831
+ await applyEdit(runtime, input, { revealPii: false, persistMeta: true }, manifest);
535
832
  // Direct edit: invalidate cache for written resource (effects-derived).
536
833
  runtime.onWriteEffects({ writes: [effectRef] });
537
834
  void options.production;
@@ -551,6 +848,7 @@ type EditSnapshot =
551
848
  readonly ref: ResourceRef;
552
849
  readonly key: string;
553
850
  readonly value: unknown;
851
+ readonly ttlMs: number | null;
554
852
  }
555
853
  | {
556
854
  readonly kind: "sql";
@@ -559,6 +857,27 @@ type EditSnapshot =
559
857
  readonly id: string;
560
858
  readonly row: Record<string, unknown> | null;
561
859
  }
860
+ | {
861
+ readonly kind: "extension";
862
+ readonly ref: ResourceRef;
863
+ readonly name: string;
864
+ readonly enabled: boolean;
865
+ readonly version: string | null;
866
+ }
867
+ | {
868
+ readonly kind: "policy";
869
+ readonly ref: ResourceRef;
870
+ readonly id: string;
871
+ readonly existed: boolean;
872
+ }
873
+ | {
874
+ readonly kind: "files";
875
+ readonly ref: ResourceRef;
876
+ readonly key: string;
877
+ readonly data: Uint8Array | null;
878
+ readonly writtenKey: string;
879
+ readonly writtenData: Uint8Array | null;
880
+ }
562
881
  | { readonly kind: "none" };
563
882
 
564
883
  async function snapshotEditTarget(
@@ -566,6 +885,21 @@ async function snapshotEditTarget(
566
885
  input: StoreEditInput,
567
886
  ): Promise<EditSnapshot> {
568
887
  const [facet] = input.ref.split(":") as [StoreFacet, string];
888
+ if (facet === "files" && input.key) {
889
+ const filesHandle = (await runtime.openRef(input.ref, {
890
+ effects: { reads: [input.ref] },
891
+ })) as FilesStoreFxHandle;
892
+ const writtenKey = coerceSafeFileObjectKey(input.key);
893
+ const data = await filesHandle.get(input.key);
894
+ return {
895
+ kind: "files",
896
+ ref: input.ref,
897
+ key: input.key,
898
+ data,
899
+ writtenKey,
900
+ writtenData: writtenKey === input.key ? data : await filesHandle.get(writtenKey),
901
+ };
902
+ }
569
903
  if (facet === "kv" && input.key) {
570
904
  const kv = (await runtime.openRef(input.ref, {
571
905
  effects: { reads: [input.ref] },
@@ -575,37 +909,83 @@ async function snapshotEditTarget(
575
909
  ref: input.ref,
576
910
  key: input.key,
577
911
  value: await kv.get(input.key),
912
+ ttlMs: await kv.ttlMs(input.key),
578
913
  };
579
914
  }
580
- if (facet === "sql" && input.child && input.id) {
915
+ if (facet === "sql" && input.child && input.id && sqlCatalogKind(input.child) === "policy") {
581
916
  const sql = (await runtime.openRef(input.ref, {
582
917
  effects: { reads: [input.ref] },
583
918
  })) as SqlStoreHandle;
584
- try {
585
- const rows = await sql.raw(`SELECT * FROM "${input.child}" WHERE "id" = ? LIMIT 1`, [
586
- input.id,
587
- ]);
588
- return {
589
- kind: "sql",
590
- ref: input.ref,
591
- child: input.child,
592
- id: input.id,
593
- row: rows[0] ?? null,
594
- };
595
- } catch {
596
- return {
597
- kind: "sql",
598
- ref: input.ref,
599
- child: input.child,
600
- id: input.id,
601
- row: null,
602
- };
919
+ const rows = await listSqlCatalog(sql, "policy", null, "", 500);
920
+ return {
921
+ kind: "policy",
922
+ ref: input.ref,
923
+ id: input.id,
924
+ existed: rows.some((r) => String(r.id) === input.id),
925
+ };
926
+ }
927
+ if (facet === "sql" && input.child && input.id && sqlCatalogKind(input.child) === "extension") {
928
+ const sql = (await runtime.openRef(input.ref, {
929
+ effects: { reads: [input.ref] },
930
+ })) as SqlStoreHandle;
931
+ const rows = await listSqlCatalog(sql, "extension", null, "", 500);
932
+ const row = rows.find((r) => String(r.name) === input.id);
933
+ return {
934
+ kind: "extension",
935
+ ref: input.ref,
936
+ name: input.id,
937
+ enabled: row?.enabled === true,
938
+ version: typeof row?.version === "string" ? row.version : null,
939
+ };
940
+ }
941
+ if (facet === "sql" && input.child) {
942
+ const id = input.id ?? sqlInsertRowId(input.patch);
943
+ if (id) {
944
+ const sql = (await runtime.openRef(input.ref, {
945
+ effects: { reads: [input.ref] },
946
+ })) as SqlStoreHandle;
947
+ try {
948
+ const rows = await sql.raw(`SELECT * FROM "${input.child}" WHERE "id" = ? LIMIT 1`, [id]);
949
+ return {
950
+ kind: "sql",
951
+ ref: input.ref,
952
+ child: input.child,
953
+ id,
954
+ row: rows[0] ?? null,
955
+ };
956
+ } catch {
957
+ return {
958
+ kind: "sql",
959
+ ref: input.ref,
960
+ child: input.child,
961
+ id,
962
+ row: null,
963
+ };
964
+ }
603
965
  }
604
966
  }
605
967
  return { kind: "none" };
606
968
  }
607
969
 
608
970
  async function restoreEditTarget(runtime: StoreRuntime, snapshot: EditSnapshot): Promise<void> {
971
+ if (snapshot.kind === "files") {
972
+ const filesHandle = (await runtime.openRef(snapshot.ref, {
973
+ effects: { writes: [snapshot.ref] },
974
+ })) as FilesStoreFxHandle;
975
+ if (snapshot.writtenKey !== snapshot.key) {
976
+ if (snapshot.writtenData === null) {
977
+ await filesHandle.delete(snapshot.writtenKey);
978
+ } else {
979
+ await filesHandle.put(snapshot.writtenKey, snapshot.writtenData);
980
+ }
981
+ }
982
+ if (snapshot.data === null) {
983
+ await filesHandle.delete(snapshot.key);
984
+ } else {
985
+ await filesHandle.put(snapshot.key, snapshot.data);
986
+ }
987
+ return;
988
+ }
609
989
  if (snapshot.kind === "kv") {
610
990
  const kv = (await runtime.openRef(snapshot.ref, {
611
991
  effects: { writes: [snapshot.ref] },
@@ -613,7 +993,33 @@ async function restoreEditTarget(runtime: StoreRuntime, snapshot: EditSnapshot):
613
993
  if (snapshot.value === undefined) {
614
994
  await kv.delete(snapshot.key);
615
995
  } else {
616
- await kv.set(snapshot.key, snapshot.value);
996
+ const ttl =
997
+ snapshot.ttlMs !== null && snapshot.ttlMs > 0
998
+ ? `${Math.ceil(snapshot.ttlMs)}ms`
999
+ : undefined;
1000
+ await kv.set(snapshot.key, snapshot.value, ttl);
1001
+ }
1002
+ return;
1003
+ }
1004
+ if (snapshot.kind === "policy") {
1005
+ if (snapshot.existed) return;
1006
+ const sql = (await runtime.openRef(snapshot.ref, {
1007
+ effects: { writes: [snapshot.ref] },
1008
+ })) as SqlStoreHandle;
1009
+ try {
1010
+ await dropSqlPolicy(sql, snapshot.id);
1011
+ } catch {
1012
+ /* best-effort restore */
1013
+ }
1014
+ return;
1015
+ }
1016
+ if (snapshot.kind === "extension") {
1017
+ const sql = (await runtime.openRef(snapshot.ref, {
1018
+ effects: { writes: [snapshot.ref] },
1019
+ })) as SqlStoreHandle;
1020
+ await setSqlExtension(sql, snapshot.name, snapshot.enabled);
1021
+ if (snapshot.enabled && snapshot.version) {
1022
+ await upgradeSqlExtension(sql, snapshot.name, snapshot.version);
617
1023
  }
618
1024
  return;
619
1025
  }
@@ -642,10 +1048,83 @@ async function restoreEditTarget(runtime: StoreRuntime, snapshot: EditSnapshot):
642
1048
  }
643
1049
  }
644
1050
 
1051
+ function findFileObjectsTable(
1052
+ manifest: Manifest | null,
1053
+ ): { readonly ref: ResourceRef; readonly table: string } | null {
1054
+ if (!manifest?.stores) return null;
1055
+ for (const [name, store] of Object.entries(manifest.stores)) {
1056
+ if (store.facet === "sql" && store.tables && "file_objects" in store.tables) {
1057
+ return { ref: `sql:${name}` as ResourceRef, table: "file_objects" };
1058
+ }
1059
+ }
1060
+ return null;
1061
+ }
1062
+
1063
+ async function upsertFileObjectsSql(
1064
+ runtime: StoreRuntime,
1065
+ manifest: Manifest | null,
1066
+ storeRef: string,
1067
+ row: {
1068
+ readonly objectKey: string;
1069
+ readonly originalName: string;
1070
+ readonly contentType: string;
1071
+ readonly sizeBytes: number;
1072
+ },
1073
+ ): Promise<void> {
1074
+ const found = findFileObjectsTable(manifest);
1075
+ if (!found) return;
1076
+ try {
1077
+ const sql = (await runtime.openRef(found.ref, {
1078
+ effects: { writes: [found.ref] },
1079
+ })) as SqlStoreHandle;
1080
+ const existing = await sql.raw(
1081
+ `SELECT "id" FROM "${found.table}" WHERE "object_key" = ? LIMIT 1`,
1082
+ [row.objectKey],
1083
+ );
1084
+ if (existing.length > 0) {
1085
+ await sql.raw(
1086
+ `UPDATE "${found.table}" SET "original_name" = ?, "content_type" = ?, "size_bytes" = ?, "store_ref" = ? WHERE "object_key" = ?`,
1087
+ [row.originalName, row.contentType, row.sizeBytes, storeRef, row.objectKey],
1088
+ );
1089
+ return;
1090
+ }
1091
+ await sql.raw(
1092
+ `INSERT INTO "${found.table}" ("id", "object_key", "original_name", "content_type", "size_bytes", "store_ref") VALUES (?, ?, ?, ?, ?, ?)`,
1093
+ [row.objectKey, row.objectKey, row.originalName, row.contentType, row.sizeBytes, storeRef],
1094
+ );
1095
+ } catch {
1096
+ /* table missing or driver refused — catalog still holds the row */
1097
+ }
1098
+ }
1099
+
1100
+ async function deleteFileObjectsSql(
1101
+ runtime: StoreRuntime,
1102
+ manifest: Manifest | null,
1103
+ storeRef: string,
1104
+ keys: readonly string[],
1105
+ ): Promise<void> {
1106
+ const found = findFileObjectsTable(manifest);
1107
+ if (!found || keys.length === 0) return;
1108
+ try {
1109
+ const sql = (await runtime.openRef(found.ref, {
1110
+ effects: { writes: [found.ref] },
1111
+ })) as SqlStoreHandle;
1112
+ for (const key of keys) {
1113
+ await sql.raw(`DELETE FROM "${found.table}" WHERE "object_key" = ? AND "store_ref" = ?`, [
1114
+ key,
1115
+ storeRef,
1116
+ ]);
1117
+ }
1118
+ } catch {
1119
+ /* best-effort */
1120
+ }
1121
+ }
1122
+
645
1123
  async function applyEdit(
646
1124
  runtime: StoreRuntime,
647
1125
  input: StoreEditInput,
648
- ctx: { readonly revealPii: boolean },
1126
+ ctx: { readonly revealPii: boolean; readonly persistMeta?: boolean },
1127
+ manifest?: Manifest | null,
649
1128
  ): Promise<void> {
650
1129
  const [facet] = input.ref.split(":") as [StoreFacet, string];
651
1130
  const handle = await runtime.openRef(input.ref, {
@@ -653,11 +1132,51 @@ async function applyEdit(
653
1132
  revealPii: ctx.revealPii,
654
1133
  });
655
1134
 
1135
+ if (facet === "files") {
1136
+ const filesHandle = handle as FilesStoreFxHandle;
1137
+ const requested = input.key;
1138
+ if (!requested) throw new Error("files edit requires key");
1139
+ const bytes = decodeFilePatchBody(input.patch);
1140
+ const key = coerceSafeFileObjectKey(requested);
1141
+ const originalName =
1142
+ typeof input.patch.originalName === "string" && input.patch.originalName.trim().length > 0
1143
+ ? input.patch.originalName.trim()
1144
+ : requested.slice(requested.lastIndexOf("/") + 1);
1145
+ await filesHandle.put(key, bytes);
1146
+ if (key !== requested) {
1147
+ await filesHandle.delete(requested);
1148
+ }
1149
+ if (ctx.persistMeta !== false) {
1150
+ if (key !== requested) {
1151
+ await removeFilesCatalogRecords(filesHandle, [requested]);
1152
+ await deleteFileObjectsSql(runtime, manifest ?? null, input.ref, [requested]);
1153
+ }
1154
+ await upsertFilesCatalogRecord(
1155
+ filesHandle,
1156
+ key,
1157
+ fileObjectRecord(originalName, bytes.byteLength, key),
1158
+ );
1159
+ await upsertFileObjectsSql(runtime, manifest ?? null, input.ref, {
1160
+ objectKey: key,
1161
+ originalName,
1162
+ contentType: inferFileContentType(originalName),
1163
+ sizeBytes: bytes.byteLength,
1164
+ });
1165
+ }
1166
+ return;
1167
+ }
1168
+
656
1169
  if (facet === "kv") {
657
1170
  const kv = handle as KvStoreFxHandle;
658
1171
  const key = input.key;
659
1172
  if (!key) throw new Error("kv edit requires key");
660
- await kv.set(key, input.patch.value ?? input.patch);
1173
+ const current = await kv.get(key);
1174
+ const nextValue = "value" in input.patch ? input.patch.value : current;
1175
+ if (nextValue === undefined) {
1176
+ throw new Error("kv edit requires a value for a new key");
1177
+ }
1178
+ const ttl = kvTtlFromPatch(input.patch, await kv.ttlMs(key));
1179
+ await kv.set(key, nextValue, ttl);
661
1180
  return;
662
1181
  }
663
1182
 
@@ -665,9 +1184,66 @@ async function applyEdit(
665
1184
  const sql = handle as SqlStoreHandle;
666
1185
  const table = input.child;
667
1186
  const id = input.id;
668
- if (!table || !id) throw new Error("sql edit requires child + id");
1187
+ if (!table) throw new Error("sql edit requires child");
1188
+ if (!id && sqlCatalogKind(table) !== null) {
1189
+ throw new Error("sql edit requires child + id");
1190
+ }
1191
+ if (id && sqlCatalogKind(table) === "policy") {
1192
+ if (input.patch.create === true) {
1193
+ await createSqlPolicy(sql, input.patch);
1194
+ return;
1195
+ }
1196
+ if (input.patch.drop === true) {
1197
+ await dropSqlPolicy(sql, id);
1198
+ return;
1199
+ }
1200
+ if (typeof input.patch.rls === "boolean") {
1201
+ const tableName = typeof input.patch.table === "string" ? input.patch.table : id;
1202
+ await setSqlRowSecurity(sql, tableName, input.patch.rls);
1203
+ return;
1204
+ }
1205
+ await alterSqlPolicy(sql, id, input.patch);
1206
+ return;
1207
+ }
1208
+ if (id && sqlCatalogKind(table) === "extension") {
1209
+ if (input.patch.upgrade === true) {
1210
+ const to = typeof input.patch.version === "string" ? input.patch.version : undefined;
1211
+ await setSqlExtension(sql, id, true);
1212
+ await upgradeSqlExtension(sql, id, to);
1213
+ return;
1214
+ }
1215
+ const enabled = input.patch.enabled;
1216
+ if (typeof enabled !== "boolean") {
1217
+ throw new Error("extension edit requires boolean enabled or upgrade");
1218
+ }
1219
+ await setSqlExtension(sql, id, enabled, {
1220
+ ...(typeof input.patch.schema === "string" ? { schema: input.patch.schema } : {}),
1221
+ ...(typeof input.patch.version === "string" ? { version: input.patch.version } : {}),
1222
+ ...(input.patch.cascade === true ? { cascade: true } : {}),
1223
+ });
1224
+ return;
1225
+ }
669
1226
  const sets = Object.keys(input.patch);
670
1227
  if (sets.length === 0) return;
1228
+ const pii = piiColumnsForRef(runtime, input.ref, table);
1229
+ for (const column of sets) {
1230
+ if (pii.has(column) && input.patch[column] === PII_MASK) {
1231
+ throw new Error(
1232
+ `refusing to persist PII mask placeholder over column "${column}" — reveal or set a new value`,
1233
+ );
1234
+ }
1235
+ }
1236
+ if (!id) {
1237
+ const insertId = sqlInsertRowId(input.patch);
1238
+ if (!insertId) throw new Error("sql insert requires an id in the patch");
1239
+ const columns = sets.map((c) => `"${c}"`).join(", ");
1240
+ const placeholders = sets.map(() => "?").join(", ");
1241
+ await sql.raw(
1242
+ `INSERT INTO "${table}" (${columns}) VALUES (${placeholders})`,
1243
+ sets.map((c) => input.patch[c]),
1244
+ );
1245
+ return;
1246
+ }
671
1247
  const assignments = sets.map((c) => `"${c}" = ?`).join(", ");
672
1248
  const params = [...sets.map((c) => input.patch[c]), id];
673
1249
  await sql.raw(`UPDATE "${table}" SET ${assignments} WHERE "id" = ?`, params);
@@ -677,6 +1253,35 @@ async function applyEdit(
677
1253
  throw new Error(`direct edit not supported for facet ${facet}`);
678
1254
  }
679
1255
 
1256
+ /**
1257
+ * Row id for a SQL insert (`patch.id`). Used when `input.id` is omitted.
1258
+ *
1259
+ * @param patch - Insert column values
1260
+ */
1261
+ function sqlInsertRowId(patch: Readonly<Record<string, unknown>>): string | undefined {
1262
+ const raw = patch.id;
1263
+ if (typeof raw === "string" && raw.length > 0) return raw;
1264
+ if (typeof raw === "number" && Number.isFinite(raw)) return String(raw);
1265
+ return undefined;
1266
+ }
1267
+
1268
+ /** PII columns for a SQL child from the Manifest bound to this runtime. */
1269
+ function piiColumnsForRef(
1270
+ runtime: StoreRuntime,
1271
+ ref: ResourceRef,
1272
+ table: string,
1273
+ ): ReadonlySet<string> {
1274
+ const manifest = runtimeManifest.get(runtime);
1275
+ const storeName = ref.split(":")[1];
1276
+ if (!storeName) return new Set();
1277
+ const store = manifest?.stores?.[storeName];
1278
+ if (!store) return new Set();
1279
+ return new Set(piiColumnsFor(store, table));
1280
+ }
1281
+
1282
+ /** Manifest captured when the Console runtime is created (for PII guard). */
1283
+ const runtimeManifest = new WeakMap<StoreRuntime, Manifest | null>();
1284
+
680
1285
  /** Delete rows/keys. */
681
1286
  export interface StoreDeleteInput {
682
1287
  readonly ref: ResourceRef;
@@ -695,6 +1300,7 @@ export interface StoreDeleteInput {
695
1300
  export async function deleteStore(
696
1301
  runtime: StoreRuntime,
697
1302
  input: StoreDeleteInput,
1303
+ manifest?: Manifest | null,
698
1304
  ): Promise<{ readonly deleted: number }> {
699
1305
  const [facet] = input.ref.split(":") as [StoreFacet, string];
700
1306
  const handle = await runtime.openRef(input.ref, {
@@ -708,9 +1314,16 @@ export async function deleteStore(
708
1314
  }
709
1315
  } else if (facet === "files") {
710
1316
  const filesHandle = handle as FilesStoreFxHandle;
1317
+ const removed: string[] = [];
711
1318
  for (const key of input.keys ?? []) {
712
- if (await filesHandle.delete(key)) deleted++;
1319
+ if (isFilesCatalogKey(key)) continue;
1320
+ if (await filesHandle.delete(key)) {
1321
+ deleted++;
1322
+ removed.push(key);
1323
+ }
713
1324
  }
1325
+ await removeFilesCatalogRecords(filesHandle, removed);
1326
+ await deleteFileObjectsSql(runtime, manifest ?? null, input.ref, removed);
714
1327
  } else if (facet === "sql") {
715
1328
  const sql = handle as SqlStoreHandle;
716
1329
  const table = input.child;
@@ -757,13 +1370,61 @@ export function purgeStoreCache(
757
1370
  return { keys: [...new Set([...event.keys, ...extra])] };
758
1371
  }
759
1372
 
1373
+ /**
1374
+ * True when `name` is `public` or a declared policy Gate (rate gates excluded).
1375
+ *
1376
+ * @param manifest - Current Manifest
1377
+ * @param name - Gate name from the query console
1378
+ */
1379
+ export function isKnownConsoleSqlGate(manifest: Manifest | null, name: string): boolean {
1380
+ if (name === "public") return true;
1381
+ const gate = manifest?.gates?.[name];
1382
+ if (!gate) return false;
1383
+ return gate.kind !== "rate" && !name.startsWith("rate:");
1384
+ }
1385
+
1386
+ const GATE_CONTEXT_DRIVERS = new Set<SqlStoreHandle["driverId"]>(["postgres", "pglite"]);
1387
+
1388
+ /** DML / DDL heads — keep in sync with `isSqlWrite` in the query console. */
1389
+ const STORE_SQL_WRITE_HEADS = new Set([
1390
+ "INSERT",
1391
+ "UPDATE",
1392
+ "DELETE",
1393
+ "DROP",
1394
+ "ALTER",
1395
+ "CREATE",
1396
+ "TRUNCATE",
1397
+ "REPLACE",
1398
+ "GRANT",
1399
+ "REVOKE",
1400
+ "VACUUM",
1401
+ "COMMENT",
1402
+ "COPY",
1403
+ "CALL",
1404
+ "REFRESH",
1405
+ "MERGE",
1406
+ ]);
1407
+
1408
+ /**
1409
+ * True when console SQL mutates the store (DML / DDL / `EXPLAIN ANALYZE`).
1410
+ *
1411
+ * @param sql - One statement (already trimmed)
1412
+ */
1413
+ export function isStoreSqlWrite(sql: string): boolean {
1414
+ const trimmed = sql.trim().replace(/;+\s*$/, "");
1415
+ const head = /^([A-Za-z]+)/.exec(trimmed)?.[1]?.toUpperCase() ?? "";
1416
+ if (head === "EXPLAIN") return /\bANALYZE\b/i.test(trimmed);
1417
+ if (head === "ANALYZE") return true;
1418
+ return STORE_SQL_WRITE_HEADS.has(head);
1419
+ }
1420
+
760
1421
  /**
761
1422
  * Raw SQL console — read-only by default.
762
1423
  *
763
1424
  * @param runtime - Store runtime
764
1425
  * @param ref - SQL store ref
765
1426
  * @param sqlText - SQL
766
- * @param options - Write allow + reveal
1427
+ * @param options - Write allow + reveal + optional Gate
767
1428
  */
768
1429
  export async function runStoreSql(
769
1430
  runtime: StoreRuntime,
@@ -773,14 +1434,18 @@ export async function runStoreSql(
773
1434
  readonly allowWrite: boolean;
774
1435
  readonly revealPii?: boolean;
775
1436
  readonly tenant?: string;
1437
+ /** View rows as this Gate (`oke.gate` GUC on postgres / pglite). */
1438
+ readonly asGate?: string;
776
1439
  },
777
1440
  ): Promise<{
778
1441
  readonly rows: readonly Record<string, unknown>[];
779
1442
  readonly masked: boolean;
780
1443
  readonly routedRole: "primary" | "replica";
1444
+ readonly asGate: string | null;
1445
+ readonly gateApplied: boolean;
781
1446
  }> {
782
- const trimmed = sqlText.trim();
783
- const isWrite = /^(INSERT|UPDATE|DELETE|DROP|ALTER|CREATE|TRUNCATE|REPLACE)\b/i.test(trimmed);
1447
+ const trimmed = sqlText.trim().replace(/;+\s*$/, "");
1448
+ const isWrite = isStoreSqlWrite(trimmed);
784
1449
  if (isWrite && !options.allowWrite) {
785
1450
  throw new Error("SQL console is read-only by default — write requires console:store.sql:write");
786
1451
  }
@@ -788,12 +1453,53 @@ export async function runStoreSql(
788
1453
  effects: isWrite ? { writes: [ref] } : { reads: [ref] },
789
1454
  revealPii: options.revealPii === true,
790
1455
  })) as SqlStoreHandle;
791
- const rows = await handle.raw(trimmed);
792
- return {
793
- rows,
794
- masked: !options.revealPii,
795
- routedRole: handle.routedRole,
796
- };
1456
+ const asGate = options.asGate?.trim() || null;
1457
+ let gateApplied = false;
1458
+ try {
1459
+ if (asGate) gateApplied = await applySqlGateContext(handle, asGate);
1460
+ const rows = await handle.raw(trimmed);
1461
+ if (gateApplied) await handle.raw("COMMIT");
1462
+ return {
1463
+ rows,
1464
+ masked: !options.revealPii,
1465
+ routedRole: handle.routedRole,
1466
+ asGate,
1467
+ gateApplied,
1468
+ };
1469
+ } catch (err) {
1470
+ if (gateApplied) {
1471
+ try {
1472
+ await handle.raw("ROLLBACK");
1473
+ } catch {
1474
+ // Connection may already be idle after a failed SET.
1475
+ }
1476
+ }
1477
+ throw err;
1478
+ }
1479
+ }
1480
+
1481
+ /**
1482
+ * Open a transaction and set `oke.gate` + `row_security` for RLS simulation.
1483
+ * No-op on memory SQL.
1484
+ *
1485
+ * @param handle - Open SQL handle
1486
+ * @param gate - Validated Gate name
1487
+ */
1488
+ async function applySqlGateContext(handle: SqlStoreHandle, gate: string): Promise<boolean> {
1489
+ if (!GATE_CONTEXT_DRIVERS.has(handle.driverId)) return false;
1490
+ try {
1491
+ await handle.raw("BEGIN");
1492
+ await handle.raw("SET LOCAL row_security = on");
1493
+ await handle.raw("SELECT set_config('oke.gate', ?, true)", [gate]);
1494
+ return true;
1495
+ } catch {
1496
+ try {
1497
+ await handle.raw("ROLLBACK");
1498
+ } catch {
1499
+ // ignore
1500
+ }
1501
+ return false;
1502
+ }
797
1503
  }
798
1504
 
799
1505
  /**
@@ -834,7 +1540,7 @@ export async function createManifestStoreRuntime(
834
1540
  case "sql":
835
1541
  runtime.register(
836
1542
  declareSql(name, {
837
- classify: store.classifications as never,
1543
+ classify: sqlClassifyFromManifest(store),
838
1544
  }),
839
1545
  );
840
1546
  break;
@@ -849,5 +1555,82 @@ export async function createManifestStoreRuntime(
849
1555
  break;
850
1556
  }
851
1557
  }
1558
+ runtimeManifest.set(runtime, manifest);
852
1559
  return runtime;
853
1560
  }
1561
+
1562
+ /**
1563
+ * Merge flat `store.classifications` with table-column tags from Manifest
1564
+ * `stores.*.tables.*.columns` into the nested `table → column → tags` shape
1565
+ * {@link declareSql} expects (driver-boundary masking).
1566
+ *
1567
+ * @param store - Manifest store row
1568
+ */
1569
+ function sqlClassifyFromManifest(
1570
+ store: NonNullable<Manifest["stores"]>[string],
1571
+ ): Readonly<Record<string, Readonly<Record<string, ColumnClassification>>>> {
1572
+ const nested: Record<string, Record<string, ColumnClassification>> = {};
1573
+
1574
+ for (const [key, value] of Object.entries(store.classifications ?? {})) {
1575
+ const dot = key.indexOf(".");
1576
+ if (dot <= 0) continue;
1577
+ const table = key.slice(0, dot);
1578
+ const column = key.slice(dot + 1);
1579
+ if (column.length === 0) continue;
1580
+ const tags = classificationFromValue(value);
1581
+ if (!tags) continue;
1582
+ putClassifyAliases(nested, table, column, tags);
1583
+ }
1584
+
1585
+ for (const [table, meta] of Object.entries(store.tables ?? {})) {
1586
+ for (const [column, tags] of Object.entries(meta.columns ?? {})) {
1587
+ const normalized = classificationFromValue(tags);
1588
+ if (!normalized) continue;
1589
+ putClassifyAliases(nested, table, column, normalized);
1590
+ const sqlName =
1591
+ "sqlName" in tags && typeof (tags as { sqlName?: unknown }).sqlName === "string"
1592
+ ? (tags as { sqlName: string }).sqlName
1593
+ : undefined;
1594
+ if (sqlName) putClassifyAliases(nested, table, sqlName, normalized);
1595
+ }
1596
+ }
1597
+
1598
+ return nested;
1599
+ }
1600
+
1601
+ /**
1602
+ * Register classify tags under JS and SQL spellings of a column.
1603
+ *
1604
+ * @param nested - table → column → tags
1605
+ * @param table - Table name
1606
+ * @param column - Manifest or SQL column name
1607
+ * @param tags - Classification tags
1608
+ */
1609
+ function putClassifyAliases(
1610
+ nested: Record<string, Record<string, ColumnClassification>>,
1611
+ table: string,
1612
+ column: string,
1613
+ tags: ColumnClassification,
1614
+ ): void {
1615
+ const row = { ...(nested[table] ?? {}) };
1616
+ for (const name of piiNameAliases(column)) {
1617
+ row[name] = tags;
1618
+ }
1619
+ nested[table] = row;
1620
+ }
1621
+
1622
+ /**
1623
+ * Normalize a Manifest classification value into tags, or null when not a
1624
+ * tag object (e.g. string / string[] classification forms).
1625
+ *
1626
+ * @param value - Manifest classification value
1627
+ */
1628
+ function classificationFromValue(value: unknown): ColumnClassification | null {
1629
+ if (!value || typeof value !== "object" || Array.isArray(value)) return null;
1630
+ const v = value as Record<string, unknown>;
1631
+ const tags: ColumnClassification = {};
1632
+ if (v.pii === true) tags.pii = true;
1633
+ if (v.sensitive === true) tags.sensitive = true;
1634
+ if (typeof v.retain === "string") tags.retain = v.retain;
1635
+ return Object.keys(tags).length > 0 ? tags : null;
1636
+ }