[TOC]python
class User(AbstractUser): mobile = models.CharField(max_length=11, unique=True, verbose_name='移動電話') icon = models.ImageField(upload_to='icon', default='icon/default.png', verbose_name='頭像') class Meta: db_table = 'o_user' # 自定義表名 verbose_name_plural = '用戶表' # admin後臺管理顯示的表名 def __str__(self): return self.self.name # admin後臺顯示的單個對象名
int自增列,必須填入參數 primary_key=True。當model中若是沒有自增列,則自動會建立一個列名爲id的列。git
一個整數類型,範圍在 -2147483648 to 2147483647。(通常不用它來存手機號(位數也不夠),直接用字符串存,)面試
字符類型,必須提供max_length參數, max_length表示字符長度。sql
這裏須要知道的是Django中的CharField對應的MySQL數據庫中的varchar類型,沒有設置對應char類型的字段,可是Django容許咱們自定義新的字段,下面我來自定義對應於數據庫的char類型數據庫
自定義字段在實際項目應用中可能會常常用到,這裏須要對他留個印象!django
from django.db import models # Create your models here. #Django中沒有對應的char類型字段,可是咱們能夠本身建立 class FixCharField(models.Field): ''' 自定義的char類型的字段類 ''' def __init__(self,max_length,*args,**kwargs): self.max_length=max_length super().__init__(max_length=max_length,*args,**kwargs) def db_type(self, connection): ''' 限定生成的數據庫表字段類型char,長度爲max_length指定的值 :param connection: :return: ''' return 'char(%s)'%self.max_length #應用上面自定義的char類型 class Class(models.Model): id=models.AutoField(primary_key=True) title=models.CharField(max_length=32) class_name=FixCharField(max_length=16) gender_choice=((1,'男'),(2,'女'),(3,'保密')) gender=models.SmallIntegerField(choices=gender_choice,default=3)
日期字段,日期格式 YYYY-MM-DD,至關於Python中的datetime.date()實例。安全
日期時間字段,格式 YYYY-MM-DD HH:MM[:ss[.uuuuuu]][TZ],至關於Python中的datetime.datetime()實例。框架
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) - 二進制類型
對應關係: '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)',
用於表示某個字段能夠爲空。fetch
若是設置爲unique=True 則該字段在此表中必須是惟一的 。優化
若是db_index=True 則表明着爲此字段設置索引。
爲該字段設置默認值。
配置auto_now_add=True,建立數據記錄的時候會把當前時間添加到數據庫。
publish_time = models.DateField(auto_now_add=True) publish_time = models.DateTimeField(auto_now_add=True)
配置上auto_now=True,每次更新數據記錄的時候會更新該字段。
publish_time = models.DateField(auto_now=True) publish_time = models.DateTimeField(auto_now=True)
外鍵類型在ORM中用來表示外鍵關聯關係,通常把ForeignKey字段設置在 '一對多'中'多'的一方。
ForeignKey能夠和其餘表作關聯關係同時也能夠和自身作關聯關係。
# 圖書表 class Book(models.Model): title = models.CharField(max_length=32) price = models.DecimalField(max_digits=8, decimal_places=2) publish_time = models.DateField(auto_now_add=True) # 出版社外鍵 # 一本書有一個出版社,一個出版社能夠出版多本書。一對多的關係 publish = models.ForeignKey(to='Publish') # 一對多 # 一本書 能夠又多個做者,一個做者能夠寫多本書。多對多 authors = models.ManyToManyField(to='Author')
設置要關聯的表
設置要關聯的表的字段
當刪除關聯表中的數據時,當前表與其關聯的行的行爲。
models.CASCADE
刪除關聯數據,與之關聯也刪除
是否在數據庫中建立外鍵約束,默認爲True。
models.DO_NOTHING 刪除關聯數據,引起錯誤IntegrityError models.PROTECT 刪除關聯數據,引起錯誤ProtectedError models.SET_NULL 刪除關聯數據,與之關聯的值設置爲null(前提FK字段須要設置爲可空) models.SET_DEFAULT 刪除關聯數據,與之關聯的值設置爲默認值(前提FK字段須要設置默認值) models.SET 刪除關聯數據, a. 與之關聯的值設置爲指定值,設置:models.SET(值) b. 與之關聯的值設置爲可執行對象的返回值,設置:models.SET(可執行對象)
def func(): return 10 class MyModel(models.Model): user = models.ForeignKey( to="User", to_field="id", on_delete=models.SET(func) )
一般一對一字段用來擴展已有字段。(通俗的說就是一我的的全部信息不是放在一張表裏面的,簡單的信息一張表,隱私的信息另外一張表,之間經過一對一外鍵關聯)
# 做者表 class Author(models.Model): name = models.CharField(max_length=32) age = models.IntegerField() # 一個做者有一個做者詳情,一個詳情只有一個做者。一對一 author_detail = models.OneToOneField('AuthorDetail')
設置要關聯的表。
設置要關聯的字段。
當刪除關聯表中的數據時,當前表與其關聯的行的行爲。
好處:第三張表自動建立,而且會自動幫你在字段名後加'_id'後綴 不足之處:第三張表沒法擴展額外的字段,擴展性低
# 圖書表 class Book(models.Model): title = models.CharField(max_length=32) price = models.DecimalField(max_digits=8, decimal_places=2) publish_time = models.DateField(auto_now_add=True) # 出版社外鍵 # 一本書有一個出版社,一個出版社能夠出版多本書。一對多的關係 publish = models.ForeignKey(to='Publish') # 一對多 # 一本書 能夠又多個做者,一個做者能夠寫多本書。多對多 authors = models.ManyToManyField(to='Author') # Author是多對多的另外一張表名
好處:第三表能夠擴展額外的字段 不足之處:orm查詢的時候會帶來不便
class Book(models.Model): title = models.CharField(max_length=32) class Author(models.Model): name = models.CharField(max_length=32) class Book2Author(models.Model): book = models.ForeignKey(to='Book') author = models.ForeignKey(to='Author') create_time = models.DateField(auto_now_add=True)
好處:第三張表能夠擴展任意的額外字段 還能夠利用orm 正反向查詢 不足之處:沒法利用 add set remove clear 對外鍵關係表操做 可是:雖然沒法使用了 但咱們還能夠本身直接操做第三表,擴展性極高
class Book(models.Model): title = models.CharField(max_length=32) authors = models.ManyToManyField(to='Author',through='Book2Author',through_fields=('book','author')) class Author(models.Model): name = models.CharField(max_length=32) books = models.ManyToManyField(to='Author',through='Book2Author',through_fields=('author','book')) class Book2Author(models.Model): book = models.ForeignKey(to='Book') author = models.ForeignKey(to='Author') create_time = models.DateField(auto_now_add=True) # 自動添加建立時間
條件能夠被徹底列舉出來 有對應關係
該字段存的仍是數字而且沒有範圍限制,可是一旦你存的數字在你上面定義的對應關係內 那麼你就能夠經過下面的方法獲取到數字對應的解釋信息 get_xxx_display() 若是沒有對應關係返回的仍是數字 獲取值:user_obj.get_gender_display() # 只要有對應關係便可 前面不必定非要是數字 # 若是數字沒有對應的關係,那麼仍是獲取到數字自己
用戶的性別 學歷 婚否 在職狀態 客戶來源 當你的數據可以被你列舉徹底 你就能夠考慮使用choices參數
案例1:
# choices字段 class Userinfo(models.Model): username = models.CharField(max_length=32) gender_choices = ( (1,'男'), (2,'女'), (3,'其餘'), ) gender = models.IntegerField(choices=gender_choices) # 該字段仍是存數字 而且能夠匹配關係以外的數字
案例2:
record_choices = (('checked', "已簽到"), ('vacate', "請假"), ('late', "遲到"), ('noshow', "缺勤"), ('leave_early', "早退"), ) record = models.CharField("上課紀錄", choices=record_choices, default="checked", max_length=64)
獲取值:
user_obj = models.Userinfo.objects.get(pk=1) print(user_obj.username) print(user_obj.gender) # 針對choices參數字段 取值的時候 get_xxx_display() print(user_obj.get_gender_display()) # # 針對沒有註釋信息的數據 get_xxx_display()獲取到的仍是數字自己 user_obj = models.Userinfo.objects.get(pk=4) print(user_obj.gender) print(user_obj.get_gender_display())
惰性:不會白白的幫你多幹事情,減緩數據庫的壓力
惰性查詢:若是下面的代碼沒有使用res,那麼就不會幫你查詢。只有使用了纔會幫你查詢。
django orm查詢都是惰性查詢 res = models.Book.objects.all() # django orm查詢都是惰性查詢 printf(res) # 使用了res
res = models.Book.objects.only('title') # 這些對象內部只有title屬性 # print(res) for r in res: print(r.title) # only括號內有title屬性,不走數據庫 print(r.price) # 括號內沒有price屬性,走數據庫拿
res = models.Book.objects.defer('title') # defer與only互爲反關係 print(res)
大白話總結: defer與only互爲相反,獲取沒有的數據走數據庫拿。 only: 括號內有指定的字段屬性 defer:括號內沒有指定的字段屬性
selected_related:內部是連表操做,封裝到對象,走一次數據庫所有查出 優勢:只走一次sql查詢 缺點:耗時耗在 鏈接表的操做 10s prefetch_related:內部是子查詢 優勢:耗時耗在 查詢次數好比10次 1s 缺點:走兩次sql查詢
使用方法:
res = models.Book.objects.select_related('publish') print(res) res = models.Book.objects.prefetch_related('publish') print(res)
原子性: 原子性(Atomicity),原子意爲最小的粒子,即不能再分的事務,要麼所有執行,要麼所有取消(就像上面的銀行例子) 一致性: 一致性(Consistency):指事務發生前和發生後,數據的總額依然匹配 隔離性: 隔離性(Isolation):簡單點說,某個事務的操做對其餘事務不可見的 持久性: 持久性(Durability):當事務完成後,其影響應該保留下來,不能撤消,只能經過「補償性事務」來抵消以前的錯誤
開啓事務:
start transaction 開啓 rollback 回滾 commit 確認
from django.db import transaction # django orm開啓事務操做 from django.db import transaction with transaction.atomic(): # 在with代碼塊中執行的orm語句同屬於一個事務 pass
MTV: django號稱是MTV框架
M 指:models 模型 T :templates 模版 V :views 視圖
MVC
M:models 模型 V:views 視圖 C:contronnar 控制器(路由分發 urls.py)
本質
本質:MTV本質也是MVC
BMS
Web領域沒有絕對的安全 也沒有絕對的不安全