From 55dcf96018d5852884da1a915372fa489d220597 Mon Sep 17 00:00:00 2001 From: Jan Potoms Date: Wed, 28 Jan 2015 22:52:41 +0100 Subject: [PATCH] Fix: Resolve globs against root option & avoid passing root option to node-glob (fixes #37) --- index.js | 23 ++++++++++++++++++----- package.json | 1 + test/main.js | 36 ++++++++++++++++++++++++++++++++++++ 3 files changed, 55 insertions(+), 5 deletions(-) diff --git a/index.js b/index.js index e403185..70dfa6e 100644 --- a/index.js +++ b/index.js @@ -10,15 +10,19 @@ var glob = require('glob'); var Minimatch = require('minimatch').Minimatch; var glob2base = require('glob2base'); var path = require('path'); +var extend = require('extend'); var gs = { // creates a stream for a single glob or filter createStream: function(ourGlob, negatives, opt) { + // remove path relativity to make globs make sense - ourGlob = unrelative(opt.cwd, ourGlob); + ourGlob = resolveGlob(ourGlob, opt); + var ourOpt = extend({}, opt); + delete ourOpt.root; // create globbing stuff - var globber = new glob.Glob(ourGlob, opt); + var globber = new glob.Glob(ourGlob, ourOpt); // extract base path from glob var basePath = opt.base || glob2base(globber); @@ -74,6 +78,9 @@ var gs = { var positives = []; var negatives = []; + var ourOpt = extend({}, opt); + delete ourOpt.root; + globs.forEach(function(glob, index) { if (typeof glob !== 'string' && !(glob instanceof RegExp)) { throw new Error('Invalid glob at index ' + index); @@ -83,7 +90,8 @@ var gs = { // create Minimatch instances for negative glob patterns if (globArray === negatives && typeof glob === 'string') { - glob = new Minimatch(unrelative(opt.cwd, glob), opt); + var ourGlob = resolveGlob(glob, opt); + glob = new Minimatch(ourGlob, ourOpt); } globArray.push({ @@ -128,13 +136,18 @@ function isNegative(pattern) { if (pattern instanceof RegExp) return true; } -function unrelative(cwd, glob) { +function resolveGlob(glob, opt) { var mod = ''; if (glob[0] === '!') { mod = glob[0]; glob = glob.slice(1); } - return mod+path.resolve(cwd, glob); + if (opt.root && glob[0] === '/') { + glob = path.resolve(opt.root, '.'+glob); + } else { + glob = path.resolve(opt.cwd, glob); + } + return mod+glob; } function indexGreaterThan(index) { diff --git a/package.json b/package.json index d4c6128..94e097b 100644 --- a/package.json +++ b/package.json @@ -8,6 +8,7 @@ "index.js" ], "dependencies": { + "extend": "^2.0.0", "glob": "^5.0.3", "minimatch": "^2.0.1", "ordered-read-streams": "^0.2.0", diff --git a/test/main.js b/test/main.js index bca757f..8761786 100644 --- a/test/main.js +++ b/test/main.js @@ -502,6 +502,42 @@ describe('glob-stream', function() { }); }); + it('should resolve relative paths when root option is given', function(done) { + var stream = gs.create('./fixtures/test.coffee', {cwd: __dirname, root: __dirname + '/fixtures'}); + should.exist(stream); + stream.on('error', function(err) { + throw err; + }); + stream.on('data', function(file) { + should.exist(file); + should.exist(file.path); + should.exist(file.base); + should.exist(file.cwd); + String(file.cwd).should.equal(__dirname); + String(file.base).should.equal(join(__dirname, 'fixtures'+sep)); + String(join(file.path,'')).should.equal(join(__dirname, './fixtures/test.coffee')); + done(); + }); + }); + + it('should resolve absolute paths when root option is given', function(done) { + var stream = gs.create('/test.coffee', {cwd: __dirname, root: __dirname + '/fixtures'}); + should.exist(stream); + stream.on('error', function(err) { + throw err; + }); + stream.on('data', function(file) { + should.exist(file); + should.exist(file.path); + should.exist(file.base); + should.exist(file.cwd); + String(file.cwd).should.equal(__dirname); + String(file.base).should.equal(join(__dirname, 'fixtures'+sep)); + String(join(file.path,'')).should.equal(join(__dirname, './fixtures/test.coffee')); + done(); + }); + }); + it('should not emit error on glob containing {} when not found', function(done) { var stream = gs.create('notfound{a,b}'); should.exist(stream);