我循环浏览目录中的文件并将文件详细信息存储到数组data
。如果我不尝试运行fs.stat
以获取文件创建/编辑日期等内容,则以下代码将填充数组:
fs.readdir('../src/templates', function (err, files) {
if (err) {
throw err;
}
var data = [];
files
.forEach(function (file) {
try {
fs.stat('../src/templates/'+file,(error,stats) => {
data.push({ Name : file,Path : path.join(query, file) });
});
} catch(e) {
console.log(e);
}
});
res.json(data);
});
});
如果我将data.push(...)
移到fs.stat
之外,则数组将返回文件数据。在fs.stat
内,它返回空。我认为这是一个异步问题,因为for循环正在运行并在fs.stat
运行之前完成。
我认为我需要在这里使用承诺,但不确定。
答案 0 :(得分:4)
如果您想要或需要异步:
const fs = require("fs");
const path = require("path");
const { promisify } = require("util");
const asyncStat = promisify(fs.stat);
fs.readdir('../src/templates', async function(err, files) {
if (err) {
throw err;
}
const data = await Promise.all(files.map(async function(file) {
try {
const stats = await asyncStat('../src/templates/' + file);
return { Name: file, Path: path.join(query, file), stats };
} catch (e) {
console.log(e);
}
}));
res.json(data);
});
请注意,我使用了map
而不是forEach
,然后等待所有Promises(async
使函数返回一个promise)。
我还需要更改fs.stat
以使用util.promisify
承诺。
答案 1 :(得分:2)
你对异步调用中的问题是正确的。您可以使用承诺,也可以使用fs.statSync(...)
,它返回fs.Stats
个对象并同步运行。
files.forEach(function (file) {
try {
var fileStats = fs.statSync('../src/templates/' + file);
data.push({
Name : file,
Path : path.join(query, file)
});
} catch(e) {
console.log(e);
}
});