【问题标题】:Node js, TCP request from front-end causing crashNode js,来自前端的TCP请求导致崩溃
【发布时间】:2017-01-31 11:51:26
【问题描述】:

我正在创建一个网站,该网站涉及用户按下一个按钮,该按钮向我的节点服务器执行 http 请求。从那里,我的节点服务器使用“net.Socket()”打开一个 TCP 套接字。之后,我在使用 res.send("ok") 成功发送消息后发送响应。当用户多次按下它时,我会收到以下错误。此外,当我与 TCP 通信的服务器不可用时,也会出现同样的问题。有没有办法可以防止来自用户的多个请求或当 TCP 服务器不可用时使我的节点服务器崩溃?

Can't set headers after they are sent.
        at ServerResponse.OutgoingMessage.setHeader (_http_outgoing.js:344:11)
        at ServerResponse.header (/Users/kevin/Documents/mic/node_modules/express/lib/response.js:719:10)
        at ServerResponse.send (/Users/kevin/Documents/mic/node_modules/express/lib/response.js:164:12)
        at ServerResponse.json (/Users/kevin/Documents/mic/node_modules/express/lib/response.js:250:15)
        at ServerResponse.send (/Users/kevin/Documents/mic/node_modules/express/lib/response.js:152:21)
        at /Users/*****/Documents/***/routes/***.js:275:15
        at Socket.<anonymous> (/Users/*****/Documents/***/routes/***.js:829:5)
        at emitOne (events.js:96:13)
        at Socket.emit (events.js:188:7)
        at TCP._handle.close [as _onclose] (net.js:492:12)

我的功能

  tcp_client_send('***.***.*.***', 3000, server, function(err, data){
    if(err){
      logger.log('error', err);
      return next("err_msg");
    }
    else{
      logger.log('info', 'Successfully sent message.');
      res.send("ok);
    }
  });

//TCP Client send
function tcp_client_send(ip, port, data, cb) {
  var client = new net.Socket();
  var message;

  client.connect(port, ip, function() {
    client.write(JSON.stringify(data));
    client.destroy();
  });

  client.on('data', function(data){
    message = data.toString();
  });

  client.on('close', function(){
    cb(null, message);
  });

  client.on('error', function(err) {
    client.destroy();
    cb(err, null);
  });
}

【问题讨论】:

  • 问题可能在这里:client.write(JSON.stringify(data)); client.destroy(); 因为write 是异步的。尝试在 write-callback 函数中销毁客户端。

标签: angularjs node.js sockets tcp


【解决方案1】:

如果发生错误,您的代码将调用回调两次:

client.on('close', function(){
  cb(null, message); // <-- here
});

client.on('error', function(err) {
  client.destroy();
  cb(err, null);     // <-- and here
});

fine manual 状态,关于error 事件:

发生错误时发出。 'close' 事件将在此事件之后直接调用。

因此closeerror 处理程序都被调用,并且都调用回调。

您应该检查传递给close 处理程序的参数,当发生错误时,该参数将是true。在这种情况下,不要调用回调:

client.on('close', function(hadError) {
  if (! hadError) cb(null, message);
});

【讨论】:

  • 感谢您的帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-03-08
  • 1970-01-01
  • 2016-03-02
相关资源
最近更新 更多