36

パート 1: 予想される動作?

onclose呼び出されるハンドラーに関して、Firefox と Chrome の間でブラウザーの動作に一貫性がありません。

oncloseユーザーページのナビゲーション/更新が原因である場合、Chrome はトリガーしないようです。ただし、Firefox はonclose.

ここでは、Firefox が正しく動作しているように思えます。

WebSocket 接続が (おそらくクリーンに) 閉じられると、ユーザー エージェントは CloseEvent インターフェースを使用するイベントを作成する必要があります。イベント名は close で、これはバブルせず、キャンセルできず、デフォルト アクションがなく、wasClean 属性が true に設定されています。 code 属性が WebSocket 接続終了コードに設定され、 reason 属性が WebSocket 接続終了理由に設定されている場合は、接続が正常に終了し、それ以外の場合は false です。タスクをキューに入れ、最初に readyState 属性の値を CLOSED (3) に変更してから、WebSocket オブジェクトでイベントをディスパッチします。

ソース: http://www.w3.org/TR/2011/WD-websockets-20110419/#closeWebSocket

卑劣なコード/予期しない動作につながる可能性がありますが.

予想される動作を確認できる人はいますか?

パート 2: 自動再接続の実装方法

ユーザーのために自動再接続するライブラリがある場合、再接続を試みる必要があるかどうかをどのように判断しますか? CloseEvent.wasClean物件をチェックしていますか?「クリーン」とは、API呼び出しWebSocket.close()またはサーバーがクローズフレームを送信することによってクローズが発生するはずだったことを意味すると想定する必要がありますか? ネットワークエラーが原因で終了した場合、どうなるでしょwasCleanfalseか?

Pusher JavaScript ライブラリでは、開発者が接続を閉じることを選択した場合 (開発者が接続を閉じることを選択した場合) を除き、閉じると再接続がトリガーされると仮定しました (onclose -> 待機中 -> 接続中)。socket.io クライアント ライブラリも同じ想定をしているようです。

これに基づいて、どちらのライブラリもプロパティをチェックしないため、ユーザーのナビゲーション/更新によって発生した Firefox の onclose イベントが不要な再接続をトリガーしCloseEvent.wasCleanます。

例とビデオ

矛盾を示すために使用できる例を次に示します: http://jsbin.com/awonod/7

問題を実演している私のビデオは次のとおりです : http://www.screenr.com/vHn8

注意すべき点の 1 つは、Escape キーを押すと、WebSocket 接続が閉じられる可能性があることです。ただし、注意深く観察したり自分で試してみると、ページが更新される直前に close イベントがログに記録されていることがわかります。

4

2 に答える 2

8

予期しない動作は、Firefox と Chrome が Websocket のクローズを処理する方法が原因です。ページが更新されると、両方のブラウザーが接続を閉じますが、Firefox は onclose コードを実行しますが、chrome は接続を閉じ、スキップして新しいページを再読み込みします。はい、私はこの奇妙な動作を確認します。
さらに奇妙なのは、私の観察によると、Chrome で websocket.close() を呼び出すと、すぐに接続が閉じられ、onclose 関数が呼び出されますが、Firefox はサーバーからのクローズ メッセージが返されるのを待ちます。

サーバーから終了メッセージを受信した場合、wasClean プロパティは true になります。

ライブラリが wasClean プロパティをチェックせずに自動再接続している場合、ページが更新されると接続を再確立しようとするため、問題が発生する可能性があります。これにはライブラリを使用せず、手動で行うことを検討する必要があります。それほど難しいことではありません。onclean プロパティが true であることを確認する if ステートメントを使用して onclose 関数で connect を呼び出すだけです。または、さらに安全にするために、onbeforeunload に変数を設定して、新しい接続を防ぎます。

お役に立てれば!

于 2013-06-18T15:57:37.570 に答える