Django框架知識要點總結筆記

哪些請求方式在請求地址的時候可以帶請求體?

只有PATCH、POST、PUT、DELETE訪問一個url地址時可以帶請求體

web框架和web服務器

在這裏插入圖片描述
web框架:flask Django

作用:

1.路由分發(根據url找到對應的處理函數)

2.調用處理函數進行業務處理。

web服務器 app.run()

作用:

1.解析請求報文,調用框架程序處理請求。

2.組織響應報文,返回內容給客戶端。

web框架學習方法

  • 如何搭建工程程序

    工程的組建

    工程的配置

    路由定義

    視圖函數的定義

  • 如何獲取請求數據(操作request對象)

  • 如何構造響應數據(構造response對象)

  • 如何使用中間層

    請求鉤子

  • 框架提供的其他功能組件

    數據庫

    模板

    admin

Django簡介

Django的主要目的是簡便、快速的開發數據庫驅動的網站。強調代碼複用、快速開發和DRY(不要自己重複造輪子)原則。

特點

1.重量級框架

Django原生提供了衆多的功能組件,讓開發更簡便快速。

  • 提供項目工程管理的自動化腳本工具
  • 數據庫ORM支持(對象關係映射,英語Object Relational Mapping)
  • 模板
  • 表單
  • Admin站點
  • 文件管理
  • 認證權限
  • session機制
  • 緩存

2.MVT開發模式

Model(模型)-View(視圖)-Template(模板)

Model,負責和數據庫交互,進行數據處理

View,用於接收請求,處理業務邏輯

Template,負責封裝構造要返回的html

其實和MVC框架一樣

Django框架環境安裝&項目創建

1)命令

mkvirtualenv name -p python3  # 創建虛擬環境
workon name # 進入虛擬環境
pip install django==1.11.11 # 安裝django
cd 目錄  # 切換目錄
django-admin startproject <項目名稱> # 創建項目
python manage.py startapp #創建子應用

2)進行子應用註冊

點開項目目錄下的settings,在INSTALLED_APPS中配置

在這裏插入圖片描述

3)啓動

python manage.py runserver

定義視圖函數

定義在子應用的views.py中

需要request接收請求並返回響應對象

def index(requset):
    """request:接收請求對象"""
    # 返回相應對象
    return HttpResponse('hello world')

URL配置

1) 在子應用中創建urls.py,設置子應用中url地址和視圖函數之間的對應關係

from django.conf.urls import url
from users import views

urlpatterns = [
    # 添加當前子應用中url地址和視圖函數之間的對應關係
    # url('地址url正則表達式','對應視圖函數')
    url(r'index',views.index),
]

2)在項目總的urls.py文件中包含子應用中的urls.py文件

from django.conf.urls import url, include
from django.contrib import admin

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    # 包含子應用中urls.py文件
    url(r'^users/',include('users.urls'))
]

3)Django路由匹配過程說明

先找項目總的urls.py中正則匹配url地址,調用視圖函數,再進入子應用中的urls.py進行正則匹配,調用視圖函數
在這裏插入圖片描述

4) 路由配置時兩個注意點:

子應用中進行url配置時,嚴格匹配開頭和結尾

Django url 地址配置的默認風格時:末尾加/

url(r'^index/$', views.index)

5)Django路由配置-url地址的反向解析

總的應用中定義別名用namespace=’’

url(r'^users/', include('users.urls', namespace='users')),

子應用中定義別名用name=’’

url(r'^index/$', views.index, name='index'),

根據視圖獲取對應的url地址,通常配合重定向進行使用。

def url_reverse(request):
    # 獲取index視圖所對應的url地址
    from django.urls import reverse
    req_url = reverse('users:index')
    return HttpResponse('OK')

配置文件settings.py

1)BASE_DIR(根目錄)

BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))

2)DEBUG

  • 修改代碼文件,程序自動重啓
  • Django程序出現異常時,向前端顯示詳細的錯誤追蹤信息

3)中國語言與時區

在settings.py中配置

# Internationalization
# https://docs.djangoproject.com/en/1.11/topics/i18n/

# LANGUAGE_CODE = 'en-us' # 設置語言
LANGUAGE_CODE = 'zh-Hans' # 設置語言

# TIME_ZONE = 'UTC' # 設置時區
TIME_ZONE = 'Asia/Shanghai' # 設置時區

4)靜態文件的使用

在settings.py中配置

1)設置訪問靜態文件路徑的前綴地址

2)指定Django中靜態文件存放的目錄

# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/1.11/howto/static-files/
# 設置訪問靜態文件路徑的前綴地址
STATIC_URL = '/static/'
# 指定Django中靜態文件存放的目錄
STATICFILES_DIRS = [os.path.join(BASE_DIR, 'static')]

請求參數傳遞

4種傳參方式

1.通過url地址傳遞參數(利用正則表達式提取參數的方法從url中獲取請求參數)
#/weather/城市名/年份/:比如:/weather/shanghai/2019/
#flask: 路由轉換器 /weather/<city>/<int:year>
#Django:

#未命名參數按定義順序傳遞,正則需要小括號括起來,分組
#在urls中配置正則
url(r'^weather/([a-z]+)/(\d{4})/$', views.weather),

#在視圖函數中獲取
def weather(request, city, year):
    print('city=%s' % city)
    print('year=%s' % year)
    return HttpResponse('OK')
    
#命名參數按名字傳遞
#在urls中配置正則 ?P給參數起別名
url(r'^weather/(?P<city>[a-z]+)/(?P<year>\d{4})/$', views.weather),

#在視圖函數中獲取
def weather(request, year, city):
    print('city=%s' % city)
    print('year=%s' % year)
    return HttpResponse('OK')
2.請求參數傳遞(通過查詢字符串傳參)
# /qs/?a=1&b=2&c=3&c=4
# flask:request.args
def get_qs(request):
    # 獲取查詢字符串的參數
    a = request.GET.get('a')
    b = request.GET.get('b')
    c = request.GET.get('c') # ,如果c對應多個值,默認只查詢到最後一個值 
    clist = request.GET.getlist('c') # 使用此方法可以查詢c的列表
    return HttpResponse('OK')
    
3.通過請求體傳遞參數(json數據或表單)
表單數據:/from_data/

request.POST:QueryDict類型的對象,允許一個鍵對應多個值

request.POST.get('name')
request.POST.get('age')

<from methods='get' action='提交地址'>
	<input type='text' name='a'/>
	<input type='text' name='b'/>
	<input type='submit' value='提交'/>
</from>

json數據:/json_data/
request.body

import json
def get_body_json(request):
    json_str = request.body
    json_str = json_str.decode()  # python3.6 無需執行此步
    req_data = json.loads(json_str)
    print(req_data['a'])
    print(req_data['b'])
    return HttpResponse('OK')

注意:使用postman必須註釋csrf功能,另外postman測試的時候網址後面一定要加斜槓!!!

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    # 'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
]
4.通過請求頭傳遞參數
/header_data/
request.META:python 字典,保存請求頭中的所有數據
請求中的任何HTTP頭部轉換爲HTTP_的鍵時,都會將所有字母大寫並將連接符替換爲下劃線,最後加上META前綴
request.META.get('HTTP_NAME')
# /header_data/
def get_header(request):
    # 獲取請求頭傳遞的參數
    type = request.META.get('CONTENT_TYPE')
    name = request.META.get('HTTP_NAME')

    return HttpResponse('OK')

Django和flask中request對象屬性對比

在這裏插入圖片描述

響應Response

響應對象的構造與說明

視圖訪問響應時返回HttpResponse類的對象或者子類的對象

response = HttpResponse(content='響應內容', content_type='響應體數據類型', status='狀態碼')
response['NAME'] = 'ITCAST' #響應頭可以直接將HttpResponse對象當做字典進行響應頭鍵值對的設置
return response

# 示例
# /get_response/
def get_response(request):
    # 響應對象構造
    response = HttpResponse('content body', content_type='text/html', status=200)

    # 向響應頭中添加數據
    response['NAME'] = 'ITCAST'
    return response

返回頁面重定向(重點)

# 反向解析獲取index視圖所對應的url地址
req_url = reverse('users:index')
return redirect(req_url)

返回json數據(重點)

from django.http import JsonResponse
return JsonResponse({'name':monkey,'age',23})

狀態保持

cookie的設置和獲取

diango中cookie的設置和獲取:
response = HttpResponse('ok')
response.set_cookie(cookie名, value=cookie值, max_age=cookie有效期) # 3600(一小時過期)
return response
讀取:
def demo_view(request):
    name = request.COOKIES.get('name')
    print(name)
    return HttpResponse('OK')
刪除:
def del_cookie(request):
	response = HttpResponse('OK')
	response.delete_cookie('name')
	return response

session儲存說明

session:數據存儲在服務器,以key-value進行存儲。

特點: session依賴於cookie,每個客戶端的session數據的標識存儲到cookie中

flask session過期時間默認一個月,django session過期時間默認爲2周。

session的三種儲存方式

1.數據庫

存儲在數據庫中,如下設置可以寫,也可以不寫,這是默認存儲方式

SESSION_ENGINE='django.contrib.sessions.backends.db'

2.混合本地緩存

存儲在本機內存中,如果丟失則不能找回,比數據庫的方式讀寫更快。

SESSION_ENGINE='django.contrib.sessions.backends.cache'

3.混合存儲

優先從本機內存中存取,如果沒有則從數據庫中存取。

SESSION_ENGINE='django.contrib.sessions.backends.cached_db'

session存儲到redis設置

安裝擴展 pip install django-redis

  1. 先將服務器緩存改爲redis

在settings.py文件中做如下設置 (緩存可以有多個空間,需要多個空間複製default從新命名就行了)

CACHES = {
    "default": {
        "BACKEND": "django_redis.cache.RedisCache",
        "LOCATION": "redis://127.0.0.1:6379/1",
        "OPTIONS": {
            "CLIENT_CLASS": "django_redis.client.DefaultClient",
        }
    }
}
SESSION_ENGINE = "django.contrib.sessions.backends.cache"
SESSION_CACHE_ALIAS = "default"
  1. 再將session設置到緩存中

session的設置和獲取

# /set_session/
def set_session(request):
    # 設置session
    request.session['name'] = 'itcast'
    request.session['age'] = 12

    return HttpResponse('OK')


# /get_session/
def get_session(request):
    # 獲取session
    name = request.session.get('name')
    age = request.session.get('age')

    return HttpResponse('name: %s age: %s' % (name, age))

session的操作

1) 以鍵值對的格式寫session。

request.session['鍵']=值

2)根據鍵讀取值。

request.session.get('鍵',默認值)

3)清除所有session,在存儲中刪除值部分。

request.session.clear()

4)清除session數據,在存儲中刪除session的整條數據。

request.session.flush()

5)刪除session中的指定鍵及值,在存儲中只刪除某個鍵及對應的值。

del request.session['鍵']

6)設置session的有效期

request.session.set_expiry(value)

類視圖

類視圖的基本使用

類視圖好處:

1.代碼更加清晰 2.代碼可重用性更高

class RegisterView(View):
    def get(self,request):
        # 返回註冊頁面
        return HttpResponse('返回註冊頁面')
        
    def post(self,request):
        # 進行註冊處理
        return HttpResponse('進行註冊處理')
    
    def put(self,request):
        # 使用哪個方法請求就def定義哪個請求方式
        return HttpResponse('put方法被調用')
       
# 子應用配置urls.py
urlpatterns = [
    url(r'^register/$', views.RegisterView.as_view(), name='register')
]
# 項目總的urls設置包含

類視圖原理

在這裏插入圖片描述

給類視圖函數添加裝飾器

注意:函數視圖的裝飾器不能直接加在類視圖方法上面,會報錯!

1)方法一:在urls中配置中裝飾

在這裏插入圖片描述
2)方法二:使用@method_decorator來進行裝飾器添加

def my_decorator(func):
    def wrapper(request, *args, **kwargs):
        print('自定義裝飾器被調用了')
        print('請求路徑%s' % request.path)
        return func(request, *args, **kwargs)
    return wrapper

# 爲全部請求方法添加裝飾器
@method_decorator(my_decorator, name='dispatch')
class DemoView(View):
    def get(self, request):
        print('get方法')
        return HttpResponse('ok')

    def post(self, request):
        print('post方法')
        return HttpResponse('ok')


# 爲特定請求方法添加裝飾器
@method_decorator(my_decorator, name='get')
class DemoView(View):
    def get(self, request):
        print('get方法')
        return HttpResponse('ok')

    def post(self, request):
        print('post方法')
        return HttpResponse('ok')

Mixin擴展類

把一些通用的功能封裝到不同的父類中,子類需要哪些功能,就可以繼承哪些父類,這些父類就是Mixin擴展類。

DRF框架

中間件

Django中的中間件,就類似於flask中的鉤子函數:可以讓我們在請求之前或之後做一些處理。

基本使用

1)在子應用目錄下創建middleware.py(但是作用域時全局的),將以下模板代碼複製到裏面

def simple_middleware(get_response):
    # 此處編寫的代碼僅在Django第一次配置和初始化的時候執行一次。

    def middleware(request):
        # 此處編寫的代碼會在每個請求處理視圖前被調用。

        response = get_response(request)

        # 此處編寫的代碼會在每個請求處理視圖之後被調用。

        return response

    return middleware

2)在settings.py中註冊

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    # 'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
    'users.middleware.my_middleware',  # 添加中間件
]

多箇中間件執行順序

init部分的代碼調用和中間件的註冊順序是相反的
before request部分的代碼和中間件的註冊順序是相同的
after request部分的代碼和中間件的註冊順序是相反的

中間件的應用場景

可以在請求之前設置CSRF跨站請求僞造判斷保護

可以在請求之前設置黑名單校驗

模板

在這裏插入圖片描述

模板的基本使用

1.創建並設置模板文件的目錄

2.在視圖中使用render(request,‘模板文件’,‘字典’)調用模板

class TemplateView(View):
    def get(self,request):
        return render(request,'temp.html',context={'content':'hello'})

3.在urls中註冊地址

使用模板文件的詳細步驟

1.加載模板文件:指定所使用的模板文件,獲取模板對象
from django.template inport loader
temp = loader.get_template('模板文件')

2.進行模板渲染:給模板文件傳遞數據,將模板文件中的變量進行替換,獲取替換之後的內容
res_html = temp.render('傳遞給模板文件的字典數據')

3.創建響應對象
return HttpResponse(res_html)

Django模板和jinja2模板使用對比

1){{模板變量}}

Django使用模板變量時,無論是字典、列表或元組的元素,都需要使用".",不能使用[]
Django中的模板變量不能直接進行算術運算

def index(request):
    context = {
        'city': '北京',
        'adict': {
            'name': '西遊記',
            'author': '吳承恩'
        },
        'alist': [1, 2, 3, 4, 5]
    }
    return render(request, 'index.html', context)
    
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <h1>{{ city }}</h1>
    <h1>{{ adict }}</h1>
    <h1>{{ adict.name }}</h1>  注意字典的取值方法
    <h1>{{ alist }}</h1>  
    <h1>{{ alist.0 }}</h1>  注意列表的取值方法
</body>
</html>
2)條件判斷

Django模板中在進行條件判斷時,比較操作符的兩邊必須有空格

3)循環/判斷

for循環:

{% for item in 列表 %}

循環邏輯
{{forloop.counter}}表示當前是第幾次循環,從1開始
{%empty%} 列表爲空或不存在時執行此邏輯

{% endfor %}

if條件:

{% if ... %}
邏輯1
{% elif ... %}
邏輯2
{% else %}
邏輯3
{% endif %}

比較運算符如下:

==
!=
<
>
<=
>=

布爾運算符如下:

and
or
not

注意:運算符左右兩側不能緊挨變量或常量,必須有空格。

{% if a == 1 %}  # 正確
{% if a==1 %}  # 錯誤
4)模板過濾器

{{模板變量|過濾器:參數}}

注:Django中的過濾器冒號後面的參數只能有一個

safe,禁用轉義,告訴模板這個變量是安全的,可以解釋執行
length,長度,返回字符串包含字符的個數,或列表、元組、字典的元素個數。
default,默認值,如果變量不存在時則返回默認值。

data|default:'默認值'
date,日期,用於對日期類型的值進行字符串格式化,常用的格式化字符如下:

Y表示年,格式爲4位,y表示兩位的年。
m表示月,格式爲01,02,12等。
d表示日, 格式爲01,02等。
j表示日,格式爲1,2等。
H表示時,24進制,h表示12進制的時。
i表示分,爲0-59。
s表示秒,爲0-59。
value|date:"Y年m月j日  H時i分s秒"

4)註釋

1)單行註釋語法如下:

{#...#}

2)多行註釋使用comment標籤,語法如下:

{% comment %}
...
{% endcomment %}
5)模板繼承
定義代碼塊:
{% block 名稱 %}
預留區域,可以編寫默認內容,也可以沒有默認內容
{% endblock  名稱 %}

子模版繼承:
{% extends "父模板路徑"%}

{% block 名稱 %}
實際填充內容
{{ block.super }}用於獲取父模板中block的內容
{% endblock 名稱 %}

數據庫

ORM框架

Django自帶ORM框架:通過類和對象可以直接進行數據庫操作,根據模型類自動生成表

數據庫鏈接配置

  1. 使用MySQL數據庫首先需要安裝驅動程序

    pip install PyMySQL
    
  2. 在Django的工程同名子目錄的__init__.py文件中添加如下語句

    from pymysql import install_as_MySQLdb
    
    install_as_MySQLdb()
    

    作用是讓Django的ORM能以mysqldb的方式來調用PyMySQL。

  3. 修改DATABASES配置信息

    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',
            'HOST': '127.0.0.1',  # 數據庫主機
            'PORT': 3306,  # 數據庫端口
            'USER': 'root',  # 數據庫用戶名
            'PASSWORD': 'mysql',  # 數據庫用戶密碼
            'NAME': 'django_demo'  # 數據庫名字
        }
    }
    
  4. 在MySQL中創建數據庫

    create database django_demo default charset=utf8;
    

模型類定義

定義模型類,在models.py文件中定義

class BookInfo(models.Model):
    """圖書類模型"""
    # 字段屬性 = models.字段類型(選項參數)
    btitle = models.CharField(max_length=20,verbose_name="標題")
    
    class Meta:
        # 指定表名
        db_table = "tb_books"

1) 數據庫表名

模型類如果未指明表名,Django默認以 小寫app應用名_小寫模型類名 爲數據庫表名。

可通過db_table 指明數據庫表名。

2) 關於主鍵

django會爲表創建自動增長的主鍵列,每個模型只能有一個主鍵列,如果使用選項設置某屬性爲主鍵列後django不會再創建自動增長的主鍵列。

默認創建的主鍵列屬性爲id,可以使用pk代替,pk全拼爲primary key。

3) 屬性命名限制

  • 不能是python的保留關鍵字。

  • 不允許使用連續的下劃線,這是由django的查詢方式決定的。

  • 定義屬性時需要指定字段類型,通過字段類型的參數指定選項,語法如下:

    屬性=models.字段類型(選項)
    

4)字段類型

類型 說明
AutoField 自動增長的IntegerField,通常不用指定,不指定時Django會自動創建屬性名爲id的自動增長屬性
BooleanField 布爾字段,值爲True或False
NullBooleanField 支持Null、True、False三種值
CharField 字符串,參數max_length表示最大字符個數
TextField 大文本字段,一般超過4000個字符時使用
IntegerField 整數
DecimalField 十進制浮點數, 參數max_digits表示總位數, 參數decimal_places表示小數位數
FloatField 浮點數
DateField 日期, 參數auto_now表示每次保存對象時,自動設置該字段爲當前時間,用於"最後一次修改"的時間戳,它總是使用當前日期,默認爲False; 參數auto_now_add表示當對象第一次被創建時自動設置當前時間,用於創建的時間戳,它總是使用當前日期,默認爲False; 參數auto_now_add和auto_now是相互排斥的,組合將會發生錯誤
TimeField 時間,參數同DateField
DateTimeField 日期時間,參數同DateField
FileField 上傳文件字段
ImageField 繼承於FileField,對上傳的內容進行校驗,確保是有效的圖片

5) 選項

選項 說明
null 如果爲True,表示允許爲空,默認值是False
db_column 字段的名稱,如果未指定,則使用屬性的名稱
db_index 若值爲True, 則在表中會爲此字段創建索引,默認值是False
default 默認
primary_key 若爲True,則該字段會成爲模型的主鍵字段,默認值是False,一般作爲AutoField的選項使用
unique 如果爲True, 這個字段在表中必須有唯一值,默認值是False

6) 外鍵

在設置外鍵時,需要通過on_delete選項指明主表刪除數據時,對於外鍵引用表數據如何處理,在django.db.models中包含了可選常量:

  • CASCADE 級聯,刪除主表數據時連通一起刪除外鍵表中數據
  • PROTECT 保護,通過拋出ProtectedError異常,來阻止刪除主表中被外鍵應用的數據
  • SET_NULL 設置爲NULL,僅在該字段null=True允許爲null時可用

生成遷移文件

python manage.py makemigrations

同步到數據庫中

python manage.py migrate

終端模式

Django shell 終端環境使用:

python manage.py shell

mysql數據庫的日誌文件:

記錄mysql數據庫操作

sudo vi /etc/mysql/mysql.conf.d/mysqld.cnf

數據庫基本操作-新增數據

# 1.創建模型對象→對象.save()
book = BookInfo(
	btitle="西遊記",
	bpub_date="1998-1-1",
	bread=10)
book.save()

# 2.模型類.objects.create(...)
hero = HeroInfo.objects.create(
	hname="沙僧",
	hcomment="你挑着擔",
	hbook=book)

數據庫基本操作-更新/刪除

更新的2種方式:
	>>> hero = HeroInfo.objects.get(id=2)
	>>> hero.hname = '豬悟能'
	>>> hero.save()
	
	HeroInfo.objects.filter(過濾條件).update(更新數據)
	>>> res = HeroInfo.objects.filter(id=3).update(hname='沙悟淨')
	
刪除的2種方式:
	>>> hero = HeroInfo.objects.get(id=3)
	>>> hero.delete()

	HeroInfo.objects.filter(過濾條件).delete()
	>>> HeroInfo.objects.filter(id=2).delete()

數據庫基本操作-查詢

models.py設置以下代碼,定義每個數據對象的顯示信息:

    def __str__(self):
        """定義每個數據對象的顯示信息"""
        return self.btitle

使用tests.py測試查詢,需要以下設置:

import os
if not os.environ.get('DJANGO_SETTINGS_MODULE'):
	os.environ.setdefault("DJANGO_SETTINGS_MODULE","demo.settings")
import django
django.setup()

# 導入模型
from booktest.models import BookInfo,HeroInfo
if __name__ == "__main__":
    print(BookInfo)
基本查詢-all&get&count
# 模型類.objects.
# get(查詢條件):返回一個模型對象,如果查不到,會報錯
book = BookInfo.objects.get(id=1)
# all():無參數,返回查詢到的所有數據
books = BookInfo.objects.all() # QuerySet查詢集:可以跟list一樣操作
# count():無參數,返回查詢到的結果數量
count = BookInfo.objects.count()
條件查詢-get&filter&exclude
# get(查詢條件):返回一個模型對象,如果查不到會報錯
book = BookInfo.objects.get(id__exact=1)
# filter(查詢條件):返回根據條件查詢到的結果,返回的是QuerySet
books = BookInfo.objects.filter(btitle__contains="傳") # 包含
books = BookInfo.objects.filter(btitle__startswith="天") # 以天開頭
books = BookInfo.objects.filter(btitle__endswith='部') # 以部結尾
books = BookInfo.objects.filter(btitle__isnull=False) # 標題不爲空
books = BookInfo.objects.filter(id__in=(1,3,5)) # 查詢id爲1,3,5的圖書
# gt 大於,gte 大於等於,lt 小於,lte 小於等於
books = BookInfo.objects.filter(id__gt=3) # 查詢id 大於3的圖書

# exclude(查詢條件):查詢不滿足條件的結果數據,返回的是QuerySet
books = BookInfo.objects.exclude(id=3) # 查詢id不等於3的圖書

# 日期查詢
# year、month、day、week_day、hour、minute、second:對日期時間類型的屬性進行運算
books = BookInfo.objects.filter(bpub_date__year=1980) # 查詢1980年發表的圖書
books = BookInfo.objects.filter(bpub_date__gt=date(1990, 1, 1)) # 該日期以後發表的圖書
數據查詢-F對象&Q對象
# F對象:用於查詢字段之間的比較
from django.db.models import F
books = BookInfo.objects.filter(bread__gte=F("bcomment")) # 查詢閱讀量大於等於評論量的圖書
books = BookInfo.objects.filter(bread__gt=F('bcomment') * 2)# 閱讀量大於2倍評論量的圖書
# Q對象:用戶查詢時條件之間的邏輯關係 與或非 
# &表示邏輯與,|表示邏輯或 ,~表示非
from django.db.models import Q
BookInfo.objects.filter(Q(bread__gt=20)&Q(id__lt=3)) # 查詢閱讀量大於20,並且編號小於3的圖書
BookInfo.objects.filter(Q(bread__gt=20) | Q(pk__lt=3)) # 查詢閱讀量大於20,或編號小於3的圖書
BookInfo.objects.filter(~Q(pk=3)) # 查詢編號不等於3的圖書
數據查詢-聚合操作&排序
# Avg 平均,Count 數量,Max 最大,Min 最小,Sum 求和
from django.db.models import Sum,Avg,Max,Min,Count
count = BookInfo.objects.aggregate(Sum('bread')) # 返回dict: {'bread__sum': 136}
res = BookInfo.objects.aggregate(Count('id')) # 查詢數量

# 排序 返回查詢集QuerySet
books = BookInfo.objects.order_by('bread') # 按照閱讀量從小到大進行排序
books = BookInfo.objects.order_by('-bread') # 按照閱讀量從大到小進行排序
關聯查詢(查詢和對象關聯的數據)
# 1.查詢和西遊記關聯的英雄人物信息
book = BookInfo.object.get(btitle='西遊記')
heros = book.heroinfo_set.all()
# 2.查詢id爲1的圖書關聯的英雄人物信息     
book = BookInfo.objects.get(id = 1)
heros = book.heroinfo_set.all()
# 3.查詢id爲1的英雄人物關聯的圖書信息
hero = HeroInfo.objects.get(id = 1)
book = hero.hbook
# 4.查詢和孫悟空關聯的圖書信息
hero = HeroInfo.objects.get(hname ='孫悟空')
book = hero.hbook

查詢和對象關聯的數據:
	BookInfo(一類)
    HeroInfo(多類)
    一對多:HeroInfo類中有一個外鍵關聯屬性:hbook = models.ForeignKey(BookInfo)
    
查詢和圖書對象關聯的英雄數據(由一查多):
	例子:heros = book.heroinfo_set.all()
    	一類對象.多類名小寫_set.all()
        
查詢和英雄關聯的圖書數據(由多查一):
	例子:book=hero.hbook
    多類對象.關聯屬性

在這裏插入圖片描述

查詢集QuerySet
以下函數返回的都是查詢集:
all():返回所有數據。
filter():返回滿足條件的數據。
exclude():返回滿足條件之外的數據。
order_by():對結果進行排序。

查詢集可以像list一樣進行操作:遍歷。取下標,切片(查詢集切片時下標不能爲負),QuerySet對象可以繼承調用上面任何查詢相關方法。
	BookInfo.objects.filter(id__gt=3).order_by('bread')
QuerySet對象還有一個方法叫:exists→判斷查詢集中是否有數據,有返回True,沒有返回Flase

兩大特點:
	惰性查詢:只有在使用查詢集中的數據時纔會真正發生數據庫的查詢
    數據緩存:使用同一個查詢集中的數據,只有第一次使用的時候會查詢數據庫,然後會將查詢的結果保存起來,
    再使用這個查詢集時,使用的時保存起來的數據,不會再去查數據庫。

Admin管理

Admin站點管理的基本使用

Django自帶admin站點管理功能。

1.語言和時區的本地化
2.創建管理員用戶

python manage.py createsuperuser

3.APP應用配置

在這裏插入圖片描述

4.註冊模型類

在子應用admin.py文件中註冊模型類

admin.site.register(模型類)

列表頁和編輯頁相關屬性

自定義Admin站點管理頁面
1.定義模型Admin管理類  admin.py
	class BookInfoAdmin(admin.ModelAdmin):
        # Django提供了很多類屬性,通過對應的屬性就可以控制管理界面對應內容的展示
        # 顯示哪些字段或方法
        list_display = ["id" , "btitle","pub_date"]
        # 每頁顯示多少條
        list_per_page=100
        # 編輯頁顯示字段
        fields = ['btitle', 'bpub_date']
        # 分組顯示編輯頁字段(與編輯頁顯示字段衝突,只能寫一種)
        fieldsets = (
        ('基本', {'fields': ['btitle', 'bpub_date']}),
        ('高級', {
            'fields': ['bread', 'bcomment'],
            'classes': ('collapse',)  # 是否摺疊顯示
        }))
	 
    class HeroInfoAdmin(admin.ModelAdmin):
    ...
        # 右側欄過濾器 
        list_filter = ['hbook', 'hgender']
        # 搜索框
        search_fields = ['hname']
2.註冊模型類時將模型類和Admin管理類對應起來
	admin.site.register(BookInfo,BookInfoAdmin)
    admin.site.register(HeroInfo,HeroInfoAdmin)

使用pub_date方法的相關models.py配置:

class BookInfo(models.Model):
    ...
    def pub_date(self):
        return self.bpub_date.strftime('%Y年%m月%d日')
	
    # 設置方法那一列的字段描述
    pub_date.short_description = '出版日期'
    # 讓方法對應的那一列支持排序
    pub_date.admin_order_field = 'bpub_date'

關聯對象

在這裏插入圖片描述

Admin站點標題設置

在admin.py文件中添加一下信息

from django.contrib import admin
admin.site.site_header = 'Monkey-文字LOGO'
admin.site.site_title = '前瞻網絡-網站標題'
admin.site.index_title = '來了老弟!-首頁標語'

Admin站點上傳圖片

打開models.py設置字段

 image = models.ImageField(upload_to='booktest',verbose_name='圖片', null=True)
  • upload_to 選項指明該字段的圖片保存在MEDIA_ROOT目錄中的哪個子目錄

然後進行數據庫遷移

python manage.py makemigrations
python manage.py migrate

使用Admin站點保存圖片,需要安裝Python的圖片操作包

pip install Pillow==4.1.0

指定Admin站點上傳圖片保存的目錄

MEDIA_ROOT=os.path.join(BASE_DIR,"static/media")
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章