Skip To Main Content

How to handle Authentication

Authentication can be a cumbersome process when building headless WordPress sites. Thankfully, Faust.js takes care of all your authentication needs in your Next.js application.

How It Works

TL;DR: Authentication in Faust.js can happen in five main steps:

  1. User initiates request to authenticate data.
  2. Faust.js facilitates the request for an authorization code from the FaustWP plugin. This code is a short-lived token used to request a refresh and access token.
  3. Faust.js facilitates a refresh and access token request from the FaustWP plugin using the authorization code.
  4. Faust.js stores the refresh token in a secure, HTTP-only cookie. The token refresh requests a new access token when the current one expires
  5. Faust.js stores the access token in memory that you can use in subsequent authenticated requests.

Initial Setup

Before you get started with implementing an authentication strategy, you’ll need to setup the API Router. You can do this by creating a file, src/pages/api/faust/[[...route]].ts, with the following code:

// src/pages/api/faust/[[...route]].ts
import '../../../faust.config';
import { apiRouter } from '@faustwp/core';

export default apiRouter;
Code language: JavaScript (javascript)

Strategies

There are two authentication strategies available in Faust.js: redirect and local.

Redirect Based Authentication

Diagram of the redirect based authentication flow

Redirect-based authentication is the default strategy in Faust.js. This strategy involves the user being redirected to WordPress to authenticate. Once the user has shown, the user redirects back to the Next.js application with an authorization code you can then use to request a refresh and access token, thus completing the login process.

This strategy is excellent for use cases where your authenticated users are admins/editors/etc. and do not necessarily need a “white label” login/register experience. Typically, you would use the redirect strategy if your primary reason for authentication is previewing.

Since Redirect based authentication is the default authentication method, there is no configuration needed on your end to use it. It comes out of the box, and you’ll see it in action when using previews.

Local Based Authentication

Diagram of the local based authentication flow

Local Based Authentication is the second strategy available in Faust.js. This strategy involves the user initiating a login request from the Next.js application via the useLogin hook. Upon successful login, useLogin returns an authorization code used to request a refresh and access token, thus completing the login process.

This strategy is excellent for use cases where you want to support a more “white label” login/register experience. This strategy routes un-authenticated requests to your specified Next.js login page. In addition, users who wish to login/register will not have to interact with WordPress or the WordPress backend at all, giving you the flexibility to implement and fine-tune your user flow.

Ensuring Authentication

To determine if a user is logged in or not, you’ll want to leverage the useAuth hook. More specifically, the isReady and isAuthenticated properties exported from the hook. isReady is first used to make sure the hook is setup and can accurately make a determination if there is a user logged in or not. Once isReady is returning a booleanisAuthenticated will return a boolean as well:

import { useAuth } from '@faustwp/core';

export function AuthenticatedView() {
  return <>My authenticated content</>;
}

export default function Page(props) {
  const { isAuthenticated, isReady, loginUrl } = useAuth();

  if (!isReady) {
    return <>Loading...</>;
  }

  if (isAuthenticated === true) {
    return <AuthenticatedView />;
  }

  return (
    <>
      <p>Welcome!</p>
      <a href={loginUrl}>Login</a>
    </>
  );
}
Code language: JavaScript (javascript)

Making Authenticated Requests

The getApolloAuthClient() function returns an instantiated client with the proper access token attached to it. With this client, you can make authenticated requests either by calling client.query, or passing the client into Apollo’s useQuery hook:

function AuthenticatedView() {
  const client = getApolloAuthClient();

  const { data, loading } = useQuery(
    gql`
      {
        viewer {
          posts {
            nodes {
              id
              title
            }
          }
          name
        }
      }
    `,
    { client },
  );

  if (loading) {
    return <>Loading...</>;
  }

  return (
    <>
      <p>Welcome {data?.viewer?.name}!</p>

      <p>My posts</p>

      <ul>
        {data?.viewer?.posts?.nodes.map((post) => (
          <li key={post.id}>{post.title}</li>
        ))}
      </ul>
    </>
  );
}
Code language: JavaScript (javascript)

Learn more

To learn more about the authentication system and how to login users, logout users, etc. take a look at the following reference docs: