gpt4 book ai didi

python - Django:通过外键查找所有反向引用

转载 作者:太空狗 更新时间:2023-10-29 21:09:47 27 4
gpt4 key购买 nike

好吧,现在我正在使用 Django 1.6+

我有一个模型:

class FileReference(models.Model):
# some data fields
# ...
pass

class Person(models.Model):
avatar = models.ForeignKey(FileReference, related_name='people_with_avatar')

class House(models.Model):
images = models.ManyToManyField(FileReference, related_name='houses_with_images')

class Document(model.Model):
attachment = models.OneToOneField(FileReference, related_name='document_with_attachment')

因此,许多其他模型将有一个引用 FileReference 模型的外键。

但有时,引用模型会被删除,而 FileReference 对象会留下。

我想删除没有外键引用的 FileReference 对象。

但是很多其他地方会有外键。

有什么有效的方法可以找到所有的引用文献吗?即获取某个模型对象的引用计数?

最佳答案

我偶然发现了这个问题,并为您找到了解决方案。请注意,不再支持 django==1.6,因此此解决方案可能适用于 django>=1.9

假设我们现在正在谈论其中的 2 个对象:

class FileReference(models.Model):
pass

class Person(models.Model):
avatar = models.ForeignKey(FileReference, related_name='people_with_avatar', on_delete=models.CASCADE)

正如您在 ForeignKey.on_delete 中看到的那样文档,当您删除相关的 FileReference 对象时,引用的对象 Person 也会被删除。

现在回答你的问题。我们如何做到受人尊敬?我们希望在 Person 删除时,FileReference 对象也将被删除。

我们将使用 post_delete signal 来做到这一点:

def delete_reverse(sender, **kwargs):
try:
if kwargs['instance'].avatar:
kwargs['instance'].avatar.delete()
except:
pass

post_delete.connect(delete_reverse, sender=Person)

我们所做的是删除 删除时 avatar 字段中的引用。请注意,try: except: block 用于防止循环异常。

额外:

上述解决方案将适用于所有 future 的对象。如果您想删除所有没有引用的过去对象,请执行以下操作:

在您的包中添加以下文件和目录:management/commands/remove_unused_file_reference.py

from django.core.management.base import BaseCommand, CommandError


class Command(BaseCommand):

def handle(self, *args, **options):

file_references = FileReference.objects.all()
file_reference_mapping = {file_reference.id: file_reference for file_reference in file_references}

persons = Person.objects.all()
person_avatar_mapping = {person.avatar.id: person for person in persons}


for file_reference_id, file_reference in file_reference_mapping.items():
if file_reference_id not in person_avatar_mapping:
file_reference.delete()

完成后,调用:python manage.py remove_unused_file_reference这是基本想法,您可以将其更改为批量删除等...

我希望这对那里的人有所帮助。祝你好运!

关于python - Django:通过外键查找所有反向引用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29158379/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com