一、在同一个app下的模型使用外键关联

  • 1、文章分类数据模型

    class CategoryModel(models.Model):
        """
        文章分类
        """
        name = models.CharField(max_length=100, verbose_name='文章分类')
    
        def __str__(self):
            return '<CategoryModel>({})'.format(self.name)
    
        class Meta(object):
            db_table = 'category'
    
  • 2、文章的数据模型

    class ArticleModel(models.Model):
        """
        文章的模型
        """
        title = models.CharField(max_length=100, verbose_name='文章标题')
        content = models.TextField(verbose_name='文章内容')
        create_time = models.DateTimeField(auto_now_add=True, verbose_name='文章创建时间')
        update_time = models.DateTimeField(auto_now=True, verbose_name='修改时间')
    
        # 创建一个外键关联
        category = models.ForeignKey('Category', on_delete=models.CASCADE, verbose_name='文章分类')
    
        class Meta(object):
            db_table = 'article'
    
        def __str__(self):
            return '<ArticleModel>({}, {})'.format(self.title, self.create_time)
    
  • 3、映射到数据库

    # [app名]表示可以写上app名字也可以不写,如果不写就会映射生成全部app的表,如果写了只会生成当前的app的数据表
    python manage.py makemigrations [article]
    python manage.py migrate [article]
    
  • 4、关于添加数据的示例代码

注意要先添加分类数据模型的数据

django2中关于外键的认识_python

class ArticleView(View):
    """
    文章的视图类
    """

    def get(self, request, *args, **kwargs):
        # 添加分类
        # models.CategoryModel.objects.create(name='java开发')
        # models.CategoryModel.objects.create(name='python开发')
        # models.CategoryModel.objects.create(name='web开发')
        # 通过添加对象的方式添加数据
        models.ArticleModel.objects.create(title='文章一', content='文章一的内存',
                                          category=models.CategoryModel.objects.get(pk=1))
        # 通过添加id的方式添加
        models.ArticleModel.objects.create(title='文章二', content='文章二的内容',
                                          category_id=models.CategoryModel.objects.all().first().id)
        return render(request, 'article.html')

二、使用别的app下的数据模型的写法

  • 1、用户表的数据模型(属于frontapp)

    class FrontAccountModel(models.Model):
        """
        前端用户数据模型
        """
        account = models.CharField(max_length=30, unique=True, verbose_name='用户名')
        password = models.CharField(max_length=30, verbose_name='用户密码')
    
        def __str__(self):
            return '<FrontUserModel>({},{})'.format(self.account, self.password)
    
        class Meta(object):
            db_table = 'front_account'
    
  • 2、文章数据模型关联到用户表模型

    class ArticleModel(models.Model):
        """
        文章的模型
        """
        title = models.CharField(max_length=100, verbose_name='文章标题')
        content = models.TextField(verbose_name='文章内容')
    
        # 创建一个外键关联
        category = models.ForeignKey('CategoryModel', on_delete=models.CASCADE, verbose_name='文章分类')
        # 关联到别的数据模型的字段: app名字.数据模型
        author = models.ForeignKey('front.FrontAccountModel', on_delete=models.CASCADE, verbose_name='文章作者')
    
        class Meta(object):
            db_table = 'article'
    
        def __str__(self):
            return '<ArticleModel>({}, {})'.format(self.title, self.content)
    
  • 3、映射到数据库

  • 4、添加数据

    from django.shortcuts import render
    from django.views import View
    from . import models
    from front.models import FrontAccountModel
    
    
    class ArticleView(View):
        """
        文章的视图类
        """
    
        def get(self, request, *args, **kwargs):
            # models.CategoryModel.objects.create(name='java开发')
            # models.CategoryModel.objects.create(name='python开发')
            # models.CategoryModel.objects.create(name='web开发')
            # 通过添加对象的方式添加数据
            models.ArticleModel.objects.create(title='文章一', content='文章一的内存',
                                              category=models.CategoryModel.objects.get(pk=1),
                                              author=FrontAccountModel.objects.first())
            # 通过添加id的方式添加
            models.ArticleModel.objects.create(title='文章二', content='文章二的内容',
                                              category_id=models.CategoryModel.objects.all().first().id,
                                              author_id=FrontAccountModel.objects.get(pk=1).id)
            return render(request, 'article.html')
    

三、同表自关联的外键(比如评论回复需要指定回复的是哪个评论)

  • 1、创建一个messageapp

  • 2、创建数据模型

    class MessageModel(models.Model):
        """
        评论数据模型
        """
        content = models.TextField(verbose_name='评论')
        origin_content = models.ForeignKey('self', on_delete=models.CASCADE, null=True, verbose_name='评论')
    
        class Meta(object):
            db_table = 'message'
    
        def __str__(self):
            return '<MessageModel>({},{})'.format(self.content, self.origin_content)
    
  • 3、添加数据

    class MessageView(View):
    	"""
    	评论的视图
    	"""
    
    	def get(self, request, *args, **kwargs):
    		# models.MessageModel.objects.create(content='评论一')
    		models.MessageModel.objects.create(content='评论11', origin_content=models.MessageModel.objects.get(pk=1))
    		return HttpResponse('评论')
    
  • 4、查询数据

    class MessageView(View):
    	"""
    	评论的视图
    	"""
    
    	def get(self, request, *args, **kwargs):
    		message_result = models.MessageModel.objects.all().last()
    		print(message_result)
    		print(message_result.origin_content)
    		print(message_result.origin_content_id)
    		return HttpResponse('评论')
    

四、关于django中外键的删除(on_delete)

  • 1、CASCADE:这就是默认的选项,级联删除。
  • 2、PROTECT: 保护模式,如果采用该选项,删除的时候,会抛出ProtectedError错误。
  • 3、SET_NULL: 置空模式,删除的时候,外键字段被设置为空,前提就是blank=True, null=True,定义该字段的时候,允许为空。
  • 4、SET_DEFAULT: 置默认值,删除的时候,外键字段设置为默认值,所以定义外键的时候注意加上一个默认值。
  • 5、SET(): 自定义一个值,该值当然只能是对应的实体了。