Удалить все отношения при удалении строки в laravel
У меня есть сообщения, комментарии и уведомления таблицы
Каждый пост имеет множество комментариев
каждый комментарий уведомления с помощью методов hasmany
каждый после уведомления о помощью методов hasmany
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();
});
}
}
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();
});
}
}
Когда я удаляю сообщение, я должен удалить уведомления и комментарии, а также, Но проблема в том, что когда я удаляю комментарии, уведомления не удаляются с ним, Они удаляются, когда я удаляю комментарий напрямую, но мне нужно удалить уведомления о комментариях, когда я удаляю сообщение !


Ответы - Удалить все отношения при удалении строки в laravel / Delete all relation when Deleting a row in laravel



20.11.2019 05:29:27
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();
});
}
}
Просто для записей я добавляю то, что мы обсуждаем в комментариях, поскольку это может служить другим, кто сталкивается с той же проблемой, и в комментариях это может остаться незамеченным. Кредит для ОП @Махмуд Бен Джабир.
Но если сообщение имеет 100 комментариев, он выполнит 100 запросов, чтобы удалить их ! Я выясню, как удалить с минимальными запросами...
У меня уже есть onDelete на комментарии, но уведомления полиморфны, поэтому он не будет работать на них...
Решение, которое я буду использовать это:
1-получить идентификаторы комментариев, которые связаны с сообщением.
2-удалить из уведомлений, где тип-комментарий и идентификатор в (идентификаторы).
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.
}


->onDelete('cascade')
, но только будет работать с базами данных relationals и настраивать внешние ключи на уровне БД




$ids = $post->comments()->pluck('id'); Notification::where('entity_type', 'App\Comment')->whereIn('entity_id', $ids)->delete(); Comment::whereIn('id', $ids)->delete(); $post->notifications()->delete();


20.11.2019 05:42:42
Пожалуйста, используйте (предполагая связь между сообщением и комментариями)
$table->foreign('post_id')
->references('id')->on('posts')
->onDelete('cascade');
чтобы создать внешнее отношение в вашем файле миграции. Поэтому, когда вы удаляете связанный пост, его комментарий также будет удален.