Thinkphp6如何通过控制器进行WebSocket消息全局广播或者指定用户广播

2025-10-16 0 911

一、安装扩展包
在 ThinkPHP6 项目根目录下执行

composer require topthink/think-worker
composer require workerman/gateway-worker

二、创建配置文件
在 config 目录下创建 gateway_worker.php 配置文件,内容可以参考以下示例:

return [
// 扩展自身需要的配置
'protocol' => 'websocket', // 协议 支持 tcp udp unix http websocket text
'host' => '0.0.0.0', // 监听地址
'port' => 2345, // 监听端口
'socket' => '', // 完整监听地址
'context' => [], // socket 上下文选项
'register_deploy' => true, // 是否需要部署register
'businessWorker_deploy' => true, // 是否需要部署businessWorker
'gateway_deploy' => true, // 是否需要部署gateway

// Register配置
'registerAddress' => '127.0.0.1:1236',

// Gateway配置
'name' => 'thinkphp',
'count' => 1,
'lanIp' => '127.0.0.1',
'startPort' => 2000,
'daemonize' => false,
'pingInterval' => 30,
'pingNotResponseLimit' => 0,
'pingData' => '{"type":"ping"}',

// BusinsessWorker配置
'businessWorker' => [
'name' => 'BusinessWorker',
'count' => 4,
// 'eventHandler' => '\think\worker\Events',
'eventHandler' => '\app\http\Events',
],
];

三、配置 Nginx 代理(可选)
若 WebSocket 服务位于 Nginx 后,需为 WebSocket 连接设置代理:

location /websocket {
proxy_pass http://127.0.0.1:2348;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "Upgrade";
proxy_set_header Host $host;
}

四、创建事件处理类
在 gateway_worker.php 配置的 eventHandler 指定位置(例如 app\connect\controller 目录)创建 Events.php 文件。这个类将处理连接、消息、关闭等事件

<?php
namespace app\connect\controller;
use GatewayWorker\Lib\Gateway;
class Events
{
/**
* 当客户端连接时触发
* @param string $clientId 连接ID
*/
public static function onConnect($client_id) {
// 可在此验证连接,或直接发送欢迎信息
Gateway::sendToClient($client_id, json_encode([
'type' => 'init',
'client_id' => $client_id
]));
}

/**
* 当客户端发来消息时触发
* @param string $clientId 连接ID
* @param mixed $data 客户端消息
*/
public static function onMessage($client_id, $data) {
// 解析和处理客户端消息
$message = json_decode($data, true);
if (!$message) {
return;
}

switch ($message['type']) {
case 'bind':
// 将 client_id 与用户 uid 绑定
if (isset($message['uid'])) {
Gateway::bindUid($client_id, $message['uid']);
Gateway::sendToClient($client_id, json_encode(['type' => 'bind_success']));
}
break;
case 'chat':
// 向特定用户或群组发送消息
if (isset($message['to_uid'])) {
Gateway::sendToUid($message['to_uid'], json_encode([
'type' => 'chat',
'from' => $message['from'],
'content' => $message['content']
]));
}
break;
default:
// 处理其他类型的消息
}
}

/**
* 当客户端连接关闭时触发
* @param string $clientId 连接ID
*/
public static function onClose($client_id) {
// 清理连接相关资源
}
}

无、在 TP6 控制器中发送消息
你可以在 ThinkPHP6 的任意控制器或模型中,通过 Gateway 类向客户端推送消息。 <?php namespace app\controller; use GatewayWorker\Lib\Gateway; class ChatController { public function sendMessage() { // 设置 Register 服务地址(通常在应用初始化时设置一次) Gateway::$registerAddress = '127.0.0.1:1236'; // 向特定用户发送消息 $uid = input('uid'); $message = json_encode([ 'type' => 'system_notice', 'content' => '您有一条新消息' ]); Gateway::sendToUid($uid, $message); return json(['code' => 200, 'msg' => '发送成功']); } }

六、启动与停止服务

  • 启动服务(开发模式):

    php think worker:gateway start

    看到类似如下输出,表示启动成功:

    Starting GatewayWorker server...
    Workerman[think] start in DEBUG mode
    ----------------------- WORKERMAN -----------------------------
    Workerman version:3.5.13          PHP version:7.2.7
    ------------------------ WORKERS -------------------------------
    user          worker          listen                    processes status
    kancloud      Register        text://127.0.0.1:1236      1         [OK]
    kancloud      BusinessWorker  none                       1         [OK]
    kancloud      thinkphp        websocket://0.0.0.0:2348   1         [OK]
  • 以守护进程方式启动(生产环境):

    php think worker:gateway start -d

  • 停止服务

    php think worker:gateway stop

  • 查看服务状态

    php think worker:gateway status

🛠️ 常见问题排查

  • 端口占用或无法启动:确认配置的端口(如 23481236)未被其他程序占用。Linux 下可使用 netstat -anp | grep 端口号 检查。

  • 防火墙阻拦:确保服务器防火墙和安全组规则允许配置端口的访问。

  • PHP 函数禁用:检查 php.ini 中 stream_socket_server 等函数是否被禁用。

  • SSL 证书配置:如需 WSS 连接,可在 gateway_worker.php 配置 ssl 相关选项:

    'protocol' => 'websocket',
    'ssl'      => true,
    'context'  => [
        'ssl' => [
            'local_cert'  => '/path/to/your/cert.pem',
            'local_pk'    => '/path/to/your/private.key',
            'verify_peer' => false,
        ]
    ],
收藏 (0) 打赏

感谢您的支持,我会继续努力的!

打开微信/支付宝扫一扫,即可进行扫码打赏哦,分享从这里开始,精彩与您同在
点赞 (0)

淘吗网 thinkphp Thinkphp6如何通过控制器进行WebSocket消息全局广播或者指定用户广播 https://www.taomawang.com/server/1224.html

常见问题

相关文章

发表评论
暂无评论
官方客服团队

为您解决烦忧 - 24小时在线 专业服务