猿问

使用 jszip 在前端下载大量文件

无法使用 jszip 压缩所有文件。JS zip 正在从控制台从大约 143 个请求中读取所有 402 个文件,如快照所示,但仅压缩 143 个文件。我正在使用并行限制同时干净地处理多个异步请求。我是如何获得结果中的所有 403 文件?


private downloadUntouchedFiles = () => {



let requestObjectInfo = [];

let index = 0;

this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: true });



this._eligibilitySubmissionInstance.getUntouchedFiles(this.state.filterObject).then((requests) => {

  debugger;

  if (!(!requests)) {

    if (requests.length > 0) {


      var zip = new JSZip();

      var zipFileName = "ES_Unviewed_Files";

      var promises = [];

      this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: true });




      const downloadSubPromises = [];

      let i =0;

          requests.forEach((req) => {

            req.Folder.Files.forEach(f => {

              f.Name = this.state.initials + '_' + this.state.userId + '_' + f.Name;

              console.log(f.Name);

              i++;

              console.log(i);

              downloadSubPromises.push((submit: any) => {

                JSZipUtils.getBinaryContent(f.ServerRelativeUrl, (err, data) => {

                  try {

                    if (err) {

                      throw err;

                    }

在这种情况下,仅使用 JS Heap 上的 55-75MB。

繁星coding
浏览 558回答 2
2回答

神不在的星期二

您可以使用asyncandawait使代码更易于理解并避免深度嵌套:const ZIP_FILE_NAME = "ES_Unviewed_Files.zip"const downloadUntouchedFiles = async () => {&nbsp; &nbsp;&nbsp;&nbsp; &nbsp; const zip = new JSZip()&nbsp; &nbsp; const untouched = this._eligibilitySubmissionInstance.getUntouchedFiles(this.state.filterObject)&nbsp; &nbsp;&nbsp;&nbsp; &nbsp; if (!untouched?.length) return&nbsp; &nbsp; const files = untouched.reduce((acc, { Folder: { Files } }) =>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; Files.forEach(f => acc.push({ name: `${this.state.userId}+${f.Name}`, ...f })), [])&nbsp; &nbsp; const downloads = files.map(({name, ServerRelativeUrl}) =>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; async () => ({ name, data: await fetchBinary(ServerRelativeUrl)}))&nbsp; &nbsp; const responses = await batched(downloads, Constants.DOWNLOAD_BATCH_MAX_FILE_LIMIT)&nbsp; &nbsp; responses.forEach(({ status, value: { name, data } }) =>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; status === 'fulfilled' && zip.file(name, data, { binary: true }))&nbsp; &nbsp; const content = await zip.generateInternalStream({ type: "blob" }).accumulate()&nbsp; &nbsp; await saveAs(content, ZIP_FILE_NAME)&nbsp; &nbsp;&nbsp;}const fetchBinary = (file) => new Promise((resolve) =>&nbsp;&nbsp; &nbsp; JSZipUtils.getBinaryContent(url, (err, data) => err ? reject(err) : resolve(data)))async function batched(fns, batchSize = 2) {&nbsp; &nbsp; const results = []&nbsp; &nbsp;&nbsp;&nbsp; &nbsp; for(let start = 0, end = batchSize; start < fns.length; start += batchSize, end = start+batchSize) {&nbsp; &nbsp; &nbsp; &nbsp; const slice = fns.slice(start, end)&nbsp; &nbsp; &nbsp; &nbsp;&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; const promises = slice.map((fn) => fn())&nbsp; &nbsp; &nbsp; &nbsp; results.push([...await Promise.allSettled(promises)])&nbsp; &nbsp; }&nbsp; &nbsp; return results.flat()}

浮云间

这将起作用private downloadUntouchedFiles = () => {this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: true });let statusUpdatePromises = [];this._eligibilitySubmissionInstance.getUntouchedFiles(this.state.filterObject).then((requests) => {&nbsp; if (!(!requests)) {&nbsp; &nbsp; if (requests.length > 0) {&nbsp; &nbsp; &nbsp; var zip = new JSZip();&nbsp; &nbsp; &nbsp; var zipFileName = "ES_Unviewed_Files";&nbsp; &nbsp; &nbsp; const downloadSubPromises = [];&nbsp; &nbsp; &nbsp; requests.forEach((req: any) => {&nbsp; &nbsp; &nbsp; &nbsp; req.Folder.Files.forEach((f: any) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; f.Name = this.state.userId + '_' + f.Name;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; downloadSubPromises.push((submit: any) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; JSZipUtils.getBinaryContent(`${new Constants().BASE_URL}${encodeURIComponent(f.ServerRelativeUrl).replace('%2F', '/')}`, (err, data) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; try {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (err) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; submit(null, true);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } else {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; zip.file(f.Name, data, { binary: true });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; submit(null, true);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } catch (err) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: false });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this._loggerInstance.logException(Constants.SISCC_ES_EXCEPTIONS, {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Component: this._canonicalName,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Message: ErrorMessages.COM007,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; UserName: !(!DataSingleton.getCurrentUser()) ? DataSingleton.getCurrentUser() : '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Group: '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Notes: err,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Source: Constants.EXCEPTION_UI_SOURCE,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; ExceptionID: Guid.create().toString()&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } as ExceptionObject).then(() => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; submit(null, false);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; statusUpdatePromises.push((submit: any) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.setState({ requestObject: req }, () => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (this.state.requestObject.Status !== Constants.ES_DOWNLOADREQUEST_STATUS) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.updateESRequestStatus(Constants.ES_DOWNLOADREQUEST_STATUS).then(res => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; submit(true);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } else {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; submit(true);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; parallelLimit(downloadSubPromises, Constants.UPLOAD_BATCH_MAX_FILE_LIMIT,&nbsp; &nbsp; &nbsp; &nbsp; (err: any, results: any) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; parallelLimit(statusUpdatePromises, Constants.UPLOAD_BATCH_MAX_FILE_LIMIT,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; (subErr: any, subResults: any) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; try {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; zip&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .generateInternalStream({ type: "blob" })&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .accumulate()&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .then((content) => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: false });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; saveAs(content, zipFileName + ".zip");&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; catch (err) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this._eventEmitter.emit(Constants.LOADER_CHANGE, { show: false });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this._loggerInstance.logException(Constants.SISCC_ES_EXCEPTIONS, {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Component: this._canonicalName,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Message: ErrorMessages.COM007,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; UserName: !(!DataSingleton.getCurrentUser()) ? DataSingleton.getCurrentUser() : '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Group: '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Notes: err,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Source: Constants.EXCEPTION_UI_SOURCE,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; ExceptionID: Guid.create().toString()&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; } as ExceptionObject).then(() => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; &nbsp; &nbsp; });&nbsp; &nbsp; }&nbsp; }});}
随时随地看视频慕课网APP

相关分类

JavaScript
我要回答