Setup
Local Postgres, OAuth env, seeds — running in ~10 minutes
Prerequisites
- Node.js 24.10.0 and pnpm 11.5.2 (the pinned versions)
- A Supabase account (free tier works for development)
- A Google Cloud project for the OAuth client
Create a Supabase project
- Create a new Supabase project and note the project URL.
- Collect the anonymous key and the service-role key from the project API settings.
- Use the project's Postgres connection string as
DATABASE_URL, or run a local Postgres and pointDATABASE_URLat it for offline development.
Set NEXT_PUBLIC_SUPABASE_URL, NEXT_PUBLIC_SUPABASE_ANON_KEY, and SUPABASE_SERVICE_ROLE_KEY in your local env file. Never commit env values.
Configure Google OAuth
- In the Google Cloud Console, create an OAuth client of type Web application.
- Add the authorized redirect URI for Supabase:
https://<project-ref>.supabase.co/auth/v1/callback. - In the Supabase dashboard, enable the Google provider under Authentication and paste the client id and secret.
- Add the app callback URLs to the allowed redirect list:
- local development:
http://localhost:3000/auth/callback - public sample:
https://demo.buildgrain.com/auth/callback
- local development:
- Keep the Google client id and secret in the Supabase dashboard. The app does not read separate Google credential env vars.
If NEXT_PUBLIC_SUPABASE_URL or NEXT_PUBLIC_SUPABASE_ANON_KEY is missing in development, the login screen shows a setup blocker that links back to this guide. The kit never fakes a Google login.
Environment variables
The full matrix of key names per mode (development / test / demo / production-kit) lives in the env matrix module and renders in the admin Developer surface. Key names only — values are never displayed or stored in content.
Database: migrate and seed
pnpm install --frozen-lockfile
DATABASE_URL=postgres://... pnpm db:setup # run committed Drizzle migrations
DATABASE_URL=postgres://... pnpm db:seed # seed sample-co, atlas-pilot, northstar-trialThe three seed accounts are protected from deletion. The current repository does not ship an automated restore or workspace-cleanup schedule; rerunning pnpm db:seed is an explicit operator action. Both commands require an explicit DATABASE_URL.
Verify test rollback and reset
Run the database safety probe only in test mode:
NODE_ENV=test APP_MODE=test pnpm db:test:resetThe command rejects every DATABASE_URL and persistent PGlite path. It verifies transaction rollback, then creates a second disposable in-memory PGlite database and verifies a clean migrate-and-seed reset. It never connects to or resets Postgres, so it cannot touch a production database.
Run the app
pnpm dev # http://localhost:3000Sign in with Google. Your first sign-in clones the seed template into a private sample workspace and assigns you the owner role.
System admin access
Add your email to ADMIN_ALLOWLIST_EMAILS (comma-separated, case-insensitive). On your next sign-in the kit upserts systemAdmin=true for that account; removing the email downgrades it on the following sign-in. There is no UI toggle for system admin — the allowlist is the only mechanism.
Verification commands
pnpm lint
pnpm typecheck
pnpm test
pnpm build
pnpm e2e
pnpm check:ui-copy
pnpm secret:scan
pnpm verifyRun pnpm verify before handing work off; it chains the lint, test, build, and copy-scan gates.