UNPKG

@avdl/folder-walker

Version:

A powerful, fluent, and configurable directory traversal utility for Node.js with TypeScript support

911 lines (905 loc) 29.9 kB
'use strict'; Object.defineProperty(exports, '__esModule', { value: true }); var fs = require('fs'); var path = require('path'); function _OverloadYield(e, d) { this.v = e, this.k = d; } function _arrayLikeToArray(r, a) { (null == a || a > r.length) && (a = r.length); for (var e = 0, n = Array(a); e < a; e++) n[e] = r[e]; return n; } function _asyncGeneratorDelegate(t) { var e = {}, n = !1; function pump(e, r) { return n = !0, r = new Promise(function (n) { n(t[e](r)); }), { done: !1, value: new _OverloadYield(r, 1) }; } return e["undefined" != typeof Symbol && Symbol.iterator || "@@iterator"] = function () { return this; }, e.next = function (t) { return n ? (n = !1, t) : pump("next", t); }, "function" == typeof t.throw && (e.throw = function (t) { if (n) throw n = !1, t; return pump("throw", t); }), "function" == typeof t.return && (e.return = function (t) { return n ? (n = !1, t) : pump("return", t); }), e; } function _asyncIterator(r) { var n, t, o, e = 2; for ("undefined" != typeof Symbol && (t = Symbol.asyncIterator, o = Symbol.iterator); e--;) { if (t && null != (n = r[t])) return n.call(r); if (o && null != (n = r[o])) return new AsyncFromSyncIterator(n.call(r)); t = "@@asyncIterator", o = "@@iterator"; } throw new TypeError("Object is not async iterable"); } function AsyncFromSyncIterator(r) { function AsyncFromSyncIteratorContinuation(r) { if (Object(r) !== r) return Promise.reject(new TypeError(r + " is not an object.")); var n = r.done; return Promise.resolve(r.value).then(function (r) { return { value: r, done: n }; }); } return AsyncFromSyncIterator = function (r) { this.s = r, this.n = r.next; }, AsyncFromSyncIterator.prototype = { s: null, n: null, next: function () { return AsyncFromSyncIteratorContinuation(this.n.apply(this.s, arguments)); }, return: function (r) { var n = this.s.return; return void 0 === n ? Promise.resolve({ value: r, done: !0 }) : AsyncFromSyncIteratorContinuation(n.apply(this.s, arguments)); }, throw: function (r) { var n = this.s.return; return void 0 === n ? Promise.reject(r) : AsyncFromSyncIteratorContinuation(n.apply(this.s, arguments)); } }, new AsyncFromSyncIterator(r); } function asyncGeneratorStep(n, t, e, r, o, a, c) { try { var i = n[a](c), u = i.value; } catch (n) { return void e(n); } i.done ? t(u) : Promise.resolve(u).then(r, o); } function _asyncToGenerator(n) { return function () { var t = this, e = arguments; return new Promise(function (r, o) { var a = n.apply(t, e); function _next(n) { asyncGeneratorStep(a, r, o, _next, _throw, "next", n); } function _throw(n) { asyncGeneratorStep(a, r, o, _next, _throw, "throw", n); } _next(void 0); }); }; } function _awaitAsyncGenerator(e) { return new _OverloadYield(e, 0); } function _createForOfIteratorHelperLoose(r, e) { var t = "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (t) return (t = t.call(r)).next.bind(t); if (Array.isArray(r) || (t = _unsupportedIterableToArray(r)) || e && r && "number" == typeof r.length) { t && (r = t); var o = 0; return function () { return o >= r.length ? { done: !0 } : { done: !1, value: r[o++] }; }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } function _regenerator() { /*! regenerator-runtime -- Copyright (c) 2014-present, Facebook, Inc. -- license (MIT): https://github.com/babel/babel/blob/main/packages/babel-helpers/LICENSE */ var e, t, r = "function" == typeof Symbol ? Symbol : {}, n = r.iterator || "@@iterator", o = r.toStringTag || "@@toStringTag"; function i(r, n, o, i) { var c = n && n.prototype instanceof Generator ? n : Generator, u = Object.create(c.prototype); return _regeneratorDefine(u, "_invoke", function (r, n, o) { var i, c, u, f = 0, p = o || [], y = !1, G = { p: 0, n: 0, v: e, a: d, f: d.bind(e, 4), d: function (t, r) { return i = t, c = 0, u = e, G.n = r, a; } }; function d(r, n) { for (c = r, u = n, t = 0; !y && f && !o && t < p.length; t++) { var o, i = p[t], d = G.p, l = i[2]; r > 3 ? (o = l === n) && (u = i[(c = i[4]) ? 5 : (c = 3, 3)], i[4] = i[5] = e) : i[0] <= d && ((o = r < 2 && d < i[1]) ? (c = 0, G.v = n, G.n = i[1]) : d < l && (o = r < 3 || i[0] > n || n > l) && (i[4] = r, i[5] = n, G.n = l, c = 0)); } if (o || r > 1) return a; throw y = !0, n; } return function (o, p, l) { if (f > 1) throw TypeError("Generator is already running"); for (y && 1 === p && d(p, l), c = p, u = l; (t = c < 2 ? e : u) || !y;) { i || (c ? c < 3 ? (c > 1 && (G.n = -1), d(c, u)) : G.n = u : G.v = u); try { if (f = 2, i) { if (c || (o = "next"), t = i[o]) { if (!(t = t.call(i, u))) throw TypeError("iterator result is not an object"); if (!t.done) return t; u = t.value, c < 2 && (c = 0); } else 1 === c && (t = i.return) && t.call(i), c < 2 && (u = TypeError("The iterator does not provide a '" + o + "' method"), c = 1); i = e; } else if ((t = (y = G.n < 0) ? u : r.call(n, G)) !== a) break; } catch (t) { i = e, c = 1, u = t; } finally { f = 1; } } return { value: t, done: y }; }; }(r, o, i), !0), u; } var a = {}; function Generator() {} function GeneratorFunction() {} function GeneratorFunctionPrototype() {} t = Object.getPrototypeOf; var c = [][n] ? t(t([][n]())) : (_regeneratorDefine(t = {}, n, function () { return this; }), t), u = GeneratorFunctionPrototype.prototype = Generator.prototype = Object.create(c); function f(e) { return Object.setPrototypeOf ? Object.setPrototypeOf(e, GeneratorFunctionPrototype) : (e.__proto__ = GeneratorFunctionPrototype, _regeneratorDefine(e, o, "GeneratorFunction")), e.prototype = Object.create(u), e; } return GeneratorFunction.prototype = GeneratorFunctionPrototype, _regeneratorDefine(u, "constructor", GeneratorFunctionPrototype), _regeneratorDefine(GeneratorFunctionPrototype, "constructor", GeneratorFunction), GeneratorFunction.displayName = "GeneratorFunction", _regeneratorDefine(GeneratorFunctionPrototype, o, "GeneratorFunction"), _regeneratorDefine(u), _regeneratorDefine(u, o, "Generator"), _regeneratorDefine(u, n, function () { return this; }), _regeneratorDefine(u, "toString", function () { return "[object Generator]"; }), (_regenerator = function () { return { w: i, m: f }; })(); } function _regeneratorDefine(e, r, n, t) { var i = Object.defineProperty; try { i({}, "", {}); } catch (e) { i = 0; } _regeneratorDefine = function (e, r, n, t) { if (r) i ? i(e, r, { value: n, enumerable: !t, configurable: !t, writable: !t }) : e[r] = n;else { function o(r, n) { _regeneratorDefine(e, r, function (e) { return this._invoke(r, n, e); }); } o("next", 0), o("throw", 1), o("return", 2); } }, _regeneratorDefine(e, r, n, t); } function _regeneratorValues(e) { if (null != e) { var t = e["function" == typeof Symbol && Symbol.iterator || "@@iterator"], r = 0; if (t) return t.call(e); if ("function" == typeof e.next) return e; if (!isNaN(e.length)) return { next: function () { return e && r >= e.length && (e = void 0), { value: e && e[r++], done: !e }; } }; } throw new TypeError(typeof e + " is not iterable"); } function _unsupportedIterableToArray(r, a) { if (r) { if ("string" == typeof r) return _arrayLikeToArray(r, a); var t = {}.toString.call(r).slice(8, -1); return "Object" === t && r.constructor && (t = r.constructor.name), "Map" === t || "Set" === t ? Array.from(r) : "Arguments" === t || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(t) ? _arrayLikeToArray(r, a) : void 0; } } function _wrapAsyncGenerator(e) { return function () { return new AsyncGenerator(e.apply(this, arguments)); }; } function AsyncGenerator(e) { var r, t; function resume(r, t) { try { var n = e[r](t), o = n.value, u = o instanceof _OverloadYield; Promise.resolve(u ? o.v : o).then(function (t) { if (u) { var i = "return" === r ? "return" : "next"; if (!o.k || t.done) return resume(i, t); t = e[i](t).value; } settle(n.done ? "return" : "normal", t); }, function (e) { resume("throw", e); }); } catch (e) { settle("throw", e); } } function settle(e, n) { switch (e) { case "return": r.resolve({ value: n, done: !0 }); break; case "throw": r.reject(n); break; default: r.resolve({ value: n, done: !1 }); } (r = r.next) ? resume(r.key, r.arg) : t = null; } this._invoke = function (e, n) { return new Promise(function (o, u) { var i = { key: e, arg: n, resolve: o, reject: u, next: null }; t ? t = t.next = i : (r = t = i, resume(e, n)); }); }, "function" != typeof e.return && (this.return = void 0); } AsyncGenerator.prototype["function" == typeof Symbol && Symbol.asyncIterator || "@@asyncIterator"] = function () { return this; }, AsyncGenerator.prototype.next = function (e) { return this._invoke("next", e); }, AsyncGenerator.prototype.throw = function (e) { return this._invoke("throw", e); }, AsyncGenerator.prototype.return = function (e) { return this._invoke("return", e); }; var FolderWalker = /*#__PURE__*/function () { function FolderWalker() { this.options = { includeFiles: true, includeFolders: true, followSymlinks: false, includeHidden: false, readContents: false, customFilters: [] }; this.collectingFiles = false; this.collectingFolders = false; } var _proto = FolderWalker.prototype; _proto.withDepth = function withDepth(depth) { this.options.maxDepth = depth; return this; }; _proto.withFilesOnly = function withFilesOnly() { this.options.includeFiles = true; this.options.includeFolders = false; return this; }; _proto.withFoldersOnly = function withFoldersOnly() { this.options.includeFiles = false; this.options.includeFolders = true; return this; }; _proto.withFilesAndFolders = function withFilesAndFolders() { this.options.includeFiles = true; this.options.includeFolders = true; return this; }; _proto.withFileContents = function withFileContents(encoding) { if (encoding === void 0) { encoding = 'utf-8'; } this.options.readContents = true; this.options.encoding = encoding; return this; }; _proto.withExtensions = function withExtensions(extensions) { this.options.extensions = extensions.map(function (ext) { return ext.startsWith('.') ? ext : "." + ext; }); return this; }; _proto.withPattern = function withPattern(pattern) { this.options.pattern = pattern; return this; }; _proto.exclude = function exclude(patterns) { this.options.exclude = patterns; return this; }; _proto.include = function include(patterns) { this.options.include = patterns; return this; }; _proto.withHidden = function withHidden() { this.options.includeHidden = true; return this; }; _proto.withSymlinks = function withSymlinks() { this.options.followSymlinks = true; return this; }; _proto.withMaxFileSize = function withMaxFileSize(bytes) { this.options.maxFileSize = bytes; return this; }; _proto.withFilter = function withFilter(filter) { if (!this.options.customFilters) { this.options.customFilters = []; } this.options.customFilters.push(filter); return this; }; _proto.onFile = function onFile(handler) { var newWalker = this; newWalker.fileHandler = handler; return newWalker; }; _proto.onFolder = function onFolder(handler) { var newWalker = this; newWalker.folderHandler = handler; return newWalker; }; _proto.onError = function onError(handler) { this.errorHandler = handler; return this; }; _proto.withFileCollector = function withFileCollector(collector) { var newWalker = this; newWalker.collectingFiles = true; newWalker.fileCollector = collector; return newWalker; }; _proto.withFolderCollector = function withFolderCollector(collector) { var newWalker = this; newWalker.collectingFolders = true; newWalker.folderCollector = collector; return newWalker; }; _proto.execute = /*#__PURE__*/function () { var _execute = /*#__PURE__*/_asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee3(path) { var fileResults, folderResults, originalFileHandler, originalFolderHandler; return _regenerator().w(function (_context3) { while (1) switch (_context3.n) { case 0: this.rootPath = path; fileResults = []; folderResults = []; // Store original handlers originalFileHandler = this.fileHandler; originalFolderHandler = this.folderHandler; // Wrap handlers to collect results if needed if (this.collectingFiles && this.fileHandler) { this.fileHandler = /*#__PURE__*/function () { var _ref = _asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee(entry) { var result; return _regenerator().w(function (_context) { while (1) switch (_context.n) { case 0: _context.n = 1; return originalFileHandler(entry); case 1: result = _context.v; if (result !== undefined) { fileResults.push(result); } return _context.a(2, result); } }, _callee); })); return function (_x2) { return _ref.apply(this, arguments); }; }(); } if (this.collectingFolders && this.folderHandler) { this.folderHandler = /*#__PURE__*/function () { var _ref2 = _asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee2(entry) { var result; return _regenerator().w(function (_context2) { while (1) switch (_context2.n) { case 0: _context2.n = 1; return originalFolderHandler(entry); case 1: result = _context2.v; if (result !== undefined) { folderResults.push(result); } return _context2.a(2, result); } }, _callee2); })); return function (_x3) { return _ref2.apply(this, arguments); }; }(); } // Execute the walk _context3.n = 1; return this.walk(path, 0); case 1: // Restore original handlers this.fileHandler = originalFileHandler; this.folderHandler = originalFolderHandler; // Return collected results if (!this.collectingFiles) { _context3.n = 4; break; } if (!this.fileCollector) { _context3.n = 3; break; } _context3.n = 2; return this.fileCollector(fileResults); case 2: return _context3.a(2, _context3.v); case 3: return _context3.a(2, fileResults); case 4: if (!this.collectingFolders) { _context3.n = 7; break; } if (!this.folderCollector) { _context3.n = 6; break; } _context3.n = 5; return this.folderCollector(folderResults); case 5: return _context3.a(2, _context3.v); case 6: return _context3.a(2, folderResults); case 7: return _context3.a(2, undefined); } }, _callee3, this); })); function execute(_x) { return _execute.apply(this, arguments); } return execute; }(); _proto.files = function files(path) { if (path) this.rootPath = path; return this.createAsyncIterable('file'); }; _proto.folders = function folders(path) { if (path) this.rootPath = path; return this.createAsyncIterable('folder'); }; _proto.entries = function entries(path) { if (path) this.rootPath = path; return this.createAsyncIterable('all'); }; _proto.createAsyncIterable = function createAsyncIterable(type) { var _this = this; return _wrapAsyncGenerator(/*#__PURE__*/_regenerator().m(function _callee4() { return _regenerator().w(function (_context4) { while (1) switch (_context4.n) { case 0: if (_this.rootPath) { _context4.n = 1; break; } throw new Error('Root path not set. Call execute() or use iterator with path.'); case 1: return _context4.d(_regeneratorValues(_asyncGeneratorDelegate(_asyncIterator(_this.walkIterator(_this.rootPath, 0, type)))), 2); case 2: return _context4.a(2); } }, _callee4); }))(); }; _proto.walkIterator = function walkIterator(dirPath, depth, type) { var _this2 = this; return _wrapAsyncGenerator(/*#__PURE__*/_regenerator().m(function _callee5() { var entries, _iterator2, _step2, entry, fullPath, stats, folderEntry, fileEntry, _t, _t2, _t3; return _regenerator().w(function (_context5) { while (1) switch (_context5.n) { case 0: if (!(_this2.options.maxDepth !== undefined && depth > _this2.options.maxDepth)) { _context5.n = 1; break; } return _context5.a(2); case 1: _context5.p = 1; _context5.n = 2; return _awaitAsyncGenerator(fs.promises.readdir(dirPath)); case 2: entries = _context5.v; _iterator2 = _createForOfIteratorHelperLoose(entries); case 3: if ((_step2 = _iterator2()).done) { _context5.n = 18; break; } entry = _step2.value; fullPath = path.join(dirPath, entry); if (_this2.shouldProcess(entry, fullPath)) { _context5.n = 4; break; } return _context5.a(3, 17); case 4: _context5.p = 4; _context5.n = 5; return _awaitAsyncGenerator(fs.promises.stat(fullPath)); case 5: stats = _context5.v; if (!stats.isDirectory()) { _context5.n = 10; break; } if (!((type === 'folder' || type === 'all') && _this2.options.includeFolders)) { _context5.n = 8; break; } folderEntry = { path: fullPath, relativePath: path.relative(_this2.rootPath, fullPath), name: entry, stats: stats, depth: depth, isFile: false, isDirectory: true }; // Apply custom filters _context5.n = 6; return _awaitAsyncGenerator(_this2.passesCustomFilters(folderEntry)); case 6: if (!_context5.v) { _context5.n = 8; break; } if (!_this2.folderHandler) { _context5.n = 7; break; } _context5.n = 7; return _awaitAsyncGenerator(_this2.folderHandler(folderEntry)); case 7: _context5.n = 8; return folderEntry; case 8: return _context5.d(_regeneratorValues(_asyncGeneratorDelegate(_asyncIterator(_this2.walkIterator(fullPath, depth + 1, type)))), 9); case 9: _context5.n = 15; break; case 10: if (!stats.isFile()) { _context5.n = 15; break; } if (!((type === 'file' || type === 'all') && _this2.options.includeFiles)) { _context5.n = 15; break; } _context5.n = 11; return _awaitAsyncGenerator(_this2.createFileEntry(fullPath, entry, stats, depth)); case 11: fileEntry = _context5.v; _t = fileEntry; if (!_t) { _context5.n = 13; break; } _context5.n = 12; return _awaitAsyncGenerator(_this2.passesCustomFilters(fileEntry)); case 12: _t = _context5.v; case 13: if (!_t) { _context5.n = 15; break; } if (!_this2.fileHandler) { _context5.n = 14; break; } _context5.n = 14; return _awaitAsyncGenerator(_this2.fileHandler(fileEntry)); case 14: _context5.n = 15; return fileEntry; case 15: _context5.n = 17; break; case 16: _context5.p = 16; _t2 = _context5.v; _this2.handleError(_t2, fullPath); case 17: _context5.n = 3; break; case 18: _context5.n = 20; break; case 19: _context5.p = 19; _t3 = _context5.v; _this2.handleError(_t3, dirPath); case 20: return _context5.a(2); } }, _callee5, null, [[4, 16], [1, 19]]); }))(); }; _proto.createFileEntry = /*#__PURE__*/function () { var _createFileEntry = /*#__PURE__*/_asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee6(fullPath, name, stats, depth) { var ext, fileEntry, _t4; return _regenerator().w(function (_context6) { while (1) switch (_context6.n) { case 0: if (!(this.options.maxFileSize && stats.size > this.options.maxFileSize)) { _context6.n = 1; break; } return _context6.a(2, null); case 1: ext = path.extname(name); if (!(this.options.extensions && !this.options.extensions.includes(ext))) { _context6.n = 2; break; } return _context6.a(2, null); case 2: if (!(this.options.pattern && !this.options.pattern.test(name))) { _context6.n = 3; break; } return _context6.a(2, null); case 3: fileEntry = { path: fullPath, relativePath: path.relative(this.rootPath, fullPath), name: name, ext: ext, stats: stats, depth: depth, isFile: true, isDirectory: false }; if (!this.options.readContents) { _context6.n = 7; break; } _context6.p = 4; _context6.n = 5; return fs.promises.readFile(fullPath, this.options.encoding); case 5: fileEntry.content = _context6.v; _context6.n = 7; break; case 6: _context6.p = 6; _t4 = _context6.v; this.handleError(_t4, fullPath); case 7: return _context6.a(2, fileEntry); } }, _callee6, this, [[4, 6]]); })); function createFileEntry(_x4, _x5, _x6, _x7) { return _createFileEntry.apply(this, arguments); } return createFileEntry; }(); _proto.walk = /*#__PURE__*/function () { var _walk = /*#__PURE__*/_asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee7(dirPath, depth) { var _iteratorAbruptCompletion, _didIteratorError, _iteratorError, _iterator, _step, _t5; return _regenerator().w(function (_context7) { while (1) switch (_context7.n) { case 0: // Use the iterator for consistency // eslint-disable-next-line @typescript-eslint/no-unused-vars _iteratorAbruptCompletion = false; _didIteratorError = false; _context7.p = 1; _iterator = _asyncIterator(this.walkIterator(dirPath, depth, 'all')); case 2: _context7.n = 3; return _iterator.next(); case 3: if (!(_iteratorAbruptCompletion = !(_step = _context7.v).done)) { _context7.n = 5; break; } case 4: _iteratorAbruptCompletion = false; _context7.n = 2; break; case 5: _context7.n = 7; break; case 6: _context7.p = 6; _t5 = _context7.v; _didIteratorError = true; _iteratorError = _t5; case 7: _context7.p = 7; _context7.p = 8; if (!(_iteratorAbruptCompletion && _iterator["return"] != null)) { _context7.n = 9; break; } _context7.n = 9; return _iterator["return"](); case 9: _context7.p = 9; if (!_didIteratorError) { _context7.n = 10; break; } throw _iteratorError; case 10: return _context7.f(9); case 11: return _context7.f(7); case 12: return _context7.a(2); } }, _callee7, this, [[8,, 9, 11], [1, 6, 7, 12]]); })); function walk(_x8, _x9) { return _walk.apply(this, arguments); } return walk; }(); _proto.shouldProcess = function shouldProcess(name, fullPath) { if (!this.options.includeHidden && name.startsWith('.')) { return false; } if (this.options.exclude) { for (var _iterator3 = _createForOfIteratorHelperLoose(this.options.exclude), _step3; !(_step3 = _iterator3()).done;) { var pattern = _step3.value; if (name === pattern || fullPath.includes(pattern)) { return false; } } } if (this.options.include) { var included = false; for (var _iterator4 = _createForOfIteratorHelperLoose(this.options.include), _step4; !(_step4 = _iterator4()).done;) { var _pattern = _step4.value; if (name === _pattern || fullPath.includes(_pattern)) { included = true; break; } } if (!included) { return false; } } return true; }; _proto.passesCustomFilters = /*#__PURE__*/function () { var _passesCustomFilters = /*#__PURE__*/_asyncToGenerator(/*#__PURE__*/_regenerator().m(function _callee8(entry) { var _iterator5, _step5, filter, result, _t6; return _regenerator().w(function (_context8) { while (1) switch (_context8.n) { case 0: if (!(!this.options.customFilters || this.options.customFilters.length === 0)) { _context8.n = 1; break; } return _context8.a(2, true); case 1: _iterator5 = _createForOfIteratorHelperLoose(this.options.customFilters); case 2: if ((_step5 = _iterator5()).done) { _context8.n = 8; break; } filter = _step5.value; _context8.p = 3; _context8.n = 4; return filter(entry); case 4: result = _context8.v; if (result) { _context8.n = 5; break; } return _context8.a(2, false); case 5: _context8.n = 7; break; case 6: _context8.p = 6; _t6 = _context8.v; this.handleError(_t6, entry.path); return _context8.a(2, false); case 7: _context8.n = 2; break; case 8: return _context8.a(2, true); } }, _callee8, this, [[3, 6]]); })); function passesCustomFilters(_x0) { return _passesCustomFilters.apply(this, arguments); } return passesCustomFilters; }(); _proto.handleError = function handleError(error, path) { if (this.errorHandler) { this.errorHandler(error, path); } }; return FolderWalker; }(); exports.FolderWalker = FolderWalker; //# sourceMappingURL=folder-walker.cjs.development.js.map