@@ -28,7 +28,6 @@ const {
2828 ArrayFromAsync,
2929 ArrayPrototypePush,
3030 BigIntPrototypeToString,
31- Boolean,
3231 FunctionPrototypeCall,
3332 MathMax,
3433 Number,
@@ -57,9 +56,6 @@ const {
5756 F_OK ,
5857 O_WRONLY ,
5958 O_SYMLINK ,
60- UV_DIRENT_DIR ,
61- UV_DIRENT_LINK ,
62- UV_DIRENT_UNKNOWN ,
6359} = constants ;
6460
6561const pathModule = require ( 'path' ) ;
@@ -105,8 +101,8 @@ const {
105101 } ,
106102 copyObject,
107103 Dirent,
108- getDirent,
109104 getDirents,
105+ getRecursiveDirents,
110106 getOptions,
111107 getValidatedFd,
112108 getValidatedPath,
@@ -1742,43 +1738,6 @@ function mkdirSync(path, options) {
17421738 }
17431739}
17441740
1745- /**
1746- * Appends one directory's entries to `context.results` and the subdirectories
1747- * still to visit to `context.dirs` (with the prefix their entries get in
1748- * string results in `context.prefixes`). `result` is a `binding.readdir()`
1749- * result with file types, so only symbolic links and entries of unknown type
1750- * need a stat() to find out whether they lead to a directory.
1751- * @param {string } dir
1752- * @param {string } prefix
1753- * @param {[string[], number[]] } result
1754- * @param {{ withFileTypes: boolean, results: (string | Dirent)[], dirs: string[], prefixes: string[] } } context
1755- */
1756- function collectRecursiveReaddirResult ( dir , prefix , { 0 : names , 1 : types } , context ) {
1757- const { length } = names ;
1758- for ( let i = 0 ; i < length ; i ++ ) {
1759- const name = names [ i ] ;
1760- const relative = prefix === '' ? name : `${ prefix } ${ pathModule . sep } ${ name } ` ;
1761- let isDirectory ;
1762- if ( context . withFileTypes ) {
1763- const dirent = getDirent ( dir , name , types [ i ] ) ;
1764- ArrayPrototypePush ( context . results , dirent ) ;
1765- // Follow symbolic links to directories, see https://github.com/nodejs/node/issues/52663
1766- isDirectory = dirent . isDirectory ( ) ||
1767- ( dirent . isSymbolicLink ( ) && binding . internalModuleStat ( pathModule . join ( dir , name ) ) === 1 ) ;
1768- } else {
1769- ArrayPrototypePush ( context . results , relative ) ;
1770- const type = types [ i ] ;
1771- isDirectory = type === UV_DIRENT_DIR ||
1772- ( ( type === UV_DIRENT_LINK || type === UV_DIRENT_UNKNOWN ) &&
1773- binding . internalModuleStat ( pathModule . join ( dir , name ) ) === 1 ) ;
1774- }
1775- if ( isDirectory ) {
1776- ArrayPrototypePush ( context . dirs , pathModule . join ( dir , name ) ) ;
1777- ArrayPrototypePush ( context . prefixes , relative ) ;
1778- }
1779- }
1780- }
1781-
17821741/*
17831742 * An recursive algorithm for reading the entire contents of the `basePath` directory.
17841743 * This function does not validate `basePath` as a directory. It is passed directly to
@@ -1792,79 +1751,30 @@ function collectRecursiveReaddirResult(dir, prefix, { 0: names, 1: types }, cont
17921751 * @returns {void }
17931752*/
17941753function readdirRecursive ( basePath , options , callback ) {
1795- const context = {
1796- withFileTypes : Boolean ( options . withFileTypes ) ,
1797- results : [ ] ,
1798- dirs : [ basePath ] ,
1799- prefixes : [ '' ] ,
1754+ const withFileTypes = ! ! options . withFileTypes ;
1755+ const req = new FSReqCallback ( ) ;
1756+ req . oncomplete = ( err , result ) => {
1757+ if ( err ) {
1758+ callback ( err ) ;
1759+ return ;
1760+ }
1761+ callback ( null , withFileTypes ? getRecursiveDirents ( basePath , result ) : result ) ;
18001762 } ;
1801-
1802- let i = 0 ;
1803-
1804- /**
1805- * Reads one directory from `context.dirs` and then moves on to the next
1806- * one, or calls back once none are left.
1807- * @param {string } path
1808- * @param {string } prefix path of this directory relative to `basePath`
1809- */
1810- function read ( path , prefix ) {
1811- const req = new FSReqCallback ( ) ;
1812- req . oncomplete = ( err , result ) => {
1813- if ( err ) {
1814- callback ( err ) ;
1815- return ;
1816- }
1817-
1818- if ( result === undefined ) {
1819- callback ( null , context . results ) ;
1820- return ;
1821- }
1822-
1823- try {
1824- collectRecursiveReaddirResult ( path , prefix , result , context ) ;
1825- } catch ( err ) {
1826- callback ( err ) ;
1827- return ;
1828- }
1829-
1830- if ( i < context . dirs . length ) {
1831- read ( context . dirs [ i ] , context . prefixes [ i ++ ] ) ;
1832- } else {
1833- callback ( null , context . results ) ;
1834- }
1835- } ;
1836-
1837- binding . readdir ( path , options . encoding , true , req ) ;
1838- }
1839-
1840- read ( context . dirs [ i ] , context . prefixes [ i ++ ] ) ;
1763+ binding . readdirRecursive ( basePath , options . encoding , withFileTypes , req ) ;
18411764}
18421765
18431766/**
1844- * An iterative algorithm for reading the entire contents of the `basePath` directory.
1845- * This function does not validate `basePath` as a directory. It is passed directly to
1846- * `binding.readdir `.
1847- * @param {string } basePath
1767+ * Synchronously reads the entire contents of the `basePath` directory.
1768+ * This function does not validate `basePath` as a directory. It is passed
1769+ * directly to `binding.readdirRecursive `.
1770+ * @param {string | Buffer } basePath
18481771 * @param {{ encoding: string, withFileTypes: boolean } } options
1849- * @returns {string[] | Dirent[] }
1772+ * @returns {string[] | Buffer[] | Dirent[] }
18501773 */
18511774function readdirSyncRecursive ( basePath , options ) {
1852- const context = {
1853- withFileTypes : Boolean ( options . withFileTypes ) ,
1854- results : [ ] ,
1855- dirs : [ basePath ] ,
1856- prefixes : [ '' ] ,
1857- } ;
1858-
1859- for ( let i = 0 ; i < context . dirs . length ; i ++ ) {
1860- const dir = context . dirs [ i ] ;
1861- const result = binding . readdir ( dir , options . encoding , true ) ;
1862- if ( result !== undefined ) {
1863- collectRecursiveReaddirResult ( dir , context . prefixes [ i ] , result , context ) ;
1864- }
1865- }
1866-
1867- return context . results ;
1775+ const withFileTypes = ! ! options . withFileTypes ;
1776+ const result = binding . readdirRecursive ( basePath , options . encoding , withFileTypes ) ;
1777+ return result !== undefined && withFileTypes ? getRecursiveDirents ( basePath , result ) : result ;
18681778}
18691779
18701780/**
@@ -1898,9 +1808,6 @@ function readdir(path, options, callback) {
18981808 }
18991809
19001810 if ( options . recursive ) {
1901- // Make shallow copy to prevent mutating options from affecting results
1902- options = copyObject ( options ) ;
1903-
19041811 readdirRecursive ( path , options , callback ) ;
19051812 return ;
19061813 }
0 commit comments