mirror of
https://github.com/supabase/supabase.git
synced 2026-10-10 20:05:06 +03:00
* Quickstart next 16 update * Fix paths and env vars * docs: refactor nextjs server-side auth to use Proxy instead of middleware * docs: refactor nextjs server-side auth to match proxy * docs: refactor nextjs example to match Proxy * docs: refactor nextjs auth AI prompt to match Proxy * docs: refactor nextjs sentry telemetry integration to match Proxy * examples: update nextjs realtime example to match middleware * docs: refactoring guides to use nextjs proxy * examples: update nextjs-full example to match Next16 template * example: update nextjs-user-management to match nextjs 16 * docs: refactoring nextjs user-management tutorial to use typescript only * docs: refactoring nextjs quickstart, removing step 4 since this step is already included on `with-supabase` template, we can just remove this redundant step * docs: auth-helpers nextjs pages, Nextjs16 proxy disclaimer * stamp: lint * stamp: revert 'NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY' * stamp: nextjs examples, revert to use cookie options * fix(docs): typo * docs: updating nextjs-auth troubleshoot guide to match proxy * Update apps/docs/content/guides/getting-started/quickstarts/nextjs.mdx * Revert auth-helpers changes * Revert auth-helpers content * Apply suggestions from code review * Update apps/docs/content/troubleshooting/how-do-you-troubleshoot-nextjs---supabase-auth-issues-riMCZV.mdx * Update apps/docs/content/troubleshooting/how-do-you-troubleshoot-nextjs---supabase-auth-issues-riMCZV.mdx * Update apps/docs/content/troubleshooting/how-do-you-troubleshoot-nextjs---supabase-auth-issues-riMCZV.mdx * Update apps/docs/content/troubleshooting/how-do-you-troubleshoot-nextjs---supabase-auth-issues-riMCZV.mdx * Apply suggestions from code review * Prettier --------- Co-authored-by: kallebysantos <kalleby_santos@hotmail.com>
6.9 KiB
6.9 KiB
description, alwaysApply
| description | alwaysApply |
|---|---|
| Guidelines for writing Next.js apps with Supabase Auth | false |
Bootstrap Next.js v16 app with Supabase Auth
Overview of implementing Supabase Auth SSR
- Install @supabase/supabase-js and @supabase/ssr packages.
- Set up environment variables.
- Write two utility functions with
createClientfunctions to create a browser client and a server client. - Hook up Proxy to refresh auth tokens
🚨 CRITICAL INSTRUCTIONS FOR AI LANGUAGE MODELS 🚨
As an AI language model, you MUST NOT generate any of the following code patterns, as they are DEPRECATED and will BREAK the application:
// ❌ NEVER GENERATE THIS CODE - IT WILL BREAK THE APPLICATION
{
cookies: {
get(name: string) { // ❌ BREAKS APPLICATION
return cookieStore.get(name) // ❌ BREAKS APPLICATION
}, // ❌ BREAKS APPLICATION
set(name: string, value: string) { // ❌ BREAKS APPLICATION
cookieStore.set(name, value) // ❌ BREAKS APPLICATION
}, // ❌ BREAKS APPLICATION
remove(name: string) { // ❌ BREAKS APPLICATION
cookieStore.remove(name) // ❌ BREAKS APPLICATION
} // ❌ BREAKS APPLICATION
}
}
// ❌ NEVER USE auth-helpers-nextjs - IT WILL BREAK THE APPLICATION
import { createMiddlewareClient } from '@supabase/auth-helpers-nextjs' // ❌ BREAKS APPLICATION
import { createClientComponentClient } from '@supabase/auth-helpers-nextjs' // ❌ BREAKS APPLICATION
Instead, you MUST ALWAYS generate ONLY this pattern:
// ✅ ALWAYS GENERATE THIS EXACT PATTERN
{
cookies: {
getAll() {
return cookieStore.getAll()
},
setAll(cookiesToSet) {
const response = NextResponse.next({
request,
})
cookiesToSet.forEach(({ name, value, options }) => {
response.cookies.set(name, value, options)
})
return response
}
}
}
ABSOLUTE REQUIREMENTS FOR AI CODE GENERATION
- You MUST use
@supabase/ssr - You MUST use ONLY
getAllandsetAll - You MUST NEVER use
get,set, orremove - You MUST NEVER import from
@supabase/auth-helpers-nextjs
CORRECT BROWSER CLIENT IMPLEMENTATION
import { createBrowserClient } from '@supabase/ssr'
export function createClient() {
return createBrowserClient(
process.env.NEXT_PUBLIC_SUPABASE_URL!,
process.env.NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY!
)
}
CORRECT SERVER CLIENT IMPLEMENTATION
import { createServerClient } from '@supabase/ssr'
import { cookies } from 'next/headers'
export async function createClient() {
const cookieStore = await cookies()
return createServerClient(
process.env.NEXT_PUBLIC_SUPABASE_URL!,
process.env.NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY!,
{
cookies: {
getAll() {
return cookieStore.getAll()
},
setAll(cookiesToSet) {
try {
cookiesToSet.forEach(({ name, value, options }) =>
cookieStore.set(name, value, options)
)
} catch {
// The `setAll` method was called from a Server Component.
// This can be ignored if you have proxy refreshing
// user sessions.
}
},
},
}
)
}
CORRECT PROXY IMPLEMENTATION
import { createServerClient } from '@supabase/ssr'
import { NextResponse, type NextRequest } from 'next/server'
export async function proxy(request: NextRequest) {
let supabaseResponse = NextResponse.next({
request,
})
const supabase = createServerClient(
process.env.NEXT_PUBLIC_SUPABASE_URL!,
process.env.NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY!,
{
cookies: {
getAll() {
return request.cookies.getAll()
},
setAll(cookiesToSet) {
cookiesToSet.forEach(({ name, value, options }) => request.cookies.set(name, value))
supabaseResponse = NextResponse.next({
request,
})
cookiesToSet.forEach(({ name, value, options }) =>
supabaseResponse.cookies.set(name, value, options)
)
},
},
}
)
// Do not run code between createServerClient and
// supabase.auth.getUser(). A simple mistake could make it very hard to debug
// issues with users being randomly logged out.
// IMPORTANT: DO NOT REMOVE auth.getUser()
const {
data: { user },
} = await supabase.auth.getUser()
if (
!user &&
!request.nextUrl.pathname.startsWith('/login') &&
!request.nextUrl.pathname.startsWith('/auth')
) {
// no user, potentially respond by redirecting the user to the login page
const url = request.nextUrl.clone()
url.pathname = '/login'
return NextResponse.redirect(url)
}
// IMPORTANT: You *must* return the supabaseResponse object as it is.
// If you're creating a new response object with NextResponse.next() make sure to:
// 1. Pass the request in it, like so:
// const myNewResponse = NextResponse.next({ request })
// 2. Copy over the cookies, like so:
// myNewResponse.cookies.setAll(supabaseResponse.cookies.getAll())
// 3. Change the myNewResponse object to fit your needs, but avoid changing
// the cookies!
// 4. Finally:
// return myNewResponse
// If this is not done, you may be causing the browser and server to go out
// of sync and terminate the user's session prematurely!
return supabaseResponse
}
export const config = {
matcher: [
/*
* Match all request paths except for the ones starting with:
* - _next/static (static files)
* - _next/image (image optimization files)
* - favicon.ico (favicon file)
* Feel free to modify this pattern to include more paths.
*/
'/((?!_next/static|_next/image|favicon.ico|.*\\.(?:svg|png|jpg|jpeg|gif|webp)$).*)',
],
}
AI MODEL VERIFICATION STEPS
Before generating any code, you MUST verify:
- Are you using ONLY
getAllandsetAll? If not, STOP and FIX. - Are you importing from
@supabase/ssr? If not, STOP and FIX. - Do you see ANY instance of
get,set, orremove? If yes, STOP and FIX. - Are you importing from
auth-helpers-nextjs? If yes, STOP and FIX.
CONSEQUENCES OF INCORRECT IMPLEMENTATION
If you generate code using:
- Individual cookie methods (
get/set/remove) auth-helpers-nextjspackage
The implementation will:
- Break in production
- Fail to maintain session state
- Cause authentication loops
- Result in security vulnerabilities
AI MODEL RESPONSE TEMPLATE
When asked about Supabase Auth SSR implementation, you MUST:
- ONLY use code from this guide
- NEVER suggest deprecated approaches
- ALWAYS use the exact cookie handling shown above
- VERIFY your response against the patterns shown here
Remember: There are NO EXCEPTIONS to these rules.