当前位置: 首页 > article >正文

《Uniapp-Vue 3-TS 实战开发》构建HTTP请求拦截器

引言

        在 UniApp 结合 TypeScript 和 Vue3 的项目开发中,请求拦截器起着至关重要的作用。它能够在请求发送前和响应接收后对数据进行统一处理,极大地提高了代码的可维护性和功能性。本文将详细解析上述代码中请求拦截器的实现及其在 UniApp-Ts-Vue3 项目中的应用,让您更直观地理解其工作流程。

一、请求拦截器的作用

        请求拦截器主要用于在请求发送到服务器之前对请求进行预处理,以及在接收到服务器响应后对响应进行后处理。在我们的代码中,它实现了以下几个关键功能:

(一)基础 URL 补全

if (!options.url.startsWith('https://')) {options.url = baseURLhttp + options.url;
}

      当请求的 URL 不是以 https:// 开头时,会自动将基础 URL中的 baseURLhttp(项目中发起https的请求头) (比如:https://11.12.55.666666:8080)拼接在前面。这确保了所有请求都使用正确的基础路径,尤其在开发和上线不同环境切换时,能方便地统一管理请求地址。例如,若我们有一个相对路径的请求 '/api/user',经过拦截器处理后会变为:    

 'https://11.12.55.666666:8080/api/user'。

(二)设置请求超时

options.timeout = TIMEOUT

        设置了请求的超时时间为 TIMEOUT(30000 毫秒,即 30 秒)。这是一个很重要的设置,防止请求因为网络问题或服务器故障而长时间等待,提升用户体验。当请求超过 30 秒还未得到响应时,会触发 fail 回调,提示用户网络连接失败。

(三)添加小程序端请求头标识

options.header = {'source - client':'miniapp',...options.header, // 允许覆盖默认 header
}

        在请求头中添加了 source - client 字段,值为 miniapp,用于标识该请求来自小程序端。同时,通过 ...options.header 保留了原有的请求头信息,这样既添加了自定义标识,又不会影响其他可能需要的请求头设置。例如,在服务器端可以根据这个标识对来自小程序的请求进行特定的处理。

(四)添加 token 请求头标识

const memberStore = useMemberStore()
const token = memberStore.profile?.token
if (token) {options.header.token = token
}

        从状态管理(这里使用的是 Pinia 库的 useMemberStore)中获取用户的 token,并将其添加到请求头的 token 字段中。这样,服务器可以通过验证 token 来确认用户身份,实现对受保护资源的访问控制。比如,用户在登录成功后,token 被存储在状态管理中,后续的请求通过拦截器自动带上 token,无需在每个请求中手动添加。

二、拦截器的实现与注册

(一)拦截器定义

const httpInterceptor = {// 拦截前触发invoke(options: UniApp.RequestOptions) {// 一系列处理逻辑},
}

        这里定义了一个名为 httpInterceptor 的拦截器对象,它包含一个 invoke 方法。invoke 方法在每次请求被拦截时触发,接收一个 options 参数,类型为 UniApp.RequestOptions,这个参数包含了本次请求的所有配置信息,我们可以在这个方法中对这些配置进行修改。

(二)拦截器注册

uni.addInterceptor('request', httpInterceptor)
uni.addInterceptor('uploadFile', httpInterceptor)

        通过 uni.addInterceptor 方法将 httpInterceptor 注册到 request 和 uploadFile 这两种请求类型上。这意味着无论是普通的 request 请求(如获取数据、提交表单等),还是 uploadFile 文件上传请求,都会经过 httpInterceptor 的处理。

三、封装请求函数

(一)函数定义与返回值

type Data<T> = {categorys(categorys: any): unknowncode: stringmsg: stringresult: T
}
// 2.2 添加类型,支持泛型
export const http = <T>(options: UniApp.RequestOptions) => {//1.返回Promise对象return new Promise<Data<T>>((resolve, reject) => {// 请求处理逻辑})
}

        定义了一个名为 http 的函数,它是对 uni.request 的封装。通过泛型 <T> 支持不同类型的响应数据。函数返回一个 Promise 对象,这样可以使用 async/await 语法来处理异步请求,使代码更简洁易读。Data<T> 类型定义了响应数据的结构,包含 code(状态码)、msg(错误信息)、result(实际数据,其类型由泛型 T 决定)以及一个 categorys 函数(这里可能是特定业务需求的函数定义,具体功能需根据业务进一步分析)。

(二)请求成功处理

success(res) {if (res.statusCode >= 200 && res.statusCode < 300) {// 获取数据成功, 调用resolveresolve(res.data as Data<T>)} else if (res.statusCode === 401) {// 401错误  -> 清理用户信息,跳转到登录页等,具体看你的需求逻辑handleUnauthorized()reject(res)} else {// 其他HTTP错误 -> 根据后端错误信息轻提示const errMsg = getHttpErrorMsg(res.statusCode)uni.showToast({ icon: 'none', title: errMsg })reject(res)}
}

        在 uni.request 的 success 回调中,首先判断响应状态码 statusCode。如果状态码在 200 到 299 之间,表示请求成功,将响应数据转换为 Data<T> 类型后调用 resolve,将数据传递出去。若状态码为 401,表示用户未授权,调用 handleUnauthorized 函数清理用户信息并跳转到登录页面,同时调用 reject 拒绝 Promise,传递错误响应。对于其他状态码,通过 getHttpErrorMsg 函数获取对应的错误信息,并使用 uni.showToast 进行轻提示,然后拒绝 Promise。

(三)请求失败处理

fail(err) {uni.showToast({icon: 'none',title: '网络连接失败',})reject(err)
}

        当请求失败(如网络故障、超时等),在 fail 回调中使用 uni.showToast 提示用户网络连接失败,并调用 reject 拒绝 Promise,传递错误信息。

四、辅助函数

(一)处理 401 未授权

const handleUnauthorized = () => {const memberStore = useMemberStore()memberStore.clearProfile()uni.navigateTo({ url: '/pages/login/login' })uni.showToast({ icon: 'none', title: '登录已过期' })
}

handleUnauthorized 函数在用户遇到 401 未授权错误时被调用。它从状态管理中获取 memberStore,调用 clearProfile 方法清理用户信息,然后使用 uni.navigateTo 跳转到登录页面,并通过 uni.showToast 提示用户登录已过期。

(二)获取 HTTP 错误信息

const getHttpErrorMsg = (code: number): string => {const messages: Record<number, string> = {400: '请求参数错误',403: '禁止访问',404: '资源不存在',500: '服务器错误',502: '网关错误'}return messages[code] || `请求失败(${code})`
}

getHttpErrorMsg 函数根据传入的 HTTP 状态码 code 返回对应的错误信息。它通过一个 Record 类型的 messages 对象存储常见状态码对应的错误描述。如果状态码在 messages 中存在,则返回对应的描述;否则返回通用的错误提示 请求失败(${code})

五、工作流程示意图

        从发起,经过拦截器处理,到服务器响应,再经过拦截器处理返回给调用者的整个流程,包括基础 URL 补全、请求头添加、超时设置等在流程中的位置]

六、总结

        通过上述代码和详细解析,我们深入了解了在 UniApp-Ts-Vue3 项目中如何构建和使用请求拦截器。请求拦截器不仅能简化请求处理逻辑,还能统一管理请求相关的配置和错误处理,提升项目的开发效率和稳定性。在实际项目中,我们可以根据具体业务需求进一步扩展和优化拦截器的功能,使其更好地服务于整个应用程序。

最后,附上完整代码:

​
/*** 添加拦截器:*   拦截 request 请求*   拦截 uploadFile 文件上传** TODO:*   1. 非 http 开头需拼接地址*   2. 请求超时*   3. 添加小程序端请求头标识*   4. 添加 token 请求头标识
*/
import { useMemberStore } from '@/stores'const baseURLhttp = 'https://11.12.55.666666:8080'; //后期注意要申请SSL证书,上线小程序的请求必须是https类型的
const TIMEOUT = 30000; // 请求超时 默认 30秒 超时//request请求拦截
const httpInterceptor = {// 拦截前触发invoke(options: UniApp.RequestOptions) {//1. 补全基础路径(非 https 开头时)if (!options.url.startsWith('https://')) {options.url = baseURLhttp + options.url;}//设置超时时间options.timeout = TIMEOUT//3.添加小程序请求头options.header = {'source-client': 'miniapp',...options.header, // 允许覆盖默认 header}//4.自动添加 token 信息到请求头const memberStore = useMemberStore()const token = memberStore.profile?.tokenif (token) {options.header.token = token}//输出options// console.log(options)},
}// 拦截 request 请求
uni.addInterceptor('request', httpInterceptor)
// 拦截 uploadFile 文件上传
uni.addInterceptor('uploadFile', httpInterceptor)/*** 封装请求函数* @param  UniApp.RequestOptions* @returns Promise*  1. 返回 Promise 对象*  2. 获取数据成功*    2.1 提取核心数据 res.data*    2.2 添加类型,支持泛型*  3. 获取数据失败*    3.1 401错误  -> 清理用户信息,跳转到登录页*    3.2 其他错误 -> 根据后端错误信息轻提示*    3.3 网络错误 -> 提示用户换网络
*/type Data<T> = {categorys(categorys: any): unknowncode: stringmsg: stringresult: T
}
// 2.2 添加类型,支持泛型
export const http = <T>(options: UniApp.RequestOptions) => {//1.返回Promise对象return new Promise<Data<T>>((resolve, reject) => {uni.request({...options,//2.请求成功success(res) {// if (res.statusCode == 0 || (res.statusCode >= 200 && res.statusCode < 300)) {if (res.statusCode >= 200 && res.statusCode < 300) {// 获取数据成功, 调用resolveresolve(res.data as Data<T>)} else if (res.statusCode === 401) {// 401错误  -> 清理用户信息,跳转到登录页handleUnauthorized()reject(res)} else {// 其他HTTP错误 -> 根据后端错误信息轻提示const errMsg = getHttpErrorMsg(res.statusCode)uni.showToast({ icon: 'none', title: errMsg })reject(res)}},// 响应失败fail(err) {uni.showToast({icon: 'none',title: '网络连接失败',})reject(err)},})})
}/*** 处理 401 未授权*/
const handleUnauthorized = () => {const memberStore = useMemberStore()memberStore.clearProfile()uni.navigateTo({ url: '/pages/login/login' })uni.showToast({ icon: 'none', title: '登录已过期' })
}/*** 获取 HTTP 错误信息*/
const getHttpErrorMsg = (code: number): string => {const messages: Record<number, string> = {400: '请求参数错误',403: '禁止访问',404: '资源不存在',500: '服务器错误',502: '网关错误'}return messages[code] || `请求失败(${code})`
}​

相关文章:

《Uniapp-Vue 3-TS 实战开发》构建HTTP请求拦截器

引言 在 UniApp 结合 TypeScript 和 Vue3 的项目开发中&#xff0c;请求拦截器起着至关重要的作用。它能够在请求发送前和响应接收后对数据进行统一处理&#xff0c;极大地提高了代码的可维护性和功能性。本文将详细解析上述代码中请求拦截器的实现及其在 UniApp-Ts-Vue3 项目中…...

C#基础类型系统-接口

接口 - 定义多种类型的行为 接口包含非抽象 class 或 struct 必须实现的一组相关功能的定义。接口可以定义 static 方法&#xff0c;此类方法必须具有实现。接口可为成员定义默认实现。接口不能声明实例数据&#xff0c;如字段、自动实现的属性或类似属性的事件。C#不支持类的…...

StringTemplate修仙指南:字符串处理的“言出法随“大法

各位在字符串处理苦海中挣扎的道友们&#xff01;今天要解锁的是StringTemplate这门"言出法随"的绝学——用模板语法让字符串替换变得优雅如诗&#xff01;无论是代码生成、邮件模板还是动态SQL&#xff0c;都能一键搞定&#xff01;准备好告别String.format()的混沌…...

从PDF中提取表格:以GB/T2260—2007为例

文章目录 先说结论前因后果思路1、PDF2CSV2、PDF2MD → MD2CSV3、针对不同表格的两种思路1&#xff09; 竖形三线表2&#xff09;五元素为一组 还没结束批量处理1、分割markdown文档2、跳过另一种格式的文档 总结一下 先说结论 结论就是&#xff0c;博主用了一天的时间去研究如…...

初识MySQL · 复合查询(内外连接)

目录 前言&#xff1a; 基本查询回顾 笛卡尔积和子查询 笛卡尔积 内外连接 子查询 单行子查询 多行子查询 多列子查询 from中使用子查询 合并查询 前言&#xff1a; 在前文我们学习了MySQL的基本查询&#xff0c;就是简单的套用了select语句&#xff0c;最多不过是…...

电视剧角色扮演AI Agent中的大模型操作流程

电视剧角色扮演AI Agent中的大模型操作流程 在您描述的 “电视剧角色扮演 + 挑战任务” 的AI Agent场景中,大模型(如GPT-4、Claude等)需要完成多个关键操作,以下是详细的技术流程分解: 1. 用户输入处理阶段 操作:文本向量化(Embedding) 技术实现: 使用 文本嵌入模型…...

Android学习总结之数据结构篇

Java 的集合体系 Java 的集合框架主要分为两大接口体系&#xff1a;Collection 和 Map。以下是对这两大体系下常见集合类的介绍&#xff1a; Collection 体系 Collection 是单列集合的根接口&#xff0c;它有三个主要的子接口&#xff1a;List、Set 和 Queue。 List 接口&a…...

OpenCV--图像平滑处理

在数字图像处理领域&#xff0c;图像平滑处理是一项极为重要的技术&#xff0c;广泛应用于计算机视觉、医学影像分析、安防监控等多个领域。在 OpenCV 这一强大的计算机视觉库的助力下&#xff0c;我们能便捷地实现多种图像平滑算法。本文将深入探讨图像平滑的原理&#xff0c;…...

8. git branch

基本概述 git branch 的作用是&#xff1a;查看、创建、删除、重命名和跟踪分支等。 查看分支 1.查看本地分支 git branch当前分支前会标记 * 2.查看远程分支 git branch -r3.查看所有分支 git branch -a4.查看分支信息 git branch -v会显示分支的最新提交信息 5.查看…...

辛格迪客户案例 | 北京舒曼德医药实施电子合约系统(eSign)

01 北京舒曼德医药科技开发有限公司&#xff1a;医药科技的数字化先锋 北京舒曼德医药科技开发有限公司&#xff08;以下简称“舒曼德医药”&#xff09;作为国内医药科技领域的领军企业&#xff0c;致力于创新药物的研发、临床试验和市场推广。公司以“科技兴药、质量为先、服…...

Python面向对象-开闭原则(OCP)

1. 什么是开闭原则&#xff1f; 开闭原则(Open-Closed Principle, OCP) 是面向对象设计的五大SOLID原则之一&#xff0c;由Bertrand Meyer提出。其核心定义是&#xff1a; “软件实体(类、模块、函数等)应该对扩展开放&#xff0c;对修改关闭。” 对扩展开放&#xff1a;当需求…...

网络安全-等级保护(等保) 1-0 等级保护制度公安部前期发文总结

################################################################################ 等级保护从1994年开始已经有相关文件下发,进行建设,后续今年多年制度完善,现在已进入等保2.0时代,相关政策已运行多年。 前期等保相关发文,目前还在使用的包括:《中华人民共和国计算…...

Class 文件和类加载机制

一、Class 文件 与 类加载机制 概述 什么是 Class 文件&#xff1f; Java 源码&#xff08;.java&#xff09;经过 javac 编译器 编译生成的字节码文件&#xff08;.class&#xff09;&#xff1b;由 JVM 识别执行&#xff0c;包含类的完整结构信息&#xff08;如字段、方法、…...

Vue3+Vite+TypeScript+Element Plus开发-07.Mockjs引用与Axios封装

系列文档目录 Vue3ViteTypeScript安装 Element Plus安装与配置 主页设计与router配置 静态菜单设计 Pinia引入 Header响应式菜单缩展 Mockjs引用与Axios封装 登录设计 登录成功跳转主页 多用户动态加载菜单 Pinia持久化 动态路由-配置 文章目录 目录 系列文档目…...

安全理念和安全产品发展史

从安全理念的发展历史来看,技术与产品的演进始终围绕 “威胁对抗” 与 “业务适配” 两大核心展开。以下从七个关键阶段解析安全技术与产品的发展脉络,并结合最新实践与未来趋势提供深度洞察: 一、密码学奠基阶段(1970s 前) 安全理念:以 “信息保密” 为核心,防御手段…...

【Redis】背景知识

一、Redis的特性 Redis是一种基于键值对&#xff08;key-value&#xff09;的NoSQL数据库&#xff0c;与很多键值对数据库不同的是&#xff0c;Redis中的值可以是由string&#xff08;字符串&#xff09;&#xff0c;hash&#xff08;哈希&#xff09;&#xff0c;list&#xf…...

Spring MVC 返回 JSON 视图的方式及对比(6种)

Spring MVC 返回 JSON 视图的方式及对比&#xff08;新增 MappingJackson2JsonView&#xff09; 1. 方式一&#xff1a;ResponseBody 注解 作用&#xff1a;直接返回对象&#xff0c;由消息转换器&#xff08;如 Jackson&#xff09;序列化为 JSON。 适用场景&#xff1a;简单…...

【Kafka基础】消费者命令行完全指南:从基础到高级消费

Kafka消费者是消息系统的关键组成部分&#xff0c;掌握/export/home/kafka_zk/kafka_2.13-2.7.1/bin/kafka-console-consumer.sh工具的使用对于调试、测试和监控都至关重要。本文将全面介绍该工具的各种用法&#xff0c;帮助您高效地从Kafka消费消息。 1 基础消费模式 1.1 从最…...

在 Vue 中监听常用按键事件(回车,ESC 键,空格等)。

一、Vue 原生按键修饰符&#xff08;推荐&#xff09; html <!-- 常用按键监听 --> <input keyup.enter"submit" <!-- 回车键 -->keydown.esc"cancel" <!-- ESC 键 -->keyup.space"togglePlay" <!-- 空格键…...

航电系统的任务载荷集成技术要点概述!

一、任务载荷集成技术难点 1. 接口标准化与兼容性 异构设备协议冲突&#xff1a;不同厂商的载荷设备&#xff08;如光学相机、雷达、电子战模块&#xff09;采用不同的通信协议&#xff08;如1553B、RS422、以太网&#xff09;&#xff0c;需设计统一的总线接口标准以支持即…...

OceanBase V4.3.5 上线全文索引功能,让数据检索更高效

近日&#xff0c;OceanBase 4.3.5 BP1 版本正式推出了企业级全文索引功能。该版本在中文分词、查询效率及混合检索能力上进行了全面提升。经过自然语言模式和布尔模式在不同场景下的对比测试&#xff0c;OceanBase 的全文索引性能明显优于 MySQL。 点击下载 OceanBase 社区版…...

Qt中的信号与槽及其自定义

信号源&#xff1a;哪个控件发的信号 信号的类型&#xff1a;用户进行不同的操作就会触发不同的信号 如点击按钮&#xff0c;在输入框移动光标&#xff0c;勾选一个复选框&#xff0c;选 择一个下拉框 信号的处理方式&#xff1a;槽(slot)----也就是函数&#xff0c;Qt中用con…...

【PFPGA学习】状态机思想编程HDLbitsFPGA练习

目录 一、用状态机实现LED流水灯 1.1状态机思想 1.2状态机思想LED流水灯 1.3 modesim仿真 1.4 FPGA烧录实现 二、CPLD和FPGA芯片 1. 核心结构与技术原理 2. 性能与容量 3. 适用场景 &#xff14;. 选型建议 三、HDLbitsFPGA练习记录&#xff08;combinational logic…...

Android 中集成 Unity 工程的步骤

在 Adroid 项目中集成 Unity 工程,主要步骤如下: 一、前提条件 1、已有一个 Android 工程项目; 2、Unity 工程已导出为 Android 工程,目录大概如下: 二、集成步骤 1、在 Android 工程中导入 Unity 工程的 unityLibrary 模块。 在 Android Studio 中,点击菜单栏 Fil…...

Python从入门到精通全套视频教程免费

概述 &#x1f4e2; 所有想学Python的小伙伴看过来&#xff01;作为深耕编程领域的技术分享者&#xff0c;最新整理了一份Python从0到1的视频教程。 &#x1f4a1;亮点 ✅ 保姆级系统路线&#xff1a;从环境搭建、语法精讲&#xff0c;到爬虫/数据分析/AI/Web全栈开发&#…...

关于Spring MVC中@RequestMapping注解的详细解析,涵盖其核心功能、属性、使用场景及最佳实践

以下是关于Spring MVC中RequestMapping注解的详细解析&#xff0c;涵盖其核心功能、属性、使用场景及最佳实践&#xff1a; 1. 基础概念 RequestMapping是Spring MVC的核心注解&#xff0c;用于将HTTP请求映射到控制器&#xff08;Controller&#xff09;的方法上。它支持类级…...

蓝桥杯:对字符串处理常用知识笔记

一、前面四个是计算带有空格字符串的的长度计算 C语言代码 #include<string.h> #include<stdio.h> int main() { char s[105]; gets(s); printf("%d", strlen(s)); return 0; } 算法2 C 代码&#xff08;常用&#xff09; #include <iostream> #in…...

实现一个 Markdown 编辑器组件:Vue 3 + Vite + Highlight.js

文章目录 一、项目背景与需求分析二、搭建基础项目1. 初始化 Vue 3 项目2. 安装依赖 三、实现 Markdown 编辑器组件1. 创建 Markdown 编辑器组件2. 组件说明 四、优化与拓展1. 自动保存功能2. 文件上传功能 五、总结 一、项目背景与需求分析 在现代前端开发中&#xff0c;Mark…...

【回眸】Linux 内核 (十四)进程间通讯 之 信号量

前言 信号量概念 信号量常用API 1.创建/获取一个信号量 2.改变信号量的值 3. 控制信号量 信号量函数调用 运行结果展示 前言 上一篇文章介绍的共享内存有局限性,如:同步与互斥问题、内存管理复杂性问题、数据结构限制问题、可移植性差问题、调试困难问题。本篇博文介…...

Redis的used_memory_peak_perc和used_memory_dataset_perc超过90%会怎么样

当Redis的used_memory_peak_perc&#xff08;当前内存占历史峰值的百分比&#xff09;和used_memory_dataset_perc&#xff08;数据集内存占比&#xff09;均超过90%时&#xff0c;可能引发以下问题及风险&#xff1a; 一、used_memory_peak_perc > 90% 的影响 内存交换风险…...