一部のURLを非同期で呼び出して結果を収集しようとしています。私は "約束"でそれをやった。今、私はasync.jsの周りを頭で囲んでいます。ここでasync.eachはコールバックを実行しません
は切り取らコードです:
var request = require("request"),
cheerio = require("cheerio");
// base_url = "http://de.indeed.com/Jobs?q="; // after equal sign for instance: sinatra&l=
var async = require('async');
/* search syntax:
- http://de.indeed.com/Jobs?q=node&l=berlin&radius=100
*/
var search_words = ["django", "python", "flask",
"rails", "ruby",
"node", "javascript", "angularjs", "react", "express", "meteor",
"java", "grails", "groovy",
"php", "symfony", "laravel" ];
var base_url = "http://de.indeed.com/Jobs?q=";
var stats = [];
async.each(search_words, function(keyword) {
var url = base_url + keyword + "&l=";
request(base_url + keyword + "&l=", function(err, resp, body) {
if (err) throw err;
$ = cheerio.load(body);
num_str = $("#searchCount")[0].children[0].data.split(" ").reverse()[0];
num_str = num_str.replace(/\./, "");
num_str = num_str.replace(/,/, "");
stats.push([keyword, num_str]);
});
}, function(err) {
if (err) throw err;
console.log(stats);
});
thisによると、私は配列を処理した後、それがトリガされますasync.eachする最後の引数としてコールバック関数を渡すことができます。
私の場合、コールバックは決して誘発されないようです。
Btw:Trevor Burnhamは彼の本 "Async Javascript"でasyn.forEach関数を説明しています。これはasync.jsから削除されたようですか?
@robertklepは、iteratee関数にコールバックを追加するヒントを与えました。 //これは、作業バージョンは次のとおりです。アイテムとコールバック:
var request = require("request"),
cheerio = require("cheerio");
// base_url = "http://de.indeed.com/Jobs?q="; // after equal sign for instance: sinatra&l=
var async = require('async');
/* search syntax:
- http://de.indeed.com/Jobs?q=node&l=berlin&radius=100
*/
var search_words = ["django", "python", "flask",
"rails", "ruby",
"node", "javascript", "angularjs", "react", "express", "meteor",
"java", "grails", "groovy",
"php", "symfony", "laravel" ];
var base_url = "http://de.indeed.com/Jobs?q=";
var stats = [];
async.each(search_words, function(keyword, callback) {
var url = base_url + keyword + "&l=";
request(url, function(err, resp, body) {
if (err) {
callback("ERROR in request");
} else {
$ = cheerio.load(body);
num_str = $("#searchCount")[0].children[0].data.split(" ").reverse()[0];
num_str = num_str.replace(/\./, "");
num_str = num_str.replace(/,/, "");
num = parseInt(num_str);
stats.push([keyword, num]);
callback();
}
});
}, function(err) {
if(err) {
console.log(err);
} else {
stats_sorted = stats.sort(function(a, b) {
return b[1] - a[1];
});
console.log(stats_sorted);
}
});
あなたは、コールバックの一部について権利ですからレスポンスを返した後、コールバックで結果をパスバックする必要があります。 しかし、コールバック 'return callback();'を返す代わりに 'callback();'を実行するだけで済むわけではありません。これはContinuation Passing Style(CPS)では使用されていません。あなたが制御する関数から別の関数に戻るのではありません。 – Ugur
また、 'stats.push([keyword、num_str])'の前に 'console.log([keyword、num_str]);'を実行すると正しいデータが得られます。 'stats.push([keyword、num_str]);はなぜstats配列に追加されないのですか?またはそれは? – Ugur
Btwはasync.map()へのポインタをありがとう! – Ugur