Seamless JWT Token Refresh with Axios Interceptors in Frontend Applications
This article explains how to handle sudden login redirects caused by expired JWT access tokens in a web platform by using Axios response interceptors to automatically refresh tokens, queue failed requests, and retry them without disrupting the user experience.
In this article the author describes a common issue in web applications where a user is abruptly redirected to the login page because the JWT access token expires while the user is still interacting with the page.
The root cause is that the Axios response interceptor receives a 401 status code, indicating token expiration, and the current implementation does not automatically refresh the token or retry the failed requests.
To solve this, the author proposes handling token refresh entirely on the front‑end by intercepting 401 responses, storing the original request, invoking a refresh‑token API, updating the stored access token, and then replaying all queued requests.
The implementation consists of three main parts:
Axios response interceptor that distinguishes between normal API calls and the refresh‑token endpoint.
A utility that saves failed requests, triggers a single token refresh, and retries the saved requests once a new token is obtained.
Logic to handle the case where the refresh token itself expires, forcing a redirect to the login page.
Key code snippets are shown below.
axiosInstance.interceptors.response.use(
response => response,
error => {
let { data, config } = error.response;
return new Promise((resolve, reject) => {
if (data.statusCode === 401 && config.url !== '/api/token/refreshToken') {
refreshToken(() => {
resolve(axiosInstance(config));
});
} else if (data.statusCode === 401 && config.url === '/api/token/refreshToken') {
clearExpiredRequest();
window.location.href = `${HOME_PAGE}/login`;
} else {
reject(error.response);
}
});
}
); let expiredRequestArr = [];
const saveErrorRequest = (expiredRequest) => {
expiredRequestArr.push(expiredRequest);
};
let timer = null;
export const refreshToken = (expiredRequest) => {
saveErrorRequest(expiredRequest);
if (timer) clearTimeout(timer);
timer = setTimeout(() => {
updateTokenByRefreshToken();
}, 500);
};After integrating these pieces, the application can silently refresh the access token, retry pending requests, and only redirect the user when both the access token and refresh token are invalid, greatly improving user experience.
In summary, the solution demonstrates a practical front‑end pattern for seamless JWT renewal using Axios interceptors.
Rare Earth Juejin Tech Community
Juejin, a tech community that helps developers grow.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.