Skip to content

Data model

Summary of the schema notes in CLAUDE.md. The full design, with the reasons for each choice, is NEW_DATABASE_STRUCTURE.md (written in Italian).

GroupTables
Tenantorgs, orgs_members, orgs_invites, profiles, api_keys
Canvasprojects, canvases, nodes, nodes_connections, node_runs, assets, canvas_events
Agentschat_threads, chat_messages, ai_calls

Tables of the earlier social product (brands, products, social_accounts, posts, post_sources, scheduled_posts, the ad_* tables, social_posts, influencers) still exist in the schema but are not part of the canvas product and are not documented here.

  • org_id is on every org table; row-level security uses auth_org_ids(). The service-role key bypasses it, so every use is declared in src/lib/server/db/service-role-uses.ts.
  • nodes.data is jsonb, shaped per node type.
  • nodes.version: position is last-write-wins; data uses optimistic concurrency (where version = expected; zero rows is a conflict).
  • nodes.deleted_at: soft delete; every read filters deleted_at is null.
  • actor_kind, actor_id, agent_key wherever an action is recorded. For an agent, actor_id is the user it acts for.
  • nodes_connections.target_handle: a video with start and end frames has two inputs.
  • Realtime publishes nodes, nodes_connections, canvases, node_runs with replica identity full.
  • Types are generated (npm run db:types), never hand-written.