2011-12-27 83 views
3

我已經寫了一個這樣的最簡單的例子。代碼發佈在這裏:https://gist.github.com/1524725當服務器被終止時,NodeJS socket.io-client不會觸發'disconnect'或'close'事件

我啓動我的服務器,啓動我的客戶端,驗證兩者之間的連接是否成功,最後使用CTRL + C終止服務器。當服務器死亡時,客戶端立即運行完成並關閉,而無需在on_client_close或on_client_disconnect中打印消息。沒有可察覺的延遲。

從我所做的閱讀中,因爲客戶端進程正常終止,STDOUT緩衝區沒有被刷新的機會。

也可能值得注意的是,當我殺死客戶端而不是服務器時,服務器按照預期作出響應,觸發on_ws_disconnect函數並從其活動客戶端列表中刪除客戶端連接。

32位的Ubuntu 11.10 Socket.io v0.8.7 Socket.io客戶端v0.8.7 的NodeJS v0.6.0

謝謝!

---編輯---

請注意,在客戶端和服務器Node.js的過程,而不是傳統的Web瀏覽器客戶端和服務器的nod​​e.js。

回答

5

新的答案

絕對是IO客戶端中的錯誤。 :(

我能夠通過修改socket.io的客戶端/庫/ socket.js解決此問題。圍繞線433,我簡單移動上述if (wasConnected) {this.publish('disconnect', reason);

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後,斷開消息大火大約10秒

OLD討論

要通知關閉事件的客戶端,可以添加這樣的事情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發送(...)(或者甚至是命令你用有)取決於你的喜好和客戶結構。

對於客戶端,你可以告訴我們,如果服務器連接使用的(「斷開」,...),你在你的例子已經失去了:

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

這是非常合理的,但不真的是我在找什麼。有些情況下,服務器可能會在沒有機會自行清理的情況下死亡。考慮一下SIGKILL信號,它不能被捕獲,或者是電源故障。顯然,客戶端知道服務器已經消失,因爲它運行完成 - 我希望客戶端可靠地觸發回調,以便在此事件中執行某些操作。不過謝謝您的意見! – zslayton 2011-12-27 20:22:49

+0

所以你要找的是一種方式,在客戶端,告訴服務器的連接是否超時?我認爲你只需要將「斷開」替換爲「斷開」;我不知道我在哪裏找到了這個,但我在我的節點應用程序中使用它(示例添加到我的答案中) – Kato 2011-12-27 20:35:52

+0

另外,不要忘記,您可以告訴客戶端自動重新連接:io_client.connect(url,{reconnect :true}); – Kato 2011-12-27 20:38:19

相關問題