[] Django ORM operation # 1--2019-08-17 06:19:12

Original: http://blog.gqylpy.com/gqy/260

"@

Added: data migration and anti-migration


# 迁移:
python manage.py makemigrations  # 纪录变成
python manage.py migrate  # 迁移到数据库

# 反迁移:
python manage.py inspectdb > models.py
执行后,会在执行的文件内写入模型类(文件可随意指定)

I. INTRODUCTION


concept

Object-relational mapping (Object Relational Mapping, referred to as ORM) model is a cornerstone of object-oriented in order to solve the phenomenon and do not match the existing relational database.

Simply put, by using a mapping between objects and databases describing when ORM metadata , the program will automatically object persistence China into a relational database.

ORM between the business logic layer and the database layer acts as a bridge.
***

Origin

Let's start with O / R. It originated in the letter O "subject" (Object), and R is derived from "relationship" (Relational).

Almost all of the software development process will involve objects and relational databases. At the user level and business logic plane, we are object-oriented. When information is subject to change, we need to target information stored in a relational database.

According to the previous approach to development will occur there will be a lot of clutter programmer SQL statements to add, read, modify, delete data, and these codes are often repeated in their own business logic code.
** *

Advantage

The main problem is solved by the mapping ROM objects and relationships, it is usually a class and a correspondence table for each record a class corresponding to the instance of the table, each class attribute table corresponding to each field.

ORM provides a mapping to the database without writing SQL code directly, just as the operation of the object as the data from the database operations.

Let software developers to focus on business logic processing, improve development efficiency
***

Disadvantaged

ROM drawback is that the efficiency of the program will be sacrificed to some extent.

ORM with more, SQL statements can not write, and relational database skills related degeneration ...
***

to sum up

ORM is only a tool, the tool can really solve some repetition, simple labor, which is undeniable.

But we can not expect a tool to solve all the problems once and for all, or some special problems that require special handling.

But throughout the software development process in cases that require special handling should be small, otherwise the so-called tool will be lost meaning of its existence.

Two, Django ORM in


Django project using MySQL

1. Configure database connection information in the Django project settings.py file:

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',  # 将后缀改为mysql
        'NAME': "数据库名",
        'HOST': "数据库IP",
        'PORT': "端口",
        'USER': "远程用户",
        'PASSWORD': "远程用户密码",
    }
}

*** 2 Add the following code at the same level with the settings.py __init__.py file and tell Django uses pymysql modules connect to the MySQL database: ***

import pymysql
pymysql.install_as_MySQLdb()

Django MySQLdb is used by default, but MySQLdb is Python2.x version of the stuff we use is Python3.x, so to change the pymysql.
***

Model

In Django, model is the single, definitive source of your data, it contains important field and behavior of your stored data. Typically, a model (Model) is mapped to a database table.

basic situation:

  • Each model is a Python class that is a subclass of django.db.models.Model
  • Each attribute of the model represents a database field
  • In summary, Django provides an automatically generated database access API for you, see the official document links .

ORM's relationship with DB:
Here Insert Picture Description
***

Getting Started

The following example defines a Person model that contains the name and sex:

from django.db import models

class Person(models.Model):
    name = models.CharField(max_length=24)
    sex = models.CharField(max_length=24)

== name and sex are field model, each field is specified as an attribute, each attribute is mapped to a database column. ==

The above Person model would create a database table such as the following:

create table myapp_person (
  id   serial      not null primary key,
  name varchar(24) not null,
  sex  varchar(24) not null
);

Some explanation:

  1. Table name (myapp_person) is automatically generated, if you want to customize the table name, you need to specify db_table parameter in class Meta model, the == strongly recommended to use lowercase table names, especially when using MySQL as the backend database. ==
  2. id field is automatically added, and the primary key. If you do not want to add id or other designated primary key, just specify AutoField in one field (primary_key = True) can be. If you do not want to add the id column, you can set Field.primary_key.
  3. Django will be generated according to the corresponding SQL statement specified in the profile of the type of backend database.
  4. Django supports MySQL5.5 and later versions.

    Three, ORM common fields and parameters


    Common Fields

1. Auto Field

int auto increment, you must pass parameters: primary_key = true
If you do not specify a model in an auto-increment, it will automatically create a field named id auto-increment.

2. IntegerField

Integer type (int)
signed range: ~ -2147483648 2147483647;
unsigned range: 0 to 4,294,967,295.

Example:

# 设置性别: 1, 2为存的值; "男", "女"为显示的值.
sex = models.IntegerField(choices=((1, '男'), (2, '女')))

3. CharField

Character type (varchar), must be provided max_length parameters.
Max_length indicates the character length.

A ForeignKey (Book, on_delete = models.CASCADE)

4. ForeignKey

Used to create a foreign key

Syntax example:

class Press(models.Model):  # 出版社
    p_name = models.CharField(max_length=24)

class Author(models.Model):  # 作者
    a_name = models.CharField(max_length=24)

class Book(models.Model):  # 书籍
    b_name = models.CharField(max_length=24)

class Relation(models.Model):  # 书籍, 作者, 出版社对应关系
    # 关联3个外键
    book = models.ForeignKey(Book, on_delete=models.CASCADE)
    author = models.ForeignKey(Author, on_delete=models.CASCADE)
    press = models.ForeignKey(Press, on_delete=models.CASCADE)

** Once created, the foreign key field name will automatically add the "_id" suffix. **

5. DateField

Date field, Date format: YYYY-MM-DD
corresponds in Python datetime.date () instance.

6. DateTimeField

Time field, the format: YYYY-MM-DD HH: MM [: ss [.uuuuuu]] [TZ]
corresponds in Python A datetime.datetime () Example.

Parameters:

  • auto_now_add: Creation Time
  • auto_now: Modified

7. dalate()

delete

usage:

类名.objects.filter(字段名="条件").delete()

Fields Collection

AutoField(Field)
        - int自增列,必须填入参数 primary_key=True

    BigAutoField(AutoField)
        - bigint自增列,必须填入参数 primary_key=True

        注:当model中如果没有自增列,则自动会创建一个列名为id的列
        from django.db import models

        class UserInfo(models.Model):
            # 自动创建一个列名为id的且为自增的整数列
            username = models.CharField(max_length=32)

        class Group(models.Model):
            # 自定义自增列
            nid = models.AutoField(primary_key=True)
            name = models.CharField(max_length=32)

    SmallIntegerField(IntegerField):
        - 小整数 -32768 ~ 32767

    PositiveSmallIntegerField(PositiveIntegerRelDbTypeMixin, IntegerField)
        - 正小整数 0 ~ 32767
    IntegerField(Field)
        - 整数列(有符号的) -2147483648 ~ 2147483647

    PositiveIntegerField(PositiveIntegerRelDbTypeMixin, IntegerField)
        - 正整数 0 ~ 2147483647

    BigIntegerField(IntegerField):
        - 长整型(有符号的) -9223372036854775808 ~ 9223372036854775807

    BooleanField(Field)
        - 布尔值类型

    NullBooleanField(Field):
        - 可以为空的布尔值

    CharField(Field)
        - 字符类型
        - 必须提供max_length参数, max_length表示字符长度

    TextField(Field)
        - 文本类型

    EmailField(CharField):
        - 字符串类型,Django Admin以及ModelForm中提供验证机制

    IPAddressField(Field)
        - 字符串类型,Django Admin以及ModelForm中提供验证 IPV4 机制

    GenericIPAddressField(Field)
        - 字符串类型,Django Admin以及ModelForm中提供验证 Ipv4和Ipv6
        - 参数:
            protocol,用于指定Ipv4或Ipv6, 'both',"ipv4","ipv6"
            unpack_ipv4, 如果指定为True,则输入::ffff:192.0.2.1时候,可解析为192.0.2.1,开启此功能,需要protocol="both"

    URLField(CharField)
        - 字符串类型,Django Admin以及ModelForm中提供验证 URL

    SlugField(CharField)
        - 字符串类型,Django Admin以及ModelForm中提供验证支持 字母、数字、下划线、连接符(减号)

    CommaSeparatedIntegerField(CharField)
        - 字符串类型,格式必须为逗号分割的数字

    UUIDField(Field)
        - 字符串类型,Django Admin以及ModelForm中提供对UUID格式的验证

    FilePathField(Field)
        - 字符串,Django Admin以及ModelForm中提供读取文件夹下文件的功能
        - 参数:
                path,                      文件夹路径
                match=None,                正则匹配
                recursive=False,           递归下面的文件夹
                allow_files=True,          允许文件
                allow_folders=False,       允许文件夹

    FileField(Field)
        - 字符串,路径保存在数据库,文件上传到指定目录
        - 参数:
            upload_to = ""      上传文件的保存路径
            storage = None      存储组件,默认django.core.files.storage.FileSystemStorage

    ImageField(FileField)
        - 字符串,路径保存在数据库,文件上传到指定目录
        - 参数:
            upload_to = ""      上传文件的保存路径
            storage = None      存储组件,默认django.core.files.storage.FileSystemStorage
            width_field=None,   上传图片的高度保存的数据库字段名(字符串)
            height_field=None   上传图片的宽度保存的数据库字段名(字符串)

    DateTimeField(DateField)
        - 日期+时间格式 YYYY-MM-DD HH:MM[:ss[.uuuuuu]][TZ]

    DateField(DateTimeCheckMixin, Field)
        - 日期格式      YYYY-MM-DD

    TimeField(DateTimeCheckMixin, Field)
        - 时间格式      HH:MM[:ss[.uuuuuu]]

    DurationField(Field)
        - 长整数,时间间隔,数据库中按照bigint存储,ORM中获取的值为datetime.timedelta类型

    FloatField(Field)
        - 浮点型

    DecimalField(Field)
        - 10进制小数
        - 参数:
            max_digits,小数总长度
            decimal_places,小数位长度

    BinaryField(Field)
        - 二进制类型

ORM fields corresponding relationship database fields

'AutoField': 'integer AUTO_INCREMENT',
'BigAutoField': 'bigint AUTO_INCREMENT',
'BinaryField': 'longblob',
'BooleanField': 'bool',
'CharField': 'varchar(%(max_length)s)',
'CommaSeparatedIntegerField':'varchar(%(max_length)s)',
'DateField': 'date',
'DateTimeField': 'datetime',
'DecimalField':'numeric(%(max_digits)s,%(decimal_places)s)',
'DurationField': 'bigint',
'FileField': 'varchar(%(max_length)s)',
'FilePathField': 'varchar(%(max_length)s)',
'FloatField': 'double precision',
'IntegerField': 'integer',
'BigIntegerField': 'bigint',
'IPAddressField': 'char(15)',
'GenericIPAddressField': 'char(39)',
'NullBooleanField': 'bool',
'OneToOneField': 'integer',
'PositiveIntegerField': 'integer UNSIGNED',
'PositiveSmallIntegerField': 'smallint UNSIGNED',
'SlugField': 'varchar(%(max_length)s)',
'SmallIntegerField': 'smallint',
'TextField': 'longtext',
'TimeField': 'time',
'UUIDField': 'char(32)',


Custom Fields

from django.db import models


# 自定义字段类
class FixedCharField(models.Field):
    """自定义的char类型字段类"""

    def __init__(self, max_length, *args, **kwargs):
        self.max_length = max_length
        super(FixedCharField, self).__init__(max_length=max_length, *args, **kwargs)

    def db_type(self, connection):
        """限制生成数据库表的字段类型为char,长度为max_length指定的值"""
        return 'char(%s)' % self.max_length


# 表结构类
class Class(models.Model):
    varchar_type = models.CharField(max_length=32)  # 自带的varchar类型
    char_type = FixedCharField(max_length=32)  # 自定义的char类型

The above code creates a table structure is as follows:

mysql> desc app01_class;
+--------------+-------------+------+-----+---------+----------------+
| Field        | Type        | Null | Key | Default | Extra          |
+--------------+-------------+------+-----+---------+----------------+
| id           | int(11)     | NO   | PRI | NULL    | auto_increment |
| varchar_type | varchar(32) | NO   |     | NULL    |                |
| char_type    | char(32)    | NO   |     | NULL    |                |
+--------------+-------------+------+-----+---------+----------------+
3 rows in set (0.00 sec)

Field parameters

1. null

Specify a field can be null
null the direct operation of the database, and often use a blank = True.
Blank = True: Allow field empty ORM

2. unique

The only specify a field in the table

3. db_index

Specify a field index

4. default

Set the default value for a field

5. DateField 与 DateTimefield

parameter:

  • auto_now_add : When you create a data record, the current time will be added to the database
  • auto_now : every time you update the data record will update the field


Fourth, the relationship field


Many ForeignKey

Foreign key is used to indicate the type of the foreign key relationship in the ORM.
Usually the ForeignKey field set in the "many" of the "many" side.

ForeignKey can make tables and other associations, but also can do their own association.

Field parameters

1. to

Set the table to be associated

# 语法:
属性名 = models.FreignKey(to="类名")

2. to_field

Set the field to be associated

Example:

from django.db import models

class Test01(models.Model):
    test01 = models.CharField(max_length=32, unique=True)
    # 注意:外键的值必须唯一,所以写上 uniuqe=True
    
class Test02(models.Model):
    # 关联Test01表的test01字段
    test02 = models.ForeignKey(to='Test01', to_field='test01')

Reverse operation field names used when, for "table name _set" when instead of the original reverse lookup.

for example:

from django.db import models

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

class Employees(models.Model):
    name = models.CharField(max_length=32)
    dep = models.ForeignKey(to='Department')  # 外键

When we want to query a class associated with all students ( reverse lookup time), we can write:

models.Department.objects.first().employees_set.all()

When we add in the parameters related_name ForeignKey field,

dep = models.ForeignKey(to='Department', related_name='emps')

At this point, we want to query all students in a class association ( reverse lookup time), we can write:

models.Department.objects.first().emps.all()

Reverse query operation, connected prefix that replaces the table name.

5. on_delete

When you delete data associated table, the current table row behavior associated with it.

  1. models.CASCADE: == == default value, when you delete the associated data is associated with the line also deleted.
  2. models.DO_NOTHING: When you delete the associated data, causing errors IntegrityError
  3. models.PROTECT: When you delete the associated data, causing errors ProtectedError
  4. models.SET_NULL: delete the associated data, the value associated therewith is null (the proviso that FK fields need to be set to empty)
  5. models.SET_DEFAULT: delete the associated data value associated with them set to the default value (provided that the FK field to set the default value)
  6. models.SET: delete the associated data, the associated data will be re-defined, can be defined as a specified value, it may be defined as the return value to the executable, as follows:
def func():
    return 10

class Test(models.Model):
    user = models.ForeignKey(
        to='user',
        # 可执行对象的返回值
        on_delete=models.SET(func)
    )

6. db_constraint

Whether to create a foreign key constraint in the database, the default is True.
***

One OneToOneField

== one field is typically used to extend the existing field ==

One association is used in: when the query frequency at different field gap for a table is too large, the original can be stored in an open field in a table placed in the two tables, and then establish one-two tables the association

Example:

class Author(models.Model):
    name = models.CharField(max_length=32)
    info = models.OneToOneField(to='AuthorInfo')  # 一对一

class AuthorInfo(models.Model):
    phone = models.CharField(max_length=11)
    email = models.EmailField()

Field parameters

1. to

Set the table to be associated

2. to_field

To set the table associated fields

3. on_delete

With ForeignKey field
***

Many-ManyToManyField

Is used to represent many-many relationship.
== would create the third table in the database. ==
to-many relationships established through the third table.

Field parameters

1. to

Set the table to be associated

ForeignKey field with
reverse operation, field names used for "table name _set" when instead of the original reverse lookup

ForeignKey field with
reverse query operation, connected prefix that replaces the table name.

4. symmetrical

Specify whether to create internal fields reverse operation, the default is True.

for example:

class Dep(models.Model):  # 部门
    name = models.CharField(max_length=32)

class Emp(models.Model):  # 员工
    name = models.CharField(max_length=32)
    dep = models.ManyToManyField(to='Dep')  # 未创建反向操作字段
    
# 此时,Emp对象没有person_set属性,不可反向查询
class Dep(models.Model):  # 部门
    name = models.CharField(max_length=32)

class Emp(models.Model):  # 员工
    name = models.CharField(max_length=32)
    dep = models.ManyToManyField(to='Dep', symmetrical=False)  # 创建反向操作字段

# 此时,Emp对象就可以使用person_set属性进行反向查询.

5. through

When using ManyToManyField field, Django will automatically generate a table to manage many-many relationship.
By using this parameter, we can create a third table to manually manage many relationships.

6. through_fields

To set the table associated fields

grammar:

through_fields(field1, field2)
# field1:指定ManyToManyField的模型外键的名
# field2:指定关联目标模型的外键名

7. db_table

When the third table is created by default, the name of the database table.

Three ways-many relationship

Create your own third table

from django.db import models


class Book(models.Model):
    name = models.CharField(max_length=32, verbose_name="书籍名称")


class Author(models.Model):
    name = models.CharField(max_length=32, verbose_name="作者姓名")


# 自行创建第三张表,分别通过外键关联书和作者
class Author2Book(models.Model):
    author = models.ForeignKey(to='Author')
    book = models.ForeignKey(to='Book')


    class Meta:
        unique_together = ('author', 'book')

Automatically create a third table by ManyToManyField

from django.db import models


class Book(models.Model):
    name = models.CharField(max_length=32, verbose_name="书籍名称")


# 通过ORM自带的ManyToManyField自动创建第三张表
class Author(models.Model):
    name = models.CharField(max_length=32, verbose_name="作者姓名")
    books = models.ManyToManyField(to='Book', related_name='authors')

Set ManyToManyField and specify the third table-created

from django.db import models


class Book(models.Model):
    name = models.CharField(max_length=32, verbose_name="书籍名称")


# 自己创建第三张表,并通过ManyToManyField指定关联
class Author(models.Model):
    name = models.CharField(max_length=32, verbose_name="作者姓名")
    books = models.ManyToManyField(to='Book', through='Author2Book', through_fields=('author', 'book'))
    # through_fields接收一个2元组('field1', 'field2')
    # 其中field1指定定义ManyToManyField的模型外键的名(author)
    # field2是关联目标模型的外键名(book)


class Author2Book(models.Model):
    author = models.ForeignKey(to='Author')
    book = models.ForeignKey(to='Book')

    class Meta:
        unique_together = ('author', 'book')

Note:
When we need to store additional fields in the third relational table, you have to use a third way.

But when we create a third way to use-many relationship, you can not use the set, add, remove, clear way to manage many relationships, and the need to manage many relationships through third model table .

Meta message

ORM corresponding class which contains Meta another class, the message class encapsulates some of the Meta database. The main fields are as follows:

  • db_table: the ORM in the database table name defaults to the class name app_ by db_table rewritable table.
  • index_together: joint index
  • unique_together: United unique index
  • ordering: specify what fields are sorted default, only set this property, we query the results can be reverse ().

More Actions see: [] Django ORM operation # 2
"

Original: http://blog.gqylpy.com/gqy/260

Guess you like

Origin www.cnblogs.com/gqy02/p/11367271.html