How to unzip file with Node.js - javascript

I need to zip and unzip file with Node.js but I have a problem.
const fs = require("fs");
const zlib = require('zlib');
function UnZip(zip, paths) {
var inp = fs.createReadStream("f:/test.zip");
var Exzip = zlib.createUnzip();
inp.pipe(Exzip).pipe("f:/");
}
Error:
TypeError: dest.on is not a function

Here is how you can do it with zlib module.
const fs = require('fs');
const zlib = require('zlib');
const fileContents = fs.createReadStream('file1.txt.gz');
const writeStream = fs.createWriteStream('file1.txt');
const unzip = zlib.createGunzip();
fileContents.pipe(unzip).pipe(writeStream);

Zipping the file
const archiver = require('archiver'),
archive = archiver('zip'),
fs = require('fs'),
output = fs.createWriteStream( 'mocks.zip');
archive.pipe(output);
// temp.txt file must be available in your folder where you
// are writting the code or you can give the whole path
const file_buffer = fs.readFileSync('temp.txt')
archive.append(file_buffer, { name: 'tttt.txt'});
archive.finalize().then((err, bytes) => {
if (err) {
throw err;
}
console.log(err + bytes + ' total bytes');
});
unzipping a file
const unzip = require('unzip'),
fs = require('fs');
fs.createReadStream('temp1.zip').pipe(unzip.Extract({ path: 'path' }))

Related

create json object from csv file data coming as buffer in request in node js

I'm processing csv file data coming from request to create json object using multer,csv-parser. but can't process from long time. please help and thanks.following is example of csv file processing.
const multer = require('multer');
const fs = require('fs')
const csv = require('csv-parser')
const fileStorageEngine = multer.memoryStorage({
destination: (req, file, cb) => {
cb(null, './csv');
}
,
filename: (req, file, cb) => {
cb(null, file.originalname);
},
});
const upload = multer({storage:fileStorageEngine});
app.post('/uploadcsv',upload.single("upfile"),async(req,res)=>{
const file = req.file;
fs.createReadStream(`./csv/${file.originalname}`)
.pipe(csv())
.on("data",(data)=>console.log(data));
res.send("file uploaded")
})
here I'm using fs module that works for me but I don't want to store data in file instead I want to process buffer data coming from req.file.buffer in chunk
I'm stuck here please help. because storing file and reading same file getting process slow because csv file have thousands of data.
The idea is to create a readable stream from the buffer instead of writing it to the file as follows:
const multer = require('multer');
const { Readable } = require('stream');
const fs = require('fs')
const csv = require('csv-parser')
const fileStorageEngine = multer.memoryStorage({
destination: (req, file, cb) => {
cb(null, './csv');
}
,
filename: (req, file, cb) => {
cb(null, file.originalname);
},
});
const upload = multer({storage:fileStorageEngine});
app.post('/uploadcsv',upload.single("upfile"),async(req,res)=>{
const file = req.file;
const stream = Readable.from(file.buffer);
stream.pipe(csv()).on("data",(data)=>console.log(data));
res.send("file uploaded")
})

How to download a file with nodeJS

I want to download an image file with nodeJS, by using an API, but the problem is the API link doesn't have .jpg file in the end, how do I do,
below is how I am trying
url = 'https://i.pravatar.cc/225'
const https = require('https')
const fs = require('fs');
result = https.get(url, (resp) => {
console.log('Result of response: ', resp)
fs.writeFileSync('apiResponse', resp)
console.log('Reached end!')
})
When I click the URL it shows the image in browser, how do make my program to write the file on hard-drive,
This code uploads several different pictures
const url = 'https://i.pravatar.cc/225'
const https = require('https')
const fs = require('fs');
for(let i=0; i<10; i++)
https.get(url, resp => resp.pipe(fs.createWriteStream(`./test_${i}.jpeg`)));
Just pipe response to file
const url = 'https://i.pravatar.cc/225'
const https = require('https')
const fs = require('fs');
https.get(url, resp => resp.pipe(fs.createWriteStream('./test.jpeg')));
please use this I have try with it and working fine you can rename the downloded file too.
const https = require("https");
const fs = require("fs");
const file = fs.createWriteStream("file.jpg");
const request = https.get("https://i.pravatar.cc/225", function(response) {
response.pipe(file);
});
Try download-file library
https://www.npmjs.com/package/download-file
Install : npm install download-file --save
var download = require('download-file')
var url = "http://i.imgur.com/G9bDaPH.jpg"
var options = {
directory: "./images/cats/",
filename: "cat.gif"
}
download(url, options, function(err){
if (err) throw err
console.log("meow")
})

How to run(sync) multiple .js files from a directory

I'm trying to run multiple .js files from a directory:
exampleDir/test.js
console.log('hi');
run.js
const fs = require('fs');
const {execFileSync} = require('child_process');
const testsFolder = './exampleDir/';
const files = fs.readdirSync(testsFolder);
const funcs = files.map(function(file) {
const out = execFileSync(`node ${testsFolder}${file}`);
console.log(out.toString());
});
however I get:
> example#1.0.0 test /home/perdugames/example
> node ./run.js
child_process.js:624
throw err;
^
Error: spawnSync node ./exampleDir/test.js ENOENT
...
File paths should be specified unambiguously, preferably independent of current working directory and relative to current module. To create a new Node process, there are spawn and spawnSync in child_process:
...
const path = require('path');
const testsFolder = path.join(__dirname, './exampleDir/');
const files = fs.readdirSync(testsFolder);
const funcs = files.map(function(file) {
const filePath = path.join(testsFolder, file);
const out = spawnSync(filePath);
console.log(out.stdout.toString());
});

Write file to directory then zip directory

I am trying to write a file to a directory templates then stream a zip with the content that was written. However, the when the zip file is returned it says Failed - Network Error which is due to the fs.writeFile in the controller. If i remove the WriteFile stream then the zipping works fine. My question is how do i first write the file then run the zip. There seems to be something synchronous happening with the archiving and file writing of typeArrayString.
Controller:
exports.download_one_feed = function(req, res, next) {
Feed.findOne({'name': req.params.id})
.exec(function(err, dbfeeds){
if(err){
res.send('get error has occured in routes/feeds.js');
} else {
const feedArray = dbfeeds.feed.data;
// write file
// get from db collection & write file to download
const typeArrayString = JSON.stringify(feedArray);
let type = 'b'; // test only
fs.writeFile(path.join(appDir, 'templates/' + type + '/template.json'), typeArrayString, (err) => {
if (err) throw err;
console.log('Saved!');
})
archiverService.FileArchiver(feedArray, res);
}
})
};
Archive Service
const archiver = require('archiver')
const zip = archiver('zip')
const path = require('path')
const fs = require('fs')
const appDir = path.dirname(require.main.filename)
exports.FileArchiver = function (feedArray, res) {
// const app = this.app;
const uploadsDir = path.join(appDir, '/uploads/');
const templatesDir = path.join(appDir, '/templates/');
const extensions = [".jpg", ".png", ".svg"];
let imageArray = [];
const feedArrayObject = JSON.parse(feedArrayString);
feedArrayObject.forEach(function(x){iterate(x)}); // grab image names from object
imageArray = uniq_fast(imageArray); // remove duplicates
// zip images
for (let i = 0; i < imageArray.length; i++) {
console.log(imageArray[i])
const filePath = path.join(uploadsDir, imageArray[i]);
zip.append(fs.createReadStream(filePath), { name: 'images/'+imageArray[i] });
}
res.attachment('download.zip');
zip.pipe(res);
// zip template directory
console.log(templatesDir)
zip.directory(templatesDir, false);
zip.on('error', (err) => { throw err; });
zip.finalize();
return this;
}
Instead of writing the file then zipping the directory, i used zip.append to override the old file in the directory.

nodejs load file

I want to load test.txt with nodejs.
var fs = require('fs');
fs.readFile('./test.txt', function (err, data) {
if (err) {
throw err;
}
console.log(data);
});
The path of the server is C:\server\test\server.js. The test.txt is located in the same directory, but I get this error: Error: ENOENT, no such file or directory 'C:\Users\User\test.txt'
Paths in Node are resolved relatively to the current working directory. Prefix your path with __dirname to resolve the path to the location of your Node script.
var fs = require('fs');
fs.readFile( __dirname + '/test.txt', function (err, data) {
if (err) {
throw err;
}
console.log(data.toString());
});
With Node 0.12, it's possible to do this synchronously now:
var fs = require('fs');
var path = require('path');
// Buffer mydata
var BUFFER = bufferFile('../test.txt');
function bufferFile(relPath) {
return fs.readFileSync(path.join(__dirname, relPath)); // zzzz....
}
fs is the file system. readFileSync() returns a Buffer, or string if you ask.
fs correctly assumes relative paths are a security issue. path is a work-around.
To load as a string, specify the encoding:
return fs.readFileSync(path,{ encoding: 'utf8' });
You should use __dirname to get the directory name the file is located instead of the current working directory:
fs.readFile(__dirname + "/test.txt", ...);
Use path and fs:
const fs = require("fs");
const pth = require("path");
Sync:
let data = fs.readFileSync(pth.join(__dirname,"file.txt"));
console.log(data + "");
A-Sync:
fs.readFile(pth.join(__dirname,"file.txt"), (err, data) => {
console.log(data + "");
});
And that; If you need to read the file continuously and send it to the client and the file size is not large, you may be able to keep a copy of it:
const exp = require("express");
const app = exp();
const fs = require("fs");
const pth = require("path");
let file = "";
app.get("/file", (q, r) => {
if (file === "")
file = fs.readFileSync(pth.join(__dirname,"file.txt")) + "";
r.writeHead(200, { "Content-Type": "text/plain" });
r.write(file);
r.end();
});
so if it is in the same directory just do this
fs.readFile(__dirname+'/foo.txt',function(e,d){console.log(d)})
If it's in same directory it should work. I have tested with the same code, with a file name.txt and it's working fine:
var fs = require('fs');
fs.readFile('./test.txt', function (err, data) {
if (err) {
throw err;
}
console.log(data.toString());
});

Categories