diff options
Diffstat (limited to 'lib/internal/fs/utils.js')
-rw-r--r-- | lib/internal/fs/utils.js | 117 |
1 files changed, 116 insertions, 1 deletions
diff --git a/lib/internal/fs/utils.js b/lib/internal/fs/utils.js index a2f1015c62..f065ba41e8 100644 --- a/lib/internal/fs/utils.js +++ b/lib/internal/fs/utils.js @@ -12,6 +12,8 @@ const { const { isUint8Array } = require('internal/util/types'); const pathModule = require('path'); const util = require('util'); +const kType = Symbol('type'); +const kStats = Symbol('stats'); const { O_APPEND, @@ -31,17 +33,84 @@ const { S_IFREG, S_IFSOCK, UV_FS_SYMLINK_DIR, - UV_FS_SYMLINK_JUNCTION + UV_FS_SYMLINK_JUNCTION, + UV_DIRENT_UNKNOWN, + UV_DIRENT_FILE, + UV_DIRENT_DIR, + UV_DIRENT_LINK, + UV_DIRENT_FIFO, + UV_DIRENT_SOCKET, + UV_DIRENT_CHAR, + UV_DIRENT_BLOCK } = process.binding('constants').fs; const isWindows = process.platform === 'win32'; +let fs; +function lazyLoadFs() { + if (!fs) { + fs = require('fs'); + } + return fs; +} + function assertEncoding(encoding) { if (encoding && !Buffer.isEncoding(encoding)) { throw new ERR_INVALID_OPT_VALUE_ENCODING(encoding); } } +class Dirent { + constructor(name, type) { + this.name = name; + this[kType] = type; + } + + isDirectory() { + return this[kType] === UV_DIRENT_DIR; + } + + isFile() { + return this[kType] === UV_DIRENT_FILE; + } + + isBlockDevice() { + return this[kType] === UV_DIRENT_BLOCK; + } + + isCharacterDevice() { + return this[kType] === UV_DIRENT_CHAR; + } + + isSymbolicLink() { + return this[kType] === UV_DIRENT_LINK; + } + + isFIFO() { + return this[kType] === UV_DIRENT_FIFO; + } + + isSocket() { + return this[kType] === UV_DIRENT_SOCKET; + } +} + +class DirentFromStats extends Dirent { + constructor(name, stats) { + super(name, null); + this[kStats] = stats; + } +} + +for (const name of Reflect.ownKeys(Dirent.prototype)) { + if (name === 'constructor') { + continue; + } + DirentFromStats.prototype[name] = function() { + return this[kStats][name](); + }; +} + function copyObject(source) { var target = {}; for (var key in source) @@ -49,6 +118,50 @@ function copyObject(source) { return target; } +function getDirents(path, [names, types], callback) { + var i; + if (typeof callback == 'function') { + const len = names.length; + let toFinish = 0; + for (i = 0; i < len; i++) { + const type = types[i]; + if (type === UV_DIRENT_UNKNOWN) { + const name = names[i]; + const idx = i; + toFinish++; + lazyLoadFs().stat(pathModule.resolve(path, name), (err, stats) => { + if (err) { + callback(err); + return; + } + names[idx] = new DirentFromStats(name, stats); + if (--toFinish === 0) { + callback(null, names); + } + }); + } else { + names[i] = new Dirent(names[i], types[i]); + } + } + if (toFinish === 0) { + callback(null, names); + } + } else { + const len = names.length; + for (i = 0; i < len; i++) { + const type = types[i]; + if (type === UV_DIRENT_UNKNOWN) { + const name = names[i]; + const stats = lazyLoadFs().statSync(pathModule.resolve(path, name)); + names[i] = new DirentFromStats(name, stats); + } else { + names[i] = new Dirent(names[i], types[i]); + } + } + return names; + } +} + function getOptions(options, defaultOptions) { if (options === null || options === undefined || typeof options === 'function') { @@ -342,6 +455,8 @@ function validatePath(path, propName = 'path') { module.exports = { assertEncoding, copyObject, + Dirent, + getDirents, getOptions, nullCheck, preprocessSymlinkDestination, |