--- tags: PHP, Laravel, Backend --- # Laravel 事件和監聽器 `Laravel` 的事件提供了一個簡單的觀察者模式,允許訂閱和監聽應用程序中發生的各種事件。事件類通常存儲在`app/Events`目錄中,而它們的監聽器存儲在`app/Listeners`,可以利用`php artisan make`來創建相關檔案。 事件在應用程式解藕相當好用,例如:如果希望在商家創建時通知使用者,無須將商家創建的代碼與通知使用者代碼放在一起,可以引發一個`App\Events\StoreCreated`事件,監聽器可以接收並使用該事件來分派通知。 ## 創建事件和監聽器 首先先創建`StoreCreated`事件和`NotifyStoreCreated`監聽器,使用以下artisan指令來創建。 ```cmd= php artisan make:event StoreCreated php artisan make:listener NotifyStoreCreated --event="StoreCreated" ``` 上面的指令將分別在 `app/Events` 和 `app/Listeners` 文件夾中創建事件和監聽器。 ## 註冊事件和監聽器 在`app/Providers/EventServiceProvider.php`文件中註冊您的事件和偵聽器。 `protected $listen`屬性包含所有事件及其偵聽器作為鍵值對的數組。接下來,我們將事件`StoreCreated`和偵聽器添加`NotifyStoreCreated`到數組`$listen`中,如下所示。 ```php= use App/Events/StoreCreated; use App/Listeners/NotifyStoreCreated; class EventServiceProvider extends ServiceProvider { /** * The event listener mappings for the application. * * @var array */ protected $listen = [ StoreCreated::class => [ NotifyStoreCreated::class, ] ]; //... } ``` :::info 可以使用此指令`php artisan event:list`查看應用程序註冊的所有事件和偵聽器的列表 ::: ## 定義事件和監聽器 編輯`StoreCreated.php`,我們要在每次商家創建時發送通知,我們需要將`$store`的實例傳給`StoreCreated`,讓監聽器可以訪問`$store`的實例 ```php= # app/Events/StoreCreated.php <?php namespace App\Events; .... use App\Post; class StoreCreated { use Dispatchable, InteractsWithSockets, SerializesModels; public $store; /** * Create a new event instance. * * @return void */ public function __construct(Store $store) { $this->$store = $store; } } ``` 再來編輯`NotifyStoreCreated.php`,`NotifyStoreCreated`監聽器類別將用來發送通知給用戶,可以看到有一個`handle`函式,是事件將調用的方法,在這個`handle`方法中,我們將編寫必要的代碼來發送通知。 ```php= # app/Listeners/NotifyPostCreated.php <?php namespace App\Listeners; use App\Events\StoreCreated; use App\Notifications\StoreNotification; use App\User; use Mail; class NotifyStoreCreated { .... .... /** * Handle the event. * * @param StoreCreated $event * @return void */ public function handle(StoreCreated $event) { // 要發送通知對象邏輯 $users = User::all(); foreach($users as $user) { // 傳入$store實例,發送通知 $user->notify(new StoreNotification($event->store)); } } } ``` ## 調度事件 最後一步就是觸發`StoreCreated`事件,使用`event()`這個`helper`函式,這個函式會把事件分派給有註冊的監聽器`(listeners)` ```php= # app/Http/Controllers/StoreController.php <?php namespace App\Http\Controllers; use App\Events\StoreCreated; use App\Http\Controllers\Controller; use App\Model\Store; class StoreController extends Controller { //... public function store(Request $request) { // 商家新增時邏輯 event(new StoreCreated($store)); } } ``` 如果事件使用`Illuminate\Foundation\Events\Dispatchabletrait`,可以像這樣調用事件的靜態`dispatch`方法。 ```php= public function store(Request $request) { // 商家新增時邏輯 StoreCreated::dispatch($store); } ``` 之後在商家新增時`StoreCreated`都會引發事件並最終執行偵聽`NotifyStoreCreated`監聽器以通知用戶。 ## 補充資料 [Laravel events](https://laravel.com/docs/9.x/events)
×
Sign in
Email
Password
Forgot password
or
By clicking below, you agree to our
terms of service
.
Sign in via Facebook
Sign in via Twitter
Sign in via GitHub
Sign in via Dropbox
Sign in with Wallet
Wallet (
)
Connect another wallet
New to HackMD?
Sign up