vue3+TypeScript+axios封装一个网络请求函数,拿了就能用

一、前言:

做业务的时候我估计大家请求网络的方法调了无数次了,但很少自己去封装一个,刚好最近有个vue3+TypeScript的新坑我负责去搭框架,封装axios请求的时候发现和JS还是有点区别的,所以记录一下。

二、认识axios中的AxiosRequestConfig和AxiosResponse

封装过程中用到了这两个类型,在用vue3项目的小伙伴不知道有没有看到过这行代码。如果看到过你知道AxiosRequestConfig和 AxiosResponse是啥意思不?

javascript 复制代码
import axios, { AxiosRequestConfig, AxiosResponse } from 'axios';

在axios中,AxiosRequestConfig 和AxiosResponse 都是一种axios库自带的类型可以直接用也可以自己重写:

AxiosRequestConfig: 用于配置HTTP请求的相关参数。它包含了一系列可配置的选项,用于定制化请求的行为。以下是一些常见的AxiosRequestConfig 选项:

  1. url : 发送请求的URL地址。
  2. method : 请求使用的HTTP方法(例如GET、POST、PUT、DELETE等)。
  3. params : 一个包含键值对的对象,用于作为GET请求的查询参数。
  4. data : 要作为POST或PUT请求体发送的数据。
  5. headers : 一个包含自定义请求头的对象。
  6. timeout : 请求超时时间,单位为毫秒。
  7. responseType : 期望在响应中接收的数据类型(例如'json'、'text'、'blob'等)。

AxiosResponse : 用于表示HTTP请求的响应数据。它包含了请求的响应信息,如状态码、响应头、响应数据等。以下是一些AxiosResponse 接口中常见的属性:

  1. data : 响应数据,通常是一个包含服务器响应的数据的对象。
  2. status : HTTP状态码,表示请求的结果。
  3. statusText : HTTP状态消息,与状态码对应的文本描述。
  4. headers : 响应头信息,包含服务器返回的所有响应头。
  5. config : 包含发起请求时提供的配置信息的对象。
  6. request : 包含关于请求的详细信息的对象。

三、封装完整请求函数和用法说明

(1)封装函数,文件命名为request.ts

typescript 复制代码
import axios, { AxiosRequestConfig, AxiosResponse } from 'axios';
import { ElMessage, ElMessageBox } from 'element-plus';
import useStore from '@/store';

// 创建一个 axios 实例
const service = axios.create({
  baseURL: import.meta.env.VITE_APP_BASE_API,
  timeout: 50000,
  headers: { 'Content-Type': 'application/json;charset=utf-8' }
});

// 请求拦截器
service.interceptors.request.use(
  (config: AxiosRequestConfig) => {
    if (!config.headers) {
      throw new Error(
        `好像没有请求头哦`
      );
    }
    // 这里是从vuex或者pinia中拿到token, 并且放到请求头中
    const { user } = useStore();
    if (user.token) {
      config.headers.Authorization = `${window.localStorage.getItem('token')}`;
    }
    return config;
  },
  (error: any) => {
    return Promise.reject(error);
  }
);

// 响应拦截器
service.interceptors.response.use(
  (response: AxiosResponse) => {
    const { code, msg } = response.data;
    if (code === '00000') {
      return response.data;
    } else {
      // 响应数据为二进制流处理(Excel导出)
      if (response.data instanceof ArrayBuffer) {
        return response;
      }

      ElMessage({
        message: msg || '系统出错',
        type: 'error'
      });
      return Promise.reject(new Error(msg || 'Error'));
    }
  },
  (error: any) => {
    if (error.response.data) {
      const { code, msg } = error.response.data;
      // token 过期,重新登录
      if (code === 'A0999') {
        ElMessageBox.confirm('当前页面已失效,请重新登录', 'Warning', {
          confirmButtonText: 'OK',
          type: 'warning'
        }).then(() => {
          window.localStorage.clear();
          window.location.href = '/';
        });
      } else {
        ElMessage({
          message: msg || '系统出错',
          type: 'error'
        });
      }
    }
    return Promise.reject(error.message);
  }
);

// 导出 axios 实例
export default service;

(2)需要请求某个接口时

写在api.ts文件中

php 复制代码
import request from '@/utils/request';

/**
 * 使用添加用户信息接口
 * @param data
 */
export function addUser(data: any) {
  return request({
    url: '/api/index/users',
    method: 'post',
    data: data
  });
}

(3)在业务页面使用addUser接口

javascript 复制代码
import { addUser } from '@/api/user';

/**
 * 提交接口
 */
function saveForm() {
  formRef.value.validate((valid: any) => {
    if (valid) {
        addUser(state.formData).then(() => {
          ElMessage.success('提交成功咯');
        });
      }
  });
}

小结:

从封装到使用的流程都写出来了,应该挺好理解的吧。其实还能封装的更细节的,但怕越写越复杂难懂就点到即止了,例如:

1.自己重写一个类型用extends继承AxiosRequestConfig 和AxiosResponse使其在原有基础上更加灵活

2、对单个请求对请求config的处理,使每个请求有自己的拦截器,不传就用默认拦截器

3、封装到具体的get、post类型,而且不是传过去

相关推荐
jonjia几秒前
注解与断言
typescript
jonjia1 分钟前
IDE 超能力
typescript
jonjia2 分钟前
对象类型
typescript
jonjia2 分钟前
快速搭建 TypeScript 开发环境
typescript
jonjia3 分钟前
TypeScript 的奇怪之处
typescript
jonjia6 分钟前
类型派生
typescript
jonjia6 分钟前
开发流程中的 TypeScript
typescript
jonjia10 分钟前
设计你的类型
typescript
jonjia12 分钟前
Total TypeScript 精要
typescript
前端Hardy16 分钟前
HTML&CSS&JS:打造丝滑的3D彩纸飘落特效
前端·javascript·css