Prepare for the PgBouncer and IPv4 deprecations on 26th January 2024

Learn more

Supabase is now compatible with Next.js 14

2023-11-01

7 minute read

As part of Next.js Conf 2023, the team at Vercel released Next.js 14. The huge headline feature was...

Tweet from Lee Robinson about Next.js 14 containing no new APIs

That's right, the headline feature is no new features!

This may sound underwhelming at first, but is incredibly good news for the stability of Next.js. This release comes with a huge number of performance and stability improvements—such as Server Actions being marked as stable. This means we can finally start promoting this fantastically simple way of authenticating users—entirely server-side!

export default async function Page() {
const signIn = async () => {
'use server'
supabase.auth.signInWithOAuth({...})
}

return (
<form action={signIn}>
<button>Sign in with GitHub</button>
</form>
)
}

With Server Components, fetching data in Next.js became as simple as:

export default async function Page() {
const { data } = await supabase.from('...').select()
return ...
}

With Server Actions, you can now place mutation logic alongside the Server Components responsible for fetching data and rendering the page:

export default async function Page() {
const { data } = await supabase.from('...').select()

const createNote = async () => {
'use server'
await supabase.from('...').insert({...})
}

return ...
}

To hear more about our thoughts on Next.js Conf and the release of Next.js 14, check out our Twitter space. Yuri, Alaister, Terry and myself talk through how we use Next.js at Supabase and what we personally found most exciting about Next.js Conf and the release of Next.js 14.

Is Supabase compatible with Next.js 14?

Yes, it is! So much so that Guillermo Rauch shouted us out in the keynote!

Tweet showing Guillermo Rauch mentioning Supabase as one of the companies compatible with the Next.js App Router

Since the release of the App Router—launched as beta with Next.js 13—we have been working closely with the team at Vercel to ensure that Supabase is fully compatible with every part of Next.js.

So for the App Router, that's:

And for the Pages Router:

So why does it require work on the Supabase side to make it compatible with Next.js?

Configuring Supabase to use Cookies

By default, supabase-js uses localStorage to store the user's session. This works well for client-side apps, but will fail when you try to use supabase-js in a Server Component, as there is no concept of 'localStorage' on the server.

To do this, we need to configure supabase-js to use cookies instead of localStorage when running on the server. But this code is a little verbose to ask people to duplicate across every app they build with Supabase:

const supabase = createClient(supabaseUrl, supabaseAnonKey, {
auth: {
flowType: 'pkce',
autoRefreshToken: false,
detectSessionInUrl: false,
persistSession: true,
storage: {
getItem: async (key: string) => {
cookieStore.get(key)
},
setItem: async (key: string, value: string) => {
cookieStore.set(key, value)
},
removeItem: async (key: string) => {
cookieStore.remove(key)
},
},
},
})

That takes care of the server-side pieces of Next.js, but since we recommend securing your apps with Row Level Security (RLS) policies, you can safely access your user's session client-side too. Therefore, we need to tell the browser how access that cookie too:

const supabase = createClient(supabaseUrl, supabaseAnonKey, {
auth: {
flowType: 'pkce',
autoRefreshToken: true,
detectSessionInUrl: true,
persistSession: true,
storage: {
getItem: async (key: string) => {
return parse(document.cookie[key])
},
setItem: async (key: string, value: string) => {
document.cookie = serialize(key, value)
},
},
removeItem: async (key: string) => {
document.cookie = serialize(key, '', {
maxAge: 0,
})
},
},
})

That is a lot of very confusing code! So we decided to create a package called @supabase/ssr that does all of this for you. Then we took it one step further and created a Next.js and Supabase Starter Template, so you can just focus on building your awesome app! 🚀

Check out my Next.js Conf talk to see this starter template in action!

How do I get started?

One command:

npx create-next-app@latest -e with-supabase

The landing page will guide you through the process of creating a Supabase project and configuring your environment variables.

Build in a weekend on a Friday night! Scale to millions!

Meme zone

As you probably know, we love memes, so we are signing off with one about the least controversial commands coming out of Next.js Conf:

Tweet from Terry Sutton running the `with-supabase` command

More Supabase and Next.js resources

Share this article

Build in a weekend, scale to millions

We only collect analytics essential to ensuring smooth operation of our services. Learn more