contenttypes

contenttypes组件的内部帮我们讲django的ORM中定义的所有表都自动手机起来,并保存至
image
后续开发中如果遇到 一张表 与 其他n张表进行关联,就可以基于contenttypes实现。
image

表定义

image

from django.db import models
from django.contrib.contenttypes.fields import GenericForeignKey, GenericRelation
from django.contrib.contenttypes.models import ContentType


class DegreeCourse(models.Model):
    """学位课程"""
    name = models.CharField(max_length=128, unique=True)
    # 用于GenericForeignKey反向查询,不会生成表字段
    degree_price_policy = GenericRelation("PricePolicy")


class Course(models.Model):
    """课程"""
    name = models.CharField(max_length=128, unique=True)
    # 用于GenericForeignKey反向查询,不会生成表字段
    price_policy = GenericRelation("PricePolicy")


class PricePolicy(models.Model):
    """价格与有课程效期表"""
    content_type = models.ForeignKey(ContentType, on_delete=models.CASCADE)  # 关联course or degree_course
    object_id = models.PositiveIntegerField()

    # 方便设置值,不会生成表字段(直接设置为对象,自动生成 content_type和object_id)
    content_object = GenericForeignKey('content_type', 'object_id')
    price = models.IntegerField()

新建数据

def demo(request):
    from app03 import models
    models.Course.objects.create(name="APP逆向") # 1
    models.Course.objects.create(name="django项目") # 2
    models.Course.objects.create(name="小程序") # 3
    models.DegreeCourse.objects.create(name="Python全栈")  # 1
    models.DegreeCourse.objects.create(name="爬虫")  # 2
    models.DegreeCourse.objects.create(name="Linux")  # 3

     models.PricePolicy.objects.create(
         content_object=models.DegreeCourse.objects.get(name="Python全栈"),
         priod="3个月",
         price=100
     )
    
     models.PricePolicy.objects.create(
         content_object=models.Course.objects.get(name="django项目"),
         priod="6个月",
         price=150
     )
    return HttpResponse("ok")

用于GenericForeignKey反向查询

obj = models.DegreeCourse.objects.filter(name="Python全栈").first()
print(  obj.degree_price_policy.all()  )
"""
<QuerySet [<PricePolicy: PricePolicy object (2)>]>
"""

查询

price_policy_queryset = models.PricePolicy.objects.all()
for obj in price_policy_queryset:
    print(obj.content_object, obj.price)
    
"""
DegreeCourse object (1) 100
Course object (1) 200
"""

其他参考

https://www.jianshu.com/p/7a0ddbb02ae3contenttypes应用

posted @ 2023-03-12 10:41  Sherwin_szw  阅读(12)  评论(0编辑  收藏  举报