fs-pathdigger v2.0.4
fs-pathdigger
Recursively walks a filesystem and allows modifications and filtering to the rersults
Usage
const walk = require ('fs-pathdigger');
walk( /root/path/to/start/from, options )
// => returns an object with two properties,
// one for folders and one for files.In a nutshell
fs-pathdigger starts at a specified root folder and walks the file system, returning an object with a folders property, containing all the folders it finds (including empty ones) and a files property, containing all the files it finds.
By default, hidden files are not returned and links are not followed, but that behavior can be altered by specifying the hidden and followLinks options, respectively.
fs-pathdigger understands the following options:
hidden => type: Boolean
=> Include hidden files/folders? (default: false)
followLinks => type: Boolean
=> Follow links? (default: false)
relative => type: Boolean
=> Return relative paths? (default: false)
include => type: RegEx, String, or Array
=> A pattern, or array of patterns
return only and any results that match
exclude => type: RegEx, String, or Array
=> A pattern, or array of patterns
exclude any results that match
precedence => type: String
=> Valid settings are 'folders' or 'files'
restricts filtering to one or the other
beforeRoot => type: String
=> Text to insert into each result
before the root folder
afterRoot => type: String
=> Text to insert into each result
after the root folder
beforeExt => type: String
=> Text to insert into each result
before the file extension
afterExt => type: String
=> Text to insert into each result
after the file extension
replaceExt => type: Map
=> A Map of extensions search and replace pairings
happens before insertionsExamples
All examples use the following tree:
.
|____test
| |____lab
| | |____otherFiles
| | | |____asset.png
| | |____index.html
| | |____source
| | | |____views2
| | | | |____view2a.js
| | | | |____view2b.js
| | | |____views1
| | | | |____view1a.jsx
| | | | |____view1b.jsx
| | |____emptyFolder
| | |____link (symbolic link to ../linked)
| | |____assets
| | | |____image1.jpg
| | | |____image2.jpg
| | |____.hiddenFile
| |____linked
| | |____linkedFile.htmlBasic options - hidden, followLinks, relative
With no options at all (hidden files/folders being omitted and links treated like files),
walk ( "/test/lab" ) returns:
{
folders: [
'/test/lab',
'/test/lab/assets',
'/test/lab/emptyFolder',
'/test/lab/otherFiles',
'/test/lab/source',
'/test/lab/source/views1',
'/test/lab/source/views2'
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/index.html',
'/test/lab/link',
'/test/lab/otherFiles/asset.png',
'/test/lab/source/views1/view1a.jsx',
'/test/lab/source/views1/view1b.jsx',
'/test/lab/source/views2/view2a.js',
'/test/lab/source/views2/view2b.js'
]
}To include hidden files and following all links, set hidden or followLinks to true, respectively
walk ( "/test/lab", { followLinks: true, hidden: true } )would return the following:
{
folders: [
'/test/lab',
'/test/lab/assets',
'/test/lab/emptyFolder',
'/test/lab/link',
'/test/lab/otherFiles',
'/test/lab/source',
'/test/lab/source/views1',
'/test/lab/source/views2'
],
files: [
'/test/lab/.hiddenFile',
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/index.html',
'/test/lab/link/linkedFile.html',
'/test/lab/otherFiles/asset.png',
'/test/lab/source/views1/view1a.jsx',
'/test/lab/source/views1/view1b.jsx',
'/test/lab/source/views2/view2a.js',
'/test/lab/source/views2/view2b.js'
]
}To produce the same output as the last example, but return realtive paths, instead, set relative to true.
walk ( "/test/lab", { followLinks: true, hidden: true, relative: true } )returns:
{
folders: [
'.',
'assets',
'emptyFolder',
'link',
'otherFiles',
'source',
'source/views1',
'source/views2'
],
files: [
'.hiddenFile',
'assets/image1.jpg',
'assets/image2.jpg',
'index.html',
'link/linkedFile.html',
'otherFiles/asset.png',
'source/views1/view1a.jsx',
'source/views1/view1b.jsx',
'source/views2/view2a.js',
'source/views2/view2b.js'
]
}Advanced options - filtering and precedence
By default, fs-pathdigger will return both arrays, folders and files with any filters applied to both results equally. In other words, by default, there is no correlation between the two results. Ergo,
walk ( "/test/lab", { include: /html/ } ) // => Using a regex patternreturns:
{
folders: [],
files: [
'/test/lab/index.html'
]
}and
walk ( "/test/lab", { include: "asset" } ) // => Using a regex stringreturns:
{
folders: [
'/test/lab/assets',
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/otherFiles/asset.png'
]
}If you want to apply a filter only to one set of results, files/folders, and produce matching results for the other that correlate, use precedence
For example, let's say you wanted to apply filters to just the filesand have the folders returned be just the parent folders for those file results, you would set the option precedence: 'files'.
Likewise to apply filters to just the folders returned, you would set the option precedence: 'folders'. The files returned would be all children of those folders, regardless of filters applied.
Thus,
walk ( "/test/lab", { include: "asset", precedence: 'files' } )returns:
{
folders: [
'/test/lab/assets',
'/test/lab/otherFiles'
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/otherFiles/asset.png'
]
}and
walk ( "/test/lab", { include: "asset", precedence: 'folders' } )returns:
{
folders: [
'/test/lab/assets'
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg'
]
}You can also exclude patterns, as well, by using the exclude option. Like, include, the option takes either a pattern or an array of patterns.
walk ( "/test/lab", { exclude: [ /\.js.?$/, "html" ] } )returns:
{
folders: [
'/test/lab',
'/test/lab/assets',
'/test/lab/emptyFolder',
'/test/lab/otherFiles',
'/test/lab/source',
'/test/lab/source/views1',
'/test/lab/source/views2'
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/link',
'/test/lab/otherFiles/asset.png'
]
}Using the same pattern in an include and an exclude will always produce a null result.
So, this:
walk ( "/test/lab", { exclude: [ /\.js.?$/, "html" ], include "html" } )returns:
{
folders: [],
files: []
}Extra options for inserting text and replacing file extensions
You can insert text before and after the root folder specified, in the results, by using the beforeRoot and afterRoot options. Paths will be normalized, so don't worry about unneeded slashes.
For example:
walk ( "/test/lab", { beforeRoot: "C:/", afterRoot: "/test/" } )returns
{
folders: [
'C:/test/lab/test',
'C:/test/lab/test/assets',
'C:/test/lab/test/emptyFolder',
'C:/test/lab/test/otherFiles',
'C:/test/lab/test/source',
'C:/test/lab/test/source/views1',
'C:/test/lab/test/source/views2'
],
files: [
'C:/test/lab/test/assets/image1.jpg',
'C:/test/lab/test/assets/image2.jpg',
'C:/test/lab/test/index.html',
'C:/test/lab/test/link',
'C:/test/lab/test/source/views1/view1a.jsx',
'C:/test/lab/test/source/views1/view1b.jsx',
'C:/test/lab/test/source/views2/view2a.js',
'C:/test/lab/test/source/views2/view2b.js'
]
}You can also insert text before and after all file extensions, in the results, by using the beforeExt and afterExt options. Note that files without extensions will be ignored by these options.
For example:
walk ( "/test/lab", { beforeExt: ".spec", afterExt: ".backup" } )returns
{
folders: [
'/test/lab',
'/test/lab/assets',
'/test/lab/emptyFolder',
'/test/lab/otherFiles',
'/test/lab/source',
'/test/lab/source/views1',
'/test/lab/source/views2'
],
files: [
'/test/lab/assets/image1.spec.jpg.backup',
'/test/lab/assets/image2.spec.jpg.backup',
'/test/lab/index.spec.html.backup',
'/test/lab/link',
'/test/lab/otherFiles/asset.spec.png.backup',
'/test/lab/source/views1/view1a.spec.jsx.backup',
'/test/lab/source/views1/view1b.spec.jsx.backup',
'/test/lab/source/views2/view2a.spec.js.backup',
'/test/lab/source/views2/view2b.spec.js.backup'
]
}If you want to be more specific, when modifying extensions, use the 'replaceExt' option. This option takes a Map of extensions to search for and their corresponding replacements. Provided extensions should be literal strings starting with a dot (.); patterns are not supported with this option.
Note that if for some reason you wanted to add an extension to all files with no extension, you can add ['','.some_extension'] to your Map.
For example:
let swapit = new Map([ ['.js','.spec.js'], ['.jsx','.spec.jsx'] ]);
walk ( "/test/lab", { replaceExt: swapit } )returns:
{
folders: [
'/test/lab',
'/test/lab/assets',
'/test/lab/emptyFolder',
'/test/lab/otherFiles',
'/test/lab/source',
'/test/lab/source/views1',
'/test/lab/source/views2'
],
files: [
'/test/lab/assets/image1.jpg',
'/test/lab/assets/image2.jpg',
'/test/lab/index.html',
'/test/lab/link',
'/test/lab/otherFiles/asset.png',
'/test/lab/source/views1/view1a.spec.jsx',
'/test/lab/source/views1/view1b.spec.jsx',
'/test/lab/source/views2/view2a.spec.js',
'/test/lab/source/views2/view2b.spec.js'
]
}TO-DOs
I don't know. You tell me.
Credit
fs-pathdigger wouldn't be possible without my good friend, Oibaf.
I mostly did this for fun and to create something a little more robust and easier to use than other solutions I've tried. I hope you enjoy!
License
Licensed under MIT (Mother Insured Task) - a.k.a. contribute please, but no criticizing Oibaf's mother's cooking or she will beat you senseless with an old wooden soup ladel.
Copyleft (c) 2019 by Nosaj and Oibaf - "we code, you like, that how work"