サーバーへのリクエスト処理中に ajax リクエストを手動でキャンセルする方法

リクエスト送信プロセス中に、サーバーがリクエストを返す前に手動でリクエストをキャンセルできます。

ネイティブ ajax

リクエストは、リクエスト オブジェクトのメソッドを介してキャンセルできますabort()

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    <button>点击发送</button>
    <button>点击取消</button>
    <script>
        // 获取元素;
        const btns = document.getElementsByTagName('button');
        let xhr = null
        // 发送请求
        btns[0].onclick =function (){
      
      
            xhr = new XMLHttpRequest();
            xhr.open('GET','http://127.0.0.1:8000/delay')
            xhr.send()   
        }
        // abort取消请求
        btns[1].onclick = function (){
      
      
           xhr.abort();
        }
         
    </script>
</body>
</html>

アクシオス

道:

1. AbortController : v0.22.0以降、axiosはfetch APIメソッドをサポートしますAbortController.—リクエストのキャンセル.このメソッドでは、axiosのバージョンに注意する必要があり、v0.22.0未満では失敗します.

2. cancelToken: この API は v0.22.0 から廃止されました不应在新项目中使用ただし、私のaxiosの現在のバージョンv1.2.0は引き続き使用できますcancelToken

fetch と ajax の違いを知りたい場合は、この記事を読むことができます: https://zhuanlan.zhihu.com/p/401232894

AbortController インターフェイスは、必要に応じて 1 つまたは複数の Web リクエストを中止できるコントローラー オブジェクトを表します。

MDN の公式ドキュメントの例を見てください:

let controller;
const url = 'video.mp4';

const downloadBtn = document.querySelector('.download');
const abortBtn = document.querySelector('.abort');

downloadBtn.addEventListener('click', fetchVideo);

abortBtn.addEventListener('click', () => {
    
    
  if (controller) {
    
    
    controller.abort();
    console.log('中止下载');
  }
});

function fetchVideo() {
    
    
  controller = new AbortController();
  const signal = controller.signal;
  fetch(url, {
    
     signal })
    .then((response) => {
    
    
      console.log('下载完成', response);
    })
    .catch((err) => {
    
    
      console.error(`下载错误:${
      
      err.message}`);
    });
}

アクシオスで使用

this.abortController = new AbortController();
const res = await http({
    
    
	url: 'http://0.0.0.0:8088',
	method: 'get',
	signal: this.abortController.signal,  // 带上参数
	params: {
    
    
		
	}
}).catch((err) => {
    
    
	this.isRequesting3 = false;
	console.log(err);
})

cancel メソッドで直接呼び出される

this.abortController.abort();

ここに画像の説明を挿入
ここに画像の説明を挿入

複数の繰り返しリクエストをキャンセルする

httpRequest.js

import axios from 'axios'
import store from '@/store'
import {
    
     message } from 'ant-design-vue'
 
const CancelToken = axios.CancelToken
 
let pedding = {
    
    }
 
const service = axios.create({
    
    
  baseURL: '/',
  timeout: 60000,
})
 
service.interceptors.request.use(config => {
    
    
  config.headers['token'] = store.state.user.token
 
  // 在参数中加个isCancelToken,用来判断该接口是否需要做多次请求取消上一个请求的操作
  if (config.isCancelToken) {
    
    
 
    // 第一种 AbortController
    const controller = new AbortController();
    config['signal'] = controller.signal
    pedding[config.url + '&' + config.method] && pedding[config.url + '&' + config.method].abort()
    pedding[config.url + '&' + config.method] = controller
 
    // 第二种 CancelToken.source
    const source = CancelToken.source()
    config['cancelToken'] = source.token
    pedding[config.url + '&' + config.method] && pedding[config.url + '&' + config.method].cancel()
    pedding[config.url + '&' + config.method] = source
 
    // 第三种 CancelToken
    pedding[config.url + '&' + config.method] && pedding[config.url + '&' + config.method]()
    config['cancelToken'] = new CancelToken((c) => {
    
    
      pedding[config.url + '&' + config.method] = c
    })
 
  }
 
  return config
}, error => {
    
    
  return Promise.reject(error)
})
 
service.interceptors.response.use(response => {
    
    
  // 这里删除key
  pedding[response.config.url + '&' + response.config.method] && delete pedding[response.config.url + '&' + response.config.method]
 
  if (response.data.code == 200) {
    
    
    return response.data
  } else {
    
    
    message.error(response.data.msg)
    return Promise.reject(response.data)
  }
}, error => {
    
    
  return Promise.reject(error)
})
 
export default service

上記の 3 つの方法のいずれかを選択できます。

使用
home.vue

<template>
  <div>
    <a-button>home</a-button>
    <router-link to="/about">跳转about</router-link>
    <a-input placeholder=""></a-input>
    <a-checkbox></a-checkbox>
  </div>
</template>
 
<script>
import {
      
       login } from '@/axios/api/home'
export default {
      
      
  setup() {
      
      
    login({
      
      timeRange: 'ONE_DAY'}).then(res => {
      
      
      console.log('第一次调用-success')
    }).catch((err) => {
      
      
      console.log('第一次调用-err')
    })
    setTimeout(() => {
      
      
      login({
      
      timeRange: 'ONE_DAY', num: 1}).then(res => {
      
      
        console.log('第二次调用-success')
      }).catch((err) => {
      
      
        console.log('第二次调用-err')
      })
    }, 200)
  }
}
</script>
 
<style lang="scss" scoped>
</style>

home.js

import request from '@/axios'
 
export const login = (data) => {
    
    
  return request({
    
    
    url: '/dc/pc/heatMap',
    method: 'get',
    params: data,
    isCancelToken: true
  })
}

複数のリクエストが順番に返されるようにする

  1. promise.all を使用する
  2. リクエストインターフェースにはインデックス識別子があり、バックエンドとの合意に従って返されるデータに含まれ、結果を取得した後にソートされます

ここに画像の説明を挿入

おすすめ

転載: blog.csdn.net/woyebuzhidao321/article/details/129732967