Moved file functions to internal lib with some tests as well

This commit is contained in:
Danielv123 committed 2017-05-21 22:00:30 +02:00
1 parent d9e897836b
commit 5f3a160b75
7 files changed
+218 -60

No files matched your search

+9 -56
View File
@@ -10,7 +10,10 @@ var Rcon = require('simple-rcon');
var hashFiles = require('hash-files');
var _ = require('underscore');
// internal libraries
var libomega = require("./lib/libomega.js");
var fileOps = require("./lib/fileOps.js");
// require config.json
var config = require('./config');
var global = {};
@@ -29,21 +32,6 @@ const instancedirectory = './instances/' + instance;
const command = process.argv[2];
var instanceInfo = {};
// Functions
function deleteFolderRecursive(path) {
if (fs.existsSync(path)) {
fs.readdirSync(path).forEach(function (file, index) {
var curPath = path + "/" + file;
if (fs.lstatSync(curPath).isDirectory()) { // recurse
deleteFolderRecursive(curPath);
} else { // delete file
fs.unlinkSync(curPath);
}
});
fs.rmdirSync(path);
}
};
// simple string hasher
String.prototype.hashCode = function () {
var hash = 0;
@@ -94,14 +82,14 @@ if (!command || command == "help" || command == "--help") {
console.error("node client.js download");
process.exit(1);
} else if (command == "list") {
console.dir(getDirectories("./instances/"));
console.dir(fileOps.getDirectories("./instances/"));
process.exit(1);
} else if (command == "delete") {
if (!process.argv[3]) {
console.error("Usage: node client.js delete [instance]");
process.exit(1);
} else if (typeof process.argv[3] == "string" && fs.existsSync("./instances/" + process.argv[3]) && process.argv[3] != "/" && process.argv[3] != "") {
deleteFolderRecursive("./instances/" + process.argv[3]);
fileOps.deleteFolderRecursive("./instances/" + process.argv[3]);
console.log("Deleted instance " + process.argv[3]);
process.exit(1);
} else {
@@ -228,7 +216,7 @@ write-data=__PATH__executable__/../../../instances/" + instance + "\r\n\
// Spawn factorio server
//var serverprocess = child_process.exec(commandline);
getNewestFile(instancedirectory + "/saves/", fs.readdirSync(instancedirectory + "/saves/"),function(latestSave) {
fileOps.getNewestFile(instancedirectory + "/saves/", fs.readdirSync(instancedirectory + "/saves/"),function(latestSave) {
// implicit global
serverprocess = child_process.spawn(
'./' + config.factorioDirectory + '/bin/x64/factorio', [
@@ -307,11 +295,13 @@ write-data=__PATH__executable__/../../../instances/" + instance + "\r\n\
lastSignalCheck = Date.now();
});
}
// ensure instancemanagement only runs once
_.once(instanceManagement);
function instanceManagement() {
console.log("Started instanceManagement();");
// load plugins and execute onLoad event
let pluginDirectories = getDirectories("./sharedPlugins/");
let pluginDirectories = fileOps.getDirectories("./sharedPlugins/");
let plugins = [];
for(i=0; i<pluginDirectories.length; i++) {
let I = i
@@ -674,13 +664,6 @@ function instanceManagement() {
}, 1000);
} // END OF INSTANCE START ---------------------------------------------------------------------
// get all directories in folder
function getDirectories(srcpath) {
return fs.readdirSync(srcpath).filter(function (file) {
return fs.statSync(path.join(srcpath, file)).isDirectory();
});
}
// string, function
// returns [{modName:string,hash:string}, ... ]
function hashMods(instanceName, callback) {
@@ -725,33 +708,3 @@ function hashMods(instanceName, callback) {
});
}
}
// gets newest file in a directory
// dir is directory
// files is array of filenames
// callback(filename string);
function getNewestFile(dir, files, callback) {
if (!callback) return;
if (!files || (files && files.length === 0)) {
callback();
}
var newest = { file: files[0] };
var checked = 0;
fs.stat(dir + newest.file, function(err, stats) {
newest.mtime = stats.mtime;
for (var i = 0; i < files.length; i++) {
var file = files[i];
(function(file) {
fs.stat(file, function(err, stats) {
++checked;
if (stats.mtime.getTime() > newest.mtime.getTime()) {
newest = { file : file, mtime : stats.mtime };
}
if (checked == files.length) {
callback(newest);
}
});
})(dir + file);
}
});
}
+94
View File
@@ -0,0 +1,94 @@
{"name":"combat-shotgun","count":"1","_id":"01jLIbbQ2ZXo8xet"}
{"name":"crude-oil","count":3399414,"_id":"0z6ahVSklQcCuOmf"}
{"name":"sulfur","count":1032,"_id":"23SHYRpD6xVRNhaO"}
{"name":"science-pack-3","count":5002,"_id":"25wXED3PWYD9qk2r"}
{"name":"copper-plate","count":6144494,"_id":"2CawU9P5jgZHHiUU"}
{"name":"copper-ore","count":"102","_id":"2DYQES3PaVPuYyal"}
{"name":"stone","count":28,"_id":"2aCh9XADK403IjMu"}
{"name":"battery","count":53293,"_id":"4wzpuWq4UJGgGB0w"}
{"name":"substation","count":1035,"_id":"6EvWa5sr7aOfsOmh"}
{"name":"storage-tank","count":"4","_id":"6L8D2UUQGpqoeSyV"}
{"name":"small-pump","count":250,"_id":"6Y5Gdm7fANYWCK4S"}
{"name":"energy-shield-mk2-equipment","count":26,"_id":"7uV1wOd6YpP6YBg6"}
{"name":"pipe-to-ground","count":100,"_id":"9QP4hAy3sJkpDCrZ"}
{"name":"pipe","count":1004,"_id":"AHkpkp67PHoT2Ip8"}
{"name":"fast-inserter","count":"132","_id":"ALVxvbF1YpOzGQSI"}
{"name":"solid-fuel","count":70,"_id":"APqiAHT3a3sJRF7U"}
{"name":"chemical-plant","count":501,"_id":"CGwD3PkkPMqsCQBJ"}
{"name":"splitter","count":1008,"_id":"D6pu2w2C3tEpJSrY"}
{"name":"rail","count":2504,"_id":"DOIN6qxET53zLjAR"}
{"name":"small-electric-pole","count":55,"_id":"Dy4cKwfZtwB2pjeF"}
{"name":"battery-mk2-equipment","count":27,"_id":"E84qUcptl6eH4D14"}
{"name":"cargo-wagon","count":21,"_id":"EWkaGca01NYDnyrt"}
{"name":"steel-plate","count":1594404,"_id":"F5wIdk2J2O5Jfp64"}
{"name":"science-pack-2","count":108672,"_id":"HkKc8AFK9INvlxnD"}
{"name":"green-wire","count":"36","_id":"HoIHkVMIMSMXlfPW"}
{"name":"beacon","count":"10","_id":"ImP3SlS0bfO8kaip"}
{"name":"fusion-reactor-equipment","count":7,"_id":"JynGGRC3wgbjG1xK"}
{"name":"big-electric-pole","count":1005,"_id":"KvOb3foDB5Px2jCL"}
{"name":"solar-panel","count":1023,"_id":"LQ70r6rrvPQ1twsB"}
{"name":"productivity-module-2","count":254,"_id":"LWmYiJ4zAOcdEgRY"}
{"name":"science-pack-1","count":139816,"_id":"LXBJ6Ns3IvDtBq5Y"}
{"name":"advanced-circuit","count":645071,"_id":"LdCXjtKXYPpmmLJf"}
{"name":"electric-mining-drill","count":509,"_id":"MC0sUIbd4bNPyiWV"}
{"name":"iron-ore","count":"52","_id":"MQZOQJ132g92DlEg"}
{"name":"water","count":50058,"_id":"MTEnmbNGHKSE8Gy3"}
{"name":"destroyer-capsule","count":"100","_id":"MlXqRhCD4UZETrdK"}
{"name":"iron-gear-wheel","count":"180","_id":"NsPHgS3B2qaKmyap"}
{"name":"speed-module-2","count":254,"_id":"Nxz2ZKMbcyiqUWd1"}
{"name":"burner-inserter","count":94,"_id":"Ouwv7ZlKhaz00FAt"}
{"name":"logistic-chest-requester","count":257,"_id":"PNLjyvBGrb4Gci5G"}
{"name":"express-splitter","count":1010,"_id":"PT7b3VbWa47lJJNI"}
{"name":"piercing-shotgun-shell","count":"70","_id":"PfsRTwLQLwsnZK6F"}
{"name":"solar-panel-equipment","count":18,"_id":"S29hMsueEXwICCvp"}
{"name":"personal-roboport-equipment","count":26,"_id":"STElkhgN3HjQ9LKj"}
{"name":"logistic-chest-storage","count":250,"_id":"SscVzS8jf9xk6Eat"}
{"name":"stone-furnace","count":1001,"_id":"TIONNgEB1OcvuR4m"}
{"name":"iron-plate","count":25036,"_id":"TKUNsKLhzi9wbXLk"}
{"name":"assembling-machine-1","count":"50","_id":"VAjgjWvWSDLzJhcz"}
{"name":"rail-chain-signal","count":"97","_id":"W8KAv7VO9viuCuLO"}
{"name":"constant-combinator","count":"5","_id":"WnaALSqOZ6sHra99"}
{"name":"coal","count":853334,"_id":"WxJKZfXyX8c0rHWc"}
{"name":"red-wire","count":"13","_id":"XprwdphPUrihfASQ"}
{"name":"effectivity-module-2","count":286,"_id":"XwITKWqPlpxkAYxo"}
{"name":"logistic-chest-passive-provider","count":253,"_id":"Yr4v7SlUGXQWouxJ"}
{"name":"fast-splitter","count":1016,"_id":"YrzmqfD7u7fZp34C"}
{"name":"plastic-bar","count":50060,"_id":"Yw2qmHm6SH5dyTxs"}
{"name":"pumpjack","count":404,"_id":"Z0plqSsfLfAl9YYa"}
{"name":"small-lamp","count":"50","_id":"Zd3H118Nc2u7HmeP"}
{"name":"fast-transport-belt","count":1042,"_id":"ZmqzOJF4tVJEzgUW"}
{"name":"medium-electric-pole","count":500,"_id":"aPqWD0jxmTv8aac7"}
{"name":"electric-furnace","count":200,"_id":"bBvxS6tFmo4yCFEE"}
{"name":"raw-wood","count":22912,"_id":"d85jLuxP9EaWmHe9"}
{"name":"laser-turret","count":252,"_id":"f9MItTJWZYfsUc9f"}
{"name":"deconstruction-planner","count":10,"_id":"fmj6YZnuuinVPP4q"}
{"name":"roboport","count":25,"_id":"ijpo46GFEzZJdZDG"}
{"name":"construction-robot","count":1026,"_id":"ipGZYHapBK3gmsaV"}
{"name":"electronic-circuit","count":3768586,"_id":"iq5rntWyvPGJqWUr"}
{"name":"express-transport-belt","count":1017,"_id":"iyrTNKNZCap5CUfn"}
{"name":"boiler","count":1011,"_id":"j2UJIu2uH01RXpgo"}
{"name":"repair-pack","count":"14","_id":"jzlBCjlkSHXUwQaq"}
{"name":"blueprint","count":12,"_id":"k30PZakZ4PBVFB32"}
{"name":"stone-wall","count":551,"_id":"kjaR0wHDPqIwZNxN"}
{"name":"electric-engine-unit","count":252,"_id":"lSWfvV27887gKucW"}
{"name":"decider-combinator","count":"1","_id":"oRrRtX53cbXqkhJF"}
{"name":"petroleum-gas","count":7582906,"_id":"ovOahSJQhBOQf0sL"}
{"name":"transport-belt","count":1011,"_id":"pBF2CkAB1AFexcZE"}
{"name":"assembling-machine-3","count":293,"_id":"pevQK7kAM5v7ObfG"}
{"name":"alien-science-pack","count":"415","_id":"qlkibcDNC0OgBuy7"}
{"name":"assembling-machine-2","count":200,"_id":"rUdnyKLPhZvMoRJ8"}
{"name":"steam-engine","count":1000,"_id":"rmEFJ9OuEIn91mLx"}
{"name":"accumulator","count":1005,"_id":"tCrPS64NshuzFHtW"}
{"name":"raw-fish","count":"11","_id":"uVQshHGwOWGwIMux"}
{"name":"underground-belt","count":1008,"_id":"v1qaz21iokoxERyl"}
{"name":"diesel-locomotive","count":20,"_id":"vmyqu0WI3k1XIdlu"}
{"name":"express-underground-belt","count":1012,"_id":"vpm5zw4BlnfErJAo"}
{"name":"piercing-rounds-magazine","count":5030,"_id":"wJpfX5g4HgCyRiAa"}
{"name":"processing-unit","count":108,"_id":"wXjUBq0KIksTJcwy"}
{"name":"power-armor-mk2","count":5,"_id":"wmItTXh1bEcysw86"}
{"name":"logistic-robot","count":1048,"_id":"x2cRxrpdC7BHJFpx"}
{"name":"fast-underground-belt","count":1010,"_id":"xONgtmV0OoxKmzVv"}
{"name":"engine-unit","count":254,"_id":"y9XyUryrxgsucFJc"}
{"name":"grenade","count":"30","_id":"ygLIdsWl9JFV2aZ6"}
{"name":"concrete","count":1039,"_id":"ym8LemdTCsDO52s8"}
{"name":"logistic-chest-active-provider","count":252,"_id":"zQZ9UP3qyg6Hx9jO"}
+65
View File
@@ -0,0 +1,65 @@
var fs = require("fs");
var path = require("path");
// gets newest file in a directory
// dir is directory
// files is array of filenames
// callback(filename string);
var getNewestFile = function(dir, files, callback) {
if (!callback) return;
if (!files || (files && files.length === 0)) {
callback();
}
var newest = { file: files[0] };
var checked = 0;
fs.stat(dir + newest.file, function(err, stats) {
newest.mtime = stats.mtime;
for (var i = 0; i < files.length; i++) {
var file = files[i];
(function(file) {
fs.stat(file, function(err, stats) {
++checked;
if (stats.mtime.getTime() > newest.mtime.getTime()) {
newest = { file : file, mtime : stats.mtime };
}
if (checked == files.length) {
callback(newest);
}
});
})(dir + file);
}
});
}
// get all directories in folder
var getDirectories = function(srcpath) {
return fs.readdirSync(srcpath).filter(function (file) {
return fs.statSync(path.join(srcpath, file)).isDirectory();
});
}
var getFileNamesSync = function(srcpath) {
return fs.readdirSync(srcpath).filter(function (file) {
return !fs.statSync(path.join(srcpath, file)).isDirectory();
});
}
// does what it says on the tin
var deleteFolderRecursive = function(path) {
if (fs.existsSync(path)) {
fs.readdirSync(path).forEach(function (file, index) {
var curPath = path + "/" + file;
if (fs.lstatSync(curPath).isDirectory()) { // recurse
deleteFolderRecursive(curPath);
} else { // delete file
fs.unlinkSync(curPath);
}
});
fs.rmdirSync(path);
}
};
module.exports = {
getNewestFile:getNewestFile,
getDirectories:getDirectories,
deleteFolderRecursive:deleteFolderRecursive,
getFileNamesSync:getFileNamesSync,
}
+43
View File
@@ -0,0 +1,43 @@
var assert = require('assert');
var fileOps = require('./fileOps');
describe("fileOps.js", function(){
describe("fileOps.getDirectories()", function(){
it("gets an array of directory names from a path", function(){
let directories = fileOps.getDirectories("lib/test");
// because there are no arrays for some reason
assert(typeof directories == "object");
// they are sorted alphabetically because thats the way it is
assert(directories[0] == "another folder" && directories[1] == "folder");
});
it("does not return any filenames", function(){
let directories = fileOps.getDirectories("lib/test");
// this is a function to return directories, not files. So yeah.
assert(!directories.includes("file.txt") && !directories.includes("another file.txt"));
});
});
describe("fileOps.getFileNamesSync(path)", function(){
it("gets names of files in directory", function(){
let files = fileOps.getFileNamesSync("lib/test");
assert(files.length > 0);
assert(files.includes("file.txt") && files.includes("another file.txt"));
});
it("throws when lacking first argument", function(){
assert.throws(function(){
let files = fileOps.getFileNamesSync();
}, Error);
});
});
/*describe("fileOps.getNewestFile()", function(){
it("gets the newest file in a directory async", function(done){
fileOps.getNewestFile("lib/test", fileOps.getFileNames("lib/test"), function(newest){
assert(newest);
done();
})
});
});*/
});
View File
Whitespace-only changes.
View File
Whitespace-only changes.
+7 -4
View File
@@ -1,11 +1,11 @@
{
"name": "factorio-clusterio",
"name": "clusterio",
"version": "1.0.0",
"description": "Factorio cluster???",
"description": "Interserver communication for factorio",
"main": "master.js",
"scripts": {
"test": "npm run test-unit",
"test-unit": "SET NODE_ENV=test && mocha --recursive ./**/*.spec.js",
"test-unit": "SET NODE_ENV=test && mocha --recursive \"./{,!(node_modules)/**/}*.spec.js\"",
"start": "echo Run node client.js start [instance] to start slaves && node master.js"
},
"keywords": [
@@ -33,11 +33,14 @@
"needle": "^1.1.0",
"portfinder": "^1.0.9",
"request": "^2.79.0",
"semver": "^5.3.0",
"simple-rcon": "^0.3.1",
"sync-request": "^4.0.1",
"underscore": "^1.8.3"
},
"devDependencies": {
"mocha": "^3.4.1"
"chai": "^3.5.0",
"mocha": "^3.4.1",
"mock-fs": "^4.3.0"
}
}