diff --git a/lib/src/getStats.js b/lib/src/getStats.js deleted file mode 100644 index c118745d..00000000 --- a/lib/src/getStats.js +++ /dev/null @@ -1,19 +0,0 @@ -'use strict'; - -var through2 = require('through2'); -var fs = require('graceful-fs'); - -function getStats() { - return through2.obj(fetchStats); -} - -function fetchStats(file, enc, cb) { - fs.lstat(file.path, function(err, stat) { - if (stat) { - file.stat = stat; - } - cb(err, file); - }); -} - -module.exports = getStats; diff --git a/lib/src/index.js b/lib/src/index.js index 01b54305..6362e4af 100644 --- a/lib/src/index.js +++ b/lib/src/index.js @@ -9,7 +9,7 @@ var merge = require('merge-stream'); var filterSince = require('./filterSince'); var getContents = require('./getContents'); -var getStats = require('./getStats'); +var resolveSymlinks = require('./resolveSymlinks'); function createFile(globFile, enc, cb) { cb(null, new File(globFile)); @@ -37,8 +37,8 @@ function src(glob, opt) { var globStream = gs.create(glob, options); var outputStream = globStream - .pipe(through.obj(createFile)) - .pipe(getStats(options)); + .pipe(resolveSymlinks()) + .pipe(through.obj(createFile)); if (options.since) { outputStream = outputStream diff --git a/lib/src/resolveSymlinks.js b/lib/src/resolveSymlinks.js new file mode 100644 index 00000000..1b81b30d --- /dev/null +++ b/lib/src/resolveSymlinks.js @@ -0,0 +1,38 @@ +'use strict'; + +var through2 = require('through2'); +var fs = require('graceful-fs'); +var path = require('path'); + +function resolveSymlinks() { + return through2.obj(resolveFile); +} + +// a stat property is exposed on file objects as a (wanted) side effect +function resolveFile(globFile, enc, cb) { + fs.lstat(globFile.path, function (err, stat) { + if (err) { + return cb(err); + } + + globFile.stat = stat; + + if (!stat.isSymbolicLink()) { + return cb(null, globFile); + } + + fs.realpath(globFile.path, function (err, filePath) { + if (err) { + return cb(err); + } + + globFile.base = path.dirname(filePath); + globFile.path = filePath; + + // recurse to get real file stat + resolveFile(globFile, enc, cb); + }); + }); +} + +module.exports = resolveSymlinks; diff --git a/test/fixtures/test-symlink b/test/fixtures/test-symlink new file mode 120000 index 00000000..3fcfe6c7 --- /dev/null +++ b/test/fixtures/test-symlink @@ -0,0 +1 @@ +test.coffee \ No newline at end of file diff --git a/test/fixtures/test-symlink-dir b/test/fixtures/test-symlink-dir new file mode 120000 index 00000000..9a17374b --- /dev/null +++ b/test/fixtures/test-symlink-dir @@ -0,0 +1 @@ +wow \ No newline at end of file diff --git a/test/src.js b/test/src.js index 7c3590fc..f61e5b34 100644 --- a/test/src.js +++ b/test/src.js @@ -397,4 +397,24 @@ describe('source stream', function() { stream1.pipe(stream2).pipe(bufferStream); }); + it('should follow file symlinks', function(done) { + var expectedPath = path.join(__dirname, './fixtures/test.coffee'); + + var stream = vfs.src('./fixtures/test-symlink', {cwd: __dirname}); + stream.on('data', function(file){ + file.path.should.equal(expectedPath); + done(); + }); + }); + + it('should follow dir symlinks', function(done) { + var expectedPath = path.join(__dirname, './fixtures/wow'); + + var stream = vfs.src('./fixtures/test-symlink-dir', {cwd: __dirname}); + stream.on('data', function(file){ + file.path.should.equal(expectedPath); + done(); + }); + }); + });