NodeJS socket.io-client не запускает события «отключить» или «закрыть», когда сервер убит - PullRequest
4 голосов
/ 27 декабря 2011

Я написал минимальный пример этого.Код размещен здесь: https://gist.github.com/1524725

Я запускаю свой сервер, запускаю клиент, проверяю, что соединение между ними установлено успешно, и, наконец, уничтожаю сервер с помощью сочетания клавиш CTRL + C.Когда сервер умирает, клиент немедленно запускается до завершения и закрывается без печати сообщения в on_client_close или on_client_disconnect.Нет заметной задержки.

Из прочитанного мною чтения, поскольку процесс клиента нормально завершается, нет никаких шансов, что буфер STDOUT не будет очищен.

ЭтоТакже стоит отметить, что когда я убиваю клиента вместо сервера, сервер отвечает, как и ожидалось, запуская функцию on_ws_disconnect и удаляя клиентское соединение из списка активных клиентов..io v0.8.7 Socket.io-client v0.8.7 NodeJS v0.6.0

Спасибо!

--- EDIT ---

Обратите внимание, что оба клиентаи сервер - это процессы Node.js, а не обычный клиент веб-браузера и сервер node.js.

1 Ответ

5 голосов
/ 28 декабря 2011

НОВЫЙ ОТВЕТ

Определенно ошибка в io-клиенте.: (

Мне удалось это исправить, изменив socket.io-client / libs / socket.js. Вокруг строки 433 я просто переместил this.publish('disconnect', reason); выше if (wasConnected) {.

Socket.prototype.onDisconnect = function (reason) {
    var wasConnected = this.connected;

    this.publish('disconnect', reason);

    this.connected = false;
    this.connecting = false;
    this.open = false;

    if (wasConnected) {
      this.transport.close();
      this.transport.clearTimeouts();

После нажатия ctrl + c сообщение о разъединении срабатывает примерно через десять секунд.

СТАРЫЙ ОБСУЖДЕНИЕ

Чтобы уведомить клиента о событиях выключения, вы должны добавить что-то вродеэто для demo_server.js:

var logger = io.log;

process.on('uncaughtException', function (err) {
  if( io && io.socket ) {
     io.socket.broadcast.send({type: 'error', msg: err.toString(), stack: err.stack});
  }
  logger.error(err);
  logger.error(err.stack);

  //todo should we have some default resetting (restart server?)
  app.close();
  process.exit(-1);
});

process.on('SIGHUP', function () {
  logger.error('Got SIGHUP signal.');
  if( io && io.socket ) {
     io.socket.broadcast.send({type: 'error', msg: 'server disconnected with SIGHUP'});
  }
  //todo what happens on a sighup??
  //todo if you're using upstart, just call restart node demo_server.js
});

process.on('SIGTERM', function() {
  logger.error('Shutting down.');
  if( io && io.socket ) {
     io.socket.broadcast.send({type: 'error', msg: 'server disconnected with SIGTERM'});
  }
  app.close();
  process.exit(-1);
});

Конечно, то, что вы отправляете в broadcast.send (...) (или даже какую команду вы используете там), зависит от ваших предпочтений и структуры клиента.

Для клиентской части вы можете узнать, потеряно ли соединение с сервером, используя on ('отключить', ...), который вы используете в своем примере:

client.on('disconnect', function(data) {
   alert('disconnected from server; reconnecting...');
   // and so on...
});
...