Ts封装Axios

axios拦截器可以让我们在项目中对后端http请求和响应自动拦截处理,减少请求和响应的代码量,提升开发效率同时也方便项目后期维护。在请求响应的interceptors(因特塞泼特斯).这个里面的话.他分为请求拦截器和响应拦截器,请求拦截器里面一般在请求头里面携带token值.响应拦截器里面对状态码的判断.比方说返回401的时候就是token没权限.跳转到登录界面。

封装axiso首先下载

npm install axios

创建文件夹request,在文件夹中创建index.ts文件名,开始对axios进行手动封装封装 或 官网复制粘贴拦截器(https://www.axios-http.cn/docs/interceptors)

  1. 首先引入下载好的aixos
  2. 创建实例
  3. 请求拦截,分别包含请求成功 和 请求错误两个函数

    1. 执行时机为:发起请求时,请求还没有发送出去时执行 请求拦截
    2. 请求成功:请求头携带token
    3. 请求错误:发生错误请求时,可以处理 4 开头的错误
  4. 响应拦截,分别包响应成功 和 响应失败两个函数

    1. 执行时机为:请求结束后,服务器有响应的时候执行
    2. 响应成功:返回状态码为2xx(200...)携带的数据
    3. 响应失败:响应失败/错误时,可以对 5 开头的状态码进行处理、请求超时、错误状态码的处理。
  5. 导出封装好的axios

手动封装axios代码详情

// 引入axios
import axios from axios
// 进度条和样式
import nProgress from "nprogress" // npm install nprogress
import "nprogress/nprogress.css"
// 实例化axios
const install = axios.create({
    // 请求地址的前缀 公共全局的URL
    baseURL:"",
    // 请求时长  --- 超出定义的时长,请求超时
    timeout:5000
})
// 请求拦截
install.interceptors.request.use(
    (config)=>{
        // 开始进度条
        nProgress.start()
        // 获取token
        const token = localStorge.getItem('token')
        // 请求头携带token    
        config.headers[''] = "Bearer " + token
        return config
    },
    (error)=>{
        return Promise.reject(error)
    }
)
// 响应拦截
install.interceptors.response.use(
    (response)=>{
        // 响应成功关闭进度条
        nProgress.done()
        // 返回响应的数据
        return response
    },
    (error)=>{
        // 请求超时处理
        if(error.message.includes('timeout')){
            alert('请求超时')
            return;
        }
        // 不同错误状态码处理
        const code = error.response.status;
        switch(code){
            case 400:
                console.log('请求错误');
                break;
            case 401:
                console.log('未授权');
                break;
            case 403:
                console.log('禁止访问');
                break;
            case 404:
                console.log('页面消失');
                break;
            case 500:
                console.log('服务器内部错误');
                break;
            case 502:
                console.log('网关错误');
                break;
        }
        return Promise.reject(error)
    }
)
// 导出封装好的aixos

以上是axios两次封装,我们还可以将他们的请求方式也封装一下,比如在同文件夹内新建一个methods.ts文件,然后如下代码

// 引入封装好的axios
import install from "./index"
// 定义任意类型接口
interface anyType{
    [key:string]:any | (string|number)
}
// 定义类型接口
interface dataType{
    url:string, // 路径
    method?:string,  // 请求方法 get / post...
    headers?:anyType, // 请求头
    params?:anyType, // get请求携带参数用的
    data?:anyType, // post请求携带参数用的
}

// 创建 get 请求方法
export const get = (data:dataType)=>{
    // 定义请求方法
    data.method = "GET"
    // 返回
    return install(data)
}

// 创建post请求方法
export const = (data:dataType)=>{
    // 定义post请求方法
    data.method = "POST"
    // 返回
    return install(data)
}

模拟请求

// 引入封装好的 get post 请求方法
import {get,post} from "./methods"

// 模拟一个请求接口
export const getLogin = (data) =>{
    return get({
        url:"请求的路径",
        data:data // 传递参数
    })
}

最后只需要在组件内调用 getLogin 这个方法即可。

更详细的封装

/**
 * 
 * axios
 * 
 * 封装 axios 逻辑
 * 1.下载依赖
 * 2.创建文件
 * 3.导入/引入 axios
 * 4.添加默认配置
 * 5.定义返回的数据类型
 * 6.添加拦截器
 * 7.封装请求方法
 * 8.导出/抛出 实例
 * 
 * 
 * 1.AxiosInstance 
 *   表示:
 *       axios 实例的配置项 url 方法 headers 参数
 * 2.AxiosRequestConfig
 *   表示:
 *      axios 实例的类型
 * 3.AxiosResponse 
 *   表示:
 *      axios 响应的数据结构 状态码 响应头 响应数据
 * 4.AxiosError
 *   表示:
 *      axios 请求发生错误的错误对象 错误信息  请求配置
 * 5.InternalAxiosRequestConfig
 *   表示:
 *      扩展了 AxiosRequestConfig 接口
 * 
 */

// 导入
import axios, { AxiosInstance, AxiosResponse, AxiosRequestConfig, AxiosError, InternalAxiosRequestConfig } from 'axios';

// 默认配置 实例化
const instance: AxiosInstance = axios.create({
    baseURL: import.meta.url || "", //设置api 的基本路径 相当于 默认的根目录
    timeout: 5000, //请求时长
})

// 请求拦截器
instance.interceptors.request.use(
    (config: InternalAxiosRequestConfig) => {
        // 
        return config;
    },
    // 请求地址错误
    (error: AxiosError) => {
        return Promise.reject(error);
    }
)

// 响应拦截器
instance.interceptors.response.use(
    (response: AxiosResponse) => {
        // 判断
        if (response.status === 200) {
            return response.data
        } else {
            // 如果响应状态码不是 200 返回一个拒绝的 Promise
            // Promise 三个状态 分别 成功,失败,进行中
            return Promise.reject()
        }
    },
    (error: AxiosError) => {
        // return Promise.reject(error);
        throw new Error("Http Error: " + error)
    }
)

// 导出
export default instance

// 定义结果 接口的 result 
// unknown 未知类型
export interface Result<T = unknown> {
    message: string;
    code: number;
    data: T;
    [key: string]: any; // 其他任意类型
}

// 请求结果的类型 Result

/* 
    定义一个名为Result的接口 默认类型为 泛型T unknown 未知类型
        接口是一种用户描述对象结构的类型
    接口的属性都有
        message:字符串类型,代表结果的消息信息
        code:数字类型,代表结果的状态
        data:泛型类型T, 代表结果的数据 默认为 unknown 类型
        [key:string]:any:索引签名,代表接口可以具有任意数量的其他属性,属性名为字符串类型,属性值为任意类型
            
    PS:
        通过定义这个接口,我们可以在代码中使用Result类型来表示一个具有特定结构的结果对象。
        例如,可以使用Result<number>来表示一个具有数字类型数据的结果对象。
*/



// 定义结果接口的result
export interface Result<T = unknown> {
  message: string;
  code: number;
  data: T;
  [key: string]: any; // 其他的任意类型
}
// axios.get("xxxx", { params: {} });
export const http = {
  get<T = any>(url: string, params?: object): Promise<Result<T>> {
    console.log(params);

    return service.get<T, Result<T>>(url, { params });
  },
  post<T = any>(url: string, data?: object): Promise<Result<T>> {
    return service.post<T, Result<T>>(url, data);
  },
  put<T = any>(url: string, data?: object): Promise<Result<T>> {
    return service.put<T, Result<T>>(url, data);
  },
  delete<T = any>(url: string, data?: object): Promise<Result<T>> {
    return service.delete<T, Result<T>>(url, data);
  },
};


export const http = {
    // axios.get('xxx路径',{params:{}}) 原型
    get<T = any>(url: string, params?: object): Promise<Result<T>> {
        return instance.get<T, Result>(url, {params})
    },
    post<T = any>(url:string,data?:object): Promise<Result<T>> {
        return instance.post<T, Result<T>>(url, {data});
     },
    put<T = any>(url:string,data?:object): Promise<Result<T>> {
        return instance.put<T,Result<T>>(url, {data});
     },
    delete<T =any>(url:string,data?:object): Promise<Result<T>> {
        return instance.delete<T,Result<T>>(url, {data});
     },
}
   解析 
    这段代码是使用 TypeScript 定义的一个 HTTP 请求库的封装。这段代码主要包含两个部分,一个是 Result 接口,另一个是 http 对象。

Result 接口
    Result 接口定义了返回结果的通用结构。它包含以下属性:

    message: 字符串类型,通常用于描述操作的结果消息。
    code: 数字类型,通常用于表示操作的返回状态码。
    data: 可以是任何类型,用于存储请求返回的数据。
    [key: string]: any;: 这是一个剩余属性,意味着可以添加任何其他类型的属性。
    这个接口可以用来定义 HTTP 请求的响应格式,使得调用者可以方便地处理返回结果。

http 对象
    http 对象提供了常见的 HTTP 请求方法,并对每个方法进行了泛型参数化,使得返回结果可以灵活地适应不同的数据类型。

    get 方法:用于发送 GET 请求。它接受一个 URL 和可选的参数对象,返回一个 Promise 对象,该 Promise 在请求完成后解析为 Result 类型。调用示例:http.get<User>('/users/123').
    post 方法:用于发送 POST 请求。它接受一个 URL、一个可选的请求数据对象,返回一个 Promise 对象,该 Promise 在请求完成后解析为 Result<T> 类型,其中 T 是请求数据对象的类型。调用示例:http.post<User>('/users', userData).
    put 方法:用于发送 PUT 请求。它接受一个 URL、一个可选的请求数据对象,返回一个 Promise 对象,该 Promise 在请求完成后解析为 Result<T> 类型,其中 T 是请求数据对象的类型。调用示例:http.put<User>('/users/123', userData).
    delete 方法:用于发送 DELETE 请求。它接受一个 URL 和一个可选的请求数据对象,返回一个 Promise 对象,该 Promise 在请求完成后解析为 Result<T> 类型,其中 T 是请求数据对象的类型。调用示例:http.delete<User>('/users/123').

*** 如何调用和创建接口
    这段代码没有明确提供如何创建和实例化接口或类的具体步骤,因此无法提供关于这部分的具体说明。但通常来说,你可以使用 TypeScript 的类和接口来创建和实例化对象,然后使用这些对象的方法。例如:

    typescript
    复制代码
    import { http, Result } from './http'; // 导入 http 和 Result 接口  

    // 使用 http.get 发送 GET 请求  
    http.get<User>('/users/123').then(response => {  
        console.log(response.data); // 打印返回的用户数据  
    });
    
    
    
   详解
    /* 
        get请求方法 方法名为get
        使用了 泛型<T = any>
            默认是类型为 any(任意类型)
        
        get<T = any>(url:string,params?:object):Promise<Result = unknow>{
            return aixos.get<T,Result<T>>(url,params)
        }
    
         他接受两个参数 
            第一个是url(路径)字符串类型
            第二个是params(接受参数的)可选参数 对象类型
        get方法 返回一个promise对象
            这个对象是一个未知类型的 Result(请求结果)对象

        函数内部 调用了axios中get请求方法,同时传入了 url(字符串类型) 和 params(可选对象类型)
            内部的get请求方法也使用了泛型
                他接受两个类型参数
                    第一个类型参数是 T (any)
                    第二个类型参数是 Result<T>
                返回一个Promise对象
                    返回的Promise对象的结果可能是一个T类型的值
                    或者是一个Result<T>类型的值
                  
        总结:
            这个方法的作用是发送一个Get请求,返回一个Promise对象,
            这个Promise对象的结果是一个Result对象
                Result对象可能包含一个T类型的值,也可能是包含一个Result<T>类型的值

    */
    
    发送一个请求,默认类型泛型(any)任意类型   返回一个promise对象,接受两个参数 url(字符串类型) 和 params(可选参数类型对象)
    输入 一个aixos请求方式默认类型 泛型 或 Result 泛型 ,传递两个参数url 和 params(ps:已定义好类型))

组件内使用/调用

引入
import { http } from '@/utils/Request'

    http.get('www.baidu.com').then(res=>{
      console.log(res,'111');
    })

  • 22
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值