Laravel 9中如何将事件监听器的结果返回至控制器
问题描述
我正在使用Laravel 9开发,在用户注册的控制器方法中调用了如下事件:
$data = $request->validated(); event(new RegisterNewUserEvent($data)); $code = ActiveCode::generateCode($user); dd($code);
该RegisterNewUserEvent事件会调用监听器创建新用户记录,监听器代码如下:
public function handle(RegisterNewUserEvent $event) { $firstName = $event->data['fname']; $lastName = $event->data['lname']; $userName = $event->data['uname']; $mobilePhone = $event->data['phone']; $hashPassword = Hash::make($event->data['password']); $randomString = Str::random(20); $user = User::create([ 'usr_first_name' => $firstName, 'usr_last_name' => $lastName, 'usr_user_name' => $userName, 'usr_mobile_phone' => $mobilePhone, 'usr_password_hash' => $hashPassword, 'usr_str' => $randomString, ]); $event->data = $user->id; }
监听器中创建的用户存储在$user对象中,我需要在控制器方法中获取该对象以生成激活码(如$code = ActiveCode::generateCode($user);),但不知道如何将监听器中的$user对象返回至控制器,恳请告知实现方法。
解决方案
方法一:通过事件类属性传递用户对象
- 修改
RegisterNewUserEvent事件类,新增一个公共属性用于存储用户对象:
class RegisterNewUserEvent { public $data; public $user; // 新增属性,用于存储创建后的用户对象 public function __construct($data) { $this->data = $data; } }
- 更新监听器代码,将创建好的
$user对象赋值给事件的$user属性:
public function handle(RegisterNewUserEvent $event) { // 原有创建用户的代码保持不变 $user = User::create([ // 字段赋值逻辑不变 ]); $event->user = $user; // 将用户对象绑定到事件属性上 }
- 在控制器中,先实例化事件对象再触发,之后直接从事件对象中获取用户:
$data = $request->validated(); $event = new RegisterNewUserEvent($data); event($event); // 从事件对象中取出用户 $user = $event->user; $code = ActiveCode::generateCode($user); dd($code);
方法二:利用事件的返回值传递用户对象
Laravel的event()函数会返回所有监听器的返回值组成的数组,可让监听器直接返回用户对象:
- 修改监听器的
handle方法,返回创建好的用户对象:
public function handle(RegisterNewUserEvent $event) { // 原有创建用户的代码保持不变 $user = User::create([ // 字段赋值逻辑不变 ]); return $user; // 返回用户对象 }
- 在控制器中接收事件返回值,取出用户对象:
$data = $request->validated(); // 若只有一个监听器,直接解构数组获取用户 [$user] = event(new RegisterNewUserEvent($data)); $code = ActiveCode::generateCode($user); dd($code);
注意事项
- 方法一逻辑更直观,适合需要在事件中传递多份数据的场景;
- 若事件绑定了多个监听器,方法二的返回值数组会包含所有监听器的返回结果,需根据实际下标取值;
- 两种方案均能满足需求,可根据项目代码风格选择。
内容的提问来源于stack exchange,提问作者Pouya Vaghefi
相关产品推荐
相关产品推荐

