跳至主要內容

laravel广播

OrangBus大约 3 分钟

后端

安装依赖

创建一个路由触发事件

Route::post("seed",[\App\Http\Controllers\Api\Openai\Index::class,"seed"]);
public function seed()
{
    $message = (string)\request("message");
    AssertUtils::isEmpty($message,"请输入内容");
    $data =ChatMessage::create([
        "uid" => \request()->user()->id,
        "content" => $message,
        "type" => 1
    ]);
    // 触发事件
    event(new OpenaiMessage($data));
    return $this->success("success",$data);
}

公共消息-channel

php artisan make:event ChatMessage 

app/Events/ChatMessage.php

私有消息-

php artisan make:event FriendEvent

频道消息-

php artisan make:event GroupEvent 

频道授权方式

1、session 方式授权 (默认方式)

这种方式需要在网页端登录后的用户监听私有频道的时候,私有私有频道才能进行认证。

2、sanctum 方式授权

此方式使用了jwt的方式进行的认证,当我们使用次方式进行认证的时候,我们判断用户是否登录,需要用户在header头中写道token,在路由中设置 auth:sanctum 的中间件,从而获取到用户的的登录于是,在laravel的中我们也需要使用这个方式的认证,找到:app/Providers/BroadcastServiceProvider.php 文件,设置认证方式

<?php

namespace App\Providers;

use Illuminate\Support\Facades\Broadcast;
use Illuminate\Support\ServiceProvider;

class BroadcastServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap any application services.
     *
     * @return void
     */
    public function boot()
    {
        Broadcast::routes([
            "middleware" => ["auth:sanctum"]
        ]);

        require base_path('routes/channels.php');
    }
}

授权

// $user: 当登录的用户信息,$id:路由传递的参数
Broadcast::channel('user.{uid}', function ($user, $uid) { 
    return true; // 我们可以在这里做一些判断,最后返回是 true|false 就可以
});

前端

安装依赖

本地开启 laravel-echo

安装依赖

npm i -g laravel-echo-server 

配置连接:resources/js/bootstrap.js

import Echo from 'laravel-echo';
import Pusher from 'pusher-js';
window.Pusher = Pusher;

window.Echo = new Echo({
    broadcaster: 'socket.io',
    host: window.location.hostname + ':6001', //本地使用这个方式
    // host: 'http://home.com:6001', // laravel-echo 是一个独立运行的使用这个方式
    //可选
    auth: {
        headers: {
            Authorization: "Bearer " + LocalStorage.get(EnumData.tokenLabel) // 登录后获得的token值,主要看怎么进行权限认证的
        }
    }
});

在入口html中添加

<meta name="csrf-token" content="{{ csrf_token() }}">

<script src="//{{ Request::getHost() }}:6001/socket.io/socket.io.js"></script>

// 也可以下载之后直接引入
<script src="//home.com:6001/socket.io/socket.io.js"></script>
<script src="/js/socket.io.js"></script>

示例

<!DOCTYPE html>
<html lang="{{ str_replace('_', '-', app()->getLocale()) }}">
    <head>
        <meta charset="utf-8">
        <meta name="viewport" content="width=device-width, initial-scale=1">
        <meta name="csrf-token" content="{{ csrf_token() }}">
        <title>{{ env("APP_NAME") }}</title>
        <script src="//{{ Request::getHost() }}:6001/socket.io/socket.io.js"></script>
        <style>
            body {
                font-family: 'Nunito', sans-serif;
            }
        </style>
        @vite(["resources/css/app.css",'resources/js/app.js'])
    </head>
    <body class="antialiased">
    <div id="app">
        <router-view />
    </div>
    </body>
</html>

docker开启laravel-echo

创建一个 docker-compose.yml 文件

version: "3.5"

services:
  echo:
    image: oanhnn/laravel-echo-server
    restart: always
    ports:
      - 6001:6001
    volumes:
      - ./data:/app
    environment:
      - LARAVEL_ECHO_SERVER_GENERATE_CONFIG=true
    network_mode: host

运行:

docker-compose up -d

运行后会在当前目录的data下生成一个配置文件,如果启动失败,可以查看redis的配置是否正确。

{
  "apiOriginAllow": {},
  "authEndpoint": "/broadcasting/auth", // 注意这里的授权路劲
  "authHost": "http://localhost:6002", // 注意这里的授权地址
  "clients": [],
  "database": "redis",
  "databaseConfig": {
    "redis": {
      "host": "127.0.0.1", // 主机的ip地址:192.168.1.2
      "port": "6379",
      "password" : "redis666", 
      "keyPrefix": "",
      "options": {
        "db": "0"
     }
    },
    "sqlite": {
      "databasePath": "/database/laravel-echo-server.sqlite"
    },
    "publishPresence": true
  },
  "devMode": true,
  "host": null,
  "port": 6001,
  "protocol": "http",
  "sslCertPath": "",
  "sslKeyPath": "",
  "sslCertChainPath": "",
  "sslPassphrase": "",
  "socketio": {},
  "subscribers": {"http": true, "redis": true}
}

授权地址说明:

如果是将程序,redis,laravel-echo-server 分开部署的话,直接填写对应的域名即可。

如果是单服务器部署,以宝塔为例,如果我们绑定 :chat.cc 这样一个域名,我们在添加一个绑定,这个主要是端口的绑定这个服务,本地项目可以通过不同的端口访问不同的服务。

接收公共消息

接收私有消息

接收频道消息