Use Rainbowkit authentication with Next-auth and Sign-in with Ethereum

In the previous post we have seen how to implement Sign in with Ethereum with next-auth. In this post we will see how to use Rainbowkit authentication to replace and simplify a bit our code.

First you can take the code source from the previous post and start from there.

Next we need to install @rainbow-me/rainbowkit-siwe-next-auth

yarn add @rainbow-me/rainbowkit-siwe-next-auth

And after that we need to add one provider in pages/_app.tsx:

function App({ Component, pageProps: { session, ...pageProps } }: AppProps) {
  return (
    <WagmiConfig client={wagmiClient}>
      <SessionProvider session={session}>
        <RainbowKitSiweNextAuthProvider>
          <RainbowKitProvider chains={chains}>
            <Component {...pageProps} />
          </RainbowKitProvider>
        </RainbowKitSiweNextAuthProvider>
      </SessionProvider>
    </WagmiConfig>
  )
}

Rainbowkit authentication will take care of the authentication and the session management. That means that after clicking on the connect button, it will automatically ask the user to sign the message and then call the server to get the session. And that's the same for logout. It will disconnect wallet and then automatically call the signOut function from next-auth.

So from now we can remove all the code about the login in the the login page pages/login.tsx.

const Login: NextPage = () => {
  const { push } = useRouter()
  const { data } = useSession()

  useEffect(() => {
    if (data) {
      push('/')
    }
  }, [data])

  return (
    <div className="flex min-h-screen flex-col items-center justify-center">
      <Head>
        <title>Create Next App</title>
        <link rel="icon" href="/favicon.ico" />
      </Head>

      <Layout>
        <h1 className="pb-12 text-4xl font-bold">Login page</h1>
        <ConnectButton />
      </Layout>

      <main className="flex w-full flex-1 flex-col items-center justify-center px-20 text-center"></main>
    </div>
  )
}

export default Login

export async function getServerSideProps(context: any) {
  const session = await getServerSession(context.req, context.res, authOptions)

  if (session) {
    return {
      redirect: {
        destination: '/',
        permanent: false,
      },
    }
  }

  return {
    props: { session },
  }
}

We just observe the session data to be able to redirect the user to the home page after a successful login. And for the logout we just need to use disconnectAsync from useDisconnect hook, the session will be remove automatically.

Conclusion

By using the Rainbowkit authentication we can simplify our code and we don't need to handle the signIn and signOut. That's great because we can quickly add authentication to our app and we don't need to worry about the authentication flow, but if you need a more custom UI to this flow, you should not used this. Also using Rainbowkit authentication will not disconnect you when you switch of wallets.

The code source of this post is available on Github.