Rumah >pembangunan bahagian belakang >tutorial php >Panduan untuk acara model Laravel ' s

Panduan untuk acara model Laravel ' s

James Robert Taylor
James Robert Taylorasal
2025-03-06 02:25:14852semak imbas

A guide to Laravel's model events

Acara model Laravel adalah ciri yang sangat mudah yang membantu anda menjalankan logik secara automatik apabila melakukan operasi tertentu pada model fasih anda. Walau bagaimanapun, jika digunakan secara tidak wajar, ia kadang -kadang boleh membawa kepada kesan sampingan yang aneh.

Artikel ini akan meneroka peristiwa model apa dan bagaimana menggunakannya dalam aplikasi Laravel. Kami juga akan meneroka bagaimana untuk menguji peristiwa model dan beberapa isu yang perlu diperhatikan apabila menggunakannya. Akhirnya, kami akan merangkumi beberapa alternatif untuk memodelkan peristiwa yang boleh anda pertimbangkan.

Apakah peristiwa dan pendengar?


Anda mungkin pernah mendengar "peristiwa" dan "pendengar". Tetapi jika anda belum mendengarnya, inilah gambaran ringkas tentang mereka:

#Event

Ini adalah apa yang berlaku dalam aplikasi yang anda mahu bertindak -contohnya, pengguna mendaftar di laman web anda, pengguna log masuk, dll.

Biasanya, dalam Laravel, peristiwa adalah kelas PHP. Sebagai tambahan kepada peristiwa yang disediakan oleh rangka kerja atau pakej pihak ketiga, mereka biasanya disimpan dalam direktori

.

app/Events Berikut adalah contoh kelas acara mudah yang mungkin anda mahu jadual apabila pengguna mendaftar ke laman web anda:

Dalam contoh asas di atas, kita mempunyai kelas acara
declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}
yang menerima contoh model

dalam pembangunnya. Kelas acara ini adalah bekas mudah untuk menyimpan contoh pengguna berdaftar. AppEventsUserRegistered Apabila dihantar, acara itu akan mencetuskan mana -mana pendengar yang mendengarnya. User

Berikut adalah contoh mudah bagaimana untuk menjadualkan peristiwa apabila pengguna mendaftar:

Dalam contoh di atas, kami membuat pengguna baru dan kemudian menjadualkan acara

menggunakan contoh pengguna. Dengan mengandaikan pendengar didaftarkan dengan betul, ini akan mencetuskan mana -mana pendengar yang mendengar pada acara
use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);
.

AppEventsUserRegistered #Listener AppEventsUserRegistered

pendengar adalah blok kod yang anda mahu jalankan apabila peristiwa tertentu berlaku.

Sebagai contoh, berpegang dengan contoh pendaftaran pengguna kami, anda mungkin mahu menghantar e -mel selamat datang kepada pengguna apabila pengguna mendaftar. Anda boleh membuat pendengar ke acara

dan menghantar e -mel selamat datang.

Di Laravel, pendengar biasanya (tetapi tidak selalu) kelas yang terdapat dalam direktori AppEventsUserRegistered.

Contoh pendengar menghantar e -mel selamat datang kepada pengguna apabila daftar pengguna mungkin kelihatan seperti ini: app/Listeners

seperti yang kita lihat dalam contoh kod di atas, kelas pendengar

mempunyai kaedah
declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
yang menerima contoh acara

. Kaedah ini bertanggungjawab untuk menghantar e -mel selamat datang kepada pengguna. AppListenersSendWelcomeEmail

Untuk lebih banyak arahan yang mendalam mengenai peristiwa dan pendengar, anda mungkin ingin menyemak dokumentasi rasmi: https://www.php.cn/link/d9a8c56824cfbe66f28f85edbbe83e09

Apakah acara model?


Dalam aplikasi Laravel anda, anda biasanya perlu menjadualkan peristiwa secara manual apabila tindakan tertentu berlaku. Seperti yang kita lihat dalam contoh di atas, kita boleh menjadualkan acara menggunakan kod berikut:

Walau bagaimanapun, apabila menggunakan model fasih di Laravel, beberapa peristiwa dijadualkan secara automatik untuk kami, jadi kami tidak perlu menjadualkannya secara manual. Jika kita mahu melakukan operasi apabila peristiwa berlaku, kita hanya perlu menentukan pendengar untuk mereka.
declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}

Senarai berikut menunjukkan peristiwa dan pencetus secara automatik dijadualkan oleh model yang fasih:

Diperolehi - Ambil dari pangkalan data.
  • Membuat - Membuat model.
  • Dibuat - Model telah dibuat.
  • mengemas kini - mengemas kini model.
  • Dikemaskini - Model telah dikemas kini.
  • SAVING - Mewujudkan atau mengemas kini model.
  • disimpan - Model telah dibuat atau dikemas kini.
  • Menghapus - Memadam model.
  • dipadam - Model telah dipadamkan.
  • dibuang - model telah dipadamkan dengan lembut.
  • forcedeleting - Pemadaman model.
  • dipaksa - Model telah dipaksa dipadamkan
  • Memulihkan - Memulihkan model dari pemadaman lembut.
  • dipulihkan - Model telah pulih dari padam lembut.
  • Replikasi - mereplikasi model.
  • Dalam senarai di atas, anda mungkin melihat beberapa nama acara yang serupa; Peristiwa yang berakhir dengan
dilaksanakan sebelum operasi berlaku, dan perubahannya berterusan ke pangkalan data. Peristiwa yang berakhir dengan

dilaksanakan selepas operasi berlaku, dan perubahannya berterusan ke pangkalan data. creating created mari kita lihat cara menggunakan peristiwa model ini dalam aplikasi Laravel. ing ed Gunakan

Dengarkan Acara Model

Satu cara untuk mendengar acara model adalah untuk menentukan harta dispatchesEvents pada model anda.


Harta ini membolehkan anda memetakan acara model yang fasih ke kelas acara yang harus dijadualkan apabila peristiwa berlaku. Ini bermakna anda boleh menentukan pendengar seperti anda akan mengendalikan sebarang acara lain.

dispatchesEvents Untuk memberikan lebih banyak konteks, mari kita lihat contoh.

Katakan kami sedang membina aplikasi blog dengan dua model:

dan

. Kami akan mengatakan bahawa kedua -dua model menyokong pemadaman lembut. Apabila kita menyimpan

baru, kita ingin mengira masa bacaan artikel berdasarkan panjang kandungan. Apabila kami dengan perlahan memadam penulis, kami mahu penulis dengan perlahan memadam semua artikel.

AppModelsPost #Set model AppModelsAuthor AppModelsPost kita mungkin mempunyai model

seperti yang ditunjukkan di bawah:

Dalam model di atas, kita ada: AppModelsAuthor

  • Menambah harta yang memetakan acara model dispatchesEvents ke kelas acara deleted. Ini bermakna apabila model dipadam, acara AppEventsAuthorDeleted baru akan dijadualkan. Kami akan membuat kelas acara ini kemudian. AppEventsAuthorDeleted
  • mentakrifkan hubungan
  • . posts
  • Pemadaman lembut diaktifkan pada model dengan menggunakan ciri
  • . IlluminateDatabaseEloquentSoftDeletes
mari kita buat model

kami: AppModelsPost

declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}
dalam model

di atas, kita ada: AppModelsPost

    Menambah harta yang memetakan acara model
  • ke kelas acara dispatchesEvents. Ini bermakna apabila model dibuat atau dikemas kini, acara saving baru akan dijadualkan. Kami akan membuat kelas acara ini kemudian. AppEventsPostSaving AppEventsPostSaving mentakrifkan hubungan
  • .
  • author Pemadaman lembut diaktifkan pada model dengan menggunakan ciri
  • .
  • IlluminateDatabaseEloquentSoftDeletes
  • Model kami kini siap, jadi mari kita buat kelas acara
dan

kami. AppEventsAuthorDeleted AppEventsPostSaving #create class event

kami akan membuat kelas acara

yang akan dijadualkan apabila menyimpan artikel baru:

AppEventsPostSaving

Dalam kod di atas, kita dapat melihat kelas acara
use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);
, yang menerima contoh model

dalam pembangunnya. Kelas acara ini adalah bekas mudah untuk menyimpan contoh artikel yang disimpan. AppEventsPostSaving AppModelsPost Begitu juga, kita boleh membuat kelas acara

yang akan dijadualkan apabila memadamkan pengarang:

AppEventsAuthorDeleted

Dalam kelas di atas
declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
, kita dapat melihat bahawa pembina menerima contoh model

. AppEventsAuthorDeleted AppModelsAuthor Sekarang kita boleh terus membuat pendengar.

#create pendengar

mari kita buat pertama kali membuat pendengar yang boleh digunakan untuk mengira anggaran masa membaca artikel.

kami akan membuat kelas pendengar

baru:

AppListenersCalculateReadTime

Seperti yang kita lihat dalam kod di atas, kita hanya mempunyai satu
UserRegistered::dispatch($user);
kaedah. Ini adalah kaedah yang akan dipanggil secara automatik apabila menjadualkan acara

. Ia menerima contoh kelas acara handle yang mengandungi artikel yang disimpan. AppEventsPostSaving AppEventsPostSaving Dalam kaedah

, kami menggunakan formula mudah untuk mengira masa bacaan artikel. Dalam contoh ini, kami mengandaikan bahawa kelajuan bacaan purata adalah 265 perkataan seminit. Kami mengira masa bacaan dalam beberapa saat dan kemudian menetapkan atribut

pada model artikel. handle

Oleh kerana pendengar ini akan dipanggil apabila peristiwa model saving dicetuskan, ini bermakna bahawa atribut read_time_in_seconds dikira setiap kali artikel itu berterusan ke pangkalan data sebelum membuat atau mengemas kini.

kita juga boleh membuat pendengar yang perlahan memadam semua artikel yang berkaitan apabila lembut memadam penulis.

kita boleh membuat kelas pendengar AppListenersSoftDeleteAuthorRelationships baru:

declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}

Dalam pendengar di atas, kaedah handle menerima contoh kelas acara AppEventsAuthorDeleted. Kelas acara ini mengandungi penulis yang dipadam. Kemudian, kami menggunakan hubungan posts untuk memadamkan artikel penulis. delete Oleh itu, apabila model

dipadamkan dengan lembut, semua artikel penulis juga akan dipadamkan dengan lembut.

AppModelsAuthor Dengan cara ini, perlu diperhatikan bahawa anda mungkin mahu menggunakan penyelesaian yang lebih kuat dan boleh diguna semula untuk mencapai matlamat ini. Tetapi untuk tujuan artikel ini, kami tetap mudah.

Gunakan penutupan untuk mendengar peristiwa model

Cara lain yang boleh anda gunakan adalah untuk menentukan pendengar sebagai penutupan model itu sendiri.

Mari kita lihat contoh artikel pemadam lembut apabila kita dengan lembut menghapus pengarang. Kami boleh mengemas kini model

kami untuk mengandungi penutupan yang mendengar untuk

peristiwa model: AppModelsAuthor deleted

kita dapat melihat dalam model di atas bahawa kita menentukan pendengar dalam kaedah
use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);
model. Kami mahu mendengar acara model

, jadi kami menggunakan booted. Begitu juga, jika kita mahu membuat pendengar untuk acara model deleted, kita boleh menggunakan self::deleted dan sebagainya. Kaedah created menerima penutupan yang menerima self::created yang dipadam. Penutupan ini akan dilaksanakan apabila model dipadamkan, jadi semua artikel pengarang akan dipadam. self::deleted AppModelsAuthor Saya sangat suka cara ini untuk menentukan logik pendengar kerana ia dapat melihat dengan segera jika ia mendaftarkan pemerhati ketika membuka kelas model. Oleh itu, sementara logik masih "tersembunyi" dalam fail yang berasingan, kita dapat mengetahui bahawa kita telah mendaftarkan pendengar untuk sekurang -kurangnya satu peristiwa model. Walau bagaimanapun, jika kod dalam penutupan ini menjadi lebih kompleks, ia mungkin bernilai mengekstrak logik ke dalam kelas pendengar yang berasingan.

Trik yang berguna ialah anda juga boleh menggunakan fungsi

untuk membuat penutupan beratur. Ini bermakna bahawa kod pendengar akan ditolak ke dalam barisan untuk berjalan di latar belakang, dan bukannya dalam kitaran hayat permintaan yang sama. Kami boleh mengemas kini pendengar untuk berehat seperti berikut:

IlluminateEventsqueueable

Seperti yang kita lihat dalam contoh di atas, kita membungkus penutupan dalam fungsi
declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
.

menggunakan pemerhati untuk mendengar peristiwa model


Cara lain yang boleh anda ambil untuk mendengar acara model adalah menggunakan pemerhati model. Pemerhati model membolehkan anda menentukan semua pendengar untuk model dalam satu kelas.

Biasanya, mereka adalah kelas yang wujud dalam direktori app/Observers, dan mereka mempunyai kaedah yang sepadan dengan peristiwa model yang ingin anda dengar. Sebagai contoh, jika anda ingin mendengar acara model deleted, anda akan menentukan kaedah deleted dalam kelas pemerhati. Jika anda ingin mendengar acara model created, anda akan menentukan kaedah created dalam kelas pemerhati, dan sebagainya.

mari kita lihat cara membuat pemerhati model untuk Model AppModelsAuthor Mendengar Model untuk deleted peristiwa model:

declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}

Seperti yang kita lihat dalam kod di atas, kita membuat pemerhati dengan kaedah deleted. Kaedah ini menerima contoh model AppModelsAuthor yang dipadam. Kemudian, kami menggunakan hubungan posts untuk memadamkan artikel penulis. delete

Katakan, sebagai contoh, kami juga ingin menentukan pendengar untuk peristiwa model

dan created. Kami boleh mengemas kini pemerhati kami seperti ini: updated

use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);
Untuk menjalankan kaedah

, kita perlu mengarahkan Laravel untuk menggunakannya. Untuk melakukan ini, kita boleh menggunakan atribut AppObserversAuthorObserver. Ini membolehkan kita mengaitkan pemerhati dengan model, sama seperti bagaimana kita mendaftarkan skop pertanyaan global menggunakan atribut #[IlluminateDatabaseEloquentAttributesObservedBy] (seperti yang ditunjukkan dalam memahami bagaimana menguasai skop pertanyaan di Laravel). Kami boleh mengemas kini model #[ScopedBy] kami seperti ini untuk menggunakan pemerhati: AppModelsAuthor

declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
Saya sangat menyukai cara ini untuk menentukan logik pendengar, kerana ia dapat melihat dengan segera jika ia mendaftarkan pemerhati ketika membuka kelas model. Oleh itu, sementara logik masih "tersembunyi" dalam fail yang berasingan, kita dapat mengetahui bahawa kita telah mendaftarkan pendengar untuk sekurang -kurangnya satu peristiwa model.

menguji acara model anda


Tidak kira kaedah peristiwa model yang anda gunakan, anda mungkin ingin menulis beberapa ujian untuk memastikan logik anda berfungsi seperti yang diharapkan.

Mari lihat bagaimana untuk menguji peristiwa model yang kami buat dalam contoh di atas.

Kami mula -mula menulis ujian untuk memastikan artikel penulis dipadamkan dengan lembut apabila penulis dipadamkan dengan lembut. Ujian mungkin kelihatan seperti ini:

UserRegistered::dispatch($user);
Dalam ujian di atas, kami membuat pengarang dan artikel baru untuk penulis itu. Kami dengan lembut menghapuskan penulis dan menegaskan bahawa kedua -dua pengarang dan artikel itu dipadamkan dengan lembut.

Ini adalah ujian yang sangat mudah tetapi berkesan yang boleh kita gunakan untuk memastikan logik kami berfungsi seperti yang diharapkan. Kelebihan ujian ini ialah ia harus berfungsi dengan setiap kaedah yang kita bincangkan dalam artikel ini. Oleh itu, jika anda beralih antara mana -mana kaedah yang dibincangkan dalam artikel ini, ujian anda masih perlu lulus.

Begitu juga, kita boleh menulis beberapa ujian untuk memastikan bahawa masa bacaan artikel dikira apabila membuat atau mengemas kini. Ujian mungkin kelihatan seperti ini:

declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}

kami mempunyai dua ujian di atasnya:

  • Ujian pertama memastikan bahawa masa bacaan artikel dikira apabila menciptanya.
  • Ujian kedua memastikan bahawa masa bacaan artikel dikira apabila artikel dikemas kini.

langkah berjaga -jaga semasa menggunakan peristiwa model


Walaupun peristiwa model sangat mudah, terdapat beberapa isu yang perlu diperhatikan ketika menggunakannya.

peristiwa model dijadualkan dari model fasih sahaja. Ini bermakna jika anda menggunakan fasad IlluminateSupportFacadesDB untuk berinteraksi dengan data asas model dalam pangkalan data, peristiwa -peristiwa itu tidak akan dijadualkan.

Contohnya, mari kita lihat contoh mudah, kami menggunakan fasad

untuk memadamkan pengarang: IlluminateSupportFacadesDB

use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);
Menjalankan kod di atas akan memadamkan pengarang dari pangkalan data seperti yang diharapkan. Walau bagaimanapun, peristiwa model

dan deleting tidak dijadualkan. Jadi jika anda menentukan mana -mana pendengar untuk peristiwa model ini apabila memadam penulis, mereka tidak akan dijalankan. deleted

Begitu juga, jika anda menggunakan fasih untuk mengemaskini batch atau memadam model,

, saved, updated, dan deleting peristiwa model tidak dijadualkan untuk model yang terjejas. Ini kerana peristiwa dijadualkan dari model itu sendiri. Walau bagaimanapun, apabila kemas kini dan penghapusan batch dikemas kini, model itu sebenarnya tidak diambil dari pangkalan data, jadi peristiwa tidak dijadualkan. deleted

Sebagai contoh, katakan kami menggunakan kod berikut untuk memadamkan pengarang:

declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
Oleh kerana kaedah

dipanggil secara langsung pada pembina pertanyaan, peristiwa model delete dan deleting tidak dijadualkan untuk penulis itu. deleted

kaedah alternatif untuk dipertimbangkan


Saya suka menggunakan peristiwa model dalam projek saya. Mereka berfungsi sebagai cara yang baik untuk menghilangkan kod saya dan juga membolehkan saya untuk menjalankan logik secara automatik apabila saya tidak mempunyai banyak kawalan ke atas kod yang mempengaruhi model. Sebagai contoh, jika saya memadam penulis di Laravel Nova, saya masih boleh menjalankan beberapa logik apabila memadam penulis.

Walau bagaimanapun, adalah penting untuk mengetahui kapan untuk mempertimbangkan menggunakan kaedah yang berbeza.

Untuk menerangkan ini, mari kita lihat contoh asas di mana kita mungkin ingin mengelakkan menggunakan peristiwa model. Memperluas contoh aplikasi blog kami yang terdahulu, dengan mengandaikan kami ingin menjalankan perkara berikut semasa membuat catatan baru:

Kirakan masa bacaan artikel.
  • Hantar panggilan API ke X/Twitter untuk berkongsi artikel.
  • Hantar pemberitahuan kepada setiap pelanggan di platform.
  • jadi kita mungkin membuat tiga pendengar yang berasingan (satu untuk setiap tugas) yang berjalan setiap kali contoh
baru dicipta.

AppModelsPost Tetapi sekarang mari kita semak salah satu ujian sebelumnya:

declare(strict_types=1);

namespace App\Events;

use App\Models\User;
use Illuminate\Broadcasting\InteractsWithSockets;
use Illuminate\Foundation\Events\Dispatchable;
use Illuminate\Queue\SerializesModels;

final class UserRegistered
{
    use Dispatchable;
    use InteractsWithSockets;
    use SerializesModels;

    public function __construct(public User $user)
    {
        //
    }
}

Jika kita menjalankan ujian di atas, ia juga akan mencetuskan ketiga -tiga operasi ini apabila model AppModelsPost dibuat melalui kilangnya. Sudah tentu, mengira masa bacaan adalah tugas sekunder, jadi tidak penting. Tetapi kami tidak mahu membuat panggilan API atau menghantar pemberitahuan semasa ujian. Ini adalah kesan sampingan yang tidak dijangka. Sekiranya pemaju menulis ujian tidak menyedari kesan sampingan ini, mungkin sukar untuk menjejaki mengapa operasi ini berlaku.

kami juga ingin mengelakkan menulis sebarang logik khusus ujian dalam pendengar, yang menghalang operasi ini daripada berjalan semasa ujian. Ini akan menjadikan kod aplikasi lebih kompleks dan lebih sukar untuk dikekalkan.

Ini adalah salah satu kes di mana anda mungkin ingin mempertimbangkan pendekatan yang lebih jelas dan bukannya bergantung pada peristiwa model automatik.

Salah satu cara boleh mengekstrak kod penciptaan AppModelsPost anda ke dalam kelas perkhidmatan atau tindakan. Sebagai contoh, kelas perkhidmatan mudah mungkin kelihatan seperti ini:

use App\Events\UserRegistered;
use App\Models\User;

$user = User::create([
    'name' => 'Eric Barnes',
    'email' => 'eric@example.com',
]);

UserRegistered::dispatch($user);

Di kelas di atas, kami secara manual memanggil kod yang mengira masa membaca, menghantar pemberitahuan, dan jawatan ke Twitter. Ini bermakna kita mempunyai kawalan yang lebih baik apabila operasi ini dijalankan. Kami juga boleh mengolok -olok kaedah ini dengan mudah dalam ujian untuk menghalang mereka daripada berjalan. Kita masih boleh mengutamakan operasi ini jika diperlukan (dalam kes ini kita kemungkinan besar akan berbuat demikian).

Oleh itu, kita boleh memadamkan peristiwa model dan pendengar untuk operasi ini. Ini bermakna kita boleh menggunakan kelas

baru ini dalam kod aplikasi kami dan menggunakan kilang model dengan selamat dalam kod ujian kami. AppServicesPostService

manfaat tambahan untuk melakukan ini adalah bahawa ia juga menjadikan kod lebih mudah difahami. Seperti yang saya sebutkan secara ringkas, kritikan umum menggunakan peristiwa dan pendengar adalah bahawa ia boleh menyembunyikan logik perniagaan di tempat yang tidak dijangka. Jadi jika pemaju baru menyertai pasukan, jika mereka dicetuskan oleh peristiwa model, mereka mungkin tidak tahu di mana atau mengapa beberapa operasi berlaku.

Walau bagaimanapun, jika anda masih mahu menggunakan acara dan pendengar untuk logik sedemikian, anda mungkin mempertimbangkan menggunakan pendekatan yang lebih jelas. Sebagai contoh, anda boleh menjadualkan acara dari kelas perkhidmatan untuk mencetuskan pendengar. Dengan cara ini, anda masih boleh menggunakan kelebihan peristiwa dan pendengar, tetapi anda mempunyai kawalan yang lebih baik apabila peristiwa dijadualkan.

Contohnya, kita boleh mengemas kini kaedah

di atas dalam contoh

kami untuk menjadualkan peristiwa:

AppServicesPostService createPost Dengan menggunakan kaedah di atas, kita masih boleh mempunyai pendengar yang berasingan untuk membuat permintaan API dan menghantar pemberitahuan ke Twitter. Tetapi kami mempunyai kawalan yang lebih baik apabila operasi ini dijalankan, jadi mereka tidak dijalankan semasa ujian menggunakan kilang model.

declare(strict_types=1);

namespace App\Listeners;

use App\Events\UserRegistered;
use App\Notifications\WelcomeNotification;
use Illuminate\Support\Facades\Mail;

final readonly class SendWelcomeEmail
{
    public function handle(UserRegistered $event): void
    {
        $event->user->notify(new WelcomeNotification());
    }
}
Tidak ada peraturan emas ketika memutuskan untuk menggunakan mana -mana kaedah ini. Semuanya bergantung kepada anda, pasukan anda, dan ciri -ciri yang anda bina. Walau bagaimanapun, saya cenderung mengikut peraturan berikut:

  • Jika operasi dalam pendengar hanya membuat perubahan kecil pada model, pertimbangkan untuk menggunakan peristiwa model. Contoh: Menjana slug, hitung masa bacaan, dll.
  • Jika operasi akan menjejaskan model lain (sama ada ia dibuat secara automatik, dikemas kini atau dipadam), ia lebih jelas dan tidak menggunakan peristiwa model.
  • Jika operasi akan berfungsi dengan proses luaran (panggilan API, pemprosesan fail, pemberitahuan pencetus, pekerjaan beratur), lebih jelas bahawa anda tidak menggunakan peristiwa model.

kebaikan dan keburukan menggunakan peristiwa model


dengan cepat merumuskan apa yang telah kami diperkenalkan dalam artikel ini, berikut adalah beberapa kelebihan dan kekurangan menggunakan peristiwa model:

#pros

  • menggalakkan anda untuk merekodkan kod.
  • membolehkan anda mencetuskan tindakan secara automatik, tidak kira di mana model dibuat/dikemas kini/padam. Sebagai contoh, jika model itu dibuat di Laravel Nova, anda boleh mencetuskan logik perniagaan.
  • Anda tidak perlu ingat untuk menjadualkan acara setiap kali anda membuat/mengemas kini/memadam model.

#disadvantages

  • boleh menyebabkan kesan sampingan yang tidak dijangka. Anda mungkin mahu membuat/mengemas kini/memadam model tanpa mencetuskan beberapa pendengar, tetapi ini boleh membawa kepada tingkah laku yang tidak dijangka. Ini amat bermasalah apabila menulis ujian.
  • Logik perniagaan mungkin tersembunyi di lokasi yang tidak dijangka yang sukar untuk dijejaki. Ini akan menjadikan aliran kod lebih sukar difahami.

Kesimpulan


Harap artikel ini memberikan gambaran keseluruhan tentang peristiwa model dan pelbagai cara untuk menggunakannya. Ia juga harus menunjukkan kepada anda bagaimana untuk menguji kod acara model dan beberapa isu yang perlu diperhatikan apabila menggunakannya.

Anda kini harus mempunyai keyakinan yang cukup untuk menggunakan peristiwa model dalam aplikasi Laravel anda.

Atas ialah kandungan terperinci Panduan untuk acara model Laravel ' s. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn
Artikel sebelumnya:Versi API di Laravel 11Artikel seterusnya:Versi API di Laravel 11