Schema-level isolation
Every domain table has aworkspaceId field. Every query filters by it.
convex/schema.ts
Auth-aware scoping
In every query / mutation that returns workspace data, filter by the active workspace:URL-scoped routing
Routes include the workspace slug:/w/{slug}/projects, /w/{slug}/settings. The slug → workspaceId resolution happens in a layout component.
Per-tenant limits
For “free tier max 3 projects”:Common patterns
Workspaces + memberships
Standard. A user can belong to many workspaces. See the Multi-tenant SaaS recipe.
Personal + team workspaces
Each new user gets a personal workspace; can create / join shared ones later.
Subdomain per workspace
acme.yourapp.com, betacorp.yourapp.com. Adds setup complexity but feels premium.Database-per-tenant (don't)
Common in legacy systems; rarely worth it on Convex. Schema-level isolation is simpler and just as secure.
Related
Multi-tenant SaaS recipe
Full walkthrough.
Roles & permissions
Per-workspace roles.
Data access control
Defending against leaks.
