Django 模型:用户和关注者的数据库设计
Posted
技术标签:
【中文标题】Django 模型:用户和关注者的数据库设计【英文标题】:Django models: database design for user and follower 【发布时间】:2017-02-25 10:08:07 【问题描述】:在 Django 模型中,我正在制作一个“追随者”表,其中包含:
user's id. (this is followed by)
user's id (this is follower)
用户可以关注其他用户,这很简单。
我应该如何在 Django 中定义模型?
我试过了,但不起作用:
user = models.ForeignKey('self')
follower_id = models.ForeignKey('self')
这应该怎么做?
谢谢
【问题讨论】:
【参考方案1】:除非您有一个名为 self
的模型,否则“self”参数将不起作用。
假设您的分配模型称为Following
,并且您使用的是内置的User
模型,那么您可以这样做:
class Following(models.Model):
target = models.ForeignKey('User', related_name='followers')
follower = models.ForeignKey('User', related_name='targets')
这可能需要一些进一步的唯一性和验证逻辑。
注意related_name
属性,参见https://docs.djangoproject.com/en/1.10/ref/models/fields/#django.db.models.ForeignKey.related_name。这意味着对于给定的用户对象,您可以使用user.targets.all()
获取他们关注的用户,并使用user.followers.all()
获取关注他们的用户。
另请注意,Django 在 ORM 中返回目标模型实例,而不是 ID。这意味着即使底层表可能被称为follower_id
,在 python 代码中following.follower
将返回一个实际的用户对象。
【讨论】:
我这样做了..但我得到了这个错误:main.followers.follower_id: (fields.E304) 'followers.follower_id' 的反向访问器与 'followers.user' 的反向访问器冲突。提示:在“followers.follower_id”或“followers.user”的定义中添加或更改相关名称参数。 啊,是的。 Django 创建反向关系,以便您可以反向跟踪关系。我已修改我的答案以添加related_name
属性。
我还从您上面的回溯中注意到您的表称为Followers
。这是一件小事,但惯例是使用单数名词作为类名。我选择了Following
,因为此类的一个对象代表另一个用户的一个用户关注。不过,给事物命名很难,而且这也不是最容易封装的。
在实例化类中,self
(名称,而不是 'self'
字符串)返回当前实例。要参考模型,您可以使用self.__class__
。您还可以查看 contenttypes 框架以了解实现此目的的其他方式。但是,在这里您要引用 User 模型,而不是递归地引用此 Follow/Followers 模型。【参考方案2】:
看成Following
实际上是through 表,用于用户之间的多对多关系。我将创建一个扩展 Django User
模型的 Profile
模型,然后声明多对多关系(使用 ManyToManyField
)。
from django.contrib.auth.models import User
from django.db import models
class Profile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE, primary_key=True)
following = models.ManyToManyField(User, related_name='followers')
【讨论】:
【参考方案3】:使用多对多字段。
followers = models.ManyToManyField('self', symmetrical=False)
【讨论】:
以上是关于Django 模型:用户和关注者的数据库设计的主要内容,如果未能解决你的问题,请参考以下文章