mirror of
https://github.com/gnh1201/welsonjs.git
synced 2025-05-13 13:11:03 +00:00
225 lines
5.5 KiB
JavaScript
225 lines
5.5 KiB
JavaScript
var path = require('path');
|
|
var fs = require('fs');
|
|
var assert = require("assert");
|
|
|
|
// file.mkdirs
|
|
//
|
|
// Given a path to a directory, create it, and all the intermediate directories
|
|
// as well
|
|
//
|
|
// @path: the path to create
|
|
// @mode: the file mode to create the directory with:
|
|
// ex: file.mkdirs("/tmp/dir", 755, function () {})
|
|
// @callback: called when finished.
|
|
exports.mkdirs = function (_path, mode, callback) {
|
|
_path = exports.path.abspath(_path);
|
|
|
|
var dirs = _path.split(path.sep);
|
|
var walker = [dirs.shift()];
|
|
|
|
// walk
|
|
// @ds: A list of directory names
|
|
// @acc: An accumulator of walked dirs
|
|
// @m: The mode
|
|
// @cb: The callback
|
|
var walk = function (ds, acc, m, cb) {
|
|
if (ds.length > 0) {
|
|
var d = ds.shift();
|
|
|
|
acc.push(d);
|
|
var dir = acc.join(path.sep);
|
|
|
|
// look for dir on the fs, if it doesn't exist then create it, and
|
|
// continue our walk, otherwise if it's a file, we have a name
|
|
// collision, so exit.
|
|
fs.stat(dir, function (err, stat) {
|
|
// if the directory doesn't exist then create it
|
|
if (err) {
|
|
// 2 means it's wasn't there
|
|
if (err.errno == 2 || err.errno == 34) {
|
|
fs.mkdir(dir, m, function (erro) {
|
|
if (erro && erro.errno != 17 && erro.errno != 34) {
|
|
return cb(erro);
|
|
} else {
|
|
return walk(ds, acc, m, cb);
|
|
}
|
|
});
|
|
} else {
|
|
return cb(err);
|
|
}
|
|
} else {
|
|
if (stat.isDirectory()) {
|
|
return walk(ds, acc, m, cb);
|
|
} else {
|
|
return cb(new Error("Failed to mkdir " + dir + ": File exists\n"));
|
|
}
|
|
}
|
|
});
|
|
} else {
|
|
return cb();
|
|
}
|
|
};
|
|
return walk(dirs, walker, mode, callback);
|
|
};
|
|
|
|
// file.mkdirsSync
|
|
//
|
|
// Synchronus version of file.mkdirs
|
|
//
|
|
// Given a path to a directory, create it, and all the intermediate directories
|
|
// as well
|
|
//
|
|
// @path: the path to create
|
|
// @mode: the file mode to create the directory with:
|
|
// ex: file.mkdirs("/tmp/dir", 755, function () {})
|
|
exports.mkdirsSync = function (_path, mode) {
|
|
if (_path[0] !== path.sep) {
|
|
_path = path.join(process.cwd(), _path)
|
|
}
|
|
|
|
var dirs = _path.split(path.sep);
|
|
var walker = [dirs.shift()];
|
|
|
|
dirs.reduce(function (acc, d) {
|
|
acc.push(d);
|
|
var dir = acc.join(path.sep);
|
|
|
|
try {
|
|
var stat = fs.statSync(dir);
|
|
if (!stat.isDirectory()) {
|
|
throw "Failed to mkdir " + dir + ": File exists";
|
|
}
|
|
} catch (err) {
|
|
fs.mkdirSync(dir, mode);
|
|
}
|
|
return acc;
|
|
}, walker);
|
|
};
|
|
|
|
// file.walk
|
|
//
|
|
// Given a path to a directory, walk the fs below that directory
|
|
//
|
|
// @start: the path to startat
|
|
// @callback: called for each new directory we enter
|
|
// ex: file.walk("/tmp", function(error, path, dirs, name) {})
|
|
//
|
|
// path is the current directory we're in
|
|
// dirs is the list of directories below it
|
|
// names is the list of files in it
|
|
//
|
|
exports.walk = function (start, callback) {
|
|
fs.lstat(start, function (err, stat) {
|
|
if (err) { return callback(err) }
|
|
if (stat.isDirectory()) {
|
|
|
|
fs.readdir(start, function (err, files) {
|
|
var coll = files.reduce(function (acc, i) {
|
|
var abspath = path.join(start, i);
|
|
|
|
if (fs.statSync(abspath).isDirectory()) {
|
|
exports.walk(abspath, callback);
|
|
acc.dirs.push(abspath);
|
|
} else {
|
|
acc.names.push(abspath);
|
|
}
|
|
|
|
return acc;
|
|
}, {"names": [], "dirs": []});
|
|
|
|
return callback(null, start, coll.dirs, coll.names);
|
|
});
|
|
} else {
|
|
return callback(new Error("path: " + start + " is not a directory"));
|
|
}
|
|
});
|
|
};
|
|
|
|
// file.walkSync
|
|
//
|
|
// Synchronus version of file.walk
|
|
//
|
|
// Given a path to a directory, walk the fs below that directory
|
|
//
|
|
// @start: the path to startat
|
|
// @callback: called for each new directory we enter
|
|
// ex: file.walk("/tmp", function(error, path, dirs, name) {})
|
|
//
|
|
// path is the current directory we're in
|
|
// dirs is the list of directories below it
|
|
// names is the list of files in it
|
|
//
|
|
exports.walkSync = function (start, callback) {
|
|
var stat = fs.statSync(start);
|
|
|
|
if (stat.isDirectory()) {
|
|
var filenames = fs.readdirSync(start);
|
|
|
|
var coll = filenames.reduce(function (acc, name) {
|
|
var abspath = path.join(start, name);
|
|
|
|
if (fs.statSync(abspath).isDirectory()) {
|
|
acc.dirs.push(name);
|
|
} else {
|
|
acc.names.push(name);
|
|
}
|
|
|
|
return acc;
|
|
}, {"names": [], "dirs": []});
|
|
|
|
callback(start, coll.dirs, coll.names);
|
|
|
|
coll.dirs.forEach(function (d) {
|
|
var abspath = path.join(start, d);
|
|
exports.walkSync(abspath, callback);
|
|
});
|
|
|
|
} else {
|
|
throw new Error("path: " + start + " is not a directory");
|
|
}
|
|
};
|
|
|
|
exports.path = {};
|
|
|
|
exports.path.abspath = function (to) {
|
|
var from;
|
|
switch (to.charAt(0)) {
|
|
case "~": from = process.env.HOME; to = to.substr(1); break
|
|
case path.sep: from = ""; break
|
|
default : from = process.cwd(); break
|
|
}
|
|
return path.join(from, to);
|
|
}
|
|
|
|
exports.path.relativePath = function (base, compare) {
|
|
base = base.split(path.sep);
|
|
compare = compare.split(path.sep);
|
|
|
|
if (base[0] == "") {
|
|
base.shift();
|
|
}
|
|
|
|
if (compare[0] == "") {
|
|
compare.shift();
|
|
}
|
|
|
|
var l = compare.length;
|
|
|
|
for (var i = 0; i < l; i++) {
|
|
if (!base[i] || (base[i] != compare[i])) {
|
|
return compare.slice(i).join(path.sep);
|
|
}
|
|
}
|
|
|
|
return ""
|
|
};
|
|
|
|
exports.path.join = function (head, tail) {
|
|
if (head == "") {
|
|
return tail;
|
|
} else {
|
|
return path.join(head, tail);
|
|
}
|
|
};
|
|
|