【问题标题】:Django Model for defining a relationship between two other models and filtering later用于定义其他两个模型之间的关系并稍后过滤的 Django 模型
【发布时间】:2020-06-05 19:57:30
【问题描述】:

所以我正在为移动博客应用程序设计一个 REST API,我正在尝试为我想要实现的博客文章实现一个支持功能:

每当用户 U 为特定博客 B 点赞时,客户端将发送一个 POST 请求(带有用户名和博客名称),该请求将在数据库,以便稍后当客户端想知道特定用户是否对特定博客进行了投票时,它可以通过一些文件发送 GET 请求来了解。

我尝试创建投票模型,在其中我定义了与用户和博客文章的多对多关系(请参阅下面的投票模型以更好地理解)

这是我的模型,

class User(models.Model):
    username = models.TextField(max_length=30)

    def __str__(self):
        return self.username
class Post(models.Model):
    headline = models.CharField(max_length=200) # the name of the blog
    #some other stuff like body of the blog
    .
    .
    def __str__(self):
        return self.headline

投票模型,

class Vote(models.Model):
    user = models.ManyToManyField(User)
    post = models.ManyToManyField(Post)

    def __str__(self):
        return ("%s %s" %(self.user, self.post))

这不能很好地完成工作,例如,

  • 由于多对多关系,它需要 POST 请求中的用户和博客文章(见下文)的 URL,而不仅仅是每个人的名称。
  • 即使我们忽略上述问题并使用表单数据发出以下 POST 请求 两次
  {
    "user" = [
         "http://127.0.0.1:8000/users/1/"
     ],
    "post" = [
         "http://127.0.0.1:8000/posts/1/"
     ],
  }

它在数据库中创建了 2 个条目。

而且我仍然无法弄清楚过滤是如何进行的,即客户端应用程序如何通过 GET 请求了解用户和博客文章之间是否存在关系。

我认为这是一个非常糟糕的设计。

请在我当前的设计中提出更好的替代方案或改进(如果可能)。

【问题讨论】:

    标签: django django-models django-rest-framework django-views


    【解决方案1】:

    您应该使用Vote 作为PostUser 之间的多对多的through=… model [Django-doc],或者甚至只是让Django 构建多对多模型,因为这里你没有定义一个额外的字段。

    因此,您可以定义如下方法:

    class Post(models.Model):
        headline = models.CharField(max_length=200) # the name of the blog
        # …
        voted_users = models.ManyToManyField(User, related_name='voted_posts')
    
        def __str__(self):
            return self.headline

    对于给定的Post 主键和给定的User 主键,您可以使用以下方法创建投票:

    Post.voted_users.through.objects.create(
        post_id=post_pk,
        user_id=user_pk
    )

    因此,您可以例如开发一个适用于Post.voted_users.through 模型的序列化程序,它有两个ForeignKeys:一个用于Post 模型,一个用于User 模型。

    【讨论】:

    • 假设如果另一个用户喜欢该帖子,您将如何更新数据库?我尝试这样做,如果我们使用不同的用户名两次执行 POST req,它会创建 2 个具有相同博客名称的条目,再次浪费数据。
    • @sweetsecret: 不,这是在关系数据库中处理 m2m 关系的方法:en.wikipedia.org/wiki/Many-to-many_(data_model) 请注意,直通模型 存储博客 name 或用户 name 它存储主键,通常是整数(特别是在 Django 中,使主键统一是个好主意)。
    • 并非所有关系数据库都支持“数组”之类的东西,但即使支持,它也不保证引用完整性、索引等(或至少不以标准化的方式)。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-04-10
    • 2015-04-24
    • 2012-09-12
    • 1970-01-01
    相关资源
    最近更新 更多