React.useEffect在axios拦截后未触发状态更新的问题咨询
解决Axios拦截器刷新Token后重发请求不更新React状态的问题
问题根源
你的响应拦截器在处理401错误时,内部发起的刷新Token请求和重发请求的Promise没有被正确返回给原请求的Promise链,导致useEffect里的.then()无法获取到重发请求的响应数据,也就不会执行setTest更新状态。
修复代码
修改响应拦截器,确保整个错误处理逻辑返回完整的Promise链:
axios_server.interceptors.response.use(null, (error) => { // 处理401未授权错误 if (error.config && error.response && error.response.status === 401) { // 返回刷新Token的Promise,让原请求的Promise链能接住重发后的响应 return axios_auth.post('http://localhost:4000/refresh', {}, {withCredentials: true}) .then((res) => { // 更新AccessToken到Cookie const token = res.data.accessToken; cookies.set('AccessToken', token, { sameSite: 'strict', path: '/', expires: new Date(Date.now() + 3 * 1000) }); // 重发原请求 return axios_server.request(error.config); }) .catch((error2) => { // 刷新Token失败,直接抛出错误,可在这里跳转到登录页 console.error('刷新Token失败:', error2); // 示例:跳转到登录页 // window.location.href = '/login'; return Promise.reject(error2); }); } // 非401错误,直接抛出 return Promise.reject(error); });
更合理的处理方式
- 避免重复刷新Token:当多个请求同时触发401时,不要重复调用刷新Token接口,用全局变量标记刷新状态,其他请求等待刷新完成后统一重发:
let isRefreshing = false; let requestQueue = []; axios_server.interceptors.response.use(null, (error) => { if (error.config && error.response && error.response.status === 401) { if (!isRefreshing) { isRefreshing = true; return axios_auth.post('http://localhost:4000/refresh', {}, {withCredentials: true}) .then((res) => { const token = res.data.accessToken; cookies.set('AccessToken', token, { sameSite: 'strict', path: '/', expires: new Date(Date.now() + 3 * 1000) }); // 重发队列里的所有请求 requestQueue.forEach(cb => cb(token)); requestQueue = []; return axios_server.request(error.config); }) .catch((error2) => { requestQueue = []; window.location.href = '/login'; return Promise.reject(error2); }) .finally(() => { isRefreshing = false; }); } else { // 正在刷新,把当前请求加入队列,等待刷新完成后重发 return new Promise((resolve) => { requestQueue.push((token) => { resolve(axios_server.request(error.config)); }); }); } } return Promise.reject(error); });
- 完善错误处理:在React组件中添加错误捕获逻辑,处理请求失败的情况,给用户友好提示;
- 提前刷新Token:在请求前主动检查AccessToken的有效期,提前发起刷新请求,避免触发401错误。
内容的提问来源于stack exchange,提问作者John Smith
相关产品推荐
相关产品推荐

