Php Laravel模型关系和模型事件

Php Laravel模型关系和模型事件,php,laravel,eloquent,relational-database,Php,Laravel,Eloquent,Relational Database,目前我正在构建一个通知系统,通知通过模型事件传递。一些通知依赖于模型关系中发生的事情 示例:我有一个与用户有一对多关系的项目模型 public function projectmanager() { return $this->belongsToMany('User', 'project_managers'); } 我希望在项目模型事件中监视此关系的更改。现在,我是这样做的 $dirtyAttributes = $project->getDirty(); foreach($

目前我正在构建一个通知系统,通知通过模型事件传递。一些通知依赖于模型关系中发生的事情

示例:我有一个与用户有一对多关系的项目模型

public function projectmanager() {
    return $this->belongsToMany('User', 'project_managers');
}
我希望在项目模型事件中监视此关系的更改。现在,我是这样做的

$dirtyAttributes = $project->getDirty();
foreach($dirtyAttributes as $attribute => $value) {
   //Do something
}
这是在模型的
:更新
事件中运行的,但只查看模型属性而不查看其任何关系数据,是否可以获取旧的关系数据和新的关系数据以进行比较和处理?

您应该为此使用

虽然这个答案使用了一个稍旧的方法,在这个方法中类本身需要调用它的观察器,但它已经被相当简单和很好地涵盖了。当前版本的文档(截至本答案的5.3版)建议在您的应用程序服务提供商中注册观察器,在您的示例中,它类似于:

<?php
namespace App\Providers;

use App\Project;
use App\Observers\ProjectObserver;
use Illuminate\Support\ServiceProvider;

class AppServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap any application services.
     *
     * @return void
     */
    public function boot()
    {
        Project::observe(ProjectObserver::class);
    }
}

你找到解决办法了吗?我认为不可能。因为具有关系的数据具有不同的保存模型(在您的情况下,可能存在
ProjectManager
model right?)。尽管如此,您能否发布您如何尝试保存
Project
model?您是通过关系保存还是单独保存?您可以始终在模型事件中保存。我觉得这很奇怪,但它确实起作用了。我知道已经三年了,但我有点困惑为什么这个答案会被接受。它没有解决这个问题,即如何获取相关字段的脏值/原始值。getDirty和getOriginal不包含任何关于关系的信息(例如,外键除外)。@CharlesWood对关系本身的更改由外键决定,如果更改,外键将成为原始/dirty值的一部分(即,哪个用户更改为项目经理)。如果您想检测相关模型的更改(例如,您想知道作为管理者的用户是否更改了他们的姓名?),那么您将有一个用户模型的观察者,并在那里对更改进行处理。如果出于某种原因希望操纵项目以观察相关模型的更改,可以使用
getRelations()
relationsToArray()
。也许
getTouchedRelations()
,这要看情况而定。哦,当然!谢谢你给我解释清楚。
<?php

namespace App\Observers;

use App\Project;

class ProjectObserver
{
    /**
     * Listen to the Project updating event.
     *
     * @param  Project $project
     * @return void
     */
    public function updating(Project $project)
    {
        $dirtyAttributes = $project->getDirty();
        $originalAttributes = $project->getOriginal();
        // loop over one and compare/process against the other
        foreach ($dirtyAttributes as $attribute => $value) {
            // do something with the equivalent entry in $originalAttributes
        }
    }
}