2020-05-07 18:06:00
围观(5900)
用 PHP 写即时聊天一般是用 Workerman 或者 Swool, 博主之前有使用 Workerman 写过简单的多人聊天, 今天看到一个项目使用了 GatewayWorker , 就学习了一下.
GatewayWorker 官方手册: http://doc2.workerman.net/
GatewayWorker 是基于 Workerman 开发的, GatewayWorker 提供了一些 API 可以更方便的调用, 减少了重复写轮子的时间.
使用命令安装 Laravel:
composer create-project --prefer-dist laravel/laravel im 7.*
安装完成后 进入到 Laravel 目录, 开始安装 Workerman ( Workerman 手册: http://doc.workerman.net/install/install.html ):
composer require workerman/workerman
接着就要安装 GatewayWorker 和 GatewayClient
composer require workerman/gateway-worker
composer require workerman/gatewayclient
依赖的类库和包都装好了, 接着就是写逻辑代码, 可以进入 GatewayWorker 的手册 下载提供的 DEMO
在项目根目录创建一个 workerman 目录, 将 DEMO 提供的一些文件粘贴进去
打开 start_gateway.php / start_businessworker.php / start_register.php 将自动加载类文件的路径修改:
require_once __DIR__ . '/../../../vendor/autoload.php';
以及把 start_gateway.php 文件的协议修改成 Websocket:
$gateway = new Gateway("Websocket://0.0.0.0:8282");
此时双击 workerman 目录下的 start_for_win.bat 可以正常运行:
当然, 在 Laravel 里面使用, 就不能使用 Events.php 写业务逻辑了, Events.php 只需要返回 $client_id 就行了.
例如将 Events.php 的 onMessage 及 onClose 里的代码都注释 onConnect 方法改成:
public static function onConnect($client_id) { // 向当前client_id发送数据 Gateway::sendToClient($client_id, $client_id); }
这样前端在连接后端的 Websocket 时, 就能拿到 client_id, 后续请求接口携带 client_id 就能与其他用户一起通信了.
在 API 写一条路由:
Route::get('send_msg', 'SendMsgController@send');
使用命令创建控制器(其实按照规范 应该是在控制器目录下的 API 目录的 这里为了简单):
php artisan make:controller SendMsgController
创建完成后, 在 SendMsgController 控制器写入 send 方法:
public function send(Request $request) { $input = $request->all(); if (isset($input['client_id']) && $input['content']) { Gateway::$registerAddress = '127.0.0.1:1238'; Gateway::sendToAll("{$input['client_id']} 说: {$input['content']}"); } }
send 方法的 127.0.0.1:1238 对应的是 start_gateway.php / start_businessworker.php / start_register.php 这三个文件的注册地址, 需要要改地址或者端口 需要全都改.
不要忘了需要引入类:
use GatewayClientGateway;
另外, 在本地测试, 还需要配置一下环境 (因为使用 PHPStudy 很简单配置 所以不细说):
有了后端, 就差前端, 写一个 test.html:
<!DOCTYPE html> <html> <head> <title>不败君 - www.bubaijun.com</title> <meta charset="utf-8"> </head> <body> <input type="text" name="" id="content"> <button id="send">send</button> <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script> <script type="text/javascript"> var ws = new WebSocket("ws://127.0.0.1:8282"); ws.onopen = function() { document.getElementById('send').addEventListener('click', function(){ var client_id = localStorage.getItem("client_id"); if (!client_id) { return; console.log('缺少参数'); } var content = document.getElementById('content').value; $.ajax({ url: 'http://im.test/api/send_msg?client_id=' + client_id + '&content=' + content, type: 'GET', }); }, false) }; var open = true; ws.onmessage = function (evt) { if (open) { var client_id = evt.data; localStorage.setItem("client_id", client_id); } open = false; console.log(evt.data); }; </script> </body> </html>
打开两个或者多个浏览器按 F12 或者手动打开控制台(开发者工具).
发送消息测试:
前端与后端通信成功后, 可以修改前端让界面更美观而不是用控制台, 后端也可以修改加上更多功能.
更详细的介绍可以看官方手册的这个: http://doc2.workerman.net/326107
本文地址 : bubaijun.com/page.php?id=178
版权声明 : 未经允许禁止转载!
上一篇文章: Python生成十万个无序且唯一的数字
下一篇文章: 使用PHP Laravel 框架开发淘客站点