Roles and RBAC
Fontana uses role-based access control (RBAC) in two layers:
- Zitadel - who the user is, MFA, and which role name they hold (project role grant)
- Flow / Convex - what that role can do via a static permission catalog and dynamic role documents
You assign roles in Zitadel (or via SCIM when enabled). Admins define permission sets in Admin → Roles. There are no per-user permission overrides in the app: effective permissions always come from the user’s assigned role.
How the layers connect
Section titled “How the layers connect”Zitadel project role (e.g. editor) → JWT claim on login → Convex storeUser → users.roleId → roles.permissions → effective permission list → Flow sidebar, pages, and mutations| Layer | You configure | Fontana stores |
|---|---|---|
| Identity | Zitadel (SSO, MFA, project role grants, SCIM when enabled) | User profile, enabled flag, projected roleId |
| Authorization | Admin → Roles (permission sets), Admin → Users (enable/disable only) | Convex roles table, permission checks on every mutation |
Zitadel project role keys must match Convex role names exactly (for example admin, editor, viewer, member). If the token carries a role name with no matching Convex role, the user signs in but receives no permissions until an admin creates the role or fixes the Zitadel grant.
Default roles
Section titled “Default roles”Four roles are upserted on every workspace seed. Custom roles you create in Admin are never modified by seed.
| Role | Typical use | Permission summary |
|---|---|---|
admin | Platform and security administrators | Wildcard * (all permissions) |
editor | Builders and analysts who create workflows, agents, and knowledge | Full read/write on workflows, agents, skills, Knowledge Graph, files, and evals; AI model selection; no user admin or platform deploy |
viewer | Read-only operators and reviewers | Read workflows, agents, skills, Knowledge Graph, files, evals, and explore; edit own profile |
member | Minimal access | Explore, read workflows, edit own profile |
Grant these roles in Zitadel as project roles on the Flow application. Provisioning seeds a break-glass admin@fontana.local account with the admin project role on fresh installs.
Permission format
Section titled “Permission format”Permissions use resource:action ids (OAuth2-compatible), defined in the static catalog shipped with Fontana:
| Resource | Example actions | What it gates |
|---|---|---|
workflows | read, write, delete | Canvas, workflow lists, run and edit |
agents | read, write, delete | AI agent definitions and Admin agent surfaces |
skills | read, write, delete | Skill packages |
knowledge-graph | read, write, delete | Knowledge Graph documents and namespaces |
evals | read, write, run, delete | Evaluation tests |
files | read, write, delete | File browser and uploads |
ai | page, select_model, add_model, … | Usage page, model approval, defaults |
users | read, write, create, delete, enable | Admin → Users and user management |
teams | admin | Admin → Teams (create, rename, membership) |
platform | read, write | Admin → Deployment, API keys, releases |
profile | read, write, allow_email_change | User profile and preferences |
explore | read | Community template explore |
audit_logs_own | read | LLM debug for the caller’s chat threads |
audit_logs_team | read | LLM debug for any user’s threads (high trust) |
Wildcards are supported when editing roles in Admin:
*- all permissions (used by defaultadmin)workflows.*- all actions on one resource area
Manage roles in Admin
Section titled “Manage roles in Admin”Admin → Roles lets you:
- Create custom roles with any combination of catalog permissions or wildcards
- Edit permission sets for custom roles (default seed roles can be edited like any other Convex role document)
- Delete custom roles that are no longer needed
After you create a custom role in Flow, grant the matching project role name in Zitadel so users receive it on login.
Teams and workflow access
Section titled “Teams and workflow access”Teams add a second dimension for team-bound workflows:
teams:admin- create teams, rename teams, and manage team membership (vieweroreditoron the team)- Team-bound workflows require both global
workflows:*permissions and team membership with the right team role
Personal workflows (teamId unset) follow global RBAC only. See Admin → Teams and Team Workflows in the sidebar.
Route and UI gates
Section titled “Route and UI gates”Flow hides sidebar entries and blocks routes when the signed-in user lacks the required permission. Examples:
| Route | Permission required |
|---|---|
/workflows, /workflow | workflows:read |
/agents, /tools | agents:read |
/knowledge-graph | knowledge-graph:read |
/usage, /threads | ai:page |
/admin/users, /admin/roles | users:read |
/admin/teams | teams:admin |
/admin/deployment | platform:read |
/audit-logs/chat (own) | audit_logs_own:read |
Backend mutations call the same permission checks; missing permission fails closed with an error.
Disabled users
Section titled “Disabled users”When an admin disables a user in Admin → Users, effective permissions become empty immediately regardless of role. Re-enable restores permissions from the assigned role.
Privileged RBAC changes (role edits, user enable/disable, team membership) should appear in admin audit logs and, when producers are enabled, the immutable security audit trail. See Immutable audit trail.
Related documentation
Section titled “Related documentation”- Identity providers - SSO and federation into Zitadel before roles apply
- Identity and access - MFA, SCIM provisioning, service authentication
- Security - platform security controls and SOC 2 summary
- Immutable audit trail - identity and admin events in the WORM ledger