2行代码,解决静态冲突,自动帮你取消重复的过期请求

2行代码,解决静态冲突,自动帮你取消重复的过期请求

安装

npm i –save abort-request

使用方式

避免竞态冲突,detail 总是最新值

原始写法

import { watch, ref, unref } from vue;

// 请求方法
const getDataAPI = ({ params }: { params: { id: string } }) => {
// 发起请求
};

const id = ref();
const detail = ref();

// 调用请求方法,handleQuery 可能多次调用,detail 数据是最新的吗?

const handleQuery = () => {

getDataAPI({ params: { id: unref(id) } }).then((res) => {
detail.value = res;
});
};

watch(id, () => {
handleQuery();
});

2行代码优化

import { watch, ref, unref } from vue;
import { createAutoAbortExpiredRequest, isAbortError } from abort-request;

// 请求方法
const getDataAPI = ({ params }: { params: { id: string } }) => {
// 发起请求
};

const id = ref();
const detail = ref();

// 创建这个请求方法的自动取消版本
const getDataAPIAutoAbort = createAutoAbortExpiredRequest(getDataAPI);
const handleQuery = () => {
// 使用 getDataAPIAutoAbort 替代 getDataAPI 进行调用,传参方式不变
getDataAPIAutoAbort({ params: { id: unref(id) } }).then((res) => {
detail.value = res;
});
};

watch(id, () => {
handleQuery();
});

避免阻塞浏览器 – 如果旧请求还未完成,就取消

XHR 和 Fetch 都支持传入 signal 用于中止请求,可以按照当前项目的封装方式,确定传入 signal 的方法,axios 配置参考:signal: new AbortController().signal

const getDataAPI = ({
params,
signal,
}: {
params: { id: string };
signal?: AbortSignal;
}) => {
// 发起请求
};

const handleQuery = () => {
// getDataAPIAutoAbort 可以接受一个函数作为参数,这个函数接受 signal 参数,组装好 signal 后,返回一个数组,用做请求参数
getDataAPIAutoAbort(({ signal }) => [
{ params: { id: unref(id) }, signal },
]).then((res) => {
// 当多次调用时,未完成的请求被自动取消,不会进入 then 逻辑
detail.value = res;
});
};

处理 loading 状态

const handleQuery = () => {
loading.value = true;
getDataAPIAutoAbort(({ signal }) => [{ params: { id: unref(id) }, signal }])
.then((res) => {
// 当多次调用时,未完成的请求被自动取消,不会进入 then 逻辑
detail.value = res;
loading.value = false;
})
.catch((err) => {
// 判断不是取消请求的错误
if (!isAbortError(err)) {
loading.value = false;
}
});

// 不能在 finally 中处理 loading 状态
};

Please follow and like us:
Pin Share