如何为所有模型而不是单独实现雄辩的“保存”事件

问题描述 投票:0回答:3

基于laravel雄辩事件的文档,所有雄辩事件都是根据每个模型单独触发的,有没有办法使用“创建”事件或任何其他雄辩事件由所有模型触发

例如,如果创建任何模型,则会触发事件A

laravel laravel-5 eloquent laravel-events
3个回答
4
投票

扩展模型类:

use Auth;
use Illuminate\Database\Eloquent\Model;

class GeneralModel extends Model
{
  public static function boot()
  {
    parent::boot();

    static::creating(function ($model) {
        if (Auth::user()) {
            $model->created_by = Auth::user()->id;
            $model->updated_by = Auth::user()->id;
        }
    });
  }
}

当你说创建一个说

property
对象时,它就会被触发。将其用于您需要的所有型号。

class Property extends GeneralModel
{
  //..
}

3
投票

监听触发的 Eloquent

creating
事件。这是一个“字符串”事件,但仍然不是对象,因此您可以在此处进行一些...通配符匹配。

这是从 Eloquent 激发的事件字符串:

"eloquent.{$event}: ".static::class

因此,您可以监听“eloquent.creating: *”来捕获 Eloquent 为任何模型创建的所有字符串事件。

Event::listen('eloquent.creating: *', function ($event, $model) {
    ....
});

显然,如果您已将模型定义为使用自定义事件对象,则将无法捕获这些对象。

您还可以创建一个模型观察器,但您必须将其注册到应用程序中要捕获事件的每个模型。


0
投票

您可能会发现自己有一个很好的用例来创建特征,而不是扩展 Illuminate\Database\Eloquent\Model。考虑:

<?php

namespace App\Models\Traits;

trait UpdatesUser
{
    public static function bootUpdatesUser()
    {
        static::saving(function(self $model) {
            Auth::user()->update([
                'changed_on' => now(),
                'changed_by' => $model->id,
                'changed_by_class' => $model::class
            ]);
        });
        static::updating(function(self $model) {
            if ( $model->isDirty() ) {
                Auth::user()->update([
                    'changed_on' => now(),
                    'changed_by' => $model->id,
                    'changed_by_class' => $model::class
                ]);
            }
        });
    }
}

每次加载模型时,

boot{TraitName}
方法都会启动,这意味着您不必在模型上覆盖并调用
parent::boot()
。我个人使用此模式来标记对父模型的任何子模型的更改。

<?php

namespace App\Models;

use App\Models\Traits\UpdatesUser;
use Illuminate\Database\Eloquent\Model;

class ChildModel extends Model
{
    use UpdatesUser;
    ...
}

// Both of these will update my `users` table, notifying me a change has been made.

ChildModel::create([...]);

ChildModel::find(1)->update([...]);
© www.soinside.com 2019 - 2024. All rights reserved.