• 中止一个或多个 Web 请求


    我们在处理前后端交互的过程中,有时需要仔细斟酌接口的请求时机(例:频繁的Tab切换、树节点切换、数据录入时,请求什么时候发?)或接口返回数据的处理时机(例:接口还没返回时就要切换路由,路由都切换走了,之前请求的数据怎么办?),避免一些无用的请求或者接口返回顺序的差异(例如:同一个按钮点了多次,如果后点的先返回,先点的后返回,怎么办?)。

    常见的处理方式有:

    加防抖:控制请求时机。对于频繁操作,只在最后一次动作时,发出请求。

    锁状态:控制请求时机。直接禁止很频繁的操作,必须一个接一个。

    取消请求:控制请求处理时机。取消之前没返回的请求,不再处理了。

    AbortController

    AbortController 接口表示一个控制器对象,允许你根据需要中止一个或多个 Web 请求。

    我们先使用 AbortController() 构造函数创建一个控制器,然后使用 AbortController.signal 属性获取其关联 AbortSignal 对象的引用。

    当 fetch 请求初始化时,我们将 AbortSignal 作为一个选项传递进入请求的选项对象中(下面的 {signal})。这将 signal 和 controller 与 fetch 请求相关联,并且允许我们通过调用 AbortController.abort() 去中止它。

    const controller = new AbortController();
    
    fetch('/foo/bar', {
       signal: controller.signal
    }).then(function(response) {
       //...
    });
    // 取消请求
    controller.abort()
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    当 abort() 被调用时,这个 fetch() promise 将 reject 一个名为 AbortError 的 DOMException。

    Axios

    Axios 也支持以 fetch API 方式通过 AbortController 取消请求:

    const controller = new AbortController();
    
    axios.get('/foo/bar', {
       signal: controller.signal
    }).then(function(response) {
       //...
    });
    // 取消请求
    controller.abort()
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    使用 Axios 您还可以使用 cancel token 取消一个请求。

    const CancelToken = axios.CancelToken;
    const source = CancelToken.source();
    
    axios.get('/user/12345', {
      cancelToken: source.token
    }).catch(function (thrown) {
      if (axios.isCancel(thrown)) {
        console.log('Request canceled', thrown.message);
      } else {
        // 处理错误
      }
    });
    
    axios.post('/user/12345', {
      name: 'new name'
    }, {
      cancelToken: source.token
    })
    
    // 取消请求(message 参数是可选的)
    source.cancel('Operation canceled by the user.');
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21

    AJAX

    AJAX 正在逐渐被 JavaScript 框架中的函数和官方的 Fetch API 标准取代。如果该请求已被发出,XMLHttpRequest.abort() 方法将终止该请求。当一个请求被终止,它的 readyState 将被置为 XMLHttpRequest.UNSENT (0),并且请求的 status 置为 0。

    var xhr = new XMLHttpRequest(),
        method = "GET",
        url = "https://developer.mozilla.org/";
    xhr.open(method, url, true);
    
    xhr.send();
    
    if (OH_NOES_WE_NEED_TO_CANCEL_RIGHT_NOW_OR_ELSE) {
      xhr.abort();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    Axios 内部也提供了对 AbortController 的兼容处理。

    
    const controller = new AbortController();
    const signal = controller.signal
    signal.addEventListener('abort', () => {
      console.log('事件监听器')
    })
    
    const xhr = new XMLHttpRequest(),
        method = "GET",
        url = "https://developer.mozilla.org/";
    xhr.open(method, url, true);
    
    xhr.send();
    
    if (signal.aborted) {
      console.log('请求被终止');
    } else {
      controller.abort().
      xhr.abort();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20

    属性 aborted一个 Boolean,表示与之通信的请求是否被终止(true)或未终止(false)。

    当使用 addEventListener() 或将事件监听器分配给该接口的 onabort 属性,请求被中止时调用。

  • 相关阅读:
    一文搞懂CAN总线协议
    8086/8088CPU的储存器结构(二)
    PowerBI依据字段取一列从小到大的第三个值(没三个值取第二个,第二个没有取第一个)
    【Pytorch Lighting】第 5 章:时间序列模型
    【软考笔记】(三)知识产权
    P1547 [USACO05MAR] Out of Hay S 题解
    Function源码解析与实践
    6月,值得推荐的计算机专业新书有哪几本?
    Jenkins 带参数执行shell脚本
    【C++】特殊类设计
  • 原文地址:https://blog.csdn.net/wu_xianqiang/article/details/127950225