104

PHP5 と Chrome ブラウザーをクライアントとして使用する Web ソケットを使用しています。サイトhttp://code.google.com/p/phpwebsocket/からコードを取得しました。

サーバーを実行し、クライアントも接続しています。チャットもできます。サーバーを再起動すると(強制終了して再起動することにより)、クライアントは切断された情報を取得しますが、メッセージを送信しても自動的にサーバーに再接続しません。

これを達成する方法は?切断された情報を取得したときのように、それを確認して JavaScript に送信し、ページを更新するか、再接続する必要がありますか?

4

9 に答える 9

151

サーバーが再起動すると、Web ソケット接続が閉じられるため、JavaScriptoncloseイベントがトリガーされます。5 秒ごとに再接続を試みる例を次に示します。

function start(websocketServerLocation){
    ws = new WebSocket(websocketServerLocation);
    ws.onmessage = function(evt) { alert('message received'); };
    ws.onclose = function(){
        // Try to reconnect in 5 seconds
        setTimeout(function(){start(websocketServerLocation)}, 5000);
    };
}
于 2011-11-22T18:01:45.897 に答える
40

WebSocket の再接続

接続が切断された場合に自動的に再接続する WebSocket 接続を提供するために WebSocket API を装飾する小さな JavaScript ライブラリがあります。

gzip 圧縮で縮小されたライブラリは 600 バイト未満です。

リポジトリは次の場所から入手できます。

https://github.com/joewalnes/reconnecting-websocket

TypeScript ライブラリもあります。new WebSocketそれをインクルードして に置き換えるだけnew ReconnectingWebSocketです。

リポジトリは次の場所から入手できます。

https://github.com/pladaria/reconnecting-websocket

サーバーフラッド

サーバーの再起動時に多数のクライアントがサーバーに接続されている場合。Exponential Backoff アルゴリズムを使用して、クライアントの再接続タイミングを管理する価値がある場合があります。

アルゴリズムは次のように機能します。

  1. k 回の試行の場合、0 から 2^k - 1 の間のランダムな時間間隔を生成します。
  2. 再接続できる場合は、k を 1 にリセットします。
  3. 再接続に失敗した場合、k は 1 増加し、プロセスはステップ 1 から再開されます。
  4. 最大間隔を切り詰めるために、特定の試行回数 k に達すると、試行ごとに k の増加が停止します。

参照:

http://blog.johnryding.com/post/78544969349/how-to-reconnect-web-sockets-in-a-realtime-web-app

ReconnectingWebSocket は、このアルゴリズムを使用して再接続を処理しません。

于 2016-05-04T21:18:36.653 に答える
2

コメントはできませんが、次のとおりです。

var socket;

const socketMessageListener = (event) => {
  console.log(event.data);
};

const socketOpenListener = (event) => {
  console.log('Connected');
  socket.send('hello');
};

const socketCloseListener = (event) => {
  if (socket) {
    console.error('Disconnected.');
  }
  socket = new WebSocket('ws://localhost:8080');
  socket.addEventListener('open', socketOpenListener);
  socket.addEventListener('message', socketMessageListener);
  socket.addEventListener('close', socketCloseListener);
};

socketCloseListener();

// for testing
setTimeout(()=>{
  socket.close();
},5000);

さらに、 https://www.npmjs.com/package/backで十分です:)

于 2017-12-14T22:29:27.000 に答える
0

最後に、次のように vue+ts で ws auto reconnect を作成します。

private async mounted() {
    // Connect to WebSocket
    const sn = "sb1234567890";
    const host =
        window.location.protocol == "https:"
            ? "wss://www.xxx.net"
            : process.env.DEV_TYPE === "fullstack"
            ? "ws://10.0.0.14:8528"
            : "ws://www.xxx.net:8528";
    const wsUri = host + "/feed-home/" + sn;
    await this.startWs(wsUri, sn);
    // !!!Deprecated: failed to reconnect
    // let ws = new WebSocket();
    // console.log(ws);
    // ws.onopen = async function(event) {
    //     console.log(event, "openEvent");
    //     clearInterval(that.timer);
    // };
    // ws.onclose = async function(event) {
    //     console.log(event, "close");
    //     that.timer = setInterval(() => {
    //         console.log("Heart Beat");
    //         ws.send("HeartBeat");
    //         // ws = new WebSocket("ws://10.0.0.14:8528/feed-home/" + sn);
    //         console.log(ws);
    //     }, 60000);
    // };
    // ws.onmessage = async function(event) {
    //     console.log(event, "ws");
    //     alert("get it!");
    //     await alert("please update!");
    //     await that.getHome(sn);
    // };
}
private wsReconnected: boolean = false; // check whether WebSocket is reconnected
private async startWs(uri: string, sn: string) {
    let that = this;
    let ws = new WebSocket(uri);
    ws.onopen = async () => {
        if (that.wsReconnected) {
            await that.getHome(sn); // Refresh api data after reconnected
        }
        ws.send("Current client version: " + window.version);
    };
    ws.onmessage = async evt => {
        await that.getHome(sn);
        that.$message({
            type: "success",
            message: evt.data,
            showClose: true,
            center: true,
            duration: 20 * 1000
        });
    };
    ws.onclose = async () => {
        that.wsReconnected = true;
        await that.startWs(uri, sn);
        const sleep = (seconds: number) => {
            return new Promise(resolve =>
                setTimeout(resolve, seconds * 1000)
            );
        };
        await sleep(10); // Try to reconnect in 10 seconds
        // !!!Deprecated: Use timer will cause multiply ws connections
        // if (!that.wsTimer) {
        //     // Try to reconnect in 10 seconds
        //     that.wsTimer = setInterval(async () => {
        //         console.log("reconnecting websocket...");
        //         await that.startWs(uri, sn);
        //     }, 10 * 1000);
        // }
    };
}
于 2020-04-13T09:50:08.470 に答える