精通Django(一)

Djang學習筆記

一、基本配置

  • 1、在建立django項目後,如果要配置mysql服務器,應該先進入虛擬環境安裝mysql驅動

    pip install mysqlclient
    
  • 2、在配置DATABASES時,應有如下:

    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',
            'NAME': "django_test",
            'USER': "root",
            'PASSWORD': "123456",
            'HOST': "127.0.0.1",
        }
    }
    
  • 3、設置時區:

    # 設置時區
    LANGUAGE_CODE = 'zh-hans'  # 中文支持,django1.8以後支持;1.8以前是zh-cn
    
    TIME_ZONE = 'Asia/Shanghai'
    
    USE_I18N = True
    
    USE_L10N = True
    
    USE_TZ = False   # 默認是Ture,時間是utc時間,由於我們要用本地時間,所用手動修改爲false!!!!
    

二、MVC設計模式

2.1 MVC 設計模式非常容易理解:

  • 模型(M)是數據的表述。它不是真正的數據,而是數據的接口。使用模型從數據庫中獲取數據時,
    無需知道底層數據庫錯綜複雜的知識。模型通常還會爲數據庫提供一層抽象,這樣同一個模型就能使
    用不同的數據庫。
  • 視圖(V)是你看到的界面。它是模型的表現層。在電腦中,視圖是你在瀏覽器中看到的 Web 應用的
    頁面,或者是桌面應用的 UI。視圖還提供了收集用戶輸入的接口。
  • 控制器(C)控制模型和視圖之間的信息流動。它通過程序邏輯判斷通過模型從數據庫中獲取什麼信
    息,以及把什麼信息傳給視圖。它還通過視圖從用戶那裏收集信息,並且實現業務邏輯:變更視圖,
    或者通過模型修改數據,或者二者兼具。

2.2 MTV 開發模式:(Django 經常被稱爲 MTV 框架)

  • M 表示“模型”,即數據訪問層。這一層包含所有與數據相關的功能:訪問數據的方式、驗證數據的方
    式、數據的行爲、數據之間的關係。
  • T 表示“模板”,即表現層。這一層包含表現相關的決策:在網頁或其他文檔類型中如何顯示某個東
    西。
  • V 表示“視圖”,即業務邏輯層。這一層包含訪問模型和選擇合適模板的邏輯。你可以把視圖看做模型
    和模板之間的橋樑。

三、視圖和URL配置

3.1第一個 Django 驅動的頁面:Hello World

  • 第一個視圖:靜態

    # 新建一個空文件,名爲 views.py 。這個模塊用於保存本章編寫的視圖。生成“Hello World”的視圖很簡單。下面是完整的視圖函數,以及導入語句。把下述代碼輸入到 views.py 文件中.
    from django.http import HttpResponse
    
    def hello(request):
    	return HttpResponse("Hello world")  # 視圖函數至少有一個參數
    
  • 第一個 URL 配置:

      from django.conf.urls import include, url
        from django.contrib import admin
        urlpatterns = [
            url(r'^admin/', include(admin.site.urls)),
        ]

<!--正則表達式字符串前面的 'r' 字符。它的目的是告訴 Python,那是“原始字符串”,不要解釋裏面的反斜線.   Python 中的反斜線與正則表達式中的反斜線有衝突,因此在 Django 中定義正則表達式時最好使用原始字符
串。大多數 URL 模式都以脫字符號開頭、以美元符號結尾,不過可以靈活使用,匹配複雜的 URL。
-->

3.2 正則表達式

符號 匹配的內容
\d 單個數字
. (點號) 單個字符
[A-Z] A-Z(大寫)之間的單個字母
[a-z] a-z(小寫)之間的單個字母
[A-Za-z] a-z(不區分大小寫)之間的單個字母
+ 一個或多個前述表達式(例如, \d+ 匹配一個或多個數字)
[ˆ/]+ 一個或多個字符,直到遇到斜線(不含)
? 零個或一個前述表達式(例如, \d? 匹配零個或一個數字)
* 零個或多個前述表達式(例如, \d* 匹配零個、一個或多個數字)

| {1,3} | 介於一個到三個之間(含)的前述表達式(例如, \d{1,3} 匹配一個、兩個或三個

數字) |

3.3 關於404錯誤的簡要說明

  • 現在,URL 配置只定義了一個 URL 模式,即處理 /hello/ URL 請求的那個。那麼,如果請求其他 URL 會發生什麼呢?爲了查明,啓動 Django 開發服務器,然後訪問 http://127.0.0.1:8000/goodbye/ 。你應該會看到“Page not found”消息。Django 之所以顯示這個消息,是因爲 URL 配置中沒有定義你請求的 URL。
  • 這些是敏感信息,只供 Web 開發者查看。線上網站不應該公開顯示這些信息。鑑於此,“Page not
    found”頁面僅當 Django 項目處於調試模式時纔會顯示。

3.4 Django 處理請求的過程

  • 運行 python manage.py runserver 命令時, manage.py 腳本在內層 mysite 目錄中尋找名爲 settings.py 的文件。這個文件中保存着當前 Django 項目的全部配置,各個配置的名稱都是大寫的,例如 TEMPLATE_DIRS 、DATABASES ,等等。其中最重要的設置是 ROOT_URLCONF 。它告訴 Django,網站的 URL 配置在哪個 Python 模塊中。
    1. 請求 /hello/ 。
    1. Django 查看 ROOT_URLCONF 設置,找到根 URL 配置。
    1. Django 比較 URL 配置中的各個 URL 模式,找到與 /hello/ 匹配的那個。
    1. 如果找到匹配的模式,調用對應的視圖函數。
    1. 視圖函數返回一個 HttpResponse 對象
    1. Django 把 HttpResponse 對象轉換成正確的 HTTP 響應,得到網頁

3.5 URL 配置和鬆耦合

  • 鬆耦合是一種軟件開發方式,其價值在於讓組件可以互換。如果兩部分代碼之間是鬆耦合的,那麼改動其中一部分對另一部分的影響很小,甚至沒有影響。
  • 在 Django Web 應用中,URL 定義與所調用的視圖函數之間是鬆耦合的,即某個功能使用哪個 URL 與視圖函數的實現本身放在兩個地方。
  • 例:
    • 以 current_datetime 視圖爲例。如果想把這個功能對應的 URL 從 /time/ 移到 /current-time/ ,只需修改URL 配置,視圖則不用動。同樣,對視圖函數的邏輯所做的修改對開放這一功能的 URL 沒有影響。此外,如果想在多個 URL 上開放當前日期功能,可以編輯 URL 配置,而無需改動視圖代碼。

3.6 視圖:動態URL

  • 通配 URL 模式

  • 例:匹配1位或2位數字

    urlpatterns = [
    # ...
    url(r'^time/plus/\d{1,2}/$', hours_ahead),
    # ...
    ]
    

四、Django 模板

4.1 模板系統基礎

  • Django 模板是一些文本字符串,作用是把文檔的表現與數據區分開。模板定義一些佔位符和基本的邏輯(模
    板標籤),規定如何顯示文檔。通常,模板用於生成 HTML,不過 Django 模板可以生成任何基於文本的格
    式。
  • Django 模板能訪問多個內置的標籤和過濾器。

4.2 使用模板系統

  • 若想在 Python 代碼中使用 Django 的模板系統,基本方式如下:

    • 1.以字符串形式提供原始的模板代碼,創建 Template 對象。

      1. 在 Template 對象上調用 render() 方法,傳入一系列變量(上下文)。返回的是完全渲染模板後得到
        的字符串,模板中的變量和模板標籤已經根據上下文求出值了。
  • “塊級標籤”和“模板標籤”是同一個事物。遇到下述各種情況時,模板系統都會拋出 TemplateSyntaxError :

    • 無效標籤
    • 有效標籤的無效參數
    • 無效過濾器
    • 有效過濾器的無效參數
    • 無效模板句法
    • 未關閉的標籤(對需要結束標籤的模板標籤而言)
  • 例:

    from django.template import Context, Template
    
    t = Template('My name is {{ name }}.')   # 創建對象
    c = Context({'name': 'Stephane'})	## 渲染對象
    print(t.render(c))   # 'My name is Stephane.'	# 調用render()方法輸出
    
  • Django 解析模板的速度相當快。在背後,解析的大部分工作通過調用一個正則表達式完成。這與基於 XML
    的模板系統有顯著區別,XML 解析器會帶來額外的消耗,從而導致渲染速度比 Django 的模板渲染引擎慢幾
    個數量級。

  • 模板系統能優雅處理很多複雜的數據結構,例如列表、字典和自定義的對象。

  • 遍歷Django模板中複雜數據結構的關鍵是點號(.)。點號可以訪問字典的鍵、屬性、方法或對象的索引。

  • 總結起來,模板系統遇到變量名中的點號時會按照下述順序嘗試查找:

    • 字典查找(如 foo[“bar”] )
    • 屬性查找(如 foo.bar )
    • 方法調用(如 foo.bar() )
    • 列表索引查找(如 foo[2]
  • 例:假如我們把一個 Python 字典傳給模板。若想通過鍵訪問那個字典中的值,要使用點號:

    from django.template import Template, Context
    
    person = {'name': 'Sally', 'age': '43'}
    t = Template('{{ person.name }} is {{person.age}} years old.')
    c = Context({'person': person})
    print(t.render(c))  # 'Sally is 43 years old.
    

4.3 基本的模板標籤和過濾器

  • 4.3.1標籤:

    • if/else:

      {% if %} 計算變量的值,如果爲真(即存在、不爲空,不是假值),模板系統顯示 {% if %}{% endif %}之間的內容。
      
      例如:
      1. {% if today_is_weekend %}
      	<p>Welcome to the weekend!</p>
      {% endif %}
      
      2. {% else %} 標籤是可選的:
          {% if today_is_weekend %}
         		 <p>Welcome to the weekend!</p>
          {% else %}
        		 <p>Get back to work.</p>
          {% endif %}
          
      3. if 標籤還可以有一個或多個 {% elif %} 子句:
          {% if athlete_list %}
          	Number of athletes: {{ athlete_list|length }}
          {% elif athlete_in_locker_room_list %}
        	     <p>Athletes should be out of the locker room soon! </p>
          {% elif ...
          ...
          {% else %}
         		 <p>No athletes. </p>
          {% endif %}
           
      4. {% if %} 支持使用 andornot 測試多個變量,或者取反指定的變量。例如:
          {% if athlete_list and coach_list %}
          	<p>Both athletes and coaches are available. </p>
          {% endif %}
          {% if not athlete_list %}
          	<p>There are no athletes. </p>
          {% endif %}
          {% if athlete_list or coach_list %}
         		<p>There are some athletes or some coaches. </p>
          {% endif %}
          {% if not athlete_list or coach_list %}
          	<p>There are no athletes or there are some coaches. </p>
          {% endif %}
          {% if athlete_list and not coach_list %}
          	<p>There are some athletes and absolutely no coaches. </p>
          {% endif %}
      5. 在同一個標籤中可以同時使用 andor ,此時, and 的優先級比 or 高。例如:
      	{% if athlete_list and coach_list or cheerleader_list %}
      
      6. 如果需要通過括號指明優先級,應該使用嵌套的 if 標籤。不支持使用括號控制操作的順序。如果覺得有必要使用括號,可以考慮在模板外部執行邏輯,然後通過專用的模板變量傳入結果.或者,直接使用嵌套的 {%
      if %} 標籤,
      如下所示:
          {% if athlete_list %}
          {% if coach_list or cheerleader_list %}
          <p>We have athletes, and either coaches or cheerleaders! </p>
          {% endif %}
          {% endif %}
      
      7. 每個 {% if %} 都必須有配對的 {% endif %}
      
      
    • for:

      {% for %} 標籤用於迭代序列中的各個元素。與 Python 的 for 語句一樣,句法是 for X in Y ,其中 Y 是要迭代的序列, X 是單次循環中使用的變量。每次迭代時,模板系統會渲染 {% for %}{% endfor %} 之間的內容。
      例如,可以使用下述模板顯示 athlete_list 變量中的運動員:
          <ul>
              {% for athlete in athlete_list %}
              	<li>{{ athlete.name }}</li>
              {% endfor %}
          </ul>
       
      
      在標籤中添加 reversed ,反向迭代列表:
          {% for athlete in athlete_list reversed %}
          ...
          {% endfor %}
          
          
      {% for %} 標籤可以嵌套:
          {% for athlete in athlete_list %}
          	<h1>{{ athlete.name }}</h1>
          	<ul>
                  {% for sport in athlete.sports_played %}
                 		 <li>{{ sport }}</li>
                  {% endfor %}
         		</ul>
          {% endfor %}
              
      如果需要迭代由列表構成的列表,可以把每個子列表中的值拆包到獨立的變量中。
      比如說上下文中有一個包含 (x,y) 座標點的列表,名爲 points ,可以使用下述模板輸出這些座標點:
          {% for x, y in points %}
              <p>There is a point at {{ x }},{{ y }}</p>
          {% endfor %}
      
      
      如果需要訪問字典中的元素,也可以使用這個標籤。如果上下文中包含一個字典 data ,可以使用下述模板顯
      示字典的鍵和值:
          {% for key, value in data.items %}
         		 {{ key }}: {{ value }}
          {% endfor %}
      
      
      通常,迭代列表之前要先檢查列表的大小,如果爲空,顯示一些特殊的文字:
          {% if athlete_list %}
          	{% for athlete in athlete_list %}
          		<p>{{ athlete.name }}</p>
          	{% endfor %}
          {% else %}
          	<p>There are no athletes. Only computer programmers.</p>
          {% endif %}
      
      這種做法太常見了,因此 for 標籤支持一個可選的 {% empty %} 子句,用於定義列表爲空時顯示的內容。下
      述示例與前一個等效:
          {% for athlete in athlete_list %}
          	<p>{{ athlete.name }}</p>
          {% empty %}
          	<p>There are no athletes. Only computer programmers.</p>
          {% endfor %}
          
      在循環結束之前,無法“跳出”。如果需要這麼做,修改要迭代的變量,只包含需要迭代的值。
      同樣,也沒有“continue”語句,不能立即返回到循環的開頭。
      
    • ifqual / ifnotequal:

      1. 模板經常需要比較兩個值,在相等時顯示一些內容。爲此,Django 提供了 {% ifequal %} 標籤。
      {% ifequal %} 標籤比較兩個值,如果相等,顯示 {% ifequal %}{% endifequal %} 之間的內容。下述示例
          比較模板標籤 user 和 currentuser :
          {% ifequal user currentuser %}
          	<h1>Welcome!</h1>
          {% endifequal %}
      2.{% if %} 一樣, {% ifequal %} 標籤支持可選的 {% else %} 子句:
          {% ifequal section 'sitenews' %}
          	<h1>Site News</h1>
          {% else %}
          	<h1>No News Here</h1>
          {% endifequal %}
      3. {% ifequal %} 的參數只能是模板變量、字符串、整數和小數。其他變量類型,例如 Python 字典、列表或布爾值,不能在 {% ifequal %} 中硬編碼。
      4. {% ifnotequal %} 的作用與 ifequal 類似,不過它測試兩個參數是否不相等。 ifnotequal 標籤可以替換成 if標籤和 != 運算符。
      
    • 註釋:

      1. 註釋使用 {# #} 標明:{# This is a comment #} 渲染模板時,不輸出註釋。使用這種句法編寫的註釋不能分成多行。這一限制有助於提升模板解析性能。
      2. 如果想編寫多行註釋,使用 {% comment %} 模板標籤,如下所示:
          {% comment %}
          	This is a
          	multi-line comment.
          {% endcomment %}
      3. 註釋標籤不能嵌套。
      
  • 4.3.2 過濾器:

    • 模板過濾器是在顯示變量之前調整變量值的簡單方式。過濾器使用管道符號指定,如下所
      示:{{ name|lower }}
    • 下面是幾個最重要的過濾器。
      • ddslashes :在反斜線、單引號和雙引號前面添加一個反斜線。可用於轉義字符串。例如: {{ val-
        ue|addslashes }} 。
      • date :根據參數中的格式字符串格式化 date 或 datetime 對象。例如: {{ pub_date|date:“F j, Y”
        }} 。
      • length :返回值的長度。對列表來說,返回元素的數量。對字符串來說,返回字符的數量。如果變量
        未定義,返回 0

4.4 模板加載機制

  • 爲了從文件系統中加載模板,Django 提供了便利而強大的 API,力求去掉模板加載調用和模板自身的冗餘。若想使用這個模板加載 API,首先要告訴框架模板的存儲位置。這個位置在設置文件中配置,即前一章介紹ROOT_URLCONF 設置時提到的 settings.py 文件。打開 settings.py 文件,找到 TEMPLATES 設置。它的值是一個列表,分別針對各個模板引擎:

    TEMPLATES = [
        {
            'BACKEND': 'django.template.backends.django.DjangoTemplates',
            'DIRS': [],
            'APP_DIRS': True,
            'OPTIONS': {
            # ... 一些選項 ...
        	},
        },
    ]
    
    • BACKEND 的值是一個點分 Python 路徑,指向實現 Django 模板後端 API 的模板引擎類。內置的後端有 djan-go.template.backends.django.DjangoTemplates 和 django.template.backends.jinja2.Jinja2 。
    • 因爲多數引擎從文件中加載模板,所以各個引擎的頂層配置包含三個通用的設置:
      • DIRS 定義一個目錄列表,模板引擎按順序在裏面查找模板源文件。
      • APP_DIRS 設定是否在安裝的應用中查找模板。按約定, APPS_DIRS 設爲 True 時, DjangoTemplates 會在INSTALLED_APPS 中的各個應用裏查找名爲“templates”的子目錄。這樣,即使 DIRS 爲空,模板引擎還能查找應用模板。
      • OPTIONS 是一些針對後端的設置。同一個後端可以配置具有不同選項的多個實例,然而這並不常見。此時,要爲各個引擎定義唯一的 NAME 。

4.5 render

下面是使用 render() 重寫的 current_datetime 視圖:
from django.shortcuts import render
import datetime
def current_datetime(request):
	now = datetime.datetime.now()
	return render(request, 'current_datetime.html', {'current_date': now})

差別多麼明顯啊!下面詳細說明這次改動:
• 不用再導入 get_template 、 Template 、 Context 或 HttpResponse 了,而要導入 django.shortcuts.ren-der 。 import datetime 不變。
• 在 current_datetime 函數中,仍然要計算 now ,不過加載模板、創建上下文、渲染模板和創建 HttpRe-
sponse 對象全由 render() 調用代替了。 render() 的返回值是一個 HttpResponse 對象,因此在視圖中
可以直接返回那個值。render() 的第一個參數是請求對象,第二個參數是模板名稱,第三個單數可選,是一個字段,用於創建傳給模板的上下文。如果不指定第三個參數, render() 使用一個空字典。

4.6 include模板標籤

  • 內置模板標籤了: {% include %} 。這個標籤的作用是引入另一個模板的內容。它的參數是要引入的模板的名稱,可以是變量,也可以是硬編碼的字符串(放在引號裏,單雙引號都行)。只要想在多個模板中使用相同的代碼,就可以考慮使用 {% include %} ,去除重複。
  • include 標籤的參數指定的模板在當前 Django 應用的“templates”目錄中( APPS_DIR 爲 True 時),或者在 DIRS 設置的目錄中。引入的模板在引入它的模板的上下文中執行。
  • 如果 {% include %} 標籤的參數指定的模板不存在,Django 會做下面兩件事中的一件:
    • DEBUG 爲 True 時,渲染 Django 錯誤頁面,顯示 TemplateDoesNotExist 異常。
    • DEBUG 爲 False 時,靜默,那個標籤的位置什麼也不顯示。

4.7 模板繼承

  • 繼承經常使用下述三層結構:

    1. 創建 base.html 模板,定義網站的整體外觀。這個模板的內容很少變化。

    2. 爲網站中的各個“區域”創建 base_SECTION.html 模板(如 base_photos.html 和 base_forum.html )。這些模板擴展 base.html ,包含各區域專屬的樣式和設計。

    3. 爲各種頁面創建單獨的模板,例如論壇頁面或相冊。這些模板擴展相應的區域模板。
      這種方式能最好地複用代碼,而且便於爲共享的區域添加內容,例如同一個區域通用的導航。

  • 下面是使用模板繼承的一些指導方針:

    • 如果模板中有 {% extends %} ,必須是模板中的第一個標籤。否則,模板繼承不起作用。
    • 一般來說,基模板中的 {% block %} 標籤越多越好。記住,子模板無需定義父模板中的全部塊,因此
      可以爲一些塊定義合理的默認內容,只在子模板中覆蓋需要的塊。鉤子多總是好的。
    • 如果發現要在多個模板中重複編寫相同的代碼,或許說明應該把那些代碼移到父模板中的一個 {%
      block %} 標籤裏。
    • 如果需要從父模板中的塊裏獲取內容,使用 {{ block.super }} ,這是一個“魔法”變量,提供父模板中
      渲染後的文本。向塊中添加內容,而不是完全覆蓋時就可以這麼做。
    • 在同一個模板中不能爲多個 {% block %} 標籤定義相同的名稱。之所以有這個限制,是因爲 block 標
      籤是雙向的。即, block 標籤不僅標識供填充的空位,還用於定義填充父模板中空位的內容。如果一
      個模板中有兩個同名的塊,那麼父模板就不知道使用哪個塊裏的內容。
    • 傳給 {% extends %} 的模板名稱使用與 get_template() 相同的方法加載。即,模板在 DIRS 設置定義的
      目錄中,或者在當前 Django 應用的“templates”目錄裏。
    • 多數情況下, {% extends %} 的參數是字符串,不過如果直到運行時才知道父模板的名稱,也可以用變
      量。通過這一點可以做些動態判斷。

4.8 Django的核心

  • Django 的核心:
    1. 表現與邏輯分離
    2. 避免重複
    3. 與 HTML 解耦
    4. XML 不好
    5. 不要求具備設計能力
    6. 透明處理空格
    7. 不重造一門編程語言
    8. 確保安全有保障
    9. 可擴展

五、Django模型

  • Django 非常適合構建數據庫驅動型網站,它提供了簡單而強大的工具,易於使用 Python 執行數據庫查詢。

5.1配置數據庫

# 在 settings.py 文件中添加的初始配置:
DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',
        'NAME': "django_test",
        'USER': "root",
        'PASSWORD': "123456",
        'HOST': "127.0.0.1",
    }
}

5.2 使用Python定義模型

  • Django 模型是使用 Python 代碼對數據庫中數據的描
    述,是數據的結構,等效於 SQL 中的 CREATE TABLE 語句,不過是用 Python 代碼而非 SQL 表述的,而且不僅包含數據庫列的定義。Django 通過模型在背後執行。

  • 使用 Python 代替 SQL 定義數據模型是不是多此一舉?????????

    • Django 之所以這麼做有幾個原因:
      • 內省(introspection)有開銷,而且不完美。爲了提供便利的數據訪問 API,Django 需要以某種方式知曉數據庫佈局,而這一需求有兩種實現方式。第一種是使用 Python 明確描述數據,第二種是在運行時內省數據庫,推知數據模型。第二種方式在一個地方存儲表的元數據,看似更簡單,其實會導致幾個問題。首先,運行時內省數據庫肯定有消耗。如果每次執行請求,或者只是初始化 Web 服務器都要內省數據庫,那帶來的消耗是無法接受的。(有些人覺得那點消耗不算事,然而 Django 的開發者可是在想方設法努力降低框架的消耗。)其次,有些數據庫,尤其是舊版 MySQL,存儲的元數據不足以完成內省。
      • Python 編寫起來讓人心情舒暢,而且使用 Python 編寫所有代碼無需頻繁讓大腦切換情境。
        在一個編程環境(思維)中待久了,有助於提升效率。在 SQL 和 Python 之間換來換去容易打斷狀
        態。
      • 把數據模型保存在代碼中比保存在數據庫中易於做版本控制,易於跟蹤數據佈局的變化。
      • SQL 對數據佈局的元數據只有部分支持。例如,多數數據庫系統沒有提供專門表示電子郵件地址或
        URL 的數據類型。而 Django 模型有。高層級的數據結構有助於提升效率,讓代碼更便於複用。
      • 不同數據庫平臺使用的 SQL 不一致。分發 Web 應用程序時,更務實的做法是分發一個描述數據佈局的 Python 模塊,而不是分別針對MySQL、PostgreSQL 和 SQLite 的 CREATE TABLE 語句。
  • 缺點:模型的 Python 代碼可能與數據庫的真正結構脫節。如果修改了 Django 模型,還要在數據庫中做相同的改動,讓數據庫與模型保持一致。

5.3 基本的數據訪問

  • 添加模型的字符串表示形式

  • 插入和更新數據

  • 選擇對象

    • 查找數據時,Django 使用的不是 SELECT * ,而是把所有字段列出來。
  • 過濾數據

    • 在 Django API 中,可以使用 filter() 方法過濾數據。
  • 檢索單個對象

    • 上述 filter() 示例都返回一個查詢集合(可視作列表)。有時,較之列表,更適合獲取單個對象。此時應該使用 get() 方法:

    • 這個方法只返回一個對象,而不是一個列表(更確切地說是查詢集合)。因此,得到多個對象的查詢會導致異常。

    • 不返回對象的查詢也導致異常。

  • 排序數據

    • 在 Django 應用程序中,你可能想根據特定值排序結果,例如按字母表順序。爲此,使用 order_by() 方法。

       Publisher.objects.order_by("address")
      
    • 如果想根據多個字段排序(以第一個字段排不出順序時使用第二個字段),提供多個參數。

       Publisher.objects.order_by("state_province", "address")
      
    • 可以反向排序。方法是在字段名稱前面加上“-”(減號):

      Publisher.objects.order_by("-name")
      
    • 雖然 order_by() 有一定的靈活性,但是每次都調用它相當繁瑣。多數時候,我們始終使用同一個字段排序。此時,可以在模型中指定默認排序:

      class Meta:
      	ordering = ['name']
      
  • 鏈式查找

     # 過濾、排序一起做,鏈式捆綁
        Publisher.objects.filter(country="U.S.A.").order_by("-name")
    
  • 切片數據

    • 只查找固定數量的行。假如數據庫中有幾千個出版社記錄,但是隻想顯示第一個。爲
      此,可以使用 Python 標準的列表切片句法:

       Publisher.objects.order_by('name')[0]
      
    • 注意,不支持使用負數。

  • 在一個語句中更新多個對象

    • update() 方法有返回值,是一個整數,表示修改的記錄數量
    • update() 方法可以在任何 QuerySet 對象上調用,這意味着可以通過它批量編輯多個記錄。
  • 刪除對象

    • 若想從數據庫中刪除一個對象,只需在對象上調用 delete() 方法

六、Django管理後臺

6.1 使用Django管理後臺

  • 啓動開發服務器:
    啓動開發服務器
  • 進入管理後臺:

進入管理後臺

6.2 把模型添加到Django管理後臺中

  • 在admin.py下輸入:
from django.contrib import admin
from .models import Publisher, Auther, Book
# Register your models here.
admin.site.register(Publisher)
admin.site.register(Auther)
admin.site.register(Book)

  • 頁面顯示加入:
    加入後臺

6.3 把字段設爲可選的

  • 在管理後臺中操作一會之後,你可能會發現有個侷限:編輯表單要求填寫每個字段,而有時候某些字段需要是可選的。添加 blank=True 參數
  • 例:

字段設爲可選

  • 這個參數告訴 Django,作者的電子郵件地址允許爲空值。默認情況下,所有字段都設定了 blank=False ,意即不允許爲空值。
  • 如果想讓日期字段(如 DateField 、 TimeField 、 DateTimeField )或數值字段(如IntegerField 、 DecimalField 、 FloatField )接受空值,要同時添加 null=True 和 blank=True 。
  • 基於一些原因,Django 不會試圖自動修改數據庫模式,所以每次對模型做這種修改之後要自己動手執行 migrate 命令。

6.4 自定義字段的標註

  • 模型建立時增加:verbose_name=u"*****"

6.5 自定義ModelAdmin類

  • 目前我們所做的改動,添加 blank=True 、 null=True 和 verbose_name ,修改的其實都是模型層,只是碰巧管理後臺有用到,還未涉及管理後臺自身。除此之外,Django 管理後臺也提供了豐富的選項,可以定製處理具體模型的方式。這些選項在 ModelAdmin類中,這些類包含特定管理後臺實例中特定模型的配置。
  • 自定義修改列表
  • 自定義編輯表單

6.6 用戶、分組和權限

  • 編輯用戶和權限的權限也由權限系統控制。如果爲某人賦予編輯用戶的權限,他就能編輯自己的權限——這可能不是你想要的行爲!給用戶賦予編輯用戶的權限,其實就相當於把他變成超級用戶。
  • 用戶還可以分組。一個分組中的所有成員都有那一組具有的全部權限。使用分組便於爲多個用戶賦予相同的權限。


  • 此文章根據書籍《精通Django》學習整理
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章