ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

python – 在一对多中创建模型引用抽象模型

2019-06-20 21:43:10  阅读:208  来源: 互联网

标签:python django foreign-keys django-models abstract-class


我是Django的新手,现在我正在尝试理解抽象模型的使用.假设您正在撰写博客服务,并且您希望经过身份验证的用户和匿名用户能够对博客帖子发表评论.

虽然场景对于经过身份验证的用户来说非常简单(只有外键可以引用特定用户),但当作者不仅仅是用户而是AnonymousAuthors或RegisteredAuthors时,情况并不那么简单.

这里的直接方法是构建类的层次结构:

class Author(models.Model):
  class Meta:
    abstract = True

class AnonymousAuthor(Author):
  name = models.CharField(max_length=128)
  def display_name(self):
    return self.name

class RegisteredAuthor(Author):
  user = models.ForeignKey(User)
  def display_name(self):
    return self.user.user_name

然后可以像这样定义BlogPostComment:

class BlogPostComment(models.Model):
  author = models.ForeignKey(Author)
  ...

我喜欢这种方法,因为无论作者是谁,我都可以通过迭代BlogPostComments集并为每个人调用display_name()轻松构建注释列表.这里唯一的问题是它不起作用. Django说:

AssertionError: ForeignKey cannot define a relation with abstract class Author

什么是解决方案?

更新

我知道Generic relations可以在这里提供帮助.但它是唯一的解决方案吗?感觉有点矫枉过正.

解决方法:

与模型不同,泛型关系是为许多人创建外键的解决方案.一般来说,如果你有继承:

class Animal(models.Model):
    ...

class Dog(Animal):
    ...

然后是:

models.ForeignKey(Animal)

你也可以将狗作为外键存放,因为狗是一种动物.但是,在抽象类的情况下,这些不适合设置为外键的目标,因为它们不存在. Django的“抽象”模型更接近于“mixin”的定义:它们从不单独实例化,而是用于组成实例化的其他类.

所以你有三个选择:

>将作者更改为标准模型而不是抽象.然后你可以创建外键给Author并传入你喜欢的任何子类.
>使用通用外键
>首先不要分解模型.

这里的最后一个选择实际上是你最好的选择,因为当唯一的定义差异是它们是注册还是匿名时,没有理由拥有单独的作者表.这是对象的状态,而不是不同类型的对象.就像拥有像BlueCar类这样的东西是不合适的.你有一个Car类,而“blue”是它的颜色属性的值.

如果你坚持使用单独的型号.然后,您可以使用代理模型.其中AnonymousAuthor和RegisterAuthor只是Author的别名(他们没有自己的表),但是使用别名可以更改或添加自定义方法,特别是能够指定自动过滤Author的自定义管理器分别是“匿名”或“注册”类型.

标签:python,django,foreign-keys,django-models,abstract-class
来源: https://codeday.me/bug/20190620/1248547.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有