Authentication
Tonnex uses Supabase Auth for all authentication needs with enterprise-grade optimizations for performance and security.Architecture
Web App Auth Flow (Next.js 16)
- User enters credentials on
/loginor creates account on/signup - Upon success, user is redirected to
/home @supabase/ssrhandles Supabase auth call- Session stored as HTTP-only cookies
proxy.tsrefreshes session cookie on every request and callsgetUser()for JWT verificationgetAuthContext()reads fromgetSession()(local cookie, ~0ms) — safe because middleware already verified the token- Server actions and components use
getAuthContext()for token + org context
⚠️ Performance Note:getAuthContext()usesgetSession()(local, ~0ms) instead ofgetUser()(network, ~150-300ms). The middleware already verifies the JWT, so re-verification in server actions is unnecessary.getAuthContext()is deduplicated viaReact.cache().
API Auth Flow
- Web app includes JWT in
Authorization: Bearer <token>header SupabaseGuardextracts token and verifies it locally usingjose+SUPABASE_JWT_SECRET(~0.1ms)- Falls back to Supabase Auth API if local verification fails
- Authenticated user attached to
request.user - All downstream services can access the verified user + JWT claims
🔒 Security: Swagger/API docs are only available in development (NODE_ENV !== 'production'). CORS requiresWEB_URLto be set in production.
User Logout
- Click the Sign out button in the dashboard sidebar.
- The
logout()server action (inapps/web/actions/auth.ts) is triggered. - Supabase session is revoked.
- User is redirected to
/login.
JWT Claims (Custom Access Token Hook)
The Supabase custom access token hook (supabase/migrations/0001_custom_access_token_hook_onboarding.sql) enriches the JWT with:
RLS Functions
RBAC Default Behavior
TheRbacProvider defaults to deny-by-default — if a component is rendered outside the provider, hasPermission() returns false. This prevents accidental permission bypasses.