{"id":16515,"library":"readdir-glob","title":"readdir-glob: Streaming Recursive Directory Reader with Glob Filtering","description":"readdir-glob provides a memory-efficient, recursive file system directory reader with a streaming API, designed as an alternative to `node-glob` for scenarios requiring constant memory usage regardless of the file system size or the number of matched files. It leverages the `minimatch` library for glob pattern filtering. The current stable version is `3.0.0`, which requires Node.js 18 or later. The library ships with TypeScript types since v2.0.0 and supports both CommonJS and ESM. Its primary differentiator is its low, constant memory footprint, making it suitable for processing very large file systems where other glob libraries might exhaust memory. Releases appear to be driven by Node.js version updates and dependency security patches, with major versions aligning with Node.js LTS cycles.","status":"active","version":"3.0.0","language":"javascript","source_language":"en","source_url":"git://github.com/Yqnn/node-readdir-glob","tags":["javascript","recursive","fs","stream","streams","readdir","filesystem","find","filter","typescript"],"install":[{"cmd":"npm install readdir-glob","lang":"bash","label":"npm"},{"cmd":"yarn add readdir-glob","lang":"bash","label":"yarn"},{"cmd":"pnpm add readdir-glob","lang":"bash","label":"pnpm"}],"dependencies":[{"reason":"Core library for glob pattern matching.","package":"minimatch","optional":false}],"imports":[{"note":"Since v3.0.0, the main function is exported as a default export in ESM. Prior versions might have allowed named imports or different patterns.","wrong":"import { readdirGlob } from 'readdir-glob';","symbol":"readdirGlob","correct":"import readdirGlob from 'readdir-glob';"},{"note":"This CommonJS `require` syntax is fully supported across all major versions, including v3.0.0.","symbol":"readdirGlob (CommonJS)","correct":"const readdirGlob = require('readdir-glob');"},{"note":"TypeScript types are available since v2.0.0. Use `import type` for type-only imports to prevent bundling issues and ensure correct type stripping.","wrong":"import { ReaddirGlobOptions } from 'readdir-glob';","symbol":"ReaddirGlobOptions","correct":"import type { ReaddirGlobOptions, Match } from 'readdir-glob';"}],"quickstart":{"code":"import readdirGlob from 'readdir-glob';\nimport path from 'path';\n\nconst rootDir = process.env.ROOT_DIR ?? '.'; // Specify a root directory or use current\nconst globber = readdirGlob(rootDir, { pattern: '**/*.js', ignore: 'node_modules/**', stat: true });\n\nconsole.log(`Searching for .js files in '${rootDir}' (excluding node_modules)...`);\n\nglobber.on('match', match => {\n    // match.relative: relative path of the matched file\n    // match.absolute: absolute path of the matched file\n    // match.stat: stat of the matched file (only if stat:true option is used)\n    console.log(`Found: ${match.relative} (Absolute: ${match.absolute})`);\n});\n\nglobber.on('error', err => {\n    console.error('Fatal error during globbing:', err);\n});\n\nglobber.on('end', () => {\n    console.log('File search completed.');\n});\n\n// Example of pausing and resuming the search\nsetTimeout(() => {\n  if (!globber.paused) {\n    globber.pause();\n    console.log('Search paused for 2 seconds.');\n    setTimeout(() => {\n      globber.resume();\n      console.log('Search resumed.');\n    }, 2000);\n  }\n}, 1000);\n","lang":"typescript","description":"This quickstart demonstrates how to initialize `readdir-glob` to find all `.js` files recursively within a specified root directory, excluding `node_modules`, and streaming the results. It also shows basic error handling and how to use the `pause` and `resume` methods."},"warnings":[{"fix":"Upgrade your Node.js runtime to the version required by your `readdir-glob` installation (e.g., Node.js 18+ for v3.0.0).","message":"Node.js version requirements have increased with major releases. v1.x required Node.js 10+, v2.x required Node.js 14+, and v3.x now requires Node.js 18 or later. Ensure your Node.js environment meets the minimum version for the `readdir-glob` version you are using.","severity":"breaking","affected_versions":">=1.0.0"},{"fix":"Update your ESM `import` statements for `readdirGlob` from named to default: `import readdirGlob from 'readdir-glob';`.","message":"Starting with v3.0.0, the package's ESM module uses a default export for the `readdirGlob` function. If you were using a named import (e.g., `import { readdirGlob } from 'readdir-glob'`) in ESM for previous versions (v2.x), you must change it to a default import (e.g., `import readdirGlob from 'readdir-glob'`).","severity":"breaking","affected_versions":">=3.0.0"},{"fix":"Avoid `stat: true` and `follow: true` if you don't need file stats or symlink traversal. For better performance, leverage `options.skip` to restrict the search as much as possible, as it prunes the directory tree before processing.","message":"The `stat: true` and `follow: true` options can significantly reduce performance, as they require `readdir-glob` to perform `stat` calls on *all* matched results or follow symlinked directories, respectively. Use these options only when necessary.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"For entire directory branches you want to exclude from the search, use `options.skip`. For filtering individual files or directories found within explored paths, use `options.ignore`. Both `ignore` and `skip` patterns always operate in `dot:true` mode.","message":"Understand the difference between `options.ignore` and `options.skip`. `ignore` patterns filter out matched files/folders but do not prevent their contents from being explored. `skip` patterns, however, prevent a matching folder and all its children from being returned or explored, significantly improving performance for large excluded branches.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Review `minimatch` changelogs when upgrading `readdir-glob` across major versions to understand potential subtle behavior shifts in glob pattern matching. Ensure you are on a `minimatch` version >=10.2.1 to mitigate known ReDoS vulnerabilities.","message":"The underlying `minimatch` dependency has seen multiple major version bumps (e.g., from 5.x to 9.x in v2.0.0, and 9.x to 10.x in v3.0.0). While `readdir-glob` aims to abstract this, direct `minimatch` behavior (like handling of `.` and `..` in patterns, or specific glob features) might subtly change. `minimatch` versions 9.0.6 and higher require Node.js 18+. `minimatch` versions 10.2.0 and below are vulnerable to ReDoS if patterns contain many consecutive `*` wildcards.","severity":"breaking","affected_versions":">=2.0.0"}],"env_vars":null,"last_verified":"2026-04-22T00:00:00.000Z","next_check":"2026-07-21T00:00:00.000Z","problems":[{"fix":"For ESM (v3.0.0+), use `import readdirGlob from 'readdir-glob';`. For CommonJS, use `const readdirGlob = require('readdir-glob');`.","cause":"Attempting to use `readdirGlob` as a named import in ESM when it's a default export (v3.0.0+), or incorrectly importing in CommonJS.","error":"TypeError: readdirGlob is not a function"},{"fix":"Ensure the first argument to `readdirGlob` is a valid string representing the directory path to start searching, e.g., `readdirGlob('.', { pattern: '**/*.js' });`.","cause":"The `root` argument for `readdirGlob` was not provided or was `undefined`.","error":"Error: The \"path\" argument must be of type string or an instance of Buffer or URL. Received undefined"},{"fix":"Verify your `pattern` string. If matching files or directories starting with a `.` (dotfiles), ensure `options.dot` is set to `true`. Check `options.ignore` and `options.skip` patterns to confirm they aren't unintentionally excluding desired files. Note that `ignore` and `skip` patterns always operate in `dot:true` mode.","cause":"Incorrect glob pattern syntax, or `dot` option not enabled for matching dotfiles, or misconfigured `ignore`/`skip` patterns.","error":"No files are being matched, even though they exist."}],"ecosystem":"npm"}