@urql/exchange-auth
An exchange for managing authentication in urql
@urql/exchange-auth is an exchange for the urql GraphQL client which helps handle auth headers and token refresh
Quick Start Guide
First install @urql/exchange-auth alongside urql:
yarn add @urql/exchange-auth
npm install --save @urql/exchange-auth
You'll then need to add the authExchange, that this package exposes to your urql Client
import { createClient, cacheExchange, fetchExchange } from 'urql';
import { makeOperation } from '@urql/core';
import { authExchange } from '@urql/exchange-auth';
const client = createClient({
url: 'http://localhost:1234/graphql',
exchanges: [
cacheExchange,
authExchange(async utils => {
let token = localStorage.getItem('token');
let refreshToken = localStorage.getItem('refreshToken');
return {
addAuthToOperation(operation) {
if (token) {
return utils.appendHeaders(operation, {
Authorization: `Bearer ${token}`,
});
}
return operation;
},
willAuthError(_operation) {
return !token;
},
didAuthError(error, _operation) {
return error.graphQLErrors.some(e => e.extensions?.code === 'FORBIDDEN');
},
async refreshAuth() {
const result = await mutate(refreshMutation, {
token: authState?.refreshToken,
});
if (result.data?.refreshLogin) {
token = result.data.refreshLogin.token;
refreshToken = result.data.refreshLogin.refreshToken;
localStorage.setItem('token', token);
localStorage.setItem('refreshToken', refreshToken);
} else {
localStorage.clear();
logout();
}
},
};
}),
fetchExchange,
],
});
Handling Errors via the errorExchange
Handling the logout logic in refreshAuth is the easiest way to get started,
but it means the errors will always get swallowed by the authExchange.
If you want to handle errors globally, this can be done using the mapExchange:
import { mapExchange } from 'urql';
mapExchange({
onError(error) {
const isAuthError = error.graphQLErrors.some(
e => e.extensions?.code === 'FORBIDDEN',
);
if (isAuthError) {
}
}
}),