如何不同的页面统计在线人数?

hulang

问题描述

有很多文章,想知道每个文章的在线人数

我的代码

private function start()
    {
        // 初始化worker类
        $worker = new Worker('websocket://0.0.0.0:2346');

        $worker->count = 1;

        // 统计连接数
        $total_connections = 0;

        $worker->onWorkerStart = function (Worker $ws_worker) {
            // 每隔[30]秒钟向所有客户端推送一次随机数据
            Timer::add(30, function () use ($ws_worker) {
                foreach ($ws_worker->connections as $connection) {
                    global $total_connections;
                    // 处理消息
                    $json = [];
                    $json['type'] = 'workerstart';
                    $json['worker_id'] = $connection->id;
                    $json['online'] = $total_connections;
                    $json['ip'] = $connection->getRemoteIp();
                    $json['time'] = date('Y-m-d H:i:s');
                    $connection->send(json_encode($json));
                    echo (json_encode($json));
                    echo (PHP_EOL);
                }
            });
        };

        // 连接回调
        $worker->onConnect = function (TcpConnection $connection) {
            global $total_connections;
            $total_connections++;
            // 处理消息
            $json = [];
            $json['type'] = 'connect';
            $json['worker_id'] = $connection->id;
            $json['online'] = $total_connections;
            $json['ip'] = $connection->getRemoteIp();
            $json['time'] = date('Y-m-d H:i:s');
            // 输出
            $connection->send(json_encode($json));
            echo (json_encode($json));
            echo (PHP_EOL);
        };

        // 关闭回调
        $worker->onClose = function (TcpConnection $connection) {
            global $total_connections;
            $total_connections--;
            // 查询页面访问时间
            $map = [];
            $map[] = ['ip', '=', $connection->getRemoteIp()];
            $data = \app\common\model\Tongji::where($map)->findOrEmpty();
            if (!$data->isEmpty()) {
                $data = $data->toArray();
                $time = time();
                // 更新统计离开时间
                $update = [];
                $update['etime'] = $time;
                $update['online_time'] = intval($time) - intval($data['stime']);
                $where = [];
                $where[] = ['ip', '=', $connection->getRemoteIp()];
                $where[] = ['visitor_hash', '=', $data['visitor_hash']];
                \app\common\model\Tongji::update($update, $where);
                \app\common\model\TongjiSession::update($update, $where);
            }
            $json = [];
            $json['type'] = 'close';
            $json['worker_id'] = $connection->id;
            $json['online'] = $total_connections;
            $json['ip'] = $connection->getRemoteIp();
            $json['time'] = date('Y-m-d H:i:s');
            echo (json_encode($json));
            echo (PHP_EOL);
        };

        // 接收消息回调
        $worker->onMessage = function (TcpConnection $connection, $data) {
            // 给connection临时设置一个lastMessageTime属性,用来记录上次收到消息的时间
            $connection->lastMessageTime = time();
            // 统计在线人数
            global $total_connections;
            // 处理消息
            $json = [];
            $json['type'] = 'message';
            $json['data'] = $data;
            $json['online'] = $total_connections;
            $json['ip'] = $connection->getRemoteIp();
            $json['time'] = date('Y-m-d H:i:s');
            // 输出
            $connection->send(json_encode($json));
            echo (json_encode($json));
            echo (PHP_EOL);
        };

        // 运行worker
        Worker::runAll();
    }

前端js

var u = parseURL(k_win_u);
// ws
var url = 'ws://' + u['host'] + ':2346';
// WebSocket
var ws = new ReconnectingWebSocket(url);
ws.onopen = function (e) {
    console.log('连接成功!');
}
ws.onmessage = function (e) {
    storage.setItem('etime', JsToPHPTime());
    storage.setItem('diff', parseInt(JsToPHPTime()) - parseInt(loadStartTime));
    var dataConfig = storage.getItem(dataTable);
    // 获取服务器请求数据
    var data = eval("(" + e.data + ")");
    storage.setItem('ip', data.ip);
    switch (data.type) {
        case 'connect':
            GetWxShow(dataConfig.wx_tel, PAGEDATA['page_id'], data.worker_id, data.ip);
            break;
        case 'workerstart':
            GetWxPing(dataConfig.wx_tel, PAGEDATA['page_id'], data.worker_id, data.ip);
            break;
        default:
            break;
    }
};
ws.onclose = function (e) {
    console.log('连接已关闭');
};

目前代码实现了在线人数,但是无法统计每个页面的,我该怎么写。
我在后台文章列表页中,每个文章,有一个按钮,是在线人数,点开后,显示该文章的页面在线人数。。

335 2 0
2个回答

fklee

可以用joinGroup根据每篇文章ID作为唯一编号来分组,统计的时候获取每个分组的在线人数

  • hulang 2024-05-31

    我用的是Worker,不是:GatewayWorker...

兔白白

我感觉应该可以 进入的时候 把当前的页面 或者说 文章ID 给传进来, 然后在连接的地方 跟 global $total_connections; 的处理方式一样 维护一个 全局的数组 数组的键名就是页面ID 键值就是 在线人数了

  • 暂无评论
×
🔝