没有反向关系的两个 ManyToMany 字段

Posted

技术标签:

【中文标题】没有反向关系的两个 ManyToMany 字段【英文标题】:Two ManyToMany fields without backwards relation 【发布时间】:2012-07-08 03:04:53 【问题描述】:

我正在尝试创建一个包含 2 个 ManyToMany 字段的模型,而不允许反向关系。 所以这是模型:

class Camp(models.Model):
#...

free_options = models.ManyToManyField('Option', related_name='+')
paid_options = models.ManyToManyField('Option', related_name='+')

尝试做之后

python manage.py syncdb

我收到以下错误:

错误:一个或多个模型未验证:camps.camp:Accessor for m2m 字段“free_options”与相关的 m2m 字段“Option.+”发生冲突。 在“free_options”的定义中添加一个related_name 参数。 camps.camp:m2m 字段“free_options”冲突的反向查询名称 与相关的 m2m 字段“Option.+”。将related_name 参数添加到 'free_options' 的定义。

在同一个模型上不可能有 2 个没有反向关系的字段吗?我该如何解决这个问题?

谢谢!

【问题讨论】:

不确定这是否有帮助,但请尝试through 我已经将我的 related_name 值更改为 'camp_free_options' 和 'camp_paid_options',所以我不会使用反向关系。但是,如果您对此有任何解决方案,那么我将能够使用反向关系,请告诉我们。 @aisbaa 我不明白related_name 和 through 之间的区别。 使用through 选项,您必须创建负责营地和选项之间关系的模型。顺便说一句,你所描述的感觉就像 django 中的一个错误。 【参考方案1】:

根据related_name argument of the ManyToManyField 的Django 文档:

如果您有多个指向同一模型的 ManyToManyField 并想抑制向后关系,将每个相关名称设置为 以“+”结尾的唯一

强调我的。

所以如果你想这样做,你应该能够简单地:

class Camp(models.Model):
    #...

    free_options = models.ManyToManyField('Option', related_name='free_options+')
    paid_options = models.ManyToManyField('Option', related_name='paid_options+')
    #                                                             ^^^^^^^^^^^^

抑制同一模型中多个 ManyToManyField 的反向关系。

希望这会有所帮助!

【讨论】:

【参考方案2】:

我会问你为什么对反向关系感到困扰,如果你不想要就不要使用它。但是要回答这个问题,没有办法完全删除它。

【讨论】:

好的,谢谢。这就是我所做的。我还提到了related_name 值,因为如上所述,我有 2 个 ManyToMany 字段。 Docs 声明你可以删除后向关系,也许 django 团队作弊了一点。

以上是关于没有反向关系的两个 ManyToMany 字段的主要内容,如果未能解决你的问题,请参考以下文章

Hibernate:ManyToMany 反向删除

带有额外字段的 Django ManyToMany 字段不会显示在两个关系上

spring jpa ManyToMany 理解和使用

Symfony 在具有 ManyToMany 关系的两个表之间具有相同的 @groups

Hibernate - 从多对多关系访问字段

springjpa定义引用类型