NextAuth.js is a popular authentication library for Next.js that comes with built-in support for dozens of providers (including GitHub, Twitter, Google, and more).
In this guide we will continue where we left off in the guide How to use NextAuth.js as your JWT provider with Grafbase and instead use Apollo Client to send requests.
What's shown below also works with Clerk + Grafbase so you will want to check that if you're looking for an extended User Management solution.
You will want to follow the official documentation if you want to go beyond the basics. Let's begin by installing Apollo Client and its dependencies:
npm install @apollo/client graphql
You will want to create a custom ApolloProviderWrapper
component that uses setContext
to add your token
to the HTTP header authorization
.
Create the file components/apollo-provider-wrapper.tsx
and add the following:
import { useMemo } from 'react'
import {
ApolloClient,
ApolloProvider,
HttpLink,
InMemoryCache,
from,
} from '@apollo/client'
import { setContext } from '@apollo/client/link/context'
const httpLink = new HttpLink({
uri: process.env.NEXT_PUBLIC_GRAFBASE_API_URL,
})
export const ApolloProviderWrapper = ({ children }: PropsWithChildren) => {
const client = useMemo(() => {
const authMiddleware = setContext(async (operation, { headers }) => {
const { token } = await fetch('/api/auth/token').then(res => res.json())
return {
headers: {
...headers,
authorization: `Bearer ${token}`,
},
}
})
return new ApolloClient({
link: from([authMiddleware, httpLink]),
cache: new InMemoryCache(),
})
}, [getToken])
return <ApolloProvider client={client}>{children}</ApolloProvider>
}
You'll notice here we are using the environment variable NEXT_PUBLIC_GRAFBASE_API_URL
we created in the previous guide.
Now wrap your Next.js application with <ApolloProviderWrapper />
inside of pages/_app.tsx
:
import { SessionProvider } from 'next-auth/react'
import type { AppProps } from 'next/app'
import { ApolloProviderWrapper } from '../components/apollo-provider-wrapper'
export default function App({
Component,
pageProps: { session, ...pageProps },
}: AppProps) {
return (
<SessionProvider session={session}>
<ApolloProviderWrapper>
<Component {...pageProps} />
</ApolloProviderWrapper>
</SessionProvider>
)
}
Now all that's left to do is execute a GraphQL operation and the token provided by /api/auth/token
will automatically be added to the header of each request.
import { gql, useQuery } from '@apollo/client'
const QUERY = gql`
{
messageCollection(first: 100) {
edges {
node {
id
}
}
}
}
`
const MyPage = () => {
const { data, loading } = useQuery(QUERY)
if (loading) return <p>Loading!</p>
return <pre>{JSON.stringify(data, null, 2)}</pre>
}
export default MyPage
That's it! All requests will now be authenticated using the JWT generated by NextAuth.js after you successfully login.
Unauthenticated requests will not be permitted because of the auth rule we configured with Grafbase.