TLDR:

当我们需要的时候,我们可以通过AbortController接口来终止一个或者多个请求。

前言

到目前为止,我们有两个常用的基本的手段去发送请求进而局部刷新页面内容,其一是XMR(XMLHttpRequest),其二是fetch,我们一个个说

XHR

对于XHR,我们或许已经很熟悉了,当我们想要发送一个请求的时候,我们可以这样做:

const xhr = new XMLHttpRequest();
const method = 'GET';
const url = 'https://xxx'; xhr.open(method, url, true);
xhr.onreadystatechange = () => {
if (xhr.readyState === 4) {
// do something
}
}
xhr.send();

当我们由于某种原因(比如重复请求)想要终止它的时候,我们只需要调用abort即可。

xhr.abort();

很方便也很简洁,但是对于fetch呢?

fetch

首先我们看下fetch的基本定义:

看到这里我们已经知道了答案,但是我们需要再去了解一下上文所说的AbortController.

AbortController

最初es6引入fetch的时候,其实就是没有abort这样的功能,不过广大程序朋友们还会希望能有这个灵活的api,所以在2015年就有人提了这个issue,再次之后大家尝试了注入promise式的取消或者是其他hack等等,经过这份折腾最终我们迎来了AbortController和AbortSignal。

AbortController目前很简单,有一个制度的属性AbortController.signal和一个用来中断请求的.abort()

光说也没啥意思,咱看代码说话:

// 启动一个node服务,其中包括一个api和一个html页面

const Koa = require('koa');
const fs = require('fs');
const app = new Koa(); const sleep = () => {
return new Promise(res => {
setTimeout(function() {
res();
}, 3000);
});
}; app.use(async ctx => {
if (ctx.request.url === '/api') {
await sleep();
ctx.body = 'Hello World';
} else {
ctx.status = 200;
ctx.respond = false;
fs.createReadStream('./test.html').pipe(ctx.res);
}
}); app.listen(3000);

下面是test.html的内容

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<script>
fetch('/api')
.then((res) => {
console.log(res, '请求成功');
});
</script>
</body>
</html>

启动服务后,我们看下network的内容。

我们注意两个地方,一个代表fetch请求,一个代表请求的延时时间,也就是我们定义的三秒

取消fetch

这时候我们想中断,就可以这样做:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<script>
// 增加了如下几行
const controller = new AbortController();
const signal = controller.signal;
console.log(signal, 'signal的初始状态');
signal.addEventListener('abort', function (e) {
console.log(signal, 'signal的中断状态');
}); setTimeout(function() {
controller.abort();
}, 2000);
// 增加部分结束 fetch('/api', {signal})
.then((res) => {
console.log(res, '请求成功');
});
</script>
</body>
</html>

再次运行,我们会得到如下结果:

从图中我们可以很清楚的看到,请求在2s后被终止,请求状态变为canceled,然后aborted的状态由false转变为true。

就是这样,我们对fetch也进行的取消操作,还算是豁然开朗吧。嘻嘻。

兼容性

虽然AbortController已经诞生很长时间了,但是目前mdn上的定义还是实验性技术,查看mdn我们可以发现,其实主流浏览器大部分都支持了,如果我们开发的平台很新还是可以使用的,相信不远的将来,肯定会大批量使用。前端的道路也会越来越顺畅!

最后如果这边文章能帮给你带来一点帮助,欢迎关注,点赞,制作不易,与君共勉!

仅仅知道如何终止XHR请求,或许对你来说是不够的!的更多相关文章

  1. 终止ajax请求

    在做搜索功能时,文本框输入文本就得请求一次数据,如果上一次的请求还没回又请求了就导致数据错误和无用的数据请求. 我们需要输入文本时候判断上一次的ajax请求是否完毕,若还没完毕就终止本次请求. 对于j ...

  2. 自定义xhr请求

    接上一篇博客,上一篇是之前的jsonp请求方法的封装,这一篇是xhr请求的简单封装. 原理: 1:new一个xhr对象,命名为ajaxRequest,由于浏览器兼容性的问题,所以将获取xhr对象的方式 ...

  3. 怎样终止HTTP请求

    使用 xhr.abort() var xhr = new XMLHttpRequest(); xhr.open('GET', 'http://www.example.com/page.php', tr ...

  4. ajax.abort 终止AJAX请求

                               $(document).ready(function () { var ajax; $('#choice').change(function() ...

  5. XHR HTTP 请求 get post请求解决方案

    XHR请求的 测试方式, postman 64位下载地址: http://www.downza.cn/download?file=2017%2F01%2FPostmanwin64493.zip& ...

  6. 如何终止JQUERY的$.AJAX请求

    最近遇到,如果用户频繁点击ajax请求,有两个问题: 1,如果连续点击了5个ajax请求,前4个其实是无效的,趁早结束节省资源. 2,更严重的问题是:最后一个发送的请求,响应未必是最后一个,有可能造成 ...

  7. Fetch超时设置和终止请求

    1.基本使用 Fetch 是一个新的端获取资源的接口,用于替换笨重繁琐XMLHttpRequest.它有了Request 和 Response 以及Headers对象的概念,与后端语言请求资源更接近. ...

  8. 【转】Fetch超时设置和终止请求

    原文链接:https://www.cnblogs.com/yfrs/p/fetch.html 1.基本使用 Fetch 是一个新的端获取资源的接口,用于替换笨重繁琐XMLHttpRequest.它有了 ...

  9. [1.6W字] 浏览器跨域请求限制的详细原理分析&寻找一种最简单的方式实现XHR跨域(9种方法, 附大招可以纯前端实现跨域!)

    Title/ 浏览器跨域(CrossOrigin)请求的原理, 以及解决方案详细指南 #flight.Archives011 序: 最近看到又有一波新的创作活动了, 官方给出的话题中有一个" ...

随机推荐

  1. MySQL快速回顾:计算字段与函数

    9.1 计算字段 存储在数据库表中的数据一般不是应用程序所需要的格式.比如: 如果想要在一个字段中既显示公司名,又显示公式的地址,但这两个信息一般包含在不同的表列中. 城市.州和邮政编码存储在不同的列 ...

  2. springboot2 整合mongodb

    在springboot2中使用MongoDB 1.引入依赖 <dependency> <groupId>org.springframework.boot</groupId ...

  3. 世界上最流行的版本控制系统——Git

    版本控制系统,也就是VCS(Version Control System),可以说是程序员必备的工具.那么它到底是什么,有什么作用呢? 举个例子,如果你想查看你所开发的软件在一个月之前的模样,同时还想 ...

  4. 关于Matplotlib中No module named 'matplotlib.finance'的解决办法

    最近在研究量化分析,需要用到matplotlib中的一个库,输入from matplotlib.finance import quotes_historical_yahoo_ohlc, candles ...

  5. 「 从0到1学习微服务SpringCloud 」09 补充篇-maven父子模块项目

    系列文章(更新ing): 「 从0到1学习微服务SpringCloud 」06 统一配置中心Spring Cloud Config 「 从0到1学习微服务SpringCloud 」07 RabbitM ...

  6. idea怎么关闭项目

    原文地址:https://jingyan.baidu.com/article/a3a3f8112169e78da2eb8a8d.html idea关闭项目可以按File-CloseProject按钮实 ...

  7. jade 网上看到一个不错的demo 分享 一下 链接

    http://download.csdn.net/detail/sarah1992/9347903 启动的时候 先启动 http://localhost:8080/ 在 node chat 启动 ht ...

  8. redis--->事务和锁

    redis 的事务.锁.流水线 Redis与 mysql事务的对比 开启 mysql:start transaction redis:multi 语句:mysql:普通sql redis:普通命令 成 ...

  9. Windows 10搭建Apache2.4 + PHP7 + MySQL环境

    一.准备 1.资源 Apache https://www.apachelounge.com/download/ PHP http://windows.php.net/download#php-7.0 ...

  10. C# list中ConvertAll的使用

    static double TakeSquareRoot(int x) { //return Math.Sqrt(x); ; } static void Main(string[] args) { L ...