Yii:级联删除相关记录和文件
我有一个看起来有点像这样的应用程序方案:
<?php
class Category extends CActiveRecord
{
public function relations()
{
return array(
'posts' => array(self::HAS_MANY, 'Post', 'category_id'),
);
}
// ...
}
class Post extends CActiveRecord
{
public function relations()
{
return array(
'categories' => array(self::BELONGS_TO, 'Category', 'category_id'),
'pictures' => array(self::HAS_MANY, 'PostPicture', 'post_id'),
);
}
// ...
}
class PostPicture extends CActiveRecord
{
public function relations()
{
return array(
'post' => array(self::BELONGS_TO, 'Post', 'post_id'),
);
}
// ... public function deleteFiles() ...
}
PHP 代码中定义的所有关系也存在于具有适当外键和 ON DELETE CASCADE
设置的数据库中(InnoDB)。 PostPicture
提供了一种删除关联文件的方法。
当我通过$category->delete();
删除Category
对象时,发生数据库级别的ON DELETE CASCADE,图片记录在我可以访问它们之前被删除我将无法检索文件系统路径。
完全禁用外键并不是很优雅 - 我必须为几乎每个模型类实现 beforeDelete
挂钩。
检索与类别帖子关联的所有 PostPicture 行并在 Category::beforeDelete()
中调用其 deleteFiles
函数似乎是一个可接受的解决方案,但有没有更优雅的方法来实现此目的?
I have an application scheme that looks slightly like this:
<?php
class Category extends CActiveRecord
{
public function relations()
{
return array(
'posts' => array(self::HAS_MANY, 'Post', 'category_id'),
);
}
// ...
}
class Post extends CActiveRecord
{
public function relations()
{
return array(
'categories' => array(self::BELONGS_TO, 'Category', 'category_id'),
'pictures' => array(self::HAS_MANY, 'PostPicture', 'post_id'),
);
}
// ...
}
class PostPicture extends CActiveRecord
{
public function relations()
{
return array(
'post' => array(self::BELONGS_TO, 'Post', 'post_id'),
);
}
// ... public function deleteFiles() ...
}
All relations defined in PHP code also exist in the database with proper foreign keys and ON DELETE CASCADE
set up (InnoDB). PostPicture
provides a way to delete associated files.
When I delete a Category
object via $category->delete();
, ON DELETE CASCADE on the database level occurs, the picture records get deleted before I can access them and I won't be able to retrieve file system paths.
Completely disabling foreign keys is not very elegant - I would have to implement beforeDelete
hooks for nearly every model class.
Retrieving all PostPicture rows associated to the Category's posts and calling their deleteFiles
function in Category::beforeDelete()
seems like an acceptable solution but is there a more elegant way to achieve this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
onDelete级联的目的不就是删除相关记录吗?如果您想检索某些内容,请在删除之前进行。如果我理解正确的话,您想要检索文件路径,以便也可以删除系统上的文件。
由于您知道要删除的记录,因此找到数据并保存它,然后执行删除。只是一个想法。
Isn't this the objective of onDelete cascade that related records get deleted. If you want to retrieve something then do it prior to delete. If I understand correctly you want to retrieve the filepaths so the files on the system can be deleted as well.
Since you know the records you are deleting find the data and save it and then execute the delete. just a thought.
oncascade 是一个数据库设置...所以当数据库删除子记录时...Yii 或任何 PHP 代码都不“知道”这一点...这就是为什么你的对象没有被删除并且 beforeDelete/afterDelete 没有被调用。 ..
复制自这里
oncascade is a database setting... so as the database is deleting the child records... the Yii or any PHP code does not "know" that... that's why your object is not deleted and beforeDelete/afterDelete is not called...
Copied from here