【问题标题】:django admin - model cross reference - both foreign and many to many relationship - displaying in admindjango admin - 模型交叉引用 - 外部和多对多关系 - 在管理员中显示
【发布时间】:2015-02-06 04:58:08
【问题描述】:

我在同一个应用中有 2 个模型相互交叉引用。一个作为外键,另一个作为多对多键。

class VideoEmbed(models.Model):
    person = models.ForeignKey('Person')
    title = models.CharField(max_length=250) 
    video = EmbedVideoField()

class Person(models.Model):
    name = models.CharField(max_length=200)
    born = models.DateField(blank=True, null=True)
    video = models.ManyToManyField(VideoEmbed, related_name='video_embed', null=True, blank=True)

我想这样做的原因是将 Person 与其相关视频链接起来,因为一个人可以拥有多个视频。现在在 django 管理站点中,videoembed 模型将针对每个人录制视频,因此这些视频将分别显示在 Person 的每个实例中。但是在 django 站点中,我必须从多个选择框中选择这些视频中的每一个许多关系领域。

我希望此字段仅显示通过 videoembed 模型链接到此实例的视频,而不是所有添加的视频。有没有办法做到这一点?如果不是,那么我应该能够在本节中看到 2 个字段而不是一个,以便我可以选择链接到 Person 实例的视频。

【问题讨论】:

  • 我很困惑。为什么需要视频中的参考资料回传人?多对多链接已经提供了反向链接?
  • @LegoStormtroopr 嗨,每个人都有特定的视频,每个人可以链接很多视频。现在考虑总共 50-100 个视频,很难确定哪个视频属于某个特定的人。

标签: django django-models django-admin


【解决方案1】:

我认为这是对how ManyToMany relationships work的误解。定义多对多时,反向关系包含在关系的“远端”。

例如,考虑您的代码的精简版本:

class Video(models.Model):
    title = models.CharField(max_length=250) 

class Person(models.Model):
    name = models.CharField(max_length=200)
    videos = models.ManyToManyField(VideoEmbed, related_name='people', null=True, blank=True)

在此,person_object.videos 为一个人提供了一组视频,不明显的是 Django 还在Video 上设置了一个反向关系,可以访问video_object.people,这是一组所有@ 987654329@ 对象通过ManyToMany 关系引用特定的Video

默认情况下,此关系为 model_name_set,因此您的默认值为 person_set,但通过在 ManytoManyField 中设置 related_name 参数,它会覆盖此关系。

ForeignKey 添加到Video 模型会创建and entirely separate and independent relationship

考虑这个简单的模型,其中Video 现在有一个作者,并且人们在视频中被标记(实际上他们可能都在视频中,但我们正在演示 ForeignKey 和 ManyToMany 是如何独立的,并且属性名称的良好语义的价值):

class Video(models.Model):
    title = models.CharField(max_length=250) 
    author = models.ForeignKey('Person')

class Person(models.Model):
    name = models.CharField(max_length=200)
    videos_person_tagged_in = models.ManyToManyField(VideoEmbed, related_name='tagged_people', null=True, blank=True)

在这里,设置video_object.author 不会改变视频的tagged_people,也不会为Person 设置videos_person_tagged_in 改变作者。

至于为什么reverse relation for a ManyToMany isn't showing up in Django admin, this is a known issue那个requires custom forms to work around。主要是因为您在一个项目上定义了 ManyToMany,它只会显示在该模型管理页面中。

【讨论】:

  • 感谢乐高的详细解释。从您的回答中我的理解是,我无法按照我的要求进行多对多的工作。这是否也意味着我将无法在管理站点上亲自显示至少 2 个字段。所以它不仅向我显示标题,还显示作者?
  • 视情况而定。我建议更改您的模型名称和属性以更好地匹配您想要实现的目标。视频晚餐有很多人,他们有作者、演员、标注者、喜欢的人等等......
  • 你也许可以做到,但你的代码现在太模糊了,无法理解。
  • 如果这对您有所帮助,请不要忘记点赞或接受以向未来的用户表明您的问题已得到解答。
  • 是否有您正在寻找能够提供问题解决方案的特定信息。
猜你喜欢
  • 2010-11-29
  • 2021-08-28
  • 2011-02-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-07-22
  • 1970-01-01
  • 2013-06-18
相关资源
最近更新 更多