mirror of
https://github.com/Zagrios/bs-manager.git
synced 2026-07-03 14:08:25 +02:00
[chore] removed jszip and node-stream-zip packages
This commit is contained in:
Generated
+6
-13
@@ -32,11 +32,9 @@
|
||||
"got": "^14.4.4",
|
||||
"history": "^5.3.0",
|
||||
"is-elevated": "^4.0.0",
|
||||
"jszip": "^3.10.1",
|
||||
"md5-file": "^5.0.0",
|
||||
"node-abi": "^3.65.0",
|
||||
"node-fetch": "^3.3.2",
|
||||
"node-stream-zip": "^1.15.0",
|
||||
"pako": "^2.1.0",
|
||||
"protobufjs": "^7.4.0",
|
||||
"qrcode.react": "^4.0.1",
|
||||
@@ -13897,6 +13895,7 @@
|
||||
},
|
||||
"node_modules/immediate": {
|
||||
"version": "3.0.6",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/immutable": {
|
||||
@@ -15813,6 +15812,7 @@
|
||||
},
|
||||
"node_modules/jszip": {
|
||||
"version": "3.10.1",
|
||||
"dev": true,
|
||||
"license": "(MIT OR GPL-3.0-or-later)",
|
||||
"dependencies": {
|
||||
"lie": "~3.3.0",
|
||||
@@ -15823,10 +15823,12 @@
|
||||
},
|
||||
"node_modules/jszip/node_modules/pako": {
|
||||
"version": "1.0.11",
|
||||
"dev": true,
|
||||
"license": "(MIT AND Zlib)"
|
||||
},
|
||||
"node_modules/jszip/node_modules/readable-stream": {
|
||||
"version": "2.3.7",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"core-util-is": "~1.0.0",
|
||||
@@ -15944,6 +15946,7 @@
|
||||
},
|
||||
"node_modules/lie": {
|
||||
"version": "3.3.0",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"immediate": "~3.0.5"
|
||||
@@ -17230,17 +17233,6 @@
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/node-stream-zip": {
|
||||
"version": "1.15.0",
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
"node": ">=0.12.0"
|
||||
},
|
||||
"funding": {
|
||||
"type": "github",
|
||||
"url": "https://github.com/sponsors/antelle"
|
||||
}
|
||||
},
|
||||
"node_modules/nopt": {
|
||||
"version": "6.0.0",
|
||||
"dev": true,
|
||||
@@ -20047,6 +20039,7 @@
|
||||
},
|
||||
"node_modules/setimmediate": {
|
||||
"version": "1.0.5",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/setprototypeof": {
|
||||
|
||||
@@ -225,11 +225,9 @@
|
||||
"got": "^14.4.4",
|
||||
"history": "^5.3.0",
|
||||
"is-elevated": "^4.0.0",
|
||||
"jszip": "^3.10.1",
|
||||
"md5-file": "^5.0.0",
|
||||
"node-abi": "^3.65.0",
|
||||
"node-fetch": "^3.3.2",
|
||||
"node-stream-zip": "^1.15.0",
|
||||
"pako": "^2.1.0",
|
||||
"protobufjs": "^7.4.0",
|
||||
"qrcode.react": "^4.0.1",
|
||||
|
||||
@@ -23,6 +23,8 @@ export interface ZipExtractOptions {
|
||||
};
|
||||
|
||||
export interface ZipProcessOptions {
|
||||
// Stops the extraction immediately when set to true
|
||||
terminate?: (entry: ZipEntry) => boolean;
|
||||
getBuffer?: boolean;
|
||||
};
|
||||
|
||||
@@ -96,7 +98,8 @@ function handleExtractZip(
|
||||
zipEntry.buffer = undefined;
|
||||
|
||||
if (options?.terminate?.(zipEntry)) {
|
||||
return readStream.destroy();
|
||||
readStream.destroy();
|
||||
return zip.close();
|
||||
}
|
||||
|
||||
if (options?.condition) {
|
||||
@@ -129,23 +132,28 @@ function handleExtractZip(
|
||||
|
||||
// @params loop - this should not throw an error
|
||||
export function processZip<T>(
|
||||
zipPath: string,
|
||||
data: string | Buffer,
|
||||
options: Readonly<ZipProcessOptions>,
|
||||
loop: (accumulator: T, entry: ZipEntry) => T,
|
||||
initValue: T
|
||||
): Promise<T> {
|
||||
return new Promise((resolve, reject) => {
|
||||
yauzl.open(zipPath, {
|
||||
lazyEntries: true,
|
||||
decodeStrings: true,
|
||||
},
|
||||
(openError, zip) => {
|
||||
const callback = (openError: Error, zip: yauzl.ZipFile) => {
|
||||
if (openError) return reject(openError);
|
||||
handleProcessZip<T>(
|
||||
zip, options, loop, initValue,
|
||||
resolve, reject
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
if (typeof data === "string") {
|
||||
yauzl.open(data, {
|
||||
lazyEntries: true,
|
||||
decodeStrings: true,
|
||||
}, callback);
|
||||
} else {
|
||||
yauzl.fromBuffer(data, callback);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@@ -177,14 +185,21 @@ async function handleProcessZip<T>(
|
||||
zip.openReadStream(entry, (readError, readStream) => {
|
||||
if (readError) return reject(readError);
|
||||
|
||||
zipEntry.name = entry.fileName;
|
||||
zipEntry.directory = false;
|
||||
zipEntry.buffer = undefined;
|
||||
if (options?.terminate?.(zipEntry)) {
|
||||
readStream.destroy();
|
||||
zip.close();
|
||||
return;
|
||||
}
|
||||
|
||||
const chunks: Buffer[] = [];
|
||||
readStream.on("data", data => {
|
||||
chunks.push(data);
|
||||
});
|
||||
|
||||
readStream.on("end", () => {
|
||||
zipEntry.name = entry.fileName;
|
||||
zipEntry.directory = false;
|
||||
zipEntry.buffer = Buffer.concat(chunks);
|
||||
accumulator = loop(accumulator, zipEntry);
|
||||
zip.readEntry();
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
import JSZip from "jszip";
|
||||
import fetch from "node-fetch";
|
||||
import { CustomError } from "../../shared/models/exceptions/custom-error.class";
|
||||
import { mkdirs, createWriteStream, pathExists, WriteStream } from "fs-extra";
|
||||
@@ -7,6 +6,7 @@ import { inflate } from "pako"
|
||||
import { EMPTY, Observable, ReplaySubject, Subscriber, catchError, filter, from, lastValueFrom, mergeMap, scan, share, tap } from "rxjs";
|
||||
import { Progression, hashFile } from "../helpers/fs.helpers";
|
||||
import { OculusDownloaderErrorCodes } from "../../shared/models/bs-version-download/oculus-download.model";
|
||||
import { processZip } from "main/helpers/zip.helpers";
|
||||
|
||||
export class OculusDownloader {
|
||||
|
||||
@@ -23,26 +23,40 @@ export class OculusDownloader {
|
||||
return `https://securecdn.oculus.com/binaries/segment/?access_token=${token}&binary_id=${binaryId}&segment_sha256=${segmentSha256}`;
|
||||
}
|
||||
|
||||
private async downloadManifestZip(manifestUrl: string): Promise<JSZip> {
|
||||
private async downloadManifestZip(manifestUrl: string): Promise<Buffer> {
|
||||
const response = await fetch(manifestUrl);
|
||||
const arrBuffer = await response.arrayBuffer();
|
||||
return JSZip.loadAsync(arrBuffer);
|
||||
return Buffer.from(arrBuffer);
|
||||
}
|
||||
|
||||
private async getManifest(): Promise<OculusManifest> {
|
||||
const downloadUrl = this.getDownloadManifestUrl(this.options.accessToken, this.options.binaryId);
|
||||
const manifestZip = await this.downloadManifestZip(downloadUrl).catch(err => CustomError.throw(err, "DOWNLOAD_MANIFEST_FAILED"));
|
||||
const manifestFile = manifestZip.file("manifest.json");
|
||||
const buffer = await this.downloadManifestZip(downloadUrl)
|
||||
.catch(err => CustomError.throw(err, "DOWNLOAD_MANIFEST_FAILED"));
|
||||
|
||||
if(!manifestFile){
|
||||
let found = false;
|
||||
let manifestString: string | null = null;
|
||||
|
||||
// NOTE: Might be better to do get file in zip.helpers
|
||||
await processZip(buffer, {
|
||||
terminate: () => found,
|
||||
getBuffer: true,
|
||||
}, (_, entry): void => {
|
||||
if (entry.name !== "manifest.json") return;
|
||||
found = true;
|
||||
manifestString = entry.buffer.toString();
|
||||
}, undefined);
|
||||
|
||||
if(!manifestString) {
|
||||
throw new CustomError("Manifest file not found", "MANIFEST_FILE_NOT_FOUND");
|
||||
}
|
||||
|
||||
return manifestFile.async("text").then(JSON.parse).catch(err => CustomError.throw(err, "PARSE_MANIFEST_FILE_FAILED"));
|
||||
return JSON.parse(manifestString)
|
||||
.catch((err: Error) => CustomError.throw(err, "PARSE_MANIFEST_FILE_FAILED"));
|
||||
}
|
||||
|
||||
private downloadManifestFile(file: OculusManifestFile, destination: string): Observable<Progression<OculusManifestFile>> {
|
||||
|
||||
|
||||
const downloadSegment = async (segment: OculusManifestFileSegment): Promise<ArrayBuffer> => {
|
||||
const segmentUrl = this.getDownloadSegmentUrl(this.options.accessToken, this.options.binaryId, segment[1]);
|
||||
const response = await fetch(segmentUrl);
|
||||
@@ -66,11 +80,11 @@ export class OculusDownloader {
|
||||
|
||||
const arrBuffer = await downloadSegment(segment);
|
||||
const inflated = inflate(arrBuffer);
|
||||
await writeStream.write(inflated);
|
||||
writeStream.write(inflated);
|
||||
|
||||
progress.current += inflated.byteLength;
|
||||
progress.diff = inflated.byteLength;
|
||||
|
||||
|
||||
sub.next(progress);
|
||||
}
|
||||
|
||||
@@ -86,7 +100,7 @@ export class OculusDownloader {
|
||||
});
|
||||
}
|
||||
|
||||
private isFileIntegrityValid(file: OculusFileWithName, folder: string): Promise<boolean> {
|
||||
private async isFileIntegrityValid(file: OculusFileWithName, folder: string): Promise<boolean> {
|
||||
const [fileName, fileData] = file;
|
||||
const destination = path.join(folder, fileName);
|
||||
|
||||
@@ -138,7 +152,7 @@ export class OculusDownloader {
|
||||
if(this.isDownloading){
|
||||
throw new CustomError("Already downloading", "ALREADY_DOWNLOADING");
|
||||
}
|
||||
|
||||
|
||||
this.options = options;
|
||||
this.isDownloading = true;
|
||||
|
||||
@@ -182,7 +196,7 @@ export class OculusDownloader {
|
||||
})));
|
||||
|
||||
const integrity = await lastValueFrom(this.verifyIntegrity(manifest, options.destination)).catch(err => CustomError.throw(err, "VERIFY_INTEGRITY_FAILED"));
|
||||
|
||||
|
||||
if(integrity.data.length > 0){
|
||||
throw new CustomError("Some files failed to download", "SOME_FILES_FAILED_TO_DOWNLOAD", integrity.data);
|
||||
}
|
||||
@@ -242,4 +256,4 @@ interface Logger {
|
||||
info: (...args: unknown[]) => void;
|
||||
warn: (...args: unknown[]) => void;
|
||||
error: (...args: unknown[]) => void;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user