Reputation: 556
In NodeJS, I was trying to read files in a directory and its subdirectories recursively
export const readDirRecursively = (rootDir) => {
const files = [];
return new Promise((resolve, reject) => {
// Inner function for recursive operation
function innerFun(dir) {
fs.readdir(dir, (err, xpaths) => {
if (err) reject(err);
for (let xpath of xpaths) {
const absPath = path.join(dir, xpath);
if (fs.statSync(absPath).isDirectory()) {
innerFun(absPath);
} else {
files.push(absPath);
}
}
});
}
innerFun(rootDir); // Call innerFun to initate
console.log(files); // contains vaules as expected
console.log([...files]); // empty array
console.log(files.map(file => file + ' test')); // empty array
const testVar = [1,2,3,4];
console.log([...testVar]); // This log [1,2,3,4] as expected
resolve(files);
});
};
And I found this unusual behavior with the array. Array files
contains items as expected after recursive function is called. But when I try to map
or copy with rest/spread operator or iterate over it, that array turns out empty.
I tried the same with [1,2,3,4]
just to make sure. With it, everything works as expected. However, only files
array shows this unusual behavior.
Upvotes: 2
Views: 120
Reputation: 324640
When you log the array, are you then expanding it out in the console afterwards?
You've logged an array. Not a value, but an object. So when you go to view it, it shows you the values at the time you view it. But when you do [...files]
, that's a new array constructed from the values of the old one (which there aren't any of yet) and this new array isn't modified by the asynchronous function so you just see that empty array.
Same for files.map(...)
because that also returns a new array with no values.
And finally testVar
doesn't change between the time you log it and the time you view the expanded object in your console.
When debugging objects, consider using console.log(JSON.stringify(files))
to get a "snapshot" of it.
Upvotes: 2