欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

JS前端解壓zip的方法和技巧分享

 更新時間:2024年03月24日 08:52:30   作者:Senar  
這篇文章主要介紹了JS前端解壓zip的方法和技巧,業(yè)務(wù)中有時候需要獲取某個 zip 壓縮包內(nèi)的文件內(nèi)容展示到前端,在 zip 包體積不是那么大的時候并且不涉及壓縮包解密的時候,可以考慮純前端方案,需要的朋友可以參考下

業(yè)務(wù)中有時候需要獲取某個 zip 壓縮包內(nèi)的文件內(nèi)容展示到前端,在 zip 包體積不是那么大的時候(幾MB、十幾MB甚至幾十MB)并且不涉及壓縮包解密的時候,可以考慮純前端方案。

前端使用Jszip解壓zip

安裝依賴: npm i jszip

請求 zip 文件并轉(zhuǎn)為 Blob:

const blob = await fetch(url).then((res) => res.blob());

使用 jszip 解壓 Blob:

const zip = new JSZip()
const zipData = await zip.loadAsync(zipBlob)

這時候你會得到一個含有 files 列表數(shù)據(jù)的 zipData , 這個 files 就是壓縮包中的文件列表,這時候的處理就有意思了,下面慢慢說。

如果你的壓縮包里面不止一個文件怎么獲取

基于上一步,我們拿到了 files 文件列表,這時候如果我們的壓縮包里面有很多文件我們怎么全部都拿到呢?我們就需要遞歸這個列表了:

async function extractNestedZip(zipBlob: Blob) {
  const zip = new JSZip()
  const zipData = await zip.loadAsync(zipBlob)

  const extractedFiles: { name: string, data: unkown }[] = []

  // 遍歷 ZIP 文件中的所有文件
  for (const [name, file] of Object.entries(zipData.files)) {
    extractedFiles.push({name, file})
  }

  return extractedFiles
}

但是事情往往沒有這么簡單,比如壓縮包里面還有壓縮包怎么辦呢?

嵌套壓縮改咋處理

改良 extractNestedZip 方法:

async function extractNestedZip(zipBlob: Blob) {
  const zip = new JSZip()
  const zipData = await zip.loadAsync(zipBlob)

  const extractedFiles: { name: string, data: unkown }[] = []

  // 遍歷 ZIP 文件中的所有文件
  for (const [name, file] of Object.entries(zipData.files)) {
    if (name.endsWith('.zip') { // 如果是嵌套的壓縮包就繼續(xù)解壓
      const nestedZipBlob = await file.async('blob')
      const nestedFiles = await extractNestedZip(nestedZipBlob)
      extractedFiles.push(...nestedFiles)
    } else {
      extractedFiles.push({name, file})
    }
  }

  return extractedFiles
}

我們現(xiàn)在解決了嵌套的問題。如果壓縮包中有文件夾該怎么處理呢?嘗試過你會發(fā)現(xiàn)如果是文件夾,在 files 中對應(yīng)的數(shù)據(jù)就是空的,所以我們應(yīng)該過濾這種情況:

壓縮包中的文件夾要過濾

async function extractNestedZip(zipBlob: Blob) {
  const zip = new JSZip()
  const zipData = await zip.loadAsync(zipBlob)

  const extractedFiles: { name: string, data: unkown }[] = []

  // 遍歷 ZIP 文件中的所有文件
  for (const [name, file] of Object.entries(zipData.files)) {
    if (name.endsWith('.zip') { // 如果是嵌套的壓縮包就繼續(xù)解壓
      const nestedZipBlob = await file.async('blob')
      const nestedFiles = await extractNestedZip(nestedZipBlob)
      extractedFiles.push(...nestedFiles)
    } else if (!name.endsWith('/')) { // 我們可以通過判斷文件名是否以/結(jié)尾來判斷這一項是否是文件夾 
      extractedFiles.push({name, file})
    }
  }

  return extractedFiles
}

現(xiàn)在看了好像一切都沒問題了,但是我們最終的文件怎么讀到呢?

文本文件和二進制文件要分別處理

如果壓縮包中只包含文本類的文件,比如 .json,.log之類的,就可以簡單的用 file.async('text') 來獲取文件內(nèi)容,但是如果包含 .mp3,.png 就要注意了,我們接下來優(yōu)化這些情況:

async function extractNestedZip(zipBlob: Blob) {
  const zip = new JSZip()
  const zipData = await zip.loadAsync(zipBlob)

  const extractedFiles: { name: string, data: string | Blob }[] = []

  // 遍歷 ZIP 文件中的所有文件
  for (const [name, file] of Object.entries(zipData.files)) {
    if (name.endsWith('.zip')) {
      // 如果文件是嵌套的 ZIP 文件,則遞歸解壓
      const nestedZipBlob = await file.async('blob')
      const nestedFiles: { name: string, data: string | Blob }[]  = await extractNestedZip(nestedZipBlob)
      extractedFiles.push(...nestedFiles)
    }
    else {
      // 如果文件不是 ZIP 文件,則處理
      if (name.endsWith('.jpeg') || name.endsWith('.png') || name.endsWith('.mp3') || name.endsWith('.mp4')) {
        const blob = await file.async('blob')
        extractedFiles.push({ name, data: blob })
      }
      else if (!name.endsWith('/')) { // 過濾掉文件夾
        const fileData = await file.async('text')
        extractedFiles.push({ name, data: fileData })
      }
    }
  }

  return extractedFiles
}

我們這里舉了些例子,就是判斷文件名以什么結(jié)尾,如果是常見的媒體格式,就轉(zhuǎn)為 Blob,不然就轉(zhuǎn)為字符串。這個方案就可以處理壓縮包中不同格式的問題,最終我們就拿到了一個 name 是表示壓縮包中文件名稱,data 是對應(yīng)文件內(nèi)容的列表了。

總結(jié)

在業(yè)務(wù)中需要前端場景解壓壓縮包是比較少見的,但是如果有這類的場景我們就可以借助于 jszip 來做。這次分享的主要是拿到文件之后如何全部拿到壓縮包的所有內(nèi)容的技巧,大家如果有別的問題,歡迎評論區(qū)溝通。

以上就是JS前端解壓zip的方法和技巧分享的詳細內(nèi)容,更多關(guān)于JS前端解壓zip的資料請關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

最新評論