Edited at

【node.js】asyncで同期処理【サンプルリポジトリ公開】

More than 3 years have passed since last update.

node.js では非同期の動きに苦労することが多いのですが、同期処理をサポートするモジュール「async」の動きを実際に動作できる形で紹介します。


asyncについて

assyncについては以下を参照のこと。


リポジトリ

https://github.com/caolan/async


公式ドキュメント

http://caolan.github.io/async/


Node.jsへの導入

npm install async


使用例


series

順次処理


記述例

    console.log("-- Series test start ----------");

async.series([
function (callback) {
console.log("1");
setTimeout(function() {
console.log("1 done");
callback(null, 1);
}, 100);
},
function (callback) {
console.log("2");
setTimeout(function() {
console.log("2 done");
callback("exit!", 1);
}, 100);
},
function (callback) {
console.log("3");
setTimeout(function() {
console.log("3 done");
callback(null, 1);
}, 100);
},
], function (err, results) {
if (err) {
console.log("err[" + err + "]");
}
console.log("- Series test done [" + results + "] ----------");
});
console.log("Series test end of line");


結果

-- Series test start ----------

1
Series test end of line
1 done
2
2 done
err[exit!]


waterfall

順次処理(次の関数に値を渡せる)


記述例

    console.log("-- Waterfall test start ----------");

async.waterfall([
function (callback) {
console.log("1");
setTimeout(function() {
console.log("1 done");
callback(null, 1);
}, 100);
},
function (arg, callback) {
console.log("from:" + arg);
console.log("2");
setTimeout(function() {
console.log("2 done");
callback("exit!", 2);
}, 100);
},
function (arg, callback) {
console.log("3");
setTimeout(function() {
console.log("3 done");
callback(null, 1);
}, 100);
}
], function (err, results) {
if (err) {
console.log("err[" + err + "]");
}
console.log("- Waterfall test done [" + results + "] ----------");
});
console.log("Waterfall test end of line");


結果

-- Waterfall test start ----------

1
Waterfall test end of line
1 done
from:1
2
2 done
err[exit!]
- Waterfall test done [2] ----------


eachSeries

コレクションの要素に基づいた同期処理


記述例

    console.log("-- EachSeries test start ----------");

var a = [1,2,3,4,5,6,7,8,9,10];
async.eachSeries(a, function(i, callback){
setTimeout(function() {
console.log('eachSeries : ' + i);
if (i > 5) {
callback("exit!");
} else {
callback(null);
}
}, 100);

}, function(err){
if (err) {
console.log("err[" + err + "]");
}
console.log("- EachSeries test done" + " ----------");
});
console.log("EachSeries test end of line");


結果

-- EachSeries test start ----------

EachSeries test end of line
eachSeries : 1
eachSeries : 2
eachSeries : 3
eachSeries : 4
eachSeries : 5
eachSeries : 6
err[exit!]
- EachSeries test done ----------


mapSeries

コレクションの要素に基づいた同期処理(マップ使用)


記述例

    console.log("-- MapSeries test start ----------");

var m = [
{ id: 1, value:'first' },
{ id: 2, value:'second' },
{ id: 3, value:'third' },
];
async.eachSeries(m, function(item, callback){
setTimeout(function() {
console.log('mapSeries : id[' + item.id + '] value[' + item.value + ']');
if (item.value == 'second') {
callback("exit!");
} else {
callback(null);
}
}, 100);

}, function(err){
if (err) {
console.log("err[" + err + "]");
}
console.log("- MapSeries test done" + " ----------");
testComplete()
});
console.log("MapSeries test end of line");


結果

-- MapSeries test start ----------

MapSeries test end of line
mapSeries : id[1] value[first]
mapSeries : id[2] value[second]
err[exit!]
- MapSeries test done ----------


timesSeries

回数を指定しての同期処理


記述例

    console.log("-- TimesSeries test start ----------");

async.timesSeries(10, function(i, callback){
setTimeout(function() {
console.log('timesSeries : ' + i);
if (i > 5) {
callback("exit!");
} else {
callback(null);
}
}, 100);

}, function(err){
if (err) {
console.log("err[" + err + "]");
}
console.log("- TimesSeries test done" + " ----------");
testComplete()
});
console.log("TimesSeries test end of line");


結果

-- TimesSeries test start ----------

TimesSeries test end of line
timesSeries : 0
timesSeries : 1
timesSeries : 2
timesSeries : 3
timesSeries : 4
timesSeries : 5
timesSeries : 6
err[exit!]
- TimesSeries test done ----------


組み合わせ

上記の複数の同期処理を呼ぶ出す同期処理


記述例

async.series([

function (callback) {
series.test(function() {
callback(null, "series");
});
},
function (callback) {
waterfall.test(function() {
callback(null, "waterfall");
});
},
function (callback) {
eachSeries.test(function() {
callback(null, "eachSeries");
});
},
function (callback) {
mapSeries.test(function() {
callback(null, "mapSeries");
});
},
function (callback) {
timesSeries.test(function() {
callback(null, "timesSeries");
});
},
function (callback) {
each.test(function() {
callback(null, "each");
});
},
], function (err, results) {
if (err) {
console.log("err[" + err + "]");
}
console.log('async test all done. ' + results);
});


サンプルコード

上記の処理を確認できるソースコードを下記に用意したので参考にしてください。

https://github.com/k-neo/tryAsync



筆者参考

札幌圏でリモート開発、在宅勤務を中心としたシステム開発の会社を経営しています。

ローラハウス