旅游网站建设课程设计报告网站建设时间安排表
2026/5/31 23:05:16 网站建设 项目流程
旅游网站建设课程设计报告,网站建设时间安排表,织梦网站上传,三端互通传奇手游找服网站作为一名 uniapp 搬砖人#xff0c;谁没被 Token 过期搞得头大过#xff1f;接口请求一半突然 401#xff0c;用户体验直接拉胯#xff0c;手动刷新#xff1f;重复请求#xff1f;回调地狱#xff1f;不存在的#xff01;今天就给大家分享一套我实战打磨的请求封装方案…作为一名 uniapp 搬砖人谁没被 Token 过期搞得头大过接口请求一半突然 401用户体验直接拉胯手动刷新重复请求回调地狱不存在的今天就给大家分享一套我实战打磨的请求封装方案专治各种 Token 过期不服代码可直接 CV 食用 先说说痛点你是不是也踩过这些坑Token 过期了接口直接报错用户一脸懵多接口同时 401重复刷新 Token服务器直接懵刷新 Token 后原来的请求得重新发逻辑绕到晕配置合并乱七八糟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;

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询