zoukankan      html  css  js  c++  java
  • Django 使用Contenttype组件创建多关联数据库表

    from django.db import models
    
    '''contenttype使用意义:如果使用contenttypes就不需要再使用多个Foreignkey,
    因为在django_content_type表已经存储了app名和model名,
    所以我们只需要将我们创建的模型与django_content_type表关联起来,
    然后再存储一个实例 id 即可准确定位到某个app中某个模型的具体实例
    '''
    
    '''使用Django的Contenttype字段。'''
    # 导入必需模块
    from django.contrib.contenttypes.models import ContentType
    from django.contrib.contenttypes.fields import GenericForeignKey, GenericRelation
    
    '''每一个商品都有优惠劵,所以每一个商品都有coupons字段'''
    
    #电子商品表
    class Electrics(models.Model):
        name = models.CharField(max_length=32)
        coupons = GenericRelation(to='Coupon')
    
    #食物表
    class Foods(models.Model):
        name = models.CharField(max_length=32)
        price = models.IntegerField(default=100)
        coupons = GenericRelation(to='Coupon')
    
    #衣服表
    class Clothes(models.Model):
        name = models.CharField(max_length=32)
        price = models.IntegerField(default=200)
        conpons = GenericRelation(to='Coupon')
    
    #优惠劵表
    class Coupon(models.Model):
        name = models.CharField(max_length=31)
        content_type = models.ForeignKey(to=ContentType, on_delete=models.CASCADE)
        object_id = models.PositiveIntegerField()
        content_object = GenericForeignKey('content_type', 'object_id')
    
    
    '''Coupon,与contenttypes相关的就三个字段:content_tpye   object_id    content_object
    content_type字段为外键,指向ContentType这个模型,也就是上面提到的django_content_type表
    object_id为一个整数,存储了实例id,实例id不理解可以看下面的数据表结构分析
    content_object为GenericForeignKey类型,主要作用是根据content_type字段和object_id字段来定位某个模型中具体某个实例
    所以实际上在使用GenericForeignKey()函数时需要传入两个参数,即content_type和object_id字段的名字,注意是名字不是value。
    但是默认在该函数的构造函数中已经赋予了默认值,
    即"content_type"和"object_id",所以如果我们定义的变量名为这两个,那么我们可以省略该参数。
    该字段不会存储到数据库中,在查询的时候ORM会用到。'''
    models.py
    '''使用contentype创建数据的视图函数'''
    class Test(APIView):
        def get(self,request):
            # 1.ContentType表对象有model_class() 方法,取到对应model
            content = models.ContentType.objects.filter(app_label='books',model='clothes').first()
            cloth_class = content.model_class()
            res =cloth_class.objects.all()
            print(res)#[<Clothes: Clothes object (1)>, <Clothes: Clothes object (2)>]>
    
            #2.为食物创建一个优惠劵
            foods_create = models.Foods.objects.filter(id=2).first()
            models.Coupon.objects.create(name='食品优惠劵',content_object=foods_create)#content_object为隐藏字段
    
            #3.查询食物优惠劵绑定了那些食物(食物优惠劵ID=1)
            c_obj = models.Coupon.objects.filter(id=1).first()
            b_obj = c_obj.content_object
            print(b_obj)#Foods object (2)
            #4.查询食物绑定了那些优惠劵
            a_obj = models.Foods.objects.filter(id=2).first().coupons.first()
            print(a_obj) #Coupon object (1)
    
    
            return HttpResponse('ok')
    views.py

    使用Django-contenttype组件总结 : 当一张表和多个表FK关联,并且多个FK中只能选择其中一个或其中n个时,可以利用contenttypes app,只需定义三个字段就搞定!

  • 相关阅读:
    Tomcat自动部署
    java环境配置
    django-crispy-forms入门指南
    hibernate级联删除
    bzoj1659: [Usaco2006 Mar]Lights Out 关灯
    bzoj1658: [Usaco2006 Mar]Water Slides 滑水
    bzoj5470 / P4578 [FJOI2018]所罗门王的宝藏(差分约束)
    P2864 [USACO06JAN]树林The Grove
    bzoj1651 / P2859 [USACO06FEB]摊位预订Stall Reservations
    bzoj1647 / P1985 [USACO07OPEN]翻转棋
  • 原文地址:https://www.cnblogs.com/cou1d/p/12349284.html
Copyright © 2011-2022 走看看