如何實現從 Redis 中訂閱訊息轉發到 WebSocket 客戶端

韓天峰發表於2019-02-16

PHP 的redis擴充套件是阻塞式 IO ,使用訂閱/釋出模式時,會導致整個程式進入阻塞。因此必須使用SwooleRedis非同步客戶端來實現。

例項程式碼

$server = new swoole_websocket_server("0.0.0.0", 9501);

$server->on(`workerStart`, function ($server, $workerId) {
    $client = new swoole_redis;
    $client->on(`message`, function (swoole_redis $client, $result) use ($server) {
        if ($result[0] == `message`) {
            foreach($server->connections as $fd) {
                $server->push($fd, $result[1]);
            }
        }
    });
    $client->connect(`127.0.0.1`, 6379, function (swoole_redis $client, $result) {
        $client->subscribe(`msg_0`);
    });
});

$server->on(`open`, function ($server, $request) {

});

$server->on(`message`, function (swoole_websocket_server $server, $frame) {
    $server->push($frame->fd, "hello");
});

$server->on(`close`, function ($serv, $fd) {

});

$server->start();

實現過程

  • 在程式啟動(onWorkerStart)時建立了SwooleRedis客戶端,連線到Redis伺服器

  • 連線成功後,訂閱msg_0主題的訊息

  • 當有新的message時,SwooleRedis會觸發onMessage事件回撥

  • 在這個回撥函式中使用$server->connections遍歷伺服器所有的連線,傳送訊息

相關文章