SysBackup/archiver.js

80 lines
2.1 KiB
JavaScript

/* eslint-disable require-jsdoc */
const fs = require('fs');
const path = require('path');
const {EventEmitter} = require('events');
class Archiver {
constructor(backupPath, backupPaths, gzip, gzipLevel) {
this.backupPath = backupPath;
this.backupPaths = backupPaths;
this.eventEmitter = new EventEmitter();
this.archive = require('archiver')('tar', {
gzip: gzip,
gzipOptions: {level: gzipLevel},
});
this.totalFiles = 0;
}
start() {
const EVENT_EMITTER = this.eventEmitter;
const ARCHIVE_LOCATION = path.join(this.backupPath);
const OUTPUT = fs.createWriteStream(ARCHIVE_LOCATION);
OUTPUT.on('close', function() {
EVENT_EMITTER.emit('finish');
});
OUTPUT.on('end', function() {
console.log('Data has been drained');
});
this.archive.on('warning', function(err) {
if (err.code === 'ENOENT') console.log(err);
else throw err;
});
this.archive.on('error', function(err) {
throw err;
});
this.archive.on('progress', function(progressInfo) {
EVENT_EMITTER.emit('progress', progressInfo);
});
// pipe archive data to the file
this.archive.pipe(OUTPUT);
for (const ITEM of this.backupPaths) {
if (!fs.existsSync(ITEM)) continue;
const IS_DIR = fs.lstatSync(ITEM).isDirectory();
if (IS_DIR) {
this.archive.directory(ITEM, path.basename(ITEM));
const COUNTED = require('count-files-dirs').countSync(ITEM);
this.totalFiles += COUNTED.fileCount + COUNTED.dirCount;
} else {
this.archive.file(ITEM, {name: path.basename(ITEM)});
this.totalFiles++;
}
}
}
add(item) {
if (!fs.existsSync(item)) return;
const IS_DIR = fs.lstatSync(item).isDirectory();
if (IS_DIR) {
this.archive.directory(item, path.basename(item));
const COUNTED = require('count-files-dirs').countSync(item);
this.totalFiles += COUNTED.fileCount + COUNTED.dirCount;
} else {
this.archive.file(item, {name: path.basename(item)});
this.totalFiles++;
}
}
pack() {
this.archive.finalize();
}
}
module.exports = Archiver;