I am trying to loop through a directory and require every file in it. My code is working, but I was wondering why I had to modify the path in fs functions. (Code below stripped of useless info)
Folder structure:
project
|-- bin
| `-- start
|-- modules
| |-- file1.js
| `-- file2.js
`-- package.json
/bin/start:
#!/usr/bin/env node
// Require dependencies
var fs = require('fs')
// Get modules
// NOTE: fs is looking in the project folder, but this file is in the bin folder
fs.readdir('./modules', function (err, files) {
// Handle error
if (err) {
console.log(err)
process.exit(1)
}
// Loop through files
files.forEach(function (file, index) {
// Get info about file
fs.stat('./modules/' + file, function (err, stat) {
// Handle error
if (err) {
console.log(err)
process.exit(1)
}
// If it is a file
if (stat.isFile()) {
// NOTE: require is looking in the bin folder, and this file is in the bin folder
require('../modules/' + file)
}
})
})
})
package.json:
{
"name": "modular-chat",
"version": "1.0.0",
"description": "A simple modular example of a chat application",
"scripts": {
"start": "node ./bin/start"
},
"author": "JoshyRobot",
"license": "MIT"
}
require
is a Node function. It's just that require
uses __dirname
as the basename when resolving relative paths rather than the current working directory which is also the result of process.cwd()
.
You simply need to join __dirname
to your relative paths before passing them to fs
functions. Using using path.join(__dirname, '../modules')
and path.join(__dirname, '../modules', file)
. Use these in your fs.readdir
and fs.stat
calls:
fs.readdir(path.join(__dirname, '../modules'), function (err, files) {
fs.stat(path.join(__dirname, '../modules', file), function (err, stat) {
This makes both your fs calls and the require align so that the right files are loaded.
It is also not that hard to do the reverse and make require load any path:
Rather than require(path.join('../modules/', file))
:
require(path.join(process.cwd(), '../modules/', file))
This works because require
doesn't change absolute paths as it does with relative paths by prepending __dirname
.