0

私はnodejsの初心者であり、すべての非同期のものに慣れています。

以下を使用します。-Node-MySQL(https://github.com/felixge/node-mysql)-今すぐリクエスト(https://github.com/mikeal/request)モジュール。

URLの大きなリスト(10,000個のURL)をクエリし、HTTPステータスを取得するためにHTTPGETリクエストを送信しようとしています。

それは機能しますが、問題は、コードを実行すると、MySQLクエリの各行が返されるときに、processURL関数が呼び出され、各URL値の直後に「BEFORE」と「AFTER」がログに記録されることです(理解できます)HTTPリクエストを送信しますが、MySQLクエリが完了するのを待ってからHTTPステータスを返します。

単純に、クエリの実行中にこれらのURLをチェックして結果を返すことはできません。クエリが完了するのを待って、HTTPリクエストの結果を返します。

これは、各行がストリーミングされるときにprocessURL関数を実行するため、私には無意味に見えます。完全なコードは次のとおりです。

var mysql       = require('mysql');

var connection = mysql.createConnection({
  host     : 'localhost',
  user     : 'root',
  password : '',
  database : 'urlDB',
});

var query = connection.query('SELECT * FROM urls LIMIT 10000');
query.on('error', function(err) {
    console.log(err);
})
query.on('result', function(row) {
    processURL(row.urlValue, function() {

    });
    console.log(row.urlValue);
})

function processURL (url){
    var request     = require('request');
    var startTime = new Date();
    console.log('BEFORE');
    request({
        uri: url,
        method: 'GET',
    }, function(error, response, body) {
        console.log('INSIDE');
        var endTime = new Date();

        if (!error) {
            console.log(response.statusCode + '  Start: ' + startTime + '  End: ' + endTime);
        } else {
            console.log('timeout');
        }
    })
    console.log('AFTER');
}

出力は次のとおりです。www.google.comBEFOREAFTERwww.yahoo.com BEFORE AFTER www.cnn.com BEFORE AFTER ...ただし、クエリが完了するまで「INSIDE」はありません。

どんな助けでもありがたいです、そしてどうもありがとう。

4

1 に答える 1

0

結果が遅くなるように例を変更しましたが、期待どおりに機能します。コピーして貼り付けて試すことができます。

var request = require('request');

var urls = ['http://google.com', 'http://yahoo.com', 'http://ninjaturtles.com'];

getResultSlowly();

function getResultSlowly() {
  var result = urls.shift();
  if (!result) return;

  console.log(result);
  processUrl(result);
  setTimeout(getResultSlowly, 1000);
}

function processUrl(url) {
  var startTime = new Date();
  console.log('BEFORE');
  request({
    uri: url,
    method: 'GET',
  }, function(error, response, body) {
    console.log('INSIDE');
    var endTime = new Date();

    if (!error) {
      console.log(response.statusCode + '  Start: ' + startTime + '  End: ' + endTime);
    } else {
      console.log('timeout');
    }
  })
  console.log('AFTER');
}

ネットワーク遅延が非同期動作を覆い隠している可能性があります。

クエリの結果はほぼ瞬時に返さresultれ、コードを実行するとすぐにいくつかのイベントが発生します。ただし、requestイベントはgoogleやyahooなどと接続する必要があるため、かなり長くかかります(1〜2ミリ秒であっても)。

出力:

$ node asynctest.js 
http://google.com
BEFORE
AFTER
INSIDE
200  Start: Sat Dec 29 2012 11:31:34 GMT-0500 (EST)  End: Sat Dec 29 2012 11:31:34 GMT-0500 (EST)
http://yahoo.com
BEFORE
AFTER
http://ninjaturtles.com
BEFORE
AFTER
INSIDE
200  Start: Sat Dec 29 2012 11:31:36 GMT-0500 (EST)  End: Sat Dec 29 2012 11:31:37 GMT-0500 (EST)
INSIDE
200  Start: Sat Dec 29 2012 11:31:35 GMT-0500 (EST)  End: Sat Dec 29 2012 11:31:38 GMT-0500 (EST)
于 2012-12-29T16:36:11.583 に答える