This guide covers the setup and configuration of better-auth features used in this starter template.
This project uses better-auth — a self-hosted, TypeScript-first authentication library with zero vendor lock-in. Auth data is stored locally in SQLite via Drizzle ORM.
src/lib/auth.ts— Server-side better-auth configurationsrc/lib/auth-client.ts— Client-side auth client (React hooks)src/lib/auth-schema.ts— Drizzle schema (generated by better-auth CLI)src/lib/db.ts— Drizzle ORM instance with better-sqlite3src/app/api/auth/[...all]/route.ts— API catch-all route handlermiddleware.ts— Route protection usinggetSessionCookie()
BETTER_AUTH_SECRET= # Required: Auth secret key (generate with: openssl rand -base64 32)
BETTER_AUTH_URL=http://localhost:3000 # Base URL of your app
DATABASE_PATH=./sqlite.db # SQLite database pathEnabled by default. Users can sign up and sign in with email/password.
Multi-tenant workspace management with roles: owner, admin, member.
- Users can create and switch between organizations
- Organization members can be invited and managed
- Role-based access control for navigation and pages
This project uses @daveyplate/better-auth-ui for pre-built auth components:
- Auth pages:
<AuthView />for sign-in, sign-up, forgot-password - Profile:
<AccountSettingsCards />,<SecuritySettingsCards /> - Organizations:
<OrganizationSwitcher />,<OrganizationsCard />,<OrganizationSettingsCards />
The <AuthUIProvider> wraps the app in providers.tsx and provides auth context to all components.
See docs/nav-rbac.md for the client-side navigation access control system using better-auth hooks.
After modifying plugins in src/lib/auth.ts:
# Regenerate schema
echo "y" | npx @better-auth/cli@latest generate --config ./src/lib/auth.ts --output ./src/lib/auth-schema.ts
# Push to database
npx drizzle-kit push