Django ORM基本应用与原理剖析

简介: 1.ORM构建数据表由于每一个数据表对应一个Model定义,每一个Model都是一个Python类,所以,Model之间是可以继承的。Django规定,所有的Model都必须继承自django.db.models.Model


1.ORM构建数据表


由于每一个数据表对应一个Model定义,每一个Model都是一个Python类,所以,Model之间是可以继承的。Django规定,所有的Model都必须继承自django.db.models.Model


Model中的所有字段都是django.db.models.Field的子类,Django会根据Field的类型确定数据库表的字段类型


首先定义定义抽象Model基类:


class BaseModel(models.Model):
    class Meta:
        # 抽象类,表现为BaseModel不会创建数据表
        abstract = True
        # 按照创建时间逆序排序
        ordering = ['-created_time']
    # 定义了两个类属性:created_time和last_modified,且都是DateTimeField类型
    # auto_now_add用于将首次创建对象时间设置为当前时间
    # auto_now用于将每次保存对象时间设置为当前时间
    created_time = models.DateTimeField(auto_now_add=True, help_text=u'创建时间')
    last_modified = models.DateTimeField(auto_now=True, help_text=u'修改时间')
    # 优化打印(print)Model实例的样式
    def __str__(self):
        raise NotImplementedError


由于BaseModel直接继承自django.db.models.Model,所以,我们创建的实体数据表可以继承自Base Model,从而实现间接继承

例如:话题表


class Topic(BaseModel):
    title = models.CharField(max_length=255, unique=True, help_text=u'话题标题')
    content = models.TextField(help_text=u'话题内容')
    is_online = models.BooleanField(default=True, help_text=u'话题是否在线')
    user = models.ForeignKey(to=User, to_field='id', on_delete=models.CASCADE, help_text=u'关联用户表')
    def __str__(self):
        return '%d:%s' % (self.id, self.title[0:20]


Topic中除了基本类型的字段定义之外,还包含了一个外键(ForeignKey)引用的user字段

评论表:


class Comment(BaseModel):
    content = models.CharField(max_length=255, help_text=u'话题评论')
    topic = models.ForeignKey(to=Topic, to_field='id', on_delete=models.CASCADE, help_text=u'关联话题表')
    up = models.IntegerField(default=0, help_text=u'支持')
    down = models.IntegerField(default=0, help_text=u'反对')
    def __str__(self):
        return '%d:%s' % (self.id, self.content[0:20])


2.数据迁移


首先,在settings.py文件中添加此Model视图的app:(post.apps.PostConfig)


INSTALLED_APPS = [
    'post.apps.PostConfig',
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
]


生成迁移文件:


python manage.py makemigrations post


执行migrate命令将Models映射为数据库的表:


python manage.py migrate


生成的表结构:


3.Model相关的概念与使用方法


Model的组成部分


每个Model都是一个Python类,且通常会包含四个部分:继承自django.db.models.Model、Model元数据声明(Meta内部类)、若干个Field类型的字段以及__str__方法


Meta元数据类属性说明


Meta类用于定义Model的元数据,即不属于Model的字段,但是可以用来标识它的一些属性


abstract:


一个布尔类型的变量,如果设置为True,则标识当前的Model是抽象基类,这个元选项不具有传递性,只对当前声明的类有效。例如,对于之前定义的BaseModel,用abstract声明为抽象基类,但是子类Topic和Comment不受影响


db_table:


这个字段用于指定数据表的名称


默认会使用Django的表名生成规则,例如Topic会映射到post_topic表。如果想让Topic映射到topic表,定义db_table='topic'即可


ordering:


用于指定获取对象列表时的排序规则

按照created_time逆序排序,可以定义:


ordering = ['-created_time']


先按照created_time逆序排序,再按照last_modified正序排序:


ordering = ['-created_time', 'last_modified']


indexes:


它是一个列表类型的元选项,用来定义Model的索引



fields:一个列表对象,用于指定索引的字段,是必填项,且至少包含一个字段。

name:用于标识索引的名称,是可选的,如果不提供,Django会根据不同的数据库生成合适的索引名。

db_tablespace:表空间,也是可选的,常见于PostgreSQL、Oracle数据库,用于优化数据库性能

unique_together:


标识联合唯一约束,在数据库层面表现为联合唯一索引



Field的通用字段选项


blank:


对于任何一个属性,默认是不允许输入空值的,如果允许这种情况发生,需要设置blank=True


unique:


如果一个字段设置了unique=True,则表示唯一性索引


null:


规定这个字段的数据是否可以是空值


db_index:


如果该字段经常作为查询的条件,那么就需要考虑设置db_index选项,以加快数据的检索速度


default:


用于给字段设置默认值


choices:


设置了choices的字段在管理后台的显示上会由文本框变成选择框,选择框中的可选值就是choices中的元组



help_text:


这个选项用于在表单中显示字段的提示信息。例如在管理后台的编辑页面,对应在字段输入框的下方会显示该选项设定的值


基础字段类型


IntegerField:整型字段

Django还提供了SmallIntegerField(小整数)、BigIntegerField(64位整数)和PositiveIntegerField(只允许存储大于等于0的整数)等字段类型用来满足存储整数的不同业务场景

AutoField:一个根据ID自增的IntegerField

如果觉得AutoField的取值范围不够用,可以考虑使用BigAutoField

CharField:字符字段

TextField:也是用于存储字符类型的字段,但是它用于存储大文本

BooleanField:布尔类型

DateField和DateTimeField:标识时间的

它们都有两个特殊的参数选项可以设置

①auto_now:这个选项应用在对象保存的时候,会自动设置为当前时间

②auto_now_add:当首次创建对象的时候,会自动将字段设置为当前时间

EmailField:专门用来存储电子邮件地址的

除了之前介绍的几种常见的类型之外,还有GenericIPAddressField用于存储IP地址、URLField用于存储URL、FloatField用于存储浮点数的字段类型等


关系字段类型


多对一


实例:


user = models.ForeignKey(to=User, to_field='id', on_delete=models.CASCADE, help_text=u'关联用户表')


to:指定所关联的Model


on_delete:当删除关联表的数据时,Django将根据这个参数设定的值确定应该执行什么样的SQL约束


CASCADE:级联删除,它是大部分ForeignKey的定义应该选择的约束。它的表现是删除了“一”,则“多”会被自动删除

PROTECT:删除被引用对象时,将会抛出ProtectedError异常

SET_NULL:设置删除对象所关联的外键字段为null。以Topic和Comment的关系举例:删除了Topic,与之相关联的Comment的topic字段会被设置为null

SET_DEFAULT:将外键字段设置为默认值

SET(value):删除被引用对象时,设置外键字段为value

DO_NOTHING:不做任何处理


一对一


实例:


user = models.OneToOneField(to=User, on_delete=models.CASCADE, parent_link=False,
                             help_text=u'关联用户表')


多对多关系类型


实例:


books = models.ManyToManyField(to=Book)
目录
相关文章
|
3天前
|
中间件 Python
中间件应用Django Middleware(Python)
中间件应用Django Middleware(Python)
30 6
|
13天前
|
Oracle 关系型数据库 MySQL
Django框架ORM操作(二)
Django框架ORM操作(二)
|
13天前
|
SQL 存储 前端开发
Django框架ORM操作(一)
Django框架ORM操作(一)
Django框架ORM操作(一)
|
13天前
|
运维 监控 Serverless
Serverless 应用引擎产品使用之阿里函数计算中在自定义环境下用debian10运行django,用官方层的python3.9,配置好环境变量后发现自定义层的django找不到了如何解决
阿里云Serverless 应用引擎(SAE)提供了完整的微服务应用生命周期管理能力,包括应用部署、服务治理、开发运维、资源管理等功能,并通过扩展功能支持多环境管理、API Gateway、事件驱动等高级应用场景,帮助企业快速构建、部署、运维和扩展微服务架构,实现Serverless化的应用部署与运维模式。以下是对SAE产品使用合集的概述,包括应用管理、服务治理、开发运维、资源管理等方面。
22 3
|
16天前
|
SQL 缓存 数据库
在Python Web开发过程中:数据库与缓存,如何使用ORM(例如Django ORM)执行查询并优化查询性能?
在Python Web开发中,使用ORM如Django ORM能简化数据库操作。为了优化查询性能,可以:选择合适索引,避免N+1查询(利用`select_related`和`prefetch_related`),批量读取数据(`iterator()`),使用缓存,分页查询,适时使用原生SQL,优化数据库配置,定期优化数据库并监控性能。这些策略能提升响应速度和用户体验。
18 0
|
24天前
|
Python
基于Django的Python应用—学习笔记—功能完善
基于Django的Python应用—学习笔记—功能完善
|
24天前
|
存储 数据库 数据安全/隐私保护
基于Django的Python应用——学习笔记
基于Django的Python应用——学习笔记
|
24天前
|
API 数据库 数据安全/隐私保护
基于Django的python小应用——投票
基于Django的python小应用——投票
|
26天前
|
消息中间件 监控 数据库
Django的异步任务处理:提升应用响应速度与性能
【4月更文挑战第15天】Django通过集成Celery实现异步任务处理,提升Web应用性能和响应速度。异步处理用于耗时操作如数据库操作、邮件发送。基本步骤包括安装配置Celery、创建任务、在视图中调用任务并启动worker。应用场景包括发送通知、处理复杂逻辑和数据导入导出。注意任务原子性、优先级设置和任务执行监控。
|
26天前
|
开发者 Python
Django的信号机制:实现应用间的通信与响应
【4月更文挑战第15天】Django信号机制实现跨组件通信,基于订阅/发布模式,允许在事件(如模型保存、删除)发生时触发自定义函数。内置信号如`pre_save`、`post_save`,也可自定义信号。使用包括定义信号、连接处理器和触发信号。常用于模型操作监听、第三方应用集成和跨应用通信。注意避免滥用和保证处理器健壮性。信号机制提升代码可维护性和扩展性。