龙空技术网

嗯,还在用Ajax嘛?Fetch了解一下呀

山河已无恙i 2402

前言:

今天你们对“ajax查看传过来的值”大致比较关心,朋友们都想要知道一些“ajax查看传过来的值”的相关资讯。那么小编也在网络上搜集了一些有关“ajax查看传过来的值””的相关文章,希望同学们能喜欢,朋友们快快来了解一下吧!

写在前面之前写了一篇AJAX相关的博文的,看到有小伙伴讲到了Fetch,所以研究下博文内容参考: Demo是搭了一个简单的Flaskweb服务,然后通过Node环境发出请求

「此刻你在沙漠里,因此你要潜心于沙漠之中。沙漠和世上其他东西一样,可以用来理解世界。你甚至不必理解沙漠,只要观察普通的沙粒就行,从中你可以看到天地万物的神奇之处。--------《牧羊少年的人生之旅》」

Fetch API 提供了一个获取资源的接口(包括跨域请求)。任何使用过XMLHttpRequest的人都能轻松上手,而且新的 API 提供了更强大和灵活的功能集。

Fetch 提供了对RequestResponse,Headers(以及其他与网络请求有关的)对象的通用定义

fetch() 必须接受一个参数——资源的路径。无论请求成功与否,它都返回一个Promise对象,resolve 对应请求的 Response。你也可以传一个可选的第二个参数 init

一旦Response被返回,就可以使用一些方法来定义内容的形式,以及应当如何处理内容,你也可以通过 Request() 和 Response() 的构造函数直接创建请求和响应,但是我们不建议这么做。

Fetch 接口Headers:相当于 response/request 的头信息Request:相当于一个资源请求Response:相当于请求的响应使用 Fetch

Fetch API 提供了一个JavaScript接口,用于访问和操纵 HTTP 管道的一些具体部分,例如请求和响应。它还提供了一个全局fetch()方法,该方法提供了一种简单,合理的方式来跨网络异步获取资源。

fetch 规范与jQuery.ajax()主要有以下的不同:

当接收到一个代表错误的 HTTP 状态码时,从 fetch() 返回的Promise不会被标记为 reject,即使响应的 HTTP 状态码 404 或 500。相反,它会将Promise状态标记为 resolve (如果响应的 HTTP 状态码不在 200 - 299 的范围内,则设置 resolve 返回值的 ok 属性为 false ),仅当网络故障时或请求被阻止时,才会标记为 reject。 +fetch不会发送跨域 cookies,除非你使用了credentials的初始化选项。(自2018 年 8 月以后,默认的 credentials 政策变更为 same-origin。Firefox 也在 61.0b13 版本中进行了修改)fetch()使用 Promise,不使用回调函数,因此大大简化了写法,写起来更简洁。fetch()采用模块化设计,API 分散在多个对象上(Response 对象、Request 对象、Headers 对象),更合理一些;相比之下,XMLHttpRequest 的 API 设计并不是很好,输入、输出、状态都在同一个接口管理,容易写出非常混乱的代码。fetch()通过数据流(Stream 对象)处理数据,可以分块读取,有利于提高网站性能表现,减少内存占用,对于请求大文件或者网速慢的场景相当有用。XMLHTTPRequest 对象不支持数据流,所有的数据必须放在缓存里,不支持分块读取,必须等待全部拿到后,再一次性吐出来。

在用法上,fetch()接受一个URL字符串作为参数,默认向该网址发出GET请求,返回一个 Promise 对象。

环境准备

这里我们用Node环境来学习,当然在浏览器更有可比性,需要安装基于Node的依赖包node-fetch,这里一定要注意版本问题

node-fetch用于服务器端,即只能在nodejs中用whatwg-fetch用于客户端,即用于在浏览器没有原生支持fetch的情况isomorphic-fetch可以在nodejs浏览器两种环境中运行,是对whatwg-fetch包装

npm install node-fetch@2

同时我们需要一个Web服务用作测试,这里用python搭一个简单的Web服务

#!/usr/bin/env python3# -*- encoding: utf-8 -*-# Python 3.9.0# pip install flask'''@File    :   fetch.py@Time    :   2022/03/04 18:59:02@Author  :   Li Ruilong@Version :   1.0@Contact :   1224965096@qq.com@Desc    :   Fetch学习Demo'''from time import sleepfrom flask import Flask,jsonify,request,send_from_directoryimport os# configurationDEBUG = Trueapp = Flask(__name__)@app.route("/")@app.route("/index")def default():    '''    @Time    :   2022/03/04 18:58:42    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   默认页面    '''    return "<h1>Fetch学习Demo<h1/>"@app.route('/init', methods=['GET'])def init():    '''    @Time    :   2022/03/04 19:41:40    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   get请求返回JSON    '''        data = ["Ajax","Fetch","Promise","Axios"]    return jsonify(data)@app.route("/add",methods=["POST"])def add():    '''    @Time    :   2022/03/04 19:43:05    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   Post请求    '''    data = request.json    print(*data, sep='\n')    return jsonify({"msg":"Post请求成功","code":"0"})@app.route("/download/<filename>")def download(filename):    print(filename)    '''    @Time    :   2022/03/04 22:30:12    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   下载文件    '''    directory = os.getcwd()      print(directory)    return send_from_directory(directory, filename, as_attachment=True)@app.route('/upload', methods=['POST', 'PUT'])def upload():    '''    @Time    :   2021/12/15 10:32:03    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   上传文件    '''    if request.method == 'POST':        try:            f = request.files['file']            print("上传的文件名:===", f.filename)            basepath = os.path.dirname(__file__)  # 当前文件所在路径            upload_path = os.path.join(basepath, "\\", str(f.filename))              f.save(upload_path)            print("保存的文件路径:"+upload_path)        except Exception as e:            print("上传文件失败", e)    return jsonify({"msg":"上传文件OK","code":"0"}),200@app.route("/stop/<int:s>")def stop(s):    sleep(s)    return "OK",200if __name__ == '__main__':    app.run(host='127.0.0.1', port=37881, debug=DEBUG)

data.json文件

[ {  "site": "npr",  "link": ";,  "type": "rss" }, {  "site": "npr",  "link": ";,  "type": "rss" }]

准备工作做好以后,我们开始愉快的学习吧

一个基本的fetch请求设置起来很简单。看看下面的代码:

这是一个回调风格的请求,从服务器获取JSON数据。在Node环境的一个Demo

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");fetch(';)  .then(response => response.json())  .then(json => console.log(json))  .catch(err => console.log('Request Failed', err)); 

fetch()接收到的response是一个Stream对象,response.json()是一个异步操作,取出所有内容,并将其转为 JSON 对象

整理上看和axios类似,相同点都是基于ES 6 Promise对象,在Node环境,都是基于HTTP模块实现,不同点,axios在浏览器中,是基于XMLHttpRequests来实现异步通信的,而fetch是一个新的API,是XMLHttpRequest的最新替代技术 ,下面是一个axios的例子.

const axios = require('axios').default;const { v4: uuidv4 } = require('uuid');let subscriptionKey = "3c6588c7026b41a4**7f81551cb4a737";let endpoint = ";;let location = "chinanorth";axios({    baseURL: endpoint,    url: '/translate',    method: 'post',    headers: {        'Ocp-Apim-Subscription-Key': subscriptionKey,        'Ocp-Apim-Subscription-Region': location,        'Content-type': 'application/json',        'X-ClientTraceId': uuidv4().toString()    },    params: {        'api-version': '3.0',        'from': 'zh-Hans',        'to': ['zh-Hant', 'en']    },    data: [{        'text': '我徒然学会了抗拒热闹,却还来不及透悟真正的冷清。--------张大春'    }],    responseType: 'json'}).then(function(response){    console.log(JSON.stringify(response.data, null, 4));}).catch(function (error) {    console.log(error);  });

Promise 可以使用await语法改写,使得语义更清晰。

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        let data =await response.json();        console.log(data);    } catch (e) {        console.log("Oops, error", e);    }})()

await语句必须放在try...catch里面,这样才能捕捉异步操作中可能发生的错误.

=====PS D:\GolandProjects\code-master\demo> node fetch[  {    site: 'npr',    link: ';,    type: 'rss'  },  {    site: 'npr',    link: ';,    type: 'rss'  }]PS D:\GolandProjects\code-master\demo> 
Response 对象:处理 HTTP 回应

fetch()请求成功以后,得到的是一个Response对象。它对应服务器的 HTTP 回应

const response = await fetch(url);

Response 包含de同步属性,对应 HTTP 回应的标头信息(Headers),可以立即读取

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        //同步属性,对应 HTTP 回应的标头信息(Headers),可以立即读取        console.log(response.ok);        console.log(response.status);         console.log(response.statusText);        console.log(response.type);        console.log(response.url);        console.log(response.redirected)        //Response 包含的数据通过 Stream 接口异步读取        let data =await response.json();        console.log(data);    } catch (e) {        console.log("Oops, error", e);    }})()
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"true200OKundefined[ 'Ajax', 'Fetch', 'Promise', 'Axios' ][Done] exited with code=0 in 0.253 seconds

response.ok:属性返回一个布尔值,表示请求是否成功,true对应 HTTP 请求的状态码 200 到 299,false对应其他的状态码。

response.status:属性返回一个数字,表示 HTTP 回应的状态码(例如200,表示成功请求)。

response.statusText:属性返回一个字符串,表示 HTTP 回应的状态信息(例如请求成功以后,服务器返回"OK")。

response.url:属性返回请求的 URL。如果 URL 存在跳转,该属性返回的是最终 URL。

response.type:属性返回请求的类型。可能的值如下:

通过状态码判断请求是否成功

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        if (response.status >= 200 && response.status < 300){            let data = await response.json();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()

我们把python的web服务接口里抛出一个异常,直接到了catch里面

@app.route('/init', methods=['GET'])def init():    '''    @Time    :   2022/03/04 19:41:40    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   get请求返回JSON    '''        data = ["Ajax","Fetch","Promise","Axios"]    raise Exception('这是一个请求异常的模拟')    return jsonify(data)

执行报错:内部服务器错误,即500

[Running] node "d:\GolandProjects\code-master\demo\fetch.js"Oops, error Error: INTERNAL SERVER ERROR    at d:\GolandProjects\code-master\demo\fetch.js:23:15    at processTicksAndRejections (internal/process/task_queues.js:93:5)

修改接口返回状态码为400

@app.route('/init', methods=['GET'])def init():    '''    @Time    :   2022/03/04 19:41:40    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   get请求返回JSON    '''        data = ["Ajax","Fetch","Promise","Axios"]    return jsonify(data),400

报错误请求

[Running] node "d:\GolandProjects\code-master\demo\fetch.js"INTERNAL SERVER ERROROops, error Error: INTERNAL SERVER ERROR    at d:\GolandProjects\code-master\demo\fetch.js:24:19    at processTicksAndRejections (internal/process/task_queues.js:93:5)[Done] exited with code=0 in 0.261 seconds

也可以直接通过response.ok来判断

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        if (response.ok){            let data = await response.json();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()

修改接口返回状态码为404

@app.route('/init', methods=['GET'])def init():    '''    @Time    :   2022/03/04 19:41:40    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   get请求返回JSON    '''        data = ["Ajax","Fetch","Promise","Axios"]    return jsonify(data),404
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"NOT FOUNDOops, error Error: NOT FOUND    at d:\GolandProjects\code-master\demo\fetch.js:24:19    at processTicksAndRejections (internal/process/task_queues.js:93:5)[Done] exited with code=0 in 0.257 seconds
Response.headers 属性

Response 对象还有一个Response.headers属性,指向一个Headers对象,对应 HTTP 回应的所有标头。

Headers 对象可以使用for...of循环进行遍历。

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        if (response.ok){            let data = await response.json();            console.log(data);            for (let [key, value] of response.headers) {                 //console.log(key+":"+ value);                  console.log(`${key} : ${value}`);                }            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"[ 'Ajax', 'Fetch', 'Promise', 'Axios' ]content-length : 51content-type : application/jsondate : Sat, 05 Mar 2022 15:14:47 GMTserver : Werkzeug/2.0.2 Python/3.9.0[Done] exited with code=0 in 0.26 seconds

Headers 对象提供了以下方法,用来操作标头。HTTP 回应来说,修改标头意义不大

Headers.get():根据指定的键名,返回键值。Headers.has(): 返回一个布尔值,表示是否包含某个标头。Headers.set():将指定的键名设置为新的键值,如果该键名不存在则会添加。Headers.append():添加标头。Headers.delete():删除标头。Headers.keys():返回一个遍历器,可以依次遍历所有键名。Headers.values():返回一个遍历器,可以依次遍历所有键值。Headers.entries():返回一个遍历器,可以依次遍历所有键值对([key, value])。Headers.forEach():依次遍历标头,每个标头都会执行一次参数函数。读取内容的方法

Response对象根据服务器返回的不同类型的数据,提供了不同的读取方法。读取方法都是异步的,返回的都是 Promise 对象。必须等到异步操作结束,才能得到服务器返回的完整数据`。

response.text():得到文本字符串。response.json():得到 JSON 对象。response.blob():得到二进制 Blob 对象。response.formData():得到 FormData 表单对象。response.arrayBuffer():得到二进制 ArrayBuffer 对象。

「response.text()可以用于获取文本数据,比如HTML文件。」

@app.route("/")@app.route("/index")def default():    '''    @Time    :   2022/03/04 18:58:42    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   默认页面    '''    return "<h1>Fetch学习Demo<h1/>"
// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        if (response.ok){            let data = await response.text();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()

「response.json() 主要用于获取服务器返回的 JSON 数据」

「response.formData()主要用在 Service Worker 里面,拦截用户提交的表单,修改某些数据以后,再提交给服务器。」

「response.blob()用于获取二进制文件。」

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        if (response.ok){            let data = await response.blob();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"Blob {  [Symbol(type)]: 'application/json',  [Symbol(buffer)]: <Buffer 5b 0a 09 7b 0a 09 09 22 73 69 74 65 22 3a 20 22 6e 70 72 22 2c 0a 09 09 22 6c 69 6e 6b 22 3a 20 22 68 74 74 70 3a 2f 2f 77 77 77 2e 6e 70 72 2e 6f 72 ... 141 more bytes>}[Done] exited with code=0 in 0.847 seconds

response.arrayBuffer()主要用于获取流媒体文件。

const audioCtx = new window.AudioContext();const source = audioCtx.createBufferSource();const response = await fetch('song.ogg');const buffer = await response.arrayBuffer();const decodeData = await audioCtx.decodeAudioData(buffer);source.buffer = buffer;source.connect(audioCtx.destination);source.loop = true;
Response.clone()

Stream 对象只能读取一次,读取完就没了。这意味着,前一节的五个读取方法,只能使用一个,否则会报错。

Response 对象提供Response.clone()方法,创建Response对象的副本,实现多次读取。

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    try {        let response = await fetch(url);        let response1 = response.clone();        if (response.ok){            let data = await response.json();            let data1 = await response1.json()            console.log(data1);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"[  {    site: 'npr',    link: ';,    type: 'rss'  },  {    site: 'npr',    link: ';,    type: 'rss'  }][Done] exited with code=0 in 0.25 seconds

Response 对象还有一个Response.redirect()方法,用于将 Response 结果重定向到指定的 URL。该方法一般只用在 Service Worker 里面

Response.body 属性

Response.body属性是 Response 对象暴露出的底层接口,返回一个 ReadableStream 对象,供用户操作。

它可以用来分块读取内容,应用之一就是显示下载的进度。

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    let url = ';;    fetch(url)        .then(response => response.body)        .then(res => res.on('readable', () => {            let chunk;            while (null !== (chunk = res.read())) {                console.log(chunk.toString());            }        }))        .catch(err => console.log(err));})()
第二个参数init:定制 HTTP 请求

fetch()的第一个参数是 URL,还可以接受第二个参数,作为配置对象,定制发出的HTTP 请求

HTTP 请求的方法、标头、数据体都在这个对象里面设置

Post请求传递JSON

@app.route("/add",methods=["POST"])def add():    '''    @Time    :   2022/03/04 19:43:05    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   Post请求    '''    data = request.json    print(*data, sep='\n')    return jsonify({"msg":"Post请求成功","code":"0"})
// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */const fetch = require("node-fetch");(async () => {    const url = ';;    const body =  { name:  'John', surname:  'Smith'  };    try {        let response = await fetch(url,{            method: 'post',            body: JSON.stringify(body),            headers: {'Content-Type': 'application/json;charset=utf-8'}        });        if (response.ok){            const data = await response.json();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()
namesurname127.0.0.1 - - [06/Mar/2022 02:27:42] "POST /add HTTP/1.1" 200 -========[Running] node "d:\GolandProjects\code-master\demo\fetch.js"{ code: '0', msg: 'Post请求成功' }[Done] exited with code=0 in 0.293 seconds
文件上传
@app.route('/upload', methods=['POST', 'PUT'])def upload():    '''    @Time    :   2021/12/15 10:32:03    @Author  :   Li Ruilong    @Version :   1.0    @Desc    :   上传文件    '''    if request.method == 'POST':        try:            f = request.files['file']            print("上传的文件名:===", f.filename)            basepath = os.path.dirname(__file__)  # 当前文件所在路径            upload_path = os.path.join(basepath, "\\", str(f.filename))              f.save(upload_path)            print("保存的文件路径:"+upload_path)        except Exception as e:            print("上传文件失败", e)    return jsonify({"msg":"上传文件OK","code":"0"}),200
// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */ const fs = require('fs'); const fetch = require('node-fetch'); const FormData = require('form-data'); let fileStream = fs.readFileSync("./data.json");//读取文件 let formdata = new FormData(); const mimetype = 'text/plain' formdata.append("file", fileStream, {    filename: "./data.json",//上传的文件名    contentType: mimetype,//文件类型标识});(async () => {    const url = ';;    try {        let response = await fetch(url,{            method: 'post',            body: formdata ,            headers: formdata.getHeaders()        });        if (response.ok){            const data = await response.json();            console.log(data);            return data;        }else{            console.log(response.statusText);            throw new Error(response.statusText);        }    } catch (e) {        console.log("Oops, error", e);    }})()
上传的文件名:=== data.json保存的文件路径:d:\data.json127.0.0.1 - - [06/Mar/2022 01:37:51] "POST /upload HTTP/1.1" 200 -============[Running] node "d:\GolandProjects\code-master\demo\fetch.js"{ code: '0', msg: '上传文件OK' }
fetch()配置对象的完整 API
const response = fetch(url, {  method: "GET",  headers: {    "Content-Type": "text/plain;charset=UTF-8"  },  body: undefined,  referrer: "about:client", //referrer属性用于设定fetch()请求的referer标头。  referrerPolicy: "no-referrer-when-downgrade",  //referrerPolicy属性用于设定Referer标头的规则  mode: "cors",  // mode属性指定请求的模式  credentials: "same-origin",  //credentials属性指定是否发送 Cookie。  cache: "default", //cache属性指定如何处理缓存  redirect: "follow", //redirect属性指定 HTTP 跳转的处理方法  integrity: "", //integrity属性指定一个哈希值,用于检查 HTTP 回应传回的数据是否等于这个预先设定的哈希值。  keepalive: false, /// keepalive属性用于页面卸载时,告诉浏览器在后台保持连接,继续发送数据。  signal: undefined //signal属性指定一个 AbortSignal 实例,用于取消fetch()请求});
取消fetch()请求

fetch()请求发送以后,如果中途想要取消,需要使用AbortController对象。

@app.route("/stop/<int:s>")def stop(s):    sleep(s)    return "OK",200

请求进去睡眠10s,在5s的时候终止请求,新建AbortController实例,然后发送fetch()请求,配置对象的signal属性必须指定接收AbortController实例发送的信号controller.signal

controller.abort()方法用于发出取消信号。这时会触发abort事件,这个事件可以监听,也可以通过controller.signal.aborted属性判断取消信号是否已经发出

// -*- encoding: utf-8 -*-/* *@File    :   fetch.js *@Time    :   2022/03/04 22:04:04 *@Author  :   Li Ruilong *@Version :   1.0 *@Contact :   1224965096@qq.com *@Desc    :   Fetch学习 */ const fetch = require('node-fetch');  //npm  install abort-controller const AbortController = globalThis.AbortController ||  require('abort-controller') const controller = new AbortController(); const timeout = setTimeout(() => {     controller.abort(); }, 5000); (async () => {    const url = ';;    try {        const response = await fetch(url, {signal: controller.signal});        const data = await response.text();        console.log(data)    } catch (error) {            console.log('request was aborted',error);    } finally {        clearTimeout(timeout);    }})()
[Running] node "d:\GolandProjects\code-master\demo\fetch.js"request was aborted AbortError: The user aborted a request.

「Node 环境」

PS D:\GolandProjects\code-master\demo> node -vv12.13.1PS D:\GolandProjects\code-master\demo> npm -v6.12.1PS D:\GolandProjects\code-master\demo> npm init -y 
{  "name": "demo",  "version": "1.0.0",  "description": "",  "main": "fetch.js",  "dependencies": {    "abort-controller": "^3.0.0",    "form-data": "^4.0.0",    "node-fetch": "^2.6.7"  },  "devDependencies": {},  "scripts": {    "test": "echo \"Error: no test specified\" && exit 1"  },  "keywords": [],  "author": "",  "license": "ISC"}

「python 环境」

PS D:\GolandProjects\code-master> python -VPython 3.9.0PS D:\GolandProjects\code-master> pip -Vpip 20.2.3 from d:\python\python310\lib\site-packages\pip (python 3.9)PS E:\docker> flask --versionPython 3.9.0Flask 2.0.2Werkzeug 2.0.2PS E:\docker>

标签: #ajax查看传过来的值