Django的ContentType

Django进行数据化迁移的时候会生成一张django_content_type表,里面记录了各个App中的模型类.

有时候我们一张表要为多张表的一条记录保存多条记录(非简单的外键关系)

比如:

有两个不同的课程表,他们之中的每个课程都有着不同的价格策略(只为介绍ContentType)

from django.db import models

# 普通课程列表
class DegreeCourse(models.Model):
    name = models.CharField(max_length=32)
    ....

# 会员课程列表
class Course(models.Model):
    name = models.CharField(max_length=32)
    ....

class PricePolicy(models.Model):
    content_type = models.CharField(max_length=32) # 保存库名
    object_id = models.PositiveIntegerField()  # 保存课程ID
    period = models.CharField(max_length=32) # 区分价格的条件
    price = models.FloatField()    # 价格

  再或者多张表都有评论区,我们把评论存储在一张表

这时就可以通过外键关联ContentType来区分表

from django.db import models
from django.contrib.contenttypes.models import ContentType


class DegreeCourse(models.Model):
    name = models.CharField(max_length=32)

class Course(models.Model):
    name = models.CharField(max_length=32)

class PricePolicy(models.Model):
    # 这里
    content_type = models.ForeignKey(ContentType)
    object_id = models.PositiveIntegerField()
    period = models.CharField(max_length=32)
    price = models.FloatField()

操作表

为PricePolicy添加一条记录

# 通过课程的ID和所在表在content_type表中的ID来新增一条记录
PricePolicy.objects.create(period='10',price=9.9,object_id=1,content_type_id=8)

修改PricePolicy类来简化操作

from django.contrib.contenttypes.fields import GenericForeignKey
class PricePolicy(models.Model):
    content_type = models.ForeignKey(ContentType)
    object_id = models.PositiveIntegerField()

    # 不在数据库中生成,只用于帮助你做数据操作,通过上面两个字段找到一条记录
    content_object = GenericForeignKey('content_type', 'object_id')

    period = models.CharField(max_length=32)
    price = models.FloatField()

添加

course_obj = Course.objects.get(id=1)
models.PricePolicy.objects.create(period='30', price=29.9, content_object=course_obj)

课程来查找价格

# 方式一,找到课程对象,从价格表筛选
from app01.models import *
obj = Course.objects.first()
PricePolicy.objects.filter(content_type__app_label=obj._meta.app_label,content_type__model=obj._meta.model_name,object_id=obj.pk)
<QuerySet [<PricePolicy: PricePolicy object>, <PricePolicy: PricePolicy object>, <PricePolicy: PricePolicy object>]>

# 方式二,修改课程表from django.contrib.contenttypes.fields import GenericRelation
class Course(models.Model):
    name = models.CharField(max_length=32)

    # 数据库不生成,只用于链表查询
    policy_list = GenericRelation("PricePolicy")

# 查询
obj.policy_list.all()
<QuerySet [<PricePolicy: PricePolicy object>, <PricePolicy: PricePolicy object>, <PricePolicy: PricePolicy object>]>

  

posted @ 2018-04-12 16:19  瓜田月夜  阅读(127)  评论(0编辑  收藏  举报