日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

自底向上的web数据操作指南

發(fā)布時(shí)間:2025/3/21 编程问答 40 豆豆
生活随笔 收集整理的這篇文章主要介紹了 自底向上的web数据操作指南 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

簡(jiǎn)介

本篇文章主要探討JavaScript中的數(shù)據(jù)操作.

JavaScript一直以來(lái)給人一種比較低能的感覺,例如無(wú)法讀取系統(tǒng)上的文件,不能做一些底層的操作.

所以在頁(yè)面上操作數(shù)據(jù)會(huì)交由服務(wù)器處理也就成了主流的做法.

但是很多人沒有發(fā)現(xiàn),實(shí)際上JavaScript以及在逐步增強(qiáng)這些功能,現(xiàn)在我們就已經(jīng)可以放心的在web端進(jìn)行文件操作了.

起因

N個(gè)月前我去新浪面試實(shí)習(xí),我提到了原來(lái)我做過(guò)一個(gè)頁(yè)面配合上傳Excel可以完成一些功能.

我的這番話勾起了面試官在實(shí)際編碼中遇到了一些問題,就是如何不通過(guò)服務(wù)器來(lái)操作數(shù)據(jù),我和她討論了一番,最后不了了之了(當(dāng)然也沒過(guò)).

N個(gè)月后實(shí)習(xí)被坑,成了無(wú)業(yè)游民閑來(lái)無(wú)事正好也好奇這個(gè)問題然后就研究了一下.

涉及的內(nèi)容

沒有非必要的內(nèi)容,對(duì)于文件操作來(lái)說(shuō)以下API都是必須了解的,本文也會(huì)漸進(jìn)式的討論這些內(nèi)容.

  • Blob
  • ArrayBuffer
  • TypedArray
  • DataView
  • FileReader
  • File
  • URL

兼容性

我沒有詳細(xì)考證API的兼容性,不過(guò)從MDN提供的數(shù)據(jù)來(lái)看IE10以上的瀏覽器大部分都是兼容的.

總覽

一般來(lái)說(shuō)操作一個(gè)文件都要經(jīng)歷如下的步驟:

  • 知道文件的地址(存放的位置)
  • 讀取
  • 保存到Buffer中,重復(fù)上步驟直至結(jié)束
  • 進(jìn)行數(shù)據(jù)編輯
  • 知道要寫入的地址
  • 獲取要寫入的數(shù)據(jù),從Buffer中獲取還是所有數(shù)據(jù)
  • 寫入
  • 寫入完成

API名稱以及對(duì)應(yīng)的職責(zé):

名稱職責(zé)
URL制造文件地址
FileReader讀取文件的接口
Blob用于在JavaScript表示文件
File用于表示文件對(duì)象
ArrayBuffer表示Buffer(僅僅提供一片內(nèi)存空間)
TypedArray基于數(shù)組操作Buffer上的數(shù)據(jù)(操作的最小單位是數(shù)組元素)
DataView基于字節(jié)操作Buffer上的數(shù)據(jù)

上面描述的內(nèi)容之間的關(guān)系很復(fù)雜,這里我們逐步來(lái)進(jìn)行分析.

ArrayBuffer

https://developer.mozilla.org...

ArrayBuffer對(duì)象用于表示一段緩沖區(qū)域(可以理解為一段可控的內(nèi)存區(qū)域),它僅僅表示這片被開辟的區(qū)域但是不提供操作方式.

const arraybuffer = new ArrayBuffer(8) // 創(chuàng)建一個(gè)長(zhǎng)度為8字節(jié)大小的Buffer

默認(rèn)ArrayBuffer中每一個(gè)字節(jié)都被填充了0.

利用這個(gè)對(duì)象我們可以完成如下的操作:

  • 獲取

    • 該Buffer的大小(字節(jié))
    • 該Buffer的副本(范圍)
  • 修改

    • 該Buffer的大小
  • 判斷

    • 給定的數(shù)據(jù)是否是操作視圖(實(shí)例方法)
  • 異常

    • 當(dāng)創(chuàng)建的Buffer長(zhǎng)度超過(guò)Number.MAX_SAFE_INTEGER的大小會(huì)產(chǎn)生錯(cuò)誤
const arraybuffer = new ArrayBuffer(8);console.log(arraybuffer.byteLength); // 獲取長(zhǎng)度 console.log(arraybuffer.slice(4,8)); // 獲取副本 // 截止到2019年2月12日 20:11:05沒有瀏覽器實(shí)現(xiàn)該功能 console.log(arraybuffer.transfer(arraybuffer,16));// 修改原有Buffer console.log(ArrayBuffer.isView({})) // false 是否是視圖

DataView

https://developer.mozilla.org...

DataView用于操作ArrayBuffer中的數(shù)據(jù),這也是它構(gòu)造函數(shù)中接受一個(gè)ArrayBuffer的原因:

const arraybuffer = new ArrayBuffer(8); const dataview = new DataView(arraybuffer); // 默認(rèn)的視圖大小就是buffer的大小 const offset = new DataView(arraybuffer, 0, arraybuffer.byteLength); // 默認(rèn)的偏移量以及長(zhǎng)度

利用這個(gè)對(duì)象我們可以完成如下的操作:

  • 獲取

    • 被該視圖引入的Buffer(只讀)
    • 該視圖從Buffer中讀取的自己長(zhǎng)度(只讀)
    • 該視圖從Buffer中讀取的偏移量(只讀)
  • 異常

    • 如果由偏移(byteOffset)和字節(jié)長(zhǎng)度(byteLength)計(jì)算得到的結(jié)束位置超出了 buffer 的長(zhǎng)度.
  • 寫入

    • 使用xxx類型寫入(見下方)
  • 讀取

    • 使用xxx類型讀取

可以使用的類型:

類型名稱對(duì)應(yīng)的方法
Int8getInt8,setInt8
Uint8getUint8,setUint8
Int16getInt16,setInt16
Uint16getUint16,setUint16
Int32getInt32,setInt32
Uint32getUint32,setUint32
Float32getFloat32,setFloat32
Float64getFloat64,setFloat64

簡(jiǎn)單實(shí)例:

const arraybuffer = new ArrayBuffer(1); // 一個(gè)字節(jié)const dataview = new DataView(arraybuffer); // 默認(rèn)的視圖大小就是buffer的大小dataview.setInt8(0,127) // 從0開始寫入一個(gè)int8(8位無(wú)符號(hào)整形,一個(gè)字節(jié))dataview.getInt8(0) // 從偏移0開始讀取一個(gè)int8(8位無(wú)符號(hào)整形,一個(gè)字節(jié))console.log(dataview.getInt8(0));dataview.setInt16(0,65535); // 錯(cuò)誤超出了ArrayBuffer的空間 int16占兩個(gè)字節(jié)

字節(jié)序

簡(jiǎn)單來(lái)講-使用DataView:

  • 在讀寫時(shí)不用考慮平臺(tái)字節(jié)序問題。
https://developer.mozilla.org...

https://zh.wikipedia.org/wiki...

可以利用這個(gè)函數(shù)來(lái)進(jìn)行判斷:

var littleEndian = (function() {var buffer = new ArrayBuffer(2);new DataView(buffer).setInt16(0, 256, true /* 設(shè)置值時(shí)使用小端字節(jié)序 */);// Int16Array 使用系統(tǒng)字節(jié)序,由此可以判斷系統(tǒng)是否是小端字節(jié)序return new Int16Array(buffer)[0] === 256; })(); console.log(littleEndian); // true or false

TypedArray

https://developer.mozilla.org...

在上面一節(jié)中我們使用get和set的方式基于數(shù)據(jù)類型來(lái)讀寫內(nèi)存(ArrayBuffer)中的數(shù)據(jù).

而所謂的TypedArray就是使用類似于操作數(shù)組的方式來(lái)操作我們的Buffer可以理解為數(shù)組中的每一個(gè)元素都是不同類型的數(shù)據(jù),這樣一來(lái)我們可以使用數(shù)組上的很多方法,相較于干巴巴的使用get和set更加靈活一些,少掉點(diǎn)頭發(fā).

名字叫做TypedArray的這個(gè)對(duì)象或者全局構(gòu)造函數(shù)并不存在于JavaScript中.因?yàn)轭愋蛿?shù)組并不只有一個(gè),但是TypedArray代指的這些內(nèi)容擁有統(tǒng)一的構(gòu)造函數(shù),統(tǒng)一的屬性統(tǒng)一的方法,不同的只是他們的名字以及所對(duì)應(yīng)的數(shù)據(jù)類型.

TypedArray()指的是以下的其中之一: Int8Array(); Uint8Array(); Uint8ClampedArray(); Int16Array(); Uint16Array(); Int32Array(); Uint32Array(); Float32Array(); Float64Array();

看到這里我們立馬聯(lián)想到了之前DataView上不同的Get和Set,概念是一樣的,不同于ArrayBuffer的是,這里的最小數(shù)據(jù)單位是數(shù)組中的元素,不同類型元素所占用的空間是不同的,但是我們不需要考慮在字節(jié)層面上進(jìn)行控制.

接下來(lái)我們利用Int8Array來(lái)進(jìn)行討論:

  • 構(gòu)造函數(shù)

    • 傳入一個(gè)數(shù)值來(lái)表示類型數(shù)組中元素的數(shù)量
    • 傳入任意一個(gè)類型數(shù)組在保留其原有的長(zhǎng)度上進(jìn)行數(shù)據(jù)類型轉(zhuǎn)換
  • 方法(靜態(tài))

    • Int8Array.from()通過(guò)可迭代對(duì)象創(chuàng)建一個(gè)類型數(shù)組
    • Int8Array.of()通過(guò)可變參數(shù)創(chuàng)建一個(gè)類型數(shù)組

例子:

// 32無(wú)符號(hào)能表示的最大的數(shù)值 占4個(gè)字節(jié) const int32 = new Int32Array(1); // 使用length int32[0] = 4294967295;// 8位無(wú)符號(hào)能表示最大的內(nèi)容是127 占1個(gè)字節(jié) const int8 = new Int8Array(int32); // 使用另外一個(gè)類型數(shù)組 console.log(int8[0]) // -1 32位轉(zhuǎn)8位要確保,32位的值在8位的范圍內(nèi)否則無(wú)法保證精度const from = Int8Array.from([0,127]); console.log(from.length === 2) // trueconst of = Int8Array.of(0,127); console.log(of.length === 2)// true
  • 屬性(靜態(tài))

    • TypedArray.BYTES_PER_ELEMENT
    • TypedArray.length
    • TypedArray.name
    • get TypedArray[@@species\]
    • TypedArray.prototype
  • 屬性(實(shí)例)

    • TypedArray.prototype.buffer
    • TypedArray.prototype.byteLength
    • TypedArray.prototype.byteOffset
    • TypedArray.prototype.length
  • 方法(實(shí)例)

    • 方法是在是太多了Array上的方法TypedArray基本都有,例舉太多都是照搬MDN,給個(gè)貼上大家自行查閱吧.
    • 方法列表

例子(類數(shù)組操作):

const int8 = new Int8Array(2); int8[0] = 0; int8[1] = 127;int8.forEach((value)=>console.log(value));for (const elem of int8) {console.log(elem); }Array.isArray(int8) // false 類數(shù)組而不是真的數(shù)組

Blob

https://developer.mozilla.org...

Blob` 對(duì)象表示一個(gè)不可變、原始數(shù)據(jù)的類文件對(duì)象。Blob 表示的不一定是JavaScript原生格式的數(shù)據(jù)

這說(shuō)明了什么意思,類似于ArrayBuffer一樣,ArrayBuffer本身沒有為了達(dá)到某種目的而提供具體的操作方法,他的存在就類似于一個(gè)占位符一樣,Blob對(duì)象也是類似的概念,在JavaScript中我們使用Blob對(duì)象來(lái)表示一個(gè)文件,當(dāng)這個(gè)文件需要進(jìn)行操作的時(shí)候我們?cè)诶闷渌緩綄?duì)這個(gè)Blob對(duì)象進(jìn)行操作.(個(gè)人理解)

Blob的API和ArrayBuffer非常相似,因?yàn)樗麄冇兄浅C芮械穆?lián)系,創(chuàng)建Blob對(duì)象有兩種方式,對(duì)應(yīng)著兩種具體的需求:

  • 直接調(diào)用構(gòu)造函數(shù)傳入JavaScript中的數(shù)據(jù)結(jié)構(gòu)
  • 使用File對(duì)象創(chuàng)建,用于表示文件

這里我們不討論由File對(duì)象創(chuàng)建的情況,這部分留到下節(jié)中討論.

  • 構(gòu)造函數(shù)

    • 你可以利用現(xiàn)有的JavaScript數(shù)據(jù)結(jié)構(gòu)來(lái)創(chuàng)建一個(gè)Blob對(duì)象
    • 你可以選擇這個(gè)Blob對(duì)象的MIME類型
    • 你可以控制這個(gè)Blob對(duì)象中的換行符在系統(tǒng)中表現(xiàn)的行為
    • 具體參考
  • 屬性(實(shí)例)

    • size - Blob對(duì)象所包含的數(shù)據(jù)大小
    • type - Blob對(duì)象所描述的MIME類型
  • 方法(實(shí)例)

    • slice()類似于ArrayBuffer.slice()從原有的Blob中分離出一部分組成新的Blob對(duì)象

例子:

const blob1 = new Blob([JSON.stringify({content: 'success'})], {type: 'application/json'});const blob2 = new Blob(['<a id="a"><b id="b">hey!</b></a>'],{type:'text/html'});

注意:Blob對(duì)象接受的第一個(gè)參數(shù)是一個(gè)數(shù)組.

Blob對(duì)象還可以根據(jù)其他數(shù)據(jù)結(jié)構(gòu)進(jìn)行創(chuàng)建:

  • ArrayBuffer
  • ArrayBufferView(TypedArray)
  • Blob
https://developer.mozilla.org...

乍一看Blob對(duì)象看似很雞肋,不過(guò)在JavaScript中能裝載數(shù)據(jù)還可以指定MIME類型,這種情況多半都是用于和外部進(jìn)行交互.

回顧前面的內(nèi)容,我們知道了如何創(chuàng)建一片內(nèi)存中的區(qū)域,還知道了如何利用不同的工具來(lái)對(duì)這篇內(nèi)存進(jìn)行操作,最重要的一個(gè)用于描述文件Blob對(duì)象接受ArrayBuffer和TypedArray,那么還能玩出什么花樣呢?

File

文件(File)接口提供有關(guān)文件的信息,并允許網(wǎng)頁(yè)中的 JavaScript 訪問其內(nèi)容。

https://developer.mozilla.org...

File對(duì)象用于描述文件,這個(gè)對(duì)象雖然可以利用構(gòu)造函數(shù)自行創(chuàng)建,但是大多數(shù)情況下都是利用瀏覽器上的<input>元素或者拖拽API來(lái)獲取的.

File對(duì)象繼承Blob對(duì)象,所以繼承了Blob對(duì)象上的原型方法和屬性,和Blob純粹表示文件不同,File更加接地氣一點(diǎn),他還擁有了我們操作系統(tǒng)上常見的一些特征:

  • 屬性(實(shí)例)

    • lastModified 最后修改時(shí)間
    • name 文件名稱
    • size 文件大小
    • type MIME類型
    • 詳細(xì)介紹
  • 構(gòu)造函數(shù)

    • 詳細(xì)介紹

例子:

// 創(chuàng)建bufferconst buffer = new Int8Array(2);console.log(buffer.byteLength); // 2buffer[0] = 0;buffer[1] = 127console.log(buffer[0]); // 127// 利用buffer創(chuàng)建一個(gè)file對(duì)象const file = new File([buffer],'text.txt',{type:'text/plain',lastModified:Date.now()});// file繼承blob所以可以使用slice方法,返回一個(gè)blob對(duì)象const blob = file.slice(1,2,'text/plain');console.log(blob.size); //1

File對(duì)象目前看來(lái)依然扮演者'載體'的角色,不過(guò)在將他交由其他的API的時(shí)候才是他真正發(fā)揮威力的地方.

FileReader

FileReader一看名字我就有一種想喊JavaScript(瀏覽器端)永不為奴的沖動(dòng).前面鋪墊了那么多終于可以看到真正可以實(shí)際利用的內(nèi)容了.

FileReader 對(duì)象允許Web應(yīng)用程序異步讀取存儲(chǔ)在用戶計(jì)算機(jī)上的文件(或原始數(shù)據(jù)緩沖區(qū))的內(nèi)容,使用 File 或 Blob 對(duì)象指定要讀取的文件或數(shù)據(jù)。

https://developer.mozilla.org...

FileReader和前面的所提到的內(nèi)容不同的地方在于,這個(gè)API有事件,你可以使用onXXX和addEventListener進(jìn)行監(jiān)聽.

基本工作流程:

  • 獲取用戶提供的文件對(duì)象(通過(guò)input或者拖拽)

  • 或者自己創(chuàng)建File或者(Blob)對(duì)象
  • 新建一個(gè)FileReader()實(shí)例
  • 監(jiān)聽對(duì)應(yīng)的方法來(lái)獲取讀取內(nèi)容完成后的回調(diào)
  • 利用不同的方法讀取文件內(nèi)容

  • 讀取為fileReader.ArrayBuffer()
  • 讀取為DataURLfileReader.readAsDataURL()
  • 讀取為字符串fileReader.readAsText()
  • 示例1讀取計(jì)算機(jī)上的文件:

    <!DOCTYPE html> <html><head><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><title>blob</title><meta name="viewport" content="width=device-width, initial-scale=1"> </head><body><!-- 建議選中一個(gè)文本 --><label for="file">讀取文件<input id="file" type="file" ></label><script type="text/javascript">document.getElementById('file').addEventListener('change',(event)=>{const files = event.srcElement.files;if(files.length === 0){return console.log('沒有選擇任何內(nèi)容');}const file = files[0];console.log(file instanceof File); // trueconsole.log(file instanceof Blob); // trueconst reader = new FileReader();reader.addEventListener('abort',()=>console.log('讀取中斷時(shí)候觸發(fā)'));reader.addEventListener('error',()=>console.log('讀取錯(cuò)誤時(shí)候觸發(fā)'));reader.addEventListener('loadstart',()=>console.log('開始讀取的時(shí)候觸發(fā)'));reader.addEventListener('loadend',()=>console.log('讀取結(jié)束觸發(fā)'));reader.addEventListener('progress',()=>console.log('讀取過(guò)程中觸發(fā)'));// 當(dāng)內(nèi)容讀取完成后再load事件觸發(fā)reader.addEventListener('load',(event)=>{// 輸出文本文件的內(nèi)容console.log(event.target.result)});// 讀取一個(gè)文本文件reader.readAsText(file);});</script> </body></html>

    如果一切順利,你就可以從計(jì)算機(jī)上讀取一個(gè)文件,并且以文本的形式展現(xiàn)在了控制臺(tái)中.

    而且不僅如此,利用:

    reader.readAsArrayBuffer(file)

    我們可以讀取任何類型的數(shù)據(jù),然后再內(nèi)存中進(jìn)行修改,剩下的就差保存了.

    FileReaderSync

    這個(gè)API是FileReader的同步版本,這意味著代碼執(zhí)行到讀取的時(shí)候會(huì)等待文件的讀取,所以這個(gè)API只能在workers里面使用,如果在主線程中調(diào)用它會(huì)阻塞用戶界面的執(zhí)行.

    由于是同步讀取,所以沒有回調(diào)掉必要存在,也就不需要監(jiān)聽事件了.

    https://developer.mozilla.org...

    URL

    前面我們討論完成了數(shù)據(jù)的讀取,在FileReader中我們已經(jīng)可以獲取ArrayBuffer然后使用DateView和TypedArray就可以修改ArrayBuffer完成文件的修改,接下來(lái)我們旅行中的最后一程.

    https://developer.mozilla.org...

    在JavaScript(瀏覽器端)中我們可以使用URL來(lái)創(chuàng)建一個(gè)URL對(duì)象:

    new URL('https://www.xxx.com?q=10')

    他返回的對(duì)象包含如下的內(nèi)容:

    // 控制臺(tái) new URL('https://www.xxx.com?q=10')URL hash: "" host: "www.xxx.com" hostname: "www.xxx.com" href: "https://www.xxx.com/?q=10" origin: "https://www.xxx.com" password: "" pathname: "/" port: "" protocol: "https:" search: "?q=10" searchParams: URLSearchParams { } username: ""

    可見該對(duì)象是一個(gè)工具對(duì)象用于幫助我們更加容易的處理URL.

    例子(來(lái)自MDN):

    var a = new URL("/", "https://developer.mozilla.org"); // Creates a URL pointing to 'https://developer.mozilla.org/' var b = new URL("https://developer.mozilla.org"); // Creates a URL pointing to 'https://developer.mozilla.org' var c = new URL('en-US/docs', b); // Creates a URL pointing to 'https://developer.mozilla.org/en-US/docs' var d = new URL('/en-US/docs', b); // Creates a URL pointing to 'https://developer.mozilla.org/en-US/docs' var f = new URL('/en-US/docs', d); // Creates a URL pointing to 'https://developer.mozilla.org/en-US/docs' var g = new URL('/en-US/docs', "https://developer.mozilla.org/fr-FR/toto");// Creates a URL pointing to 'https://developer.mozilla.org/en-US/docs' var h = new URL('/en-US/docs', a); // Creates a URL pointing to 'https://developer.mozilla.org/en-US/docs' var i = new URL('/en-US/docs', ''); // Raises a SYNTAX ERROR exception as '/en-US/docs' is not valid var j = new URL('/en-US/docs'); // Raises a SYNTAX ERROR exception as 'about:blank/en-US/docs' is not valid var k = new URL('http://www.example.com', 'https://developers.mozilla.com');// Creates a URL pointing to 'https://www.example.com' var l = new URL('http://www.example.com', b); // Creates a URL pointing to 'https://www.example.com'

    實(shí)際上這和Node中的URL對(duì)象十分相似:

    // 終端 > Node > new URL('https://www.xxx.com/?q=10') URL {href: 'https://www.xxx.com/?q=10',origin: 'https://www.xxx.com',protocol: 'https:',username: '',password: '',host: 'www.xxx.com',hostname: 'www.xxx.com',port: '',pathname: '/',search: '?q=10',searchParams: URLSearchParams { 'q' => '10' },hash: '' }

    它和我們討論的文件下載有什么關(guān)系呢,在我們?cè)跒g覽器中一切可以利用的資源都有唯一的標(biāo)識(shí)符那就是URL.

    而我們自定義或者讀取的文件需要通過(guò)URL對(duì)象創(chuàng)建一個(gè)指向我們定義資源的鏈接.

    那么URL對(duì)象上提供了兩個(gè)靜態(tài)方法:

    • URL.createObjectURL() 創(chuàng)建根據(jù)URL或者Blob創(chuàng)建一個(gè)URL
    • URL.revokeObjectURL() 銷毀之前已經(jīng)創(chuàng)建的URL實(shí)例

    那么生成的這個(gè)URL,可以被用在任何使用URL的地方,在這個(gè)例子中我們讀取一個(gè)圖片,然后將它賦值給img標(biāo)簽的src屬性,這會(huì)在你的瀏覽器中打開一張圖片.

    <!DOCTYPE html> <html><head><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><title>blob</title><meta name="viewport" content="width=device-width, initial-scale=1"> </head><body><label for="file">讀取文件<input id="file" accept="image/*" type="file" ></label><img id="img" src="" alt=""><script type="text/javascript">document.getElementById('file').addEventListener('change',(event)=>{const files = event.srcElement.files;if(files.length === 0){return console.log('沒有選擇任何內(nèi)容');}const file = files[0];document.getElementById('img').src = URL.createObjectURL(file);});</script> </body></html>

    我們的圖片被如下格式的URL所描述:

    blob:http://127.0.0.1:5500/b285f19f-a4e2-48e7-b8c8-5eae11751593

    導(dǎo)出文件實(shí)踐

    主要是利用瀏覽器在解析到MIME為application/octet-stream類型的內(nèi)容會(huì)彈出下載對(duì)話框的特性.

    我們有如下對(duì)策:

  • 創(chuàng)建一個(gè)File對(duì)象修改他的type為application/octet-stream
  • 使用這個(gè)File利用URL.createObjectURL()創(chuàng)建一個(gè)URL
  • 重定向到這個(gè)URL,讓瀏覽器自動(dòng)彈出下載框
  • constbuffer = new ArrayBuffer(1024),array = new Int8Array(buffer);array.fill(1);const blob = new Blob(array),file = new File([blob],'test.txt',{lastModified:Date.now(),type:'application/octet-stream'});saveAs(file,'test.txt')const url = window.URL.createObjectURL(file);window.location.href = url;

    上面這種方式簡(jiǎn)單粗,不過(guò)導(dǎo)出的文件你得修改文件名稱.

    我們只需要稍稍利用利用a標(biāo)簽就可以優(yōu)雅的完成這項(xiàng)任務(wù):

    constbuffer = new ArrayBuffer(1024),array = new Int8Array(buffer);array.fill(1);const blob = new Blob(array),file = new File([blob],'test.txt',{lastModified:Date.now(),type:'text/plain;charset=utf-8'});const url = window.URL.createObjectURL(file),a = document.createElement('a');a.href = url; a.download = file.name; // see https://developer.mozilla.org/zh-CN/docs/Web/HTML/Element/a#%E5%B1%9E%E6%80%A7 a.click();

    大功告成,利用HTML5的API我們終于可以愉快的在WEB上操作數(shù)據(jù)啦!

    MDN上幾篇不錯(cuò)的指引

    分別是:

    • 在web應(yīng)用程序中操作文件指南
    • JavaScript 類數(shù)組對(duì)象
    • Base64的編碼與解碼

    參考

    https://github.com/SheetJS/js...

    https://github.com/eligrey/Fi...

    總結(jié)

    以上是生活随笔為你收集整理的自底向上的web数据操作指南的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。