模拟 laravel reverb 的广播 demo
1. 运行环境
window10,phpstudy,php8.3.13,laravel11
2. 安装 laravel reverb
2-1. php artisan install:broadcasting
2-2. composer require laravel/reverb:@beta
2-3. php artisan reverb:install
注意: 这个命令这里不能自动结束,执行后等待一会儿,然后再
执行 Ctrl + C 手动结束它。如果成功的话就会出现一条安装成功的info
测试是否成功可以执行:
php artisan reverb:start
能正常启动,也表示之前的安装命令成功了
3. 检查安装后的文件
- 在config\broadcasting.php 文件里 connections 是否有 reverb 的配置
- 是否存在 config\reverb.php 文件
- 是否存在 routes\channels.php 文件
- 在.env文件里是否存在如下配置
3. 安装客户端
3-1. npm install --save-dev laravel-echo pusher-js
3-2. npm run build
4. 创建广播事件类
<?php
namespace App\Events;
use Illuminate\Broadcasting\Channel;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Broadcasting\PresenceChannel;
use Illuminate\Broadcasting\PrivateChannel;
use Illuminate\Contracts\Broadcasting\ShouldBroadcast;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Facades\Log;
class PodcastProcessed implements ShouldBroadcast
{
use Dispatchable, InteractsWithSockets, SerializesModels;
public $channelUUID;
/**
* Create a new event instance.
*/
public function __construct($channelUUID)
{
$this->channelUUID = $channelUUID;
}
/**
* 广播频道 - 私有频道
*
* @return array<int, \Illuminate\Broadcasting\Channel>
*/
public function broadcastOn(): array
{
Log::info('广播频道 - 私有频道 : Test.Channel.' . $this->channelUUID);
return [
new PrivateChannel('Test.Channel.'.$this->channelUUID),
];
}
/**
* 事件的广播名字
* @return string
*/
public function broadcastAs(): string
{
Log::info('事件的广播名字 : test.name');
return 'test.name';
}
/**
* 获取将要广播的数据
*
* @return array<string, mixed>
*/
public function broadcastWith(): array
{
$data = ['Message' => '我是测试数据'];
Log::info('获取将要广播的数据: ' . $data);
return $data;
}
}
检查一下 .env 配置里的
BROADCAST_CONNECTION=reverb
QUEUE_CONNECTION=redis
5. 在routes\channels.php里添加广播权限验证
// 广播频道 - 私有频道 - 验证是否有权限订阅
Broadcast::channel('Test.Channel.{id}', function ($user, $id) {
Log::info('广播频道 - 私有频道 - 验证是否有权限订阅 : ' . $id);
return (int) $user->id === (int) $id;
});
6. 在routes\web.php里添加前端页面路由
// 广播路由
Route::get('broadcast', function () {
if (auth()->check()) { // 校验登录用户
return view('broadcast', ['uid' => auth()->user()->id]);
} else {
return redirect()->route('login'); // 未登录跳转登录页
}
});
// 触发广播事件
Route::get('sendMessage', function () {
event(new \App\Events\PodcastProcessed(auth()->user()->id));
return 'ok';
});
7. 创建页面
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<meta name="csrf-token" content="{{ csrf_token() }}">
<title>Document</title>
@vite(['resources/css/app.css', 'resources/js/app.js'])
</head>
<body>
<div id="app"><h2>广播demo</h2></div>
<script>
document.addEventListener('DOMContentLoaded', function() {
const uid = {{ $uid }}; // 将 PHP 变量 $uid 传递给 JavaScript
Echo.private(`Test.Channel.${uid}`) // 监听私有频道
.listen('.test.name', (e) => { // 监听广播名称
console.log(`私有频道 Test.Channel.${uid}`);
console.log(e);
});
});
</script>
</body>
</html>
8. 启动服务和监听
8-1. php artisan serve
8.2. php artisan reverb:start
8-3. php artisan queue:work
9. 测试
第一步:前台订阅广播通知
订阅成功后,日志记录信息如下
[2025-03-27 15:29:24] local.INFO: 广播频道 - 私有频道 - 验证是否有权限订阅 : 1
第二步:触发后台广播通知
后台发送信息成功后,记录日志信息如下
[2025-03-27 15:29:24] local.INFO: 广播频道 - 私有频道 - 验证是否有权限订阅 : 1
[2025-03-27 15:30:23] local.INFO: 事件的广播名字 : test.name
[2025-03-27 15:30:23] local.INFO: 广播频道 - 私有频道 : Test.Channel.1
[2025-03-27 15:30:23] local.INFO: 获取将要广播的数据: {"Message":"\u6211\u662f\u6d4b\u8bd5\u6570\u636e"}
同时前台页面的控制台里打印了接收的数据
推荐文章: