Skip to content

getServerData Support #189

@graysonhicks

Description

@graysonhicks

First, this plugin is great! Probably the most seamless auth experience I've had in a while.

I'm looking to add support for SSR auth with Gatsby. Since Gatsby 4 in October 2021, Gatsby has supported SSR rendering pages outside of SSG. The pattern is similar to Next.js, but has a few differences. I have found that using the withServerSideAuth function basically works with Gatsby, but I'm not sure it's working as well as it could.

First Gatsby relies on exporting an async function called getServerData. That makes following the HOC pattern difficult. When trying to copy and paste the example directly, the context will be undefined inside withServerSideAuth:

export const getServerData = withServerSideAuth(({ req, resolvedUrl }) => {
  const { sessionId } = req.auth

  if (!sessionId) {
    return { redirect: { destination: '/sign-in?redirect_url=' + resolvedUrl } }
  }

  return { props: {} }
})

The Gatsby pattern looks more like this:

export async function getServerData(context) {
  try {
    withServerSideAuth(context)

    return {
      status: 200, 
      props: {
        test: 'foo',
      },
      headers: {},
    }
  } catch (err) {
    console.log(err)
    return {
      status: 500,
      headers: {},
      props: {},
    }
  }
}

With this pattern, the auth actually seems to work (it redirects to the auth url from Clerk), so I assume the Node logic from the Clerk library is working. When logged in, it successfully renders the page. But note that there is no callback to get the sessionId or resolvedUrl.

My guess is that this plugin could have an ssr folder that tweaks this same logic slightly and allows for SSR auth with Gatsby as well. Something like this:

import { serverSideAuth } from 'gatsby-plugin-clerk'

// ... components

export async function getServerData(context) {
  try {
    const auth = await serverSideAuth(context)

  const { sessionId } = auth.req;

  if (!sessionId) {
    return { redirect: { destination: "/sign-in?redirect_url=" + resolvedUrl } };
  }


    return {
      status: 200, 
      props: {
        test: 'foo',
      },
      headers: {},
    }
  } catch (err) {
    console.log(err)
    return {
      status: 500,
      headers: {},
      props: {},
    }
  }
}

Or the callback could be passed in to serverSideAuth as well. Either way, I think the existing Next.js pattern is already very, very close to what would work here, with maybe additional tweaks to sanitizing/serializing props that might not be needed.

Happy to help with this, thanks!

Metadata

Metadata

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions