-1

私はnodejsでアクションをスクレイピングしています。リクエストを使用してサイトに接続し、cheerioを使用してデータにアクセスし、mongodbを使用して抽出されたデータを保存しています。また、無限再帰を避けるために async.js を使用しています。

プロセスがメモリを使用し、それを解放しないため、メモリの問題が発生しました。mongodbを使用しないとメモリが安定したままになるため、問題はmongodbにあると思います。

これは私の要約されたコードです:

// Use function scrape_urls to process the urls
var q = self.asyn.queue(scrape_urls, 3);

//I push a bunch of urls ...    
for (var j = 0; j < self.urls_data.length; j++) {
    q.push(self.urls_data[j]);
}

q.drain = function () {
    console.log("END");
};

function scrape_urls(data_url, next_action) {
    request({
        method: 'GET',
        url: data_url.url
    }, function (err, response, body) {

        var $ = cheerio.load(body);
        data = { // ... scraped data ... };

        mongo_client.connect(connection_string, function (err, db) {

            if (err) { return console.dir(err); }

            var collection = db.collection('foo');

            collection.insert(data);

            next_action();

        });
    });
};

私が言うように、mongodb を使用せずにリクエストを使用して URL に接続するだけであれば、メモリは無限に増えません。mongodb への接続が問題だと思います。

何か案は?

4

1 に答える 1

0

問題が解決しました。

ここに解決策を残します。接続を再利用して 1 つだけを維持するヘルパーを作成しました (結局のところ、nodejs はシングルスレッドです)。

var MongoDbHelper = function (mongo_client, connection_string){  
    var self = this;

    this.mongo_client = mongo_client;       
    this.connection_string = connection_string;
    this.db = undefined;

    self.log = function (thread, str)
    {
        console.log(new Date().toISOString() + ' ' + process.memoryUsage().rss + ' [' + thread + '] ' + str);
    }   

    self.getcollection = function(collection_name, callback)
    {
        var collection = null;

        try
        {
            collection = self.db.collection(collection_name);       
        }
        catch(ex)
        {
            self.db = undefined;    
        }               

        // reconnecting if the connection is lost
        if(self.db == undefined)
        {
            self.mongo_client.connect(connection_string, function(err, db) {

                self.db = db;
                var collection = self.db.collection(collection_name);
                callback(err, self.db, collection);

            });                         
        }   
        else
        {           
            callback(null, self.db, collection);    
        }
    }

};

module.exports = MongoDbHelper
于 2015-12-15T00:11:08.797 に答える