From da741c669f425dc7d783779269f16a6b8cebd5ae Mon Sep 17 00:00:00 2001 From: cadorn Date: Sat, 19 Jan 2013 23:43:15 -0800 Subject: [PATCH] export --- package.json | 4 +- plugin.js | 345 ++++++++++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 347 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 076e57f..4a92c70 100644 --- a/package.json +++ b/package.json @@ -4,6 +4,8 @@ "pm": "npm", "main": "./plugin.js", "dependencies": { - "istanbul": "0.1.x" + "istanbul": "~0.1.27", + "graceful-fs": "~1.1.14", + "ncp": "~0.2.6" } } \ No newline at end of file diff --git a/plugin.js b/plugin.js index e4b6c4a..52c2093 100644 --- a/plugin.js +++ b/plugin.js @@ -1,7 +1,8 @@ const PATH = require("path"); -const FS = require("fs"); +const FS = require("graceful-fs"); const SPAWN = require("child_process").spawn; +const COPY = require("ncp").ncp; exports.for = function(API, plugin) { @@ -79,6 +80,348 @@ throw new Error("TODO: Resolve pinf-style uris (github.com/sourcemint/loader/~0. return API.OS.spawnInline(testCommand.shift(), testCommand, opts); } + plugin.export = function(path, options) { + return API.Q.call(function() { + if (PATH.existsSync(path)) { + if (!options.delete) { + API.TERM.stdout.writenl("\0red(" + "Export target directory '" + path + "' already exists. Use --delete." + "\0)"); + throw true; + } + API.FS_RECURSIVE.rmdirSyncRecursive(path); + } + API.FS_RECURSIVE.mkdirSyncRecursive(path); + + + var ignoreRules = { + // Rules that match the top of the tree (i.e. prefixed with `/`). + top: {}, + // Rules that apply to every level. + every: {}, + filename: null + }; + + var stats = { + ignoreRulesCount: 0, + totalFiles: 0, + ignoredFiles: 0, + totalSize: 0 + }; + + function loadIgnoreRules(callback) { + function insert(rule) { + var key = rule.split("*")[0]; + var scope = (/^\//.test(rule)) ? "top" : "every"; + if (!ignoreRules[scope][key]) { + ignoreRules[scope][key] = []; + } + var re = new RegExp(rule.replace("*", "[^\\/]*?")); + ignoreRules[scope][key].push(function applyRule(path) { + if (path === rule || re.test(path)) return true; + return false; + }); + stats.ignoreRulesCount += 1; + } + [ + ".distignore", + ".npmignore", + ".gitignore" + ].forEach(function(basename) { + if (!PATH.existsSync(PATH.join(plugin.node.path, basename))) return; + if (ignoreRules.filename !== null) return; + ignoreRules.filename = basename; + FS.readFileSync(PATH.join(plugin.node.path, basename)).toString().split("\n").forEach(function(rule) { + if (!rule) return; + insert(rule); + }); + }); + if (ignoreRules.filename === null) { + // Default rules. + insert(".git/"); + insert(".DS_Store"); + } + return callback(null); + } + + function walkTree(subPath, callback) { + var list = {}; + var c = 0; + FS.readdir(PATH.join(plugin.node.path, subPath), function(err, files) { + if (err) return callback(err); + if (files.length === 0) { + return callback(null, list); + } + function error(err) { + c = -1; + return callback(err); + } + function done() { + if (c !== 0) return; + c = -1; + return callback(null, list); + } + files.forEach(function(basename) { + if (c === -1) return; + + function ignore(type) { + function select(ruleGroups, path) { + var rules = null; + if (ruleGroups[path]) { + rules = ruleGroups[path]; + } else { + for (var prefix in ruleGroups) { + if (path.substring(0, prefix.length) === prefix) { + rules = ruleGroups[prefix]; + break; + } + } + } + if (!rules && ruleGroups[""]) { + rules = ruleGroups[""]; + } + if (rules) { + for (var i=0 ; i