|
// C:\Users\Stefan\AppData\Local\Packages\Microsoft.Lovika_8wekyb3d8bbwe\LocalCache\Local\Dungeons |
|
const fs = require('fs'); |
|
const path = require('path'); |
|
const assert = require('assert'); |
|
|
|
const [toWatch, toBackup] = process.argv.slice(2); |
|
|
|
assert(fs.existsSync(toWatch), `cannot find dir ${toWatch}`); |
|
assert(fs.existsSync(toBackup), `cannot find backup dir ${toBackup}`); |
|
|
|
console.log('\n\n\n\n'); |
|
console.log('stating watcher for', toWatch); |
|
console.log('will backup to', toBackup); |
|
|
|
const watcher = fs.watch(toWatch, {recursive: true}); |
|
|
|
watcher.on('change', (event, path) => event === 'change' && backup()); |
|
|
|
|
|
const BACKUP_THROTTLE_TIME = 1 * 60 * 1000; |
|
let lastBackup = 0; |
|
let postPoneTimer = null; |
|
|
|
function backup() { |
|
const now = new Date(); |
|
console.log('\n'); |
|
console.log('~~~~~', now.toString(), '~~~~~'); |
|
|
|
if(lastBackup + BACKUP_THROTTLE_TIME > now.getTime()){ |
|
console.log('backup postponed, last backup was too close'); |
|
|
|
if(!postPoneTimer){ |
|
postPoneTimer = setTimeout(() => { |
|
console.log('\n\n\n\n ~~~~ retrying postponed backup... ~~~~~'); |
|
postPoneTimer = null; |
|
backup(); |
|
}, BACKUP_THROTTLE_TIME + 1000); |
|
} |
|
return; |
|
} |
|
|
|
lastBackup = now.getTime(); |
|
|
|
const dirToBackupTo = path.join(toBackup, `${now.getFullYear()}-${pad2(now.getMonth())}-${pad2(now.getDate())}-${pad2(now.getHours())}-${pad2(now.getMinutes())}-${pad2(now.getSeconds())}-${Date.now()}`); |
|
|
|
|
|
console.log('backing up:', toWatch, 'to:', dirToBackupTo); |
|
fs.mkdirSync(dirToBackupTo); |
|
copyFolderRecursiveSync(toWatch, dirToBackupTo); |
|
console.log('\n'); |
|
} |
|
backup(); |
|
|
|
function copyFileSync(source, target) { |
|
|
|
let targetFile = target; |
|
|
|
//if target is a directory a new file with the same name will be created |
|
if (fs.existsSync(target)) { |
|
if (fs.lstatSync(target).isDirectory() ) { |
|
targetFile = path.join(target, path.basename(source)); |
|
} |
|
} |
|
|
|
fs.copyFileSync(source, targetFile); |
|
} |
|
|
|
function copyFolderRecursiveSync(source, target) { |
|
|
|
console.group(); |
|
//check if folder needs to be created or integrated |
|
const targetFolder = path.join(target, path.basename(source)); |
|
if (!fs.existsSync(targetFolder)) { |
|
//console.log('mkdir', targetFolder); |
|
fs.mkdirSync(targetFolder); |
|
} |
|
|
|
//copy |
|
if (fs.lstatSync(source).isDirectory()) { |
|
const files = fs.readdirSync(source); |
|
files.forEach( file => { |
|
const curSource = path.join(source, file); |
|
if (fs.lstatSync(curSource).isDirectory()) { |
|
copyFolderRecursiveSync(curSource, targetFolder); |
|
} else { |
|
//console.log('copy', curSource, '->', targetFolder); |
|
copyFileSync(curSource, targetFolder); |
|
} |
|
}); |
|
} |
|
console.groupEnd(); |
|
} |
|
|
|
function pad2(x) { |
|
return x > 9 ? x : `0${x}`; |
|
} |