Replies: 6 comments 3 replies
-
The import { zip } from 'fflate';
function createAsyncZip(data: KeyValueStoreRecord<Buffer>[]): Promise<Uint8Array> {
return new Promise((resolve, reject) => {
const toZip = {};
for (const kv of data) {
toZip[kv.key] = kv.value;
}
zip(toZip, (err, res) => err ? reject(err) : resolve(res));
});
} |
Beta Was this translation helpful? Give feedback.
-
let zipFile = new Zip() const zipStream = new Transform({
}) zipStream.on('close', () => { let dataStream = await (async () => Readable.from((await readFiles('./images')).slice(0, 2)))(); dataStream.on('close', () => { pipeline(dataStream, |
Beta Was this translation helpful? Give feedback.
-
Got it working now: |
Beta Was this translation helpful? Give feedback.
-
import { Zip, ZipPassThrough } from "fflate";
import fs, { createReadStream } from "fs";
import path from "path";
import { readdir, stat } from "fs/promises";
let readFiles = async (path = '.') => {
let folders = await readdir(path);
let filePaths: string[] = []
// Read folders
for await (const folder of folders) {
if (folder.startsWith('.'))
continue;
// Read folders within folders
await stat(`${path}/${folder}`).then(async (stats) => {
if (!stats.isDirectory())
return;
let files = await readdir(path + '/' + folder)
// Read files within folders
files.forEach(async (file) => {
filePaths.push(`${path}/${folder}/${file}`)
// console.log('>>>', file);
})
})
}
return filePaths
}
readFiles('./images').then(processFiles()).then(() => {
console.log('Done...')
})
function processFiles(): (value: string[]) => void | PromiseLike<void> {
return async (files) => {
files = files.map(file => path.resolve(file));
let zipFile = new Zip();
let zipWriteStream = fs.createWriteStream("test.zip");
zipFile.ondata = (err, chunk, final) => {
zipWriteStream.write(chunk);
if (err || final) {
return zipWriteStream.close();
}
};
files
// .slice()
.forEach(file => addToZip(file));
zipFile.end();
console.log("END ZIP");
function addToZip(file: string) {
const fileName = file.split('/').pop();
const zf = new ZipPassThrough(fileName);
zipFile.add(zf);
const fileStream = createReadStream(file);
fileStream.on('readable', () => {
let chunk = fileStream.read();
while (chunk && chunk.length) {
zf.push(chunk);
chunk = fileStream.read();
}
});
fileStream.on('end', () => {
zf.push(new Uint8Array(0), true);
});
}
};
}
Edit: Cleaned up code, removed unnecessary comments. |
Beta Was this translation helpful? Give feedback.
-
This works but there's an off by one error in it. import { Zip, ZipPassThrough } from "fflate";
import fs, { createReadStream } from "fs";
import path from "path";
import { readdir, stat } from "fs/promises";
import { chunk } from "crawlee";
let readFiles = async (path = '.') => {
let folders = await readdir(path);
let filePaths: string[] = []
// Read folders
for await (const folder of folders) {
if (folder.startsWith('.'))
continue;
// Read folders within folders
await stat(`${path}/${folder}`).then(async (stats) => {
if (!stats.isDirectory())
return;
let files = await readdir(path + '/' + folder)
// Read files within folders
files.forEach(async (file) => {
filePaths.push(`${path}/${folder}/${file}`)
// console.log('>>>', file);
})
})
}
return filePaths
}
let zipFile = new Zip(
)
zipFile.ondata = (err, chunk, final) => {
zipWriteStream.write(chunk);
if (err || final) {
zipWriteStream.close();
}
};
let zipWriteStream = fs.createWriteStream("test.zip");
let files = await readFiles('./images')
let flen = files.length;
let current = 0;
for await (const iterator of chunk(files.slice(0,500), 250)) {
console.log('PROCESSING... ' + (current += iterator.length) + ' / ' + flen);
await processFiles(iterator).catch(err => console.log(err));
}
zipFile.end();
async function processFiles(files: string[]) {
files = files.map(file => path.resolve(file));
console.log("PROCESS ID: " + process.pid);
await Promise.all(files.map(file => addToZip(file)))
.then(() => console.log('DONE'))
.catch(err => console.log(err));
async function addToZip(file: string): Promise<void> {
return new Promise<void>(async (resolve, reject) => {
const fileName = file.split('/').pop();
const zf = new ZipPassThrough(fileName);
zipFile.add(zf);
const fileStream = createReadStream(file);
fileStream.on('readable', () => {
let chunk = fileStream.read();
while (chunk !== undefined && chunk !== null && chunk.length) {
zf.push(chunk);
chunk = fileStream.read();
}
});
fileStream.on('end', () => {
zf.push(new Uint8Array(0), true);
fileStream.close();
console.log('File added: ' + fileName);
resolve();
});
})
};
} |
Beta Was this translation helpful? Give feedback.
-
For some reason I am missing the last file compressed. I get 49 instead of 50. |
Beta Was this translation helpful? Give feedback.
-
I wrote this function to compress files
Whenever I run this, the files get added, the callback gets called twice then never again. When it is called, the
final
parameter is always false. I looked at the example and found this:Beta Was this translation helpful? Give feedback.
All reactions