利用Axios封装及泛型实现定制化HTTP请求处理

      本案例旨在教授如何使用Axios库结合TypeScript泛型进行HTTP请求的高级封装,以提升代码的可复用性和类型安全性。我们将通过一个具体的示例,学习如何创建一个通用的请求函数,它能够适应不同类型的API响应,并在请求前后加入自定义逻辑(如错误处理、Token注入等)。

1. 引入必要的库和类型

  • 引入Axios:首先,我们导入Axios库及其相关类型,用于发起网络请求。
  • 定义类型:引入AxiosInstance和AxiosRequestConfig类型,以增强代码的类型提示和安全性。
import axios, { type AxiosResponse } from 'axios';
import type { AxiosInstance, AxiosRequestConfig } from 'axios';

2. 创建Axios实例并配置

  • 配置基础设置:通过axios.create方法创建一个Axios实例,并设置基础URL和超时时间等默认配置
const axiosInstance: AxiosInstance = axios.create({
    baseURL: 'https://tenapi.cn/v2/',
    timeout: 10000
});

3. 添加请求和响应拦截器

  • 请求拦截器:在请求发送前可以统一处理逻辑,如添加认证信息。
  • 响应拦截器:对返回的响应进行统一处理,如错误码判断。
axiosInstance.interceptors.request.use(config => {
    // 可以在此处添加Token或其他请求头
    return config;
}, error => Promise.reject(error));

axiosInstance.interceptors.response.use(res => res, error => Promise.reject(error));

 4. 定义API响应接口

  • ApiResponse接口:定义一个泛型接口来规范API响应的结构,包含状态码、消息、时间戳和数据部分。
export interface ApiResponse<T = any> {
    code: number;
    msg: string;
    timestamp: number;
    data: T;
}

5. 封装请求函数

  • 泛型request函数:创建一个异步的泛型函数request,它接受请求配置并返回经过类型转换的响应数据。 
export async function request<T>(config: AxiosRequestConfig): Promise<T> {
    return axiosInstance.request<ApiResponse<T>>(config).then(res => res.data);
}

6. 使用封装的请求函数

  • 具体请求示例:定义一个数据模型Hot,并使用request函数发起请求,处理响应数据
interface Hot {
    name: string;
    url: string;
    hot: number;
}

request<Array<Hot>>({
    url: '/baiduhot',
    method: 'get'
}).then(res => {
    if(res.code === 200) {
        const hot = res.data[0];
        console.log(hot.name);
    }
});

6. 完整代码

import axios, {type AxiosResponse} from 'axios';
import type { AxiosInstance, AxiosRequestConfig } from 'axios';

/* 创建axios实例 */
const axiosInstance : AxiosInstance = axios.create({
    baseURL: 'https://tenapi.cn/v2/',
    timeout: 10000
});


/* 封装实例的请求拦截器 */
axiosInstance.interceptors.request.use( config  => {
    return config;
}, (error) => {
    return Promise.reject(error);
});


/* 封装实例的响应拦截器 */
axiosInstance.interceptors.response.use( (res : AxiosResponse<any>)  => {
    return res;
}, (error) => {
    return Promise.reject(error);
});


/* 定义接口 */
export interface ApiResponse<T> {
    code: number;
    msg: string;
    timestamp: number;
    data: T;
}



/* 封装实例的请求方法 */
export async function request<T>(config: AxiosRequestConfig ) {
    // axios实例的 request 接受的第一个泛型参数,就是返回数据data的类型
    return axiosInstance.request<ApiResponse<T>>(config).then((res) => res.data);
}


/* 如何使用代码如下  */
interface Hot {
    name: string;
    url: string;
    hot: number;
}

request<Array<Hot>>({
    url: '/baiduhot',
    method: 'get'
}).then(res => {
    if(res.code == 200) {
        let hot = res.data[0];
        console.log(hot.name);
    }
});

提示:更多的Axios配置信息请看官网

补充UniApp请求封装:


interface AskModel {
	url: string,
	data?: any
	method?: 'OPTIONS' | 'GET' | 'HEAD' | 'POST' | 'PUT' | 'DELETE' | 'TRACE' | 'CONNECT'
}


interface ApiRes<T> {
	 code: number;
	 message: string;
	 data: T;
}


export async function Ask<T>( option : AskModel ) : Promise<ApiRes<T>> {
	return new Promise(( resolve, reject ) => {
		uni.request({
		    url:  env.reqBaseUrl + option.url, 
		    data: option.data || {},
			method: option.method || 'GET',
		    header: {
		    	'content-type':'application/json' 
		    },
		    success: (res) => {
		        resolve(res.data as ApiRes<T>);
		    },
			fail(res) {
				reject(res);
			}
		});
	})
}

 

  • 5
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值