实现Token无感革新

[复制链接]
发表于 昨天 20:27 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
在前端开辟中,Token 无感革新是一种常见的优化技能,用于在用户无感知的环境下革新逾期的身份验证 Token,从而制止用户因 Token 逾期而须要重新登录。以下是实现 Token 无感革新的思绪和详细实现方法。
实现思绪

Token 逾期机制:

通常,身份验证 Token 有一个有用期(如 2 小时)。
当 Token 逾期后,用户须要重新登录或革新 Token。
无感革新的核心:

在 Token 逾期前,通过革新 Token 接口获取新的 Token。
利用新的 Token 更换旧的 Token,并继承用户的哀求。
实现步调:

在哀求拦截器中查抄 Token 是否即将逾期。
如果 Token 即将逾期,发起革新 Token 的哀求。
在相应拦截器中处理处罚 Token 逾期的环境,重新发起失败的哀求。
详细实现

以下是一个基于 Axios 的 Token 无感革新实现示例:

  • 安装 Axios
    如果尚未安装 Axios,可以通过以下下令安装:
  1. npm install axios
复制代码

  • 封装 Axios 实例
    创建一个封装了 Token 无感革新逻辑的 Axios 实例。
  1. import axios from "axios";
  2. // 创建 Axios 实例
  3. const instance = axios.create({
  4.   baseURL: "https://api.example.com",
  5.   timeout: 10000,
  6. });
  7. // 存储 Token 和刷新 Token
  8. let token = localStorage.getItem("token") || "";
  9. let refreshToken = localStorage.getItem("refreshToken") || "";
  10. // 请求拦截器
  11. instance.interceptors.request.use(
  12.   (config) => {
  13.     // 如果 Token 存在,添加到请求头
  14.     if (token) {
  15.       config.headers.Authorization = `Bearer ${token}`;
  16.     }
  17.     return config;
  18.   },
  19.   (error) => {
  20.     return Promise.reject(error);
  21.   }
  22. );
  23. // 响应拦截器
  24. instance.interceptors.response.use(
  25.   (response) => {
  26.     return response;
  27.   },
  28.   async (error) => {
  29.     const originalRequest = error.config;
  30.     // 如果 Token 过期且未发起过刷新请求
  31.     if (error.response.status === 401 && !originalRequest._retry) {
  32.       originalRequest._retry = true; // 标记为已发起刷新请求
  33.       try {
  34.         // 发起刷新 Token 的请求
  35.         const response = await axios.post("/refresh-token", {
  36.           refreshToken,
  37.         });
  38.         // 更新 Token 和刷新 Token
  39.         const { token: newToken, refreshToken: newRefreshToken } = response.data;
  40.         token = newToken;
  41.         refreshToken = newRefreshToken;
  42.         localStorage.setItem("token", newToken);
  43.         localStorage.setItem("refreshToken", newRefreshToken);
  44.         // 更新请求头中的 Token
  45.         originalRequest.headers.Authorization = `Bearer ${newToken}`;
  46.         // 重新发起原始请求
  47.         return instance(originalRequest);
  48.       } catch (refreshError) {
  49.         // 刷新 Token 失败,跳转到登录页
  50.         localStorage.removeItem("token");
  51.         localStorage.removeItem("refreshToken");
  52.         window.location.href = "/login";
  53.         return Promise.reject(refreshError);
  54.       }
  55.     }
  56.     return Promise.reject(error);
  57.   }
  58. );
  59. export default instance;
复制代码

  • 利用封装的 Axios 实例
    在项目中利用封装好的 Axios 实例发起哀求。
  1. import axiosInstance from "./axiosInstance";
  2. const fetchData = async () => {
  3.   try {
  4.     const response = await axiosInstance.get("/data");
  5.     console.log(response.data);
  6.   } catch (error) {
  7.     console.error("请求失败", error);
  8.   }
  9. };
  10. fetchData();
复制代码
关键点分析

Token 存储

将 Token 和革新 Token 存储在 localStorage 或 sessionStorage 中。
每次哀求时从存储中读取 Token。
哀求拦截器:

在哀求拦截器中,将 Token 添加到哀求头。
相应拦截器:

在相应拦截器中,查抄相应状态码是否为 401(未授权)。
如果 Token 逾期,发起革新 Token 的哀求。
革新乐成后,更新 Token 并重新发起原始哀求。
革新 Token 接口:

后端须要提供一个革新 Token 的接口(如 /refresh-token),罗致 refreshToken 并返回新的 token 和 refreshToken。
错误处理处罚:

如果革新 Token 失败,打扫当地存储的 Token 并跳转到登录页。
进一步优化

Token 逾期时间查抄:

在哀求拦截器中查抄 Token 的剩余有用期。
如果 Token 即将逾期(如剩余 5 分钟),提前革新 Token。
  1. const isTokenExpired = (token) => {
  2.   const payload = JSON.parse(atob(token.split(".")[1]));
  3.   const exp = payload.exp * 1000; // 转换为毫秒
  4.   return Date.now() >= exp - 5 * 60 * 1000; // 提前 5 分钟刷新
  5. };
  6. instance.interceptors.request.use(
  7.   (config) => {
  8.     if (token && isTokenExpired(token)) {
  9.       // 发起刷新 Token 的请求
  10.       refreshToken()
  11.         .then((newToken) => {
  12.           token = newToken;
  13.           localStorage.setItem("token", newToken);
  14.           config.headers.Authorization = `Bearer ${newToken}`;
  15.         })
  16.         .catch(() => {
  17.           localStorage.removeItem("token");
  18.           window.location.href = "/login";
  19.         });
  20.     }
  21.     return config;
  22.   },
  23.   (error) => {
  24.     return Promise.reject(error);
  25.   }
  26. );
复制代码
并发哀求处理处罚:

如果多个哀求同时发现 Token 逾期,确保只发起一次革新 Token 的哀求。
利用一个标志变量(如 isRefreshing)来控制革新哀求的并发。
安全性:

利用 HTTPS 加密传输 Token。
设置公道的 Token 有用期和革新 Token 的有用期。
总结

通过 Axios 的哀求拦截器和相应拦截器,可以实现 Token 的无感革新,从而提拔用户体验。关键在于:
在 Token 逾期前主动革新。
处理处罚并发哀求和错误环境。
确保 Token 存储和传输的安全性。
这种方法实用于大多数前后端分离的项目,可以大概有用镌汰用户因 Token 逾期而须要重新登录的环境。

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
继续阅读请点击广告
回复

使用道具 举报

×
登录参与点评抽奖,加入IT实名职场社区
去登录
快速回复 返回顶部 返回列表