Я недавно создавал модуль скребка, чтобы получить некоторую информацию с nodejs, пока не столкнулся с этой «маленькой» проблемой. Модули, которые я использую, являются cheeriojs и требуют. На самом деле модуль работает как шарм, если я вызываю только один метод за раз. Он содержит три функции, и только два из них экспортируются, это код:Функции, которые не могут выполняться вместе
'use strict';
var request = require('request'),
cheerio = require('cheerio'),
counter = 0;
function find(term, cat, callback) {
// All the check for the parameters
scrape("http://.../search.php?search=" + encodeURIComponent(term), cat, callback);
}
function last(cat, callback) {
// All the check for the parameters
scrape("http://google.com/", cat, callback);
}
function scrape(url, cat, callback) {
request(url, function (error, response, body) {
if (!error && response.statusCode == 200) {
var $ = cheerio.load(body);
var result = [];
var items = $('.foo, .foo2').filter(function() {
// Condition to filter the resulted items
});
items.each(function(i, row) {
// Had to do another request inside here to scrape other information
request($(".newpagelink").attr("href"), function(error, response, body) {
var name = $(".selector").text(),
surname = $(".selector2").text(),
link = cheerio.load(body)('.magnet').attr('href'); // This is the only thing that I'm scraping from the new page, the rest comes from the other "cheerio.load"
// Push an object in the array
result.push({ "name": name, "surname": surname, "link": link });
// To check when the async requests are ended
counter++;
if(counter == items.length-1) {
callback(null, result);
}
});
});
}
});
}
exports.find = find;
exports.last = last;
Проблема теперь, как я уже говорил, что если я создаю новый сценарий узла «test.js» и я называю только последний ИЛИ найти, он отлично работает! Но если я позвоню как методы последовательно, как это:
var mod = require("../index-tmp.js");
mod.find("bla", "blabla", function(err, data) {
if (err) throw err;
console.log(data.length + " find");
});
mod.last(function(err, data) {
console.log(data.length + " last");
});
Результаты полностью перепутались, иногда сценарий даже не напечатать что-то, в другое время печати результат только «найти» или «последний», и другие времена возвращают ошибку cheeriojs (я не буду добавлять сюда, чтобы не повредить вам, потому что, вероятно, это ошибка моего сценария). Я думал также повторить одну и ту же функцию два раза для обоих методов, но ничего, те же проблемы возникают ... Я не знаю, что еще попробовать, надеюсь, вы скажете мне причину такого поведения!
Btw, 'counter == items.length-1' выглядит подозрительно. Почему бы не дождаться всех предметов? Также вам не хватает обработки ошибок во внутреннем обратном вызове 'request', и' callback' никогда не будет вызываться, если 'items.length == 0' – Bergi
@Bergi items.length-1, потому что последний является пустым полем, который Мне не нужно царапать. Обработка ошибок, как вы можете видеть также из других функций, не включена в этот пост, чтобы не сделать это слишком долго, я просто забыл удалить и первый. В любом случае, это работает, вставив счетчик внутрь ... Я потратил 2 часа на мою жизнь на эту проблему. Большое спасибо –
Из кода, который вы нам показали, вы по-прежнему отправляете «запрос» для последнего окна ... И обратите внимание, что вы не можете быть уверены, кто из них игнорируется, потому что он прибывает последним. – Bergi