取消请求主要依赖于浏览器提供的 AbortControllerAPI。这是一个现代且标准的方法,适用于 fetch 和大多数支持 Promise 的 HTTP 库
具体实现
- 取消 Fetch
// 1. 创建控制器
const controller = new AbortController();
const signal = controller.signal;
// 2. 发起 fetch 请求,并传入 signal
fetch('https://api.example.com/data', { signal })
.then(response => response.json())
.then(data => console.log(data))
.catch(err => {
// 当请求被取消时,err.name 为 'AbortError'
if (err.name === 'AbortError') {
console.log('请求已被取消');
} else {
console.error('请求出错:', err);
}
});
// 3. 在某个事件(如按钮点击、组件卸载)中取消请求
document.getElementById('cancelBtn').addEventListener('click', () => {
controller.abort(); // 触发取消
});
- 取消 Axios 请求
const controller = new AbortController();
axios.get('https://api.example.com/data', {
signal: controller.signal // 直接传递 signal
}).catch(function (err) {
if (axios.isCancel(err)) {
console.log('请求取消:', err.message);
}
});
// 取消请求
controller.abort();
- 取消 XMLHttpRequest
const xhr = new XMLHttpRequest();
xhr.open('GET', 'https://api.example.com/data');
xhr.send();
// 直接调用 .abort() 方法即可取消
xhr.abort();
在 React (函数组件) 中
在 useEffect 的清理函数中取消请求,防止组件卸载后更新状态。
import { useEffect } from 'react';
function MyComponent() {
useEffect(() => {
const controller = new AbortController();
fetch('/api/data', { signal: controller.signal })
.then(res => res.json())
.then(data => {
// 更新状态...
})
.catch(err => {
if (err.name !== 'AbortError') {
// 处理非取消错误
}
});
// 清理函数:在组件卸载时执行
return () => {
controller.abort();
};
}, []); // 依赖项数组
return <div>组件内容</div>;
}
在 Vue.js 中
在组件的 beforeUnmount 生命周期钩子或 onUnmounted(Composition API) 中取消。
// Composition API 示例
import { onUnmounted } from 'vue';
export default {
setup() {
const controller = new AbortController();
fetch('/api/data', { signal: controller.signal })
.then(res => res.json())
.then(data => {
// 处理数据
});
// 组件卸载时取消请求
onUnmounted(() => {
controller.abort();
});
}
}
应用场景
页面或组件卸载时
用户频繁操作(如搜索框输入联想)
评论区