6
votes

I am following this blog post on how to use the auth0-react library.

The post describes using the getAccessTokenSilently from the useAuth0 hook to get the access token which is used as the bearer token

  const callSecureApi = async () => {
    try {
      const token = await getAccessTokenSilently();

      const response = await fetch(`${apiUrl}/api/private-message`, {
        headers: {
          Authorization: `Bearer ${token}`,
        },
      });

      const responseData = await response.json();

      setMessage(responseData);
    } catch (error) {
      setMessage(error.message);
    }
  };

The issue I'm having is the token doesn't appear to be a JWT token - it looks like:

RJq7USOcszn7rpyI5iDjbYAKp9pK60Ap

Does anyone know why getAccessTokenSilently isn't returning a JWT token?

2
Are you sure the accesstoken should be a JWT? There is a difference between ID tokens (always jwt) and access tokens: auth0.com/docs/tokens - yadejo
Hi, I expect a bearer token to be a JWT token. You can see in the code in my original post is being used as the bearer token which I got from their blog post: auth0.com/blog/complete-guide-to-react-user-authentication. The token that's being returned (RJq7USOcszn7rpyI5iDjbYAKp9pK60Ap or similar) is not a bearer token. - Vinyl Warmth

2 Answers

7
votes

The same task took me a while as well, the docs are neither very clear nor up-to-date there I feel. Here is what you need to do:

  1. For Auth0, you need both a Single Page Application under "Applications", and an API under "APIs"
  2. Your React App gets wrapped with something like the below. Note the audience parameter from your API, this is the crucial part, without it, I also got the same small and useless access token you got!
<Auth0Provider
          domain={AUTH0_DOMAIN} // taken from the SPA application in Auth0
          clientId={AUTH0_CLIENT_ID} // taken from the SPA application in Auth0
          audience={AUTH0_AUDIENCE} // taken from your API in Auth0
          redirectUri={window.location.origin}
          useRefreshTokens={true}
          cacheLocation={"localstorage"}
      >
  1. Wherever you want to call your Backend (e.g. Spring Boot), you add the following to the component:
const {user, getAccessTokenSilently} = useAuth0();
...
// this will now be a JWT token, BUT ONLY if you specified the API audience in the Auth0Provider
// looks something like this:
/* eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6IlFqZEVNMEU1TnpWRE0wTkRSRVEzUkVFMFFVSkJOamMwUmtGRE1qZzNPVGxCTURNMk56UTJSZyJ9.eyJpc3MiOiJodHRwczovL3JhcGlkbWluZXIuYXV0aDAuY29tLyIsGnN1YiI6ImF1dGgwfDUzNDc5YzMwNmU5Yjc4YTU3MzAwMDVjNSIsImF1ZCI6WyJodHRwczovL2VuZ2luZWVyaW5nLXRvb2xzLnJhcGlkbWluZXIuY29tL2FwaSIsImh0dHBzOi8vcmFwaWRtaW5lci5hdXRoMC5jb20vdXNlcmluZm8iXSwiaWF0IjoxNTk2ODM2MDMyLCJleHAiOjE1OTY5MjI0MzIsImF6cCI6IllldWhoS29JV1lTV2FYUmExNU1sNTFMZUExYkp4bjVlIiwic2NvcGUiOiJvcGVuaWQgcHJvZmlsZSBlbWFpbCJ9.zI74HHd1pCzz-xBQEDDKby9z_Ue9_AIz-r05_my1wvLQ0U94u9WrwWmSxd9BQ-2XOHKa1KgnaaxsX2aiSHil7a4YjMnrYo9f0jgMmlxcllqZJgeb0AhLQNfYQEr6nAKP_8PgN0D7QFjIxiFTpDndTcD_2nG9DEsxbraT7dDy0pf1KTGmhQnNyBuyReAEUFhlxd1LAd63ED14nCPmEehl5rLNUwClTRFQ5q4ERLjM8cX0GLLy5F-I7UjpDOBnrL_qMqfuHyuChxs-k0fHhhEfV8xE2nEV00cXcAp3zvpJ_Ox9U0OBaVUbf1vi9v1Wl6jaMZpgqRZ1bZcfDXWjoEBVlQ */
const accessToken = await getAccessTokenSilently();
  1. Now you can pass the accessToken along via Authorization header:
headers: {
    "Authorization": `bearer ${accessToken}`
}
  1. Your BE can now validate the regular JWT token.
2
votes

From Auth0 docs:

id_token: contains an ID Token and is present if the request parameter response_type included the value id_token, or the scope request parameter the value openid

From various Auth0 employees in the Auth0 forums:

So, in the options object of getAccessTokenSilently, make sure:

  • the scope parameter includes openid
  • the audience parameter refers to your API