我目前正在通过编写一个简单的音乐数据库程序来学习javascript和nodeJS。这个想法非常简单,它递归扫描一个目录,解析任何mp3文件,并根据这些信息创建一个数据库。我写了我的第一个版本,它看起来像这样:
var fs = require('graceful-fs');
var metadata = require('musicmetadata');
function recursiveScan(directory){
var files = fs.readdirSync( directory );
// loop through files
for (var i=0; i < files.length; i++) {
var filePath = directory + files[i];
var stat = fs.statSync(filePath);
// Check if it's a directory
if(stat.isDirectory()){
// Scan that directory
recursiveScan(filePath + '/');
}else{
// Find the file extension
var extension = getFileExtension(files[i]);
// If it's an mp3 file, parse it and add it the db
if (extension == 'mp3' ) {
var parser = metadata(fs.createReadStream(filePath), function (err, songInfo) {
// ... insert song into database
});
}
}
}
}
我在一个带有几十个mp3的目录上运行它并且工作正常。然后我在一个有几千个mp3的目录上运行它,很快意识到致命的缺陷。
由于元数据插件的异步特性,此脚本将以递归方式快速扫描所有目录,并尝试一次打开太多文件,导致其崩溃。
限制在给定时间打开的文件数量的最佳方法是什么?我正在考虑使用发电机,但我仍然试图围绕它们的工作方式。
答案 0 :(得分:1)
使用promises来做到这一点。它确保代码流并防止将许多文件加载到内存中一次。可以找到一个很好的探索https://cloud.google.com/appengine/docs