news 2026/4/17 21:09:54

uniapp 请求封装!Token 过期自动刷新+队列缓存!CV即用

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
uniapp 请求封装!Token 过期自动刷新+队列缓存!CV即用

作为一名 uniapp 搬砖人,谁没被 Token 过期搞得头大过?接口请求一半突然 401,用户体验直接拉胯,手动刷新?重复请求?回调地狱?不存在的!今天就给大家分享一套我实战打磨的请求封装方案,专治各种 Token 过期不服,代码可直接 CV 食用😜

🎯 先说说痛点(你是不是也踩过这些坑)

  1. Token 过期了,接口直接报错,用户一脸懵
  2. 多接口同时 401,重复刷新 Token,服务器直接懵
  3. 刷新 Token 后,原来的请求得重新发,逻辑绕到晕
  4. 配置合并乱七八糟,header 传参总是少东西

🚀 核心实现思路(划重点!)

直接上核心代码,关键地方我都标好了注释,cv稍微改点就行,code判断根据自己后端改,给什么吃什么,懂得都懂:

// 获取全局应用实例 const app = getApp(); // 默认配置 const DEFAULT_CONFIG = { baseURL: 'http://192.168.81.23:8080', timeout: 10000, header: { 'Content-Type': 'application/json' } } // 导入登录接口 import { login } from '@/api/index.js'; // 🔥 核心1:防重复刷新Token const loginExpired = async () => { // 防止重复刷新:如果正在刷新,返回等待的 Promise if (app.globalData.isRefreshing) { return new Promise((resolve, reject) => { app.globalData.refreshSubscribers.push({ resolve, reject }); }); } app.globalData.isRefreshing = true; try { const { code } = await uni.login(); const res = await login({ code }); // 校验登录接口业务码 if (res.code !== 200) { throw new Error(res.msg || '认证失败,请联系管理员'); } // 提取有效 Token const newToken = res.data?.token || res.token || res.msg; if (!newToken) { throw new Error('刷新后未获取到有效Token'); } uni.setStorageSync('token', newToken); // 执行所有挂起的请求并清空队列 app.globalData.refreshSubscribers.forEach(({ resolve }) => resolve(true)); app.globalData.refreshSubscribers = []; return true; } catch (err) { console.error('刷新 Token 失败:', err); // 刷新失败时,拒绝所有挂起的请求 app.globalData.refreshSubscribers.forEach(({ reject }) => reject(err)); app.globalData.refreshSubscribers = []; uni.showToast({ title: err.message.includes('联系管理员') ? '认证失败,请联系管理员' : '认证失败,请重新登录', icon: 'none', duration: 2000 }); throw err; } finally { app.globalData.isRefreshing = false; } }; // 🔥 核心2:带重试的请求封装 export const request = (options = {}, retryCount = 0) => { // 初始化全局数据 if (!app.globalData) app.globalData = {}; if (app.globalData.isRefreshing === undefined) app.globalData.isRefreshing = false; if (!app.globalData.refreshSubscribers) app.globalData.refreshSubscribers = []; // 读取Token const token = uni.getStorageSync('token') // 修复header合并逻辑(别再让header丢参数了!) const config = { ...DEFAULT_CONFIG, ...options, header: { ...DEFAULT_CONFIG.header, ...options.header, 'Authorization': `Bearer ${token || ''}`, 'platform': uni.getStorageSync('platform') || '', 'token': token || '' } } const { baseURL, url, method = 'GET', data, header, timeout } = config const fullUrl = baseURL + url; const MAX_RETRY = 1; // 最大重试次数,防止无限循环 // 封装请求逻辑 const requestHandler = () => { return new Promise((resolve, reject) => { uni.request({ url: fullUrl, method, data, header, timeout, success: (res) => { const { statusCode, data: responseData } = res; const code = responseData.code; // 正常返回 if (statusCode === 200 && code === 200) { resolve(responseData); } // Token 过期(401)且未超过最大重试次数 else if (code === 401 && retryCount < MAX_RETRY) { loginExpired() .then(() => { // 重试时次数+1 request(options, retryCount + 1).then(resolve).catch(reject); }) .catch(reject); } // 其他错误 else { const errMsg = code === 401 ? 'Token 失效且刷新失败,请重新登录' : (responseData.msg || '请求失败'); reject(new Error(errMsg)); } }, fail: (err) => { reject(new Error(`网络请求失败: ${err.errMsg}`)); } }); }); }; return requestHandler(); }; // 快捷方法(GET/POST直接用,懒人福音) request.get = (url, data, options) => request({...options, url, method: 'GET', data}); request.post = (url, data, options) => request({...options, url, method: 'POST', data}); export default request;
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/17 17:53:07

基于python的智慧农场管理系统

博主介绍&#xff1a;java高级开发&#xff0c;从事互联网行业六年&#xff0c;熟悉各种主流语言&#xff0c;精通java、python、php、爬虫、web开发&#xff0c;已经做了六年的毕业设计程序开发&#xff0c;开发过上千套毕业设计程序&#xff0c;没有什么华丽的语言&#xff0…

作者头像 李华
网站建设 2026/3/31 10:41:00

自动驾驶仿真软件推荐:康谋aiSim——ISO 26262 ASIL-D 认证的高保真选择

自动驾驶技术的快速发展离不开高效可靠的仿真测试工具。面对市面上众多仿真软件&#xff0c;用户常问 “自动驾驶仿真软件有哪些”“哪些自动驾驶仿真软件好用”“如何选择自动驾驶仿真软件” 等问题&#xff0c;选择一款功能全面、性价比高且符合自身研发需求的平台&#xff0…

作者头像 李华
网站建设 2026/4/12 19:26:17

设计模式——桥接模式

桥接模式 (Bridge Pattern) 什么是桥接模式&#xff1f; 桥接模式是一种结构型设计模式&#xff0c;它将抽象部分与实现部分分离&#xff0c;使它们可以独立地变化。 简单来说&#xff1a;桥接模式就是将抽象和实现解耦&#xff0c;让它们可以独立变化。 生活中的例子 想象…

作者头像 李华
网站建设 2026/4/17 10:43:29

Laravel框架学习路径全解析

以下是学习Laravel框架的系统路径&#xff1a; 一、基础准备 环境搭建 安装PHP 8.0&#xff08;推荐8.1&#xff09;配置Composer&#xff1a;composer global require laravel/installer创建项目&#xff1a;laravel new project_name 目录结构解析 app/ # 核心代码…

作者头像 李华
网站建设 2026/4/17 11:31:49

金三银四,我不允许你们不知道这些软件测试面试题

01、您所熟悉的测试用例设计方法都有哪些&#xff1f;请分别以具体的例子来说明这些方法在测试用例设计工作中的应用。 答&#xff1a;有黑盒和白盒两种测试种类&#xff0c;黑盒有等价类划分法&#xff0c;边界分析法&#xff0c;因果图法和错误猜测法。白盒有逻辑覆盖法&…

作者头像 李华
网站建设 2026/4/1 14:49:06

远程控制+智能调度,打造园区电力“无人值守”新模式

1、概述 电力监控系统实现对园区变电站、配电房内断路器、变压器、柴油发电机以及其它重要设备进行监视、测量、记录、报警等功能&#xff0c;并与保护设备和远方控制中心及其他设备通信&#xff0c;实时掌握园区变电站和配电房运行状况&#xff0c;快速排除故障&#xff0c;保…

作者头像 李华