You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

求助:实现与命令行一致的TS/JS tar.gz解压工具,解压结果不匹配

问题:JavaScript解压tar.gz文件与命令行结果不一致

我需要开发一个与命令行效果完全一致的TypeScript(或JavaScript)tar.gz解压工具,但目前遇到解压结果与原文件不匹配的问题:在MacOS命令行使用tar -xzvf解压由Python代码压缩后上传至S3的tar.gz文件时,能得到与原文件大小一致的结果;但在JavaScript中尝试tar-stream、tar、Pako等多种工具时,解压出的文件大小均存在偏差(所有小于10240字节的文件会变为10240字节,部分大文件偏差约50%)。

示例文件:email.zkeyd.tar.gz

可行的非压缩文件处理代码

const store = async function (filename: string) {
  const link = "https://zkemail-zkey-chunks.s3.amazonaws.com/email.zkeyd";
  const resp = await fetch(link, {
    method: "GET",
  });
  const zkeyBuff = await resp.arrayBuffer(); 
  await localforage.setItem(filename, zkeyBuff);
}

有问题的tar.gz处理代码

// Un-targz the arrayBuffer into the filename without the .tar.gz on the end
const uncompressAndStore = async function (filename: string) {
  const link = "https://zkemail-zkey-chunks.s3.amazonaws.com/email.zkeyd.tar.gz";
  const resp = await fetch(link, {
    method: "GET",
  });
  const zkeyBuff = await resp.arrayBuffer(); 
  
  console.log(`Started to uncompress ${filename}...!`);
  const extract = tar.extract() // create a tar extract stream
  const gunzip = zlib.createGunzip(zkeyBuff) // create a gunzip stream from the array buffer
  gunzip.pipe(extract) // pipe the gunzip stream into the tar extract stream

  // header is the tar header, stream is the content body (might be an empty stream), call next when you are done with this entry
  extract.on('entry', function(header: any, stream: any, next: Function) {
    // decompress the entry data
    const extractedData: any = []
    stream.on('data', function(chunk: any) {
      extractedData.push(chunk)
    })

    // make sure to call next when the entry is fully processed
    stream.on('end', function() {
      next()

      console.assert(filename.endsWith(zkeyExtension), `Filename doesn't end in ${zkeyExtension}`)
      const rawFilename = filename.replace(/.tar.gz$/, "");
      // save the extracted data to localForage
      localforage.setItem(rawFilename, extractedData, function(err: Error) {
        if (err) {
          console.error(`Couldn't extract data from ${filename}:` + err.message)
        } else {
          console.log('Saved extracted file to localForage')
        }
      })
    })
  })

  // all entries have been processed
  extract.on('finish', function() {
    console.log(`Finished extracting ${filename}`)
  })
}

Python压缩上传代码

import boto3
import os
import tarfile

s3 = boto3.client('s3')  # Ask Aayush for the access key and secret access key

def upload_to_s3(filename, dir=""):
    with open(dir + filename, 'rb') as file:
        print("Starting upload...")
        s3.upload_fileobj(file, bucket_name, filename, ExtraArgs={
                          'ACL': 'public-read', 'ContentType': 'binary/octet-stream'})
        print("Done uploading!")


file = "..."
# Create a zip file for the file
tar_file_name = file + '.tar.gz'
with tarfile.open(tar_file_name, 'w:gz') as tar_file:
    source_file_path = dir + file
    print("Compressing: ", source_file_path)
    tar_file.add(source_file_path, arcname=os.path.basename(source_file_path))

# Upload the zip file to the AWS bucket, overwriting any existing file with the same name
upload_to_s3(tar_file_name)

内容的提问来源于stack exchange,提问作者John Targaryen

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 22:45:33