如何广播作业调用的事件 class

how to broadcast event called by job class

在一个 Laravel 项目中,我正在尝试通过推送器广播一个名为 "closed" 的事件。

在我的控制器中,我正在调用:

App\Jobs\Closing::dispatch();

我的App\Jobs\Closing.php:

<?php
namespace App\Jobs;
use App\Jobs\Close;
use Illuminate\Bus\Queueable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
class Closing implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    public function __construct(){}
    public function handle()
    {
        $delay = mt_random(10,20);
        Close::dispatch()->delay(now()->addSeconds($delay));
    }
}

我的app\Jobs\Close.php:

<?php
namespace App\Jobs;
use App\Events\Closed;
use Illuminate\Bus\Queueable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
class Close implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    public function __construct(){}
    public function handle()
    {
        event(new Closed());
    }
}

我的App\Events\Closed.php:

<?php
namespace App\Events;
use Illuminate\Queue\SerializesModels;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Contracts\Broadcasting\ShouldBroadcastNow;
class Closed implements ShouldBroadcastNow
{
    use Dispatchable, InteractsWithSockets, SerializesModels;
    public function __construct(){}
    public function broadcastOn()
    {
        return ['updates'];
    }
    public function broadcastAs()
    {
        return 'closed';
    }
    public function broadcastWith()
    {
        return ['message' => 'Is Closed!'];
    }
}

此时我需要说明两种强制情况

第一个是我需要创建作业关闭 class 作为作业,因为我需要延迟任务关闭的执行。我能看到做到这一点的唯一方法 "delay" 是工作 Class.

第二个是我选择在事件 Closed class 中实现 "ShouldBroadcastNow" 而不是 "ShouldBroadcast" 因为我不想排队广播。

现在的问题是 运行:

php artisan queue:work --tries=1

我在命令控制台上得到以下输出:

正在处理:App\Jobs\Closing

已处理:App\Jobs\Closing

正在处理:App\Jobs\Close

正在处理:App\Events\Closed

失败:App\Events\Closed

失败:App\Jobs\Close

我觉得奇怪的第一件事是 App\Events\Closed 进入队列,尽管它实现了 "ShouldBroadcastNow"。

在 laravel.log 上似乎在 PusherBroadcaster.php 发生了 BroadcastException。

但如果在控制器中我这样做:

event(new App\Events\Closed());

事件通过推送器正确广播到客户端浏览器。

出了什么问题?

有没有其他方法可以延迟 "close" 没有工作?

目的是为了有以下工作流程:

1 - 我们有一个名为 "closing" 的事件和另一个名为 "closed";

的事件

2 - 我们有一个名为 "close" 的任务,它在事件 "closing" 后 "x" 秒发生,其中 "x" 是一个随机数;

3 - "close" 任务执行后我们广播事件 "closed".

感谢您关注我的问题

同时我发现这是一个已知问题 (https://github.com/laravel/framework/issues/16478)。

可以通过两种方式解决:

1 - 编辑相关 php.ini 文件(在我的例子中是 mamp/conf/php7.0.9/php.ini 和 mamp/bin/php/php7.0.9/php.ini)指向curl证书的位置;

2 - 编辑 config/broadcasting.php(在推送器选项中将加密设置为 false)。