Authentication with Better Auth in Makerkit Next.js Drizzle
Understand Makerkit's authentication system and add OAuth sign-in. By the end, users can sign in with Google.
This is the Drizzle SaaS Starter Kit course. Start with the Architecture & Technologies module to get the fundamentals in place.
Now that've done some of the hard (and interesting) work in setting up the application, I want to take some of your time to dive more into the authentication system - and configure Google OAuth (the most popular OAuth provider) sign-in to TeamPulse.
Furthermore, you'll learn everything you need to know about authentication in Makerkit using Better Auth - including how to dive into the internals of the authentication system by linking to the documentation.
Technologies used:
- Better Auth - Authentication framework
- Drizzle ORM - Database tables for auth
What you'll accomplish:
- Understand the existing auth system
- Add Google OAuth sign-in
- Test the complete auth flow
Understanding the Auth System
Makerkit uses Better Auth, a TypeScript-first authentication framework.
Auth Pages
The authentication system uses the following pages to allow non-authenticated users to sign up, sign in, reset their password, and verify their 2FA code (if enabled):
| URL | Purpose |
|---|---|
/auth/sign-up | Create new account |
/auth/sign-in | Sign in to existing account |
/auth/password-reset | Request password reset |
/auth/verify | Two-factor authentication (when enabled) |
Try it: Visit each page in your browser to see the UI.
Key Configuration Files
The following files are responsible for the authentication system:
| File | Purpose |
|---|---|
packages/better-auth/src/auth.ts | Server-side auth configuration |
packages/better-auth/src/auth-client.ts | Client-side auth hooks |
apps/web/config/auth.config.ts | Feature flags (OAuth, MFA, etc.) |
apps/web/app/api/auth/[...all]/route.ts | API route handler |
The main Better Auth configuration file
The main Better Auth configuration file is packages/better-auth/src/auth.ts. This file exports the super-important auth instance that is used to configure the authentication system, the plugins, emails, and interact with the Better Auth API. You will be using the auth instance a fair lot in your application.
Client Side API
This is a server-side file, so it's only available on the server. If you want to interact with the authentication system from the client, you will need to use the auth-client.ts file - which is a client-side file and exports an instance meant to be used on the client. The API differs slightly from the server-side API, so please refer to the Better Auth documentation for the client-side API.
Authentication Flow
How It Works
- Sign-up flow:
- User submits email/password
- Account created in
userstable - Verification email sent (check Mailpit at http://localhost:8025)
- User clicks link → signed in
- Sign-in flow:
- User submits credentials
- Session created in
sessionstable - Cookie set for authentication
- Redirected to
/dashboard
- Session access:
- You can access the session in server-side code using the
getSessionfunction
- You can access the session in server-side code using the
// Server-side (in server actions, loaders, pages)import { getSession } from '@kit/better-auth/context';const session = await getSession();const userId = session?.user?.id;Checkpoint: Test the Existing Flow
Before adding OAuth, verify email/password auth works:
- Go to
/auth/sign-up - Create a new account
- Check Mailpit for new emails at http://localhost:8025
- Click the verification link
- Confirm you land on the dashboard
If you seeded test data using pnpm seed, you can also sign in with user1@makerkit.dev / testingpassword.
Adding Google OAuth
Let's add "Sign in with Google" to TeamPulse. To do so, you will need to create a new OAuth client in Google Cloud Console - which requires a Google Cloud account/project.
Too boring? If this is too boring (yes, it is), skip it, and use the email/password authentication instead - you can do so when you go to production.
Step 1: Create Google Cloud Credentials
- Go to Google Cloud Console
- Create a new project (or select existing)
- Navigate to APIs & Services → Credentials
- Click Create Credentials → OAuth client ID
- Select Web application
- Add authorized redirect URI:
http://localhost:3000/api/auth/callback/google- Copy the Client ID and Client Secret
Step 2: Configure Environment Variables
Add to apps/web/.env.local:
apps/web/.env.local
# Google OAuthGOOGLE_CLIENT_ID=your-client-id.apps.googleusercontent.comGOOGLE_CLIENT_SECRET=your-client-secret# Enable Google in the OAuth providers listNEXT_PUBLIC_AUTH_OAUTH_PROVIDERS=googleNB: when you go to production, please do not use the env file for storing secret environment variables.
Step 3: Test
Now visit /auth/sign-in. You should see a "Sign in with Google" button.
Test the flow:
- Click "Sign in with Google"
- Complete Google's sign-in
- You're redirected back and signed in
How OAuth Works in Makerkit
The Plugin System
Better Auth uses plugins for OAuth providers.
The configuration lives in packages/better-auth/src/plugins/social-providers.ts - and should be modified if you require other Social providers.
When you set GOOGLE_CLIENT_ID and GOOGLE_CLIENT_SECRET, the plugin automatically:
- Handles the OAuth redirect flow
- Creates or links user accounts
- Manages OAuth tokens securely
Adding Other Providers
Please refer to the documentation to add social providers.
What Else Is Possible
The auth system has many more features you can enable. Here's what's available:
Magic Links (Passwordless)
Let users sign in via email link - no password needed.
- Enable:
NEXT_PUBLIC_AUTH_MAGIC_LINK=true
Password Requirements
Enforce stronger passwords with special characters, numbers, uppercase.
- Configure: (all default to
false)
NEXT_PUBLIC_PASSWORD_REQUIRE_SPECIAL_CHARS=trueNEXT_PUBLIC_PASSWORD_REQUIRE_NUMBERS=trueNEXT_PUBLIC_PASSWORD_REQUIRE_UPPERCASE=trueCustom Email Templates
Customize verification, password reset, and invitation emails.
- Templates:
packages/email-templates/src/emails/(React Email components)
Captcha Protection
Add Cloudflare Turnstile to prevent bot sign-ups.
To add captcha protection, you will need to create a new account on Cloudflare and create a new Turnstile widget. Once you have created the widget, you will need to copy the site key and secret key and add them to the environment variables.
I recommend skipping until going to production. But it's important to know about it.
NEXT_PUBLIC_CAPTCHA_SITE_KEY=your-site-keyTURNSTILE_SECRET_KEY=your-secretMake sure to add the Site URL to the allowed domains in the Cloudflare Turnstile widget.
- Docs: Better Auth Captcha
Module 6 Complete!
You now have:
- [x] Understanding of Makerkit's auth architecture
- [x] Google OAuth sign-in working
- [x] Awareness of advanced auth features (MFA, magic links, captcha, etc.)
Next: In Module 7: Organizations & Teams, you'll apply role-based access control to TeamPulse features.
Troubleshooting
OAuth Redirect Errors
If Google sign-in fails with "redirect_uri_mismatch":
- Verify the redirect URI in Google Console exactly matches:
http://localhost:3000/api/auth/callback/google - Wait 5 minutes after changes (Google caches)
- Clear browser cookies and try again
Verification Emails Not Arriving
If emails don't appear in Mailpit:
- Confirm Mailpit is running:
docker ps | grep mailpit - Check SMTP settings in
.env.development - Look for errors in terminal running
pnpm dev
Session Not Persisting
If you're logged out after refresh:
- Check
BETTER_AUTH_SECRETis set and consistent - Verify cookies aren't blocked by browser settings
- Ensure
NEXT_PUBLIC_SITE_URLmatches your actual URL
Frequently Asked Questions
Authentication FAQ
Can I add GitHub, Discord, or other OAuth providers?
What's the difference between magic links and OTP?
How long do sessions last?
Can users sign up with OAuth only (no password)?
Learn More
This course is built on the Next.js Drizzle SaaS Kit foundation.