一、配置數(shù)據(jù)庫
settings.py
DTABAESE = {
'default':{
'ENGINE':'dajngo.db.backends.mysql',
'NAME':'test',
'HOST':'127.0.0.1',
'PORT':3306,
'USER':'root',
'PASSWORD':'123456',
}
}
init.py
import pymysql
pymysql.install_as_MySQLdb()
二、ORM模型
使用ORM模型
當(dāng)項目越來越大的時候,就會出現(xiàn)很多原生SQL語句,就會出現(xiàn)以下問題:
1.SQL語句重復(fù)使用率不高,越復(fù)雜的sql語句就越長,會出現(xiàn)很多類似的SQL語句
2.很多SQL語句都是業(yè)務(wù)邏輯拼湊出來的,如果有數(shù)據(jù)庫發(fā)生改變就要去修改這些sql語句中的邏輯,會容易漏掉SQL的更改
3.原生SQL語句沒有考慮安全
使用ORM的好處
1.易用性:減少復(fù)雜SQL出現(xiàn)的概率,是業(yè)務(wù)更加的直觀
2.設(shè)計靈活:可以簡單的寫出復(fù)雜的SQL
3.可移植性:底層封裝了對多種數(shù)據(jù)庫的實現(xiàn),一旦更改數(shù)據(jù)庫,只需更改用戶賬號、密碼。。。
關(guān)系映射
模型類---->>>數(shù)據(jù)庫一張b表
屬性--->>>表中的字段名稱和屬性 約束條件
方法--->>>類中的普通方法
數(shù)據(jù)庫中的一條數(shù)據(jù)--->>>一個對象
注意:
在ORM上對于對象的屬性的操作,就是對一條數(shù)據(jù)中的某個字段進(jìn)行操作,不直接操作數(shù)據(jù)庫,操作ORM,ORM底層最終轉(zhuǎn)換為SQL語句
三、定義屬性
概述:
django根據(jù)屬性的類型確定一下信息:
1.當(dāng)前選擇的數(shù)據(jù)庫支持的字段類型
2渲染管理表單時使用的默認(rèn)html控件
3.在管理站點最低限度的驗證
注意:
django 會在表中自動增加主鍵列,每個模型只能有一個主鍵列,如果使用選項設(shè)置某屬性為主鍵列后,則django不會再生成默認(rèn)的逐漸列
庫
定義庫時,需要字段類型,字段類型被定義在djngo.db.models.fields目錄下,為了方便使用,被導(dǎo)入到django.db.models中
使用方式:
導(dǎo)入:
from django.db import models
通過models.Field創(chuàng)建字段類型的對象,賦值給屬性
邏輯刪除
對于重要的數(shù)據(jù)都做邏輯刪除,不做物理刪除,實現(xiàn)方法是定義isDelete屬性,類型為BooleanField,默認(rèn)值為False
字段類型
AutoField一個根據(jù)實際ID自動增長的IntegerField,通常不指定如果不指定,一個主鍵字段將自動添加到模型中
CharField(max_length=字符串長度)字符串,默認(rèn)的表單樣式是TextInput
TextField大文本字段,一般超過4000使用,默認(rèn)的表單控件是Textarea
IntegerField整數(shù)
DecimalField(max_digits=None,decimal_places=None)c參數(shù)說明DecimalField.max_digits位數(shù)總數(shù)
DecimalField.decimal_places小數(shù)位后的數(shù)字位數(shù)
FloatField用Python的float實例來表示的浮點數(shù)
BooleanFieldtrue/false字段,此字段的表單控制是CheckboxInput
NullBooleanField支持null、true、false三種值
DateField([auto_now=False,auto_now_add=False])使用Python的datetime.date實例表示的日期
參數(shù)說明:
DateField.auto_now:每次保存對象時,自動設(shè)置該字段為當(dāng)前時間,用于‘最后一次修改’的時間戳,它總是使用用當(dāng)前時間日期,默認(rèn)為false
DateField.auto_now_add:當(dāng)對象第一次被
創(chuàng)建時自動設(shè)置當(dāng)前時間,用于創(chuàng)建的時間戳,它總是使用當(dāng)前日期,默認(rèn)為false
常見問題:
如何將創(chuàng)建時間設(shè)置為“默認(rèn)當(dāng)前”并且可修改
在現(xiàn)實生產(chǎn)環(huán)境中,往往希望對象的創(chuàng)建時間默認(rèn)設(shè)置為當(dāng)前值,但又希望日后可以修改它,如何實現(xiàn)這種需求的呢。
django中所有的model字段都擁有一個default參數(shù),用來給字段設(shè)置默認(rèn)值(上面的文檔中有介紹)。
我們可以使用default=timezone.now()來替換auto_now=True或auto_now_add=True。
(default=timezone.now 對應(yīng) django.utils.timezone.now())
from django.db import models
import django.utils.timezone as timezone
class Test(models.Model):
add_date = models.DateTimeField('保存日期',default = timezone.now)
mod_date = models.DateTimeField('最后修改日期', auto_now = True
注意:
auto_now_add,auto_now和default這些設(shè)置是相互排斥的,他們之間的任何組合將會發(fā)生錯誤的結(jié)果
Timefield使用Pythonde datetime.time實例表示的時間,參同DateField
DateTimeField使用Python的datetime.datetime實例表示的日期和時間,參數(shù)同DateField
FileField一個上傳文件的字段
ImageField繼承了FileField的所有屬性和方法,但對上傳的對象進(jìn)行校驗,確保它是個有效的image
四、字段約束
概述:
1.通過字段選項,可以實現(xiàn)對字段的約束
2.在字段對象使用時通過關(guān)鍵字參數(shù)指定
null:如果為True , dajngo將空值一NULL存儲到數(shù)據(jù)庫中,默認(rèn)值是False
blank如果為True,則則該字段允許為空白,默認(rèn)值是False
null是數(shù)據(jù)庫范疇的概念,blank是表單驗證范疇的
注意: blank只對TextField這樣的生效,對數(shù)字不生效,會報錯
db_column字段的名稱,如果為指定,則使用屬性的名稱
db_index若值為True,則在表中會為此字段創(chuàng)建索引
default默認(rèn)值
primary_key若為True,則該字段會成為明星的主鍵字段
unique如果為True,這個字段在表中必須有唯一值
更改表明
# 在Model中
class Meta:
db_table = "new_tablename" # 更改表名
將模型遷移到庫中
1.創(chuàng)建遷移文件(此刻表并沒有創(chuàng)建到庫中)
python manage.py makemigrations
2.執(zhí)行遷移(將模型創(chuàng)建到庫中)
python manage.py migrate
注意:
以上操作都不需要直接操作數(shù)據(jù)庫
五、模型成員
類屬性
(1)object是Manage類的一個對象
作用:與數(shù)據(jù)庫進(jìn)行交互
當(dāng)創(chuàng)建模型類 并且沒有指定模型管理器的時候 默認(rèn)為object
(2)自定義模型管理器
class Test(model.Model):
.....
testobj = models.Manager()
使用
def select(req):
Test.testobj.get(pk=1)
注意:
默認(rèn)的objects不存在了
四、自定義管理器Manager類
繼承Manager類,重學(xué)查詢方法get_queryset方法,將查詢集按照自己的需求添加過濾篩選條件
一個模型類,可以有多個模型管理器
當(dāng)創(chuàng)建模型類對象時,django不會對數(shù)據(jù)庫進(jìn)行讀寫操作,調(diào)用save()方法才與數(shù)據(jù)庫交互,進(jìn)行insert或update操作,將數(shù)據(jù)保存到數(shù)據(jù)庫中。如果模型類的屬性比較多,逐個屬性賦值很麻煩,推薦使用管理器
實例:
models.py
class UserManager(models.Manager):
def get_queryset(self): # 查詢執(zhí)行的就是當(dāng)前的方法,更改當(dāng)前模型管理器查詢數(shù)據(jù)返回的結(jié)果
return super().get_queryset().filter(sex=True) # 返回性別為True的數(shù)據(jù)
# 使用
# 創(chuàng)建用戶模型類
class User(models.Model):
username = models.CharField(max_length,db_indexTrue,default='張三')
password = models.CharField(max_length=128,default='123456')
sex = models.BooleanField(default=True)
age = models.IntegerField(default=20)
info = models.CharFileld(max_length=100,default='個人簡歷')
icon = models.CharField(max_Length=70,default='default.jpg')
userobj = models.Manger() # 自定義模型管理器的名稱為 userobj 原來默認(rèn)的object則不存在
getSet = UserManager() # 當(dāng)前管理器的查詢結(jié)果為性別為True的數(shù)據(jù)
def __str__(self):
return self.usernmae
在view.py中使用
def select(req):
u = User.userobj.fielter() # filelt作用 查詢所有(如果沒有給過濾條件時)
# u = User.userobj.fielter(sex=True) # fielter作用 查詢所有sex為True的
# for row in u:
#print(row)
# return HttpResponse('查詢所有數(shù)據(jù)')
u = User.getSet.fielter()
return render(req,'show.html',{'obj':u})
模板show.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
table{
border-collapse: collapse;
margin: auto;
}
td,th{
width: 150px;
text-align: center;
height: 40px;
}
</style>
</head>
<body>
<table>
<caption><h2>數(shù)據(jù)查詢</h2>
<tr>
<th>用戶名</th>
<th>密碼</th>
<th>性別</th>
<th>年齡</th>
<th>個人簡介</th>
<th>頭像</th>
</tr>
{% for row in obj %}
<tr>
<td>{{ row.username }}</td>
<td>{{ row.password }}</td>
<td>
{% if row.sex %}
男
{% else %}
女
{% endif %}
</td>
<td>{{ row.age }}</td>
<td>{{ row.info }}</td>
<td>{{ row.icon }}</td>
</tr>
{% endfor%}
</caption>
</table>
</table>
</body>
</html>
