私はPHPのバックグラウンドから来て、「イベント駆動型」のNode.js環境に頭を悩ませようとしています。ディレクトリからファイルを読み取り、Redis を番組のタイトル、シーズン、エピソード番号 (現在データベースに保存されているものより新しい場合) で更新する小さなスクリプトを作成しました。Redis DB のタイトルが「My Show」、シーズン「05」、タイトル「01」のどこに頭を悩ませることができない非同期の問題が発生しているようです。「My Show S05E02」と「My Show S05E01」を含む 2 つのファイルが読み込まれています。
データベースは、シーズン/エピソードが現在のシーズン/エピソードよりも後の場合にのみ更新する必要がありますが、「updateTitle」が非常に迅速に呼び出され、何らかの理由で「My Show S05E02」が「My Show S05E01」の前に渡されるため、更新関数は常に更新されます。両方の値を元の値「My Show S05E01」と比較し、Redis を E02 で更新し、次に E01 で更新します。
コードは次のとおりです。
function processFiles()
{
fs.readdir(WATCH_DIR, function(err, files){
for (var i = 0; i <= files.length; i++)
{
checkFile(files[i]);
}
});
}
function updateTitle(title, season, episode)
{
var cur_season, cur_episode;
redis_client.hget(title, 'Season', function(err, data){
cur_season = data;
redis_client.hget(title, 'Episode', function(err, data){
cur_episode = data;
redis_client.sismember('Titles', title, function(err, data){
console.log('comparing S'+season+'E'+episode+' to current S'+cur_season+'E'+cur_episode);
if ((season == cur_season && episode >= cur_episode) || season > cur_season)
{
redis_client.hset(title, 'Season', season);
redis_client.hset(title, 'Episode', episode);
console.log('setting '+title+' S'+season+'E'+episode);
}
});
});
});
}
function checkFile(file, mtime)
{
var reg = new RegExp("^"+FILE_PREFIX);
var seasoned = new RegExp("S(\\d{2})E(\\d{2})", "i");
var cache = {}
if (reg.test(file))
{
fs.stat(WATCH_DIR + file, function(err, stats){
console.log(file, stats.mtime.toLocaleDateString() +' '+ stats.mtime.toLocaleTimeString() );
fs.readFile(WATCH_DIR + file, 'utf8', function(ferr, data){
if (seasoned.test(data))
{
title = data.replace(/S(\d{2})E(\d{2})(.*?)$/, '')
.replace(/[\._\-]+/, ' ')
.replace(/^\s+/, '')
.replace(/\s+$/, '');
var season = data.match(/S(\d{2})/i);
season = season[1];
var episode = data.match(/E(\d{2})/i);
episode = episode[1];
updateTitle(title, season, episode);
}
});
});
}
}
fs.watch(WATCH_DIR, function(type, file){
if (type == 'change')
{
processFiles();
}
});
どんな助けでも大歓迎です。ここには他にもエラーやベストプラクティスがあると確信しています。それらも自由に共有してください。しかし、私は非同期の問題を理解しようとして頭を壁にぶつけています!
参考までに - これは単なるお気に入りのプロジェクトなので、私が見て楽しんでいる各番組の現在のエピソードを思い出すことができます。