在 laravel 中删除一行时删除所有关系

Mah*_*bir 5 php laravel eloquent eloquent-relationship

我有帖子、评论和通知表

每个帖子都有很多评论

每个评论都有很多通知

每个帖子都有很多通知

class Post extends Model
{

    public function notifications() {
        return $this->morphOne(Notification::class, 'to');
    }

    public function comments() {
        return $this->hasMany(Comment::class, 'post_id');
    }

    public static function boot() {
        parent::boot();

        static::deleting(function($post) {
            $post->comments()->delete();
            $post->notifications()->delete();
        });
    } 
}
Run Code Online (Sandbox Code Playgroud)
class Comment extends Model
{
    public function notifications() {
        return $this->morphOne(Notification::class, 'to');
    }

    public static function boot() {
        parent::boot();

        static::deleting(function($comment) {
            $comment->notifications()->delete();
        });
    }
}
Run Code Online (Sandbox Code Playgroud)

当我删除帖子时,我应该删除通知和评论,但问题是当我删除评论时,通知不会随之删除,当我直接删除评论但我需要删除评论时,它们会被删除删除帖子时评论的通知!

por*_*s Ψ 4

Laravel 不会实例化它删除的相关模型,这就是为什么当您直接删除评论时会删除通知,但通过删除帖子来删除评论时不会删除通知。删除帖子时,您必须实例化评论才能使其正常工作。

class Post extends Model {
    
    public function notifications() {
        return $this->morphOne(Notification::class, 'to');
    }
    
    public function comments() {
        return $this->hasMany(Comment::class, 'post_id');
    }
    
    public static function boot() {
        parent::boot();
    
        static::deleting(function($post) {
            // here you could instantiate each related Comment
            // in this way the boot function in the Comment model will be called
            $post->comments->each(function($comment) {
                // and then the static::deleting method when you delete each one
                $comment->delete();
            });
            $post->notifications()->delete();
        });
    } 
}
Run Code Online (Sandbox Code Playgroud)

只是为了记录,我添加了我们在评论中讨论的内容,因为它可以为遇到相同问题的其他人提供服务,并且在评论中它可能会被忽视。感谢 OP @Mahmoud Ben Jabir。

但如果帖子有 100 条评论,它将执行 100 条查询来删除它们!我将弄清楚如何用最少的查询来删除......

我已经对评论进行了 onDelete,但通知是多态的,所以它对它们不起作用......

我将使用的解决方案是:
1- 获取与帖子相关的评论 ID。
2- 从通知中删除,其中类型是评论并且 (ids) 中的 id。
3-删除与该帖子相关的评论。
4- 删除与帖子相关的通知
5- 删除帖子。

public static function boot() {
    parent::boot();
    static::deleting(function($post) {
        // 1- Get Ids of Comments that are related to the Post. 
        $ids = $post->comments()->pluck('id'); 
        // 2- Delete from Notifications where type IS Comment AND id in (ids). 
        Notification::where('entity_type', 'App\Comment')->whereIn('entity_id', $ids)->delete(); 
        // 3- Delete Comments related to the Post. 
        $post->comments()->delete();
        // 4- Delete The Notifications Related to the Post 
        $post->notifications()->delete();
    });
    // 5- Delete The Post.
}
Run Code Online (Sandbox Code Playgroud)