步骤
- 修改
appProvidersEventServiceProvider.php
加入测试事件
/**
* The event listener mappings for the application.
*
* @var array
*/
protected $listen = [
// passport 移除失效令牌事件
'LaravelPassportEventsAccessTokenCreated' => [
'AppListenersRevokeOldTokens',
],
'LaravelPassportEventsRefreshTokenCreated' => [
'AppListenersPruneOldTokens',
],
// 测试事件
'AppEventsTest' => [
'AppListenersTestListener',
],
];
- 执行
php artisan event:generate
生成事件和监听器 使用命令生成的监听器会自动帮你引入ShouldQueue(队列接口),接下来你要在刚刚生成的TestListener中implements该接口。
<?php
namespace AppListeners;
use AppEventsTest;
use IlluminateQueueInteractsWithQueue;
use IlluminateContractsQueueShouldQueue;
class TestListener implements ShouldQueue
{
/**
* 任务应该发送到的队列的连接的名称
*
* @var string|null
*/
public $connection = 'redis';
/**
* 任务应该发送到的队列的名称
*
* @var string|null
*/
public $queue = 'FMock';
}
- 添加事件和监听器具体方法 这里我们以修改用户头像为例子,Test.php中传入User实例:
<?php
namespace AppEvents;
use AppModelsUser;
use IlluminateBroadcastingChannel;
use IlluminateQueueSerializesModels;
use IlluminateBroadcastingPrivateChannel;
use IlluminateBroadcastingPresenceChannel;
use IlluminateFoundationEventsDispatchable;
use IlluminateBroadcastingInteractsWithSockets;
use IlluminateContractsBroadcastingShouldBroadcast;
class Test
{
use Dispatchable, InteractsWithSockets, SerializesModels;
public $user;
/**
* Create a new event instance.
*
* @param $user
*
* @return void
*/
public function __construct(User $user)
{
//
$this->user = $user;
}
/**
* Get the channels the event should broadcast on.
*
* @return IlluminateBroadcastingChannel|array
*/
public function broadcastOn()
{
return new PrivateChannel('test');
}
}
TestListener.php中传入做具体修改操作:
代码语言:javascript复制<?php
namespace AppListeners;
use AppEventsTest;
use IlluminateQueueInteractsWithQueue;
use IlluminateContractsQueueShouldQueue;
class TestListener implements ShouldQueue
{
/**
* 任务应该发送到的队列的连接的名称
*
* @var string|null
*/
public $connection = 'redis';
/**
* 任务应该发送到的队列的名称
*
* @var string|null
*/
public $queue = 'FMock';
/**
* Create the event listener.
*
* @return void
*/
public function __construct()
{
//
}
/**
* Handle the event.
*
* @param Test $event
* @return void
*/
public function handle(Test $event)
{
//
$event->user->avatar = 'test' . rand();
$event->user->save();
}
}
- 在任意控制器调用该事件
<?php
/**
* @Author huaixiu.zhen
* http://litblc.com
* User: z00455118
* Date: 2018/12/19
* Time: 15:59
*/
namespace AppHttpControllersWeb;
use AppEventsTest;
use AppRepositoriesEloquentUserRepository;
class IndexController
{
public function index()
{
return 'hello web';
}
public function event(UserRepository $userRepository)
{
$user = $userRepository->find(14);
event(new Test($user));
return '事件测试';
}
}
- 执行队列脚本
执行
php artisan queue:work redis --queue=FMock --daemon --quiet --delay=3 --sleep=3 --tries=3
该脚本定义了一下优化参数,执行redis中名字为FMock的队列,不输出任何信息,3秒一次,失败后3秒重新执行,最多执行3次。
- 忘了,记得修改配置文件
刚刚我们在监听器中定义的队列名称是
public $queue = 'FMock';
,所以要在配置文件中增加:
'redis' => [
'driver' => 'redis',
'connection' => 'default',
'queue' => 'FMock',
'retry_after' => 90,
],
搞定!
执行一下我们的控制器方法,快速(3s内)查看redis,就可以看到queues:FMock的键值,队列执行完毕则被删除。
注意事项
- queue配置文件中,无论用哪个连接,队列的名称都要与Listener中相互对应。
- 配置完要执行执行队列命令,记得加上相应的优化参数。
代码查阅
这段测试代码可以在我的gayhub找到并执行。