我正在用Node和Cheerio构建一个网页刮板,对于某个网站,我得到以下错误(它只发生在这一个网站上,没有其他我试图刮的网站。

它每次都发生在不同的位置,所以有时是url x抛出错误,其他时候url x是好的,它是一个完全不同的url:

    Error!: Error: socket hang up using [insert random URL, it's different every time]

Error: socket hang up
    at createHangUpError (http.js:1445:15)
    at Socket.socketOnEnd [as onend] (http.js:1541:23)
    at Socket.g (events.js:175:14)
    at Socket.EventEmitter.emit (events.js:117:20)
    at _stream_readable.js:910:16
    at process._tickCallback (node.js:415:13)

这是非常棘手的调试,我真的不知道从哪里开始。首先,什么是套接字挂起错误?是404错误还是类似的错误?或者仅仅意味着服务器拒绝连接?

我在任何地方都找不到解释!

编辑:下面是(有时)返回错误的代码示例:

function scrapeNexts(url, oncomplete) {
    request(url, function(err, resp, body) {

        if (err) {
            console.log("Uh-oh, ScrapeNexts Error!: " + err + " using " + url);
            errors.nexts.push(url);
        }
        $ = cheerio.load(body);
        // do stuff with the '$' cheerio content here
    });
}

没有直接调用关闭连接,但我使用节点请求(据我所知)使用http。get所以这是不需要的,如果我错了纠正我!

编辑2:下面是一段实际使用的代码,它会导致错误。prodURL和其他变量主要是前面定义的jquery选择器。这使用了Node的异步库。

function scrapeNexts(url, oncomplete) {
    request(url, function (err, resp, body) {

        if (err) {
            console.log("Uh-oh, ScrapeNexts Error!: " + err + " using " + url);
            errors.nexts.push(url);
        }
        async.series([
                function (callback) {
                    $ = cheerio.load(body);
                    callback();
                },
                function (callback) {
                    $(prodURL).each(function () {
                        var theHref = $(this).attr('href');
                        urls.push(baseURL + theHref);
                    });
                    var next = $(next_select).first().attr('href');
                    oncomplete(next);
                }
            ]);
    });
}

当前回答

一个值得一提的例子:当使用Express从Node.js连接到Node.js时,如果我没有在请求的URL路径前面加上“/”,我就会得到“套接字挂起”。

其他回答

我在请求某些服务器时遇到了同样的问题。在我的例子中,在请求选项的头中将任何值设置为User-Agent都对我有帮助。

const httpRequestOptions = {
    hostname: 'site.address.com',
    headers: {
       'User-Agent': 'Chrome/59.0.3071.115'
    }
};

这不是一般情况,取决于服务器设置。

我在OCP集群上使用CouchDB时得到了类似的错误。

const cloudantSessionStore = sessionStore.createSessionStore(
  {
    type: 'couchdb',
    host: 'https://' + credentials['host'],
    port: credentials['port'],
    dbName: 'sessions',
    options: {
      auth: {
        username: credentials['username'],
        password: credentials['password']
      },
      cache: false
    }
  }

它应该是“http”,而不是“https”,以连接我的CouchDB实例。希望对遇到类似问题的人有所帮助。

经过长时间的调试到节点js代码,mongodb连接字符串,检查CORS等,对我来说,只是切换到不同的端口号server.listen(端口);成功了,邮差,你也试试。不更改代理设置,只更改默认值。

在我的情况下,问题仅仅是因为返回状态代码102的响应(Processing…)

下面是一个简单的例子,当我错过添加下面的例子注释代码时,我得到了相同的错误。取消注释req.end()代码将解决此问题。

var fs = require("fs");
var https = require("https");

var options = {
    host: "en.wikipedia.org",
    path: "/wiki/George_Washington",
    port: 443,
    method: "GET"
};

var req = https.request(options, function (res) {
    console.log(res.statusCode);
});


// req.end();