mirror of https://github.com/lukechilds/node.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
106 lines
3.1 KiB
106 lines
3.1 KiB
10 years ago
|
/**
|
||
|
* @fileoverview Simple directory traversal logic.
|
||
|
* @author Nicholas C. Zakas
|
||
|
*/
|
||
|
|
||
|
"use strict";
|
||
|
|
||
|
//------------------------------------------------------------------------------
|
||
|
// Requirements
|
||
|
//------------------------------------------------------------------------------
|
||
|
|
||
|
var fs = require("fs"),
|
||
|
path = require("path"),
|
||
|
debug = require("debug");
|
||
|
|
||
|
//------------------------------------------------------------------------------
|
||
|
// Helpers
|
||
|
//------------------------------------------------------------------------------
|
||
|
|
||
|
debug = debug("eslint:traverse");
|
||
|
|
||
|
/**
|
||
|
* Walks a path recursively calling the callback on each file.
|
||
|
* @param {string} name The file or directory path.
|
||
|
* @param {string[]} extensions The file extensions that should cause the callback
|
||
|
* to be called.
|
||
|
* @param {Function} exclude The function to check if file/path should be excluded.
|
||
|
* @param {Function} callback The function to call on each file.
|
||
|
* @returns {void}
|
||
|
* @private
|
||
|
*/
|
||
|
function walk(name, extensions, exclude, callback) {
|
||
|
|
||
|
var stat, basename;
|
||
|
|
||
|
stat = fs.statSync(name);
|
||
|
|
||
|
function traverse(dir, stack) {
|
||
|
stack.push(dir);
|
||
|
|
||
|
fs.readdirSync(path.join.apply(path, stack)).forEach(function(file) {
|
||
|
var filePath, fileStat;
|
||
|
|
||
|
// skip all hidded things (dirs, files, links)
|
||
|
if (file[0] === ".") {
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
filePath = path.join.apply(path, stack.concat([file]));
|
||
|
fileStat = fs.statSync(filePath);
|
||
|
|
||
|
// if this file or directory is excluded from linting, skip over it.
|
||
|
if (exclude && exclude(filePath)) {
|
||
|
// console.log("Ignoring " + filePath);
|
||
|
debug("Ignoring " + filePath);
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
// only call callback for files with correct extensions
|
||
|
if (fileStat.isFile() && extensions.indexOf(path.extname(filePath)) > -1) {
|
||
|
callback(filePath);
|
||
|
} else if (fileStat.isDirectory()) {
|
||
|
traverse(file, stack);
|
||
|
}
|
||
|
});
|
||
|
stack.pop();
|
||
|
}
|
||
|
|
||
|
basename = path.basename(name);
|
||
|
|
||
|
// don't ignore cases like 'eslint ./'
|
||
|
if ((basename !== "." && basename !== ".." && basename[0] === ".") ||
|
||
|
(exclude && exclude(name))) {
|
||
|
|
||
|
debug("Ignoring " + name);
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
// always call callback for any files that are passed on the command line
|
||
|
if (stat.isFile()) {
|
||
|
callback(name);
|
||
|
} else {
|
||
|
traverse(name, []);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Traverses multiple directories and calls a callback on each file.
|
||
|
* @param {Object} options The option for the traversal.
|
||
|
* param {string[]} options.files An array of file and directory paths to traverse.
|
||
|
* param {Function} options.exclude The function to check if file/path should be excluded.
|
||
|
* @param {Function} callback A function to call for each file.
|
||
|
* @returns {void}
|
||
|
*/
|
||
|
module.exports = function traverse(options, callback) {
|
||
|
|
||
|
var files = options.files,
|
||
|
exclude = options.exclude,
|
||
|
extensions = options.extensions;
|
||
|
|
||
|
files.forEach(function(file) {
|
||
|
walk(file, extensions, exclude, callback);
|
||
|
});
|
||
|
|
||
|
};
|