1. 程式人生 > 其它 >django之路由層詳解

django之路由層詳解

django之路由層

  • 路由層相關知識

    路由匹配
    無名分組
    有名分組
    反向解析
    名稱空間
    路由分發
    

路由層之路由匹配

路由匹配的特點是 只要匹配上了就會立刻結束執行對應的檢視函式
並且url方法的第一個引數其實是一個正則表示式
	只要正則表示式能夠從使用者輸入的字尾中匹配到內容就算匹配上了!
eg:
  正則是test  內容是test 那麼可以匹配出test文字
  正則是test  內容是testadd 那麼還可以匹配出test文字
  都算匹配上了!!!

演變過程
	正則是test/ 內容是test 那麼首次無法匹配
  	# django二次追加斜槓機制
    	首次匹配不上 那麼django還會讓瀏覽器預設加斜槓再次傳送請求
      	test  301
        test/ 200
    '''
    瞭解:斜槓機制可以取消 但是不推薦 
		APPEND_SLASH = False
    '''
 	
  正則是test/ 內容是abcdefgtest/ 那麼可以匹配出文字test/
  	可以在正則的最前面加上上箭頭來限制
  	'''解決路由前面可以隨意亂寫的問題'''
    
  正則是^test/ 內容是test/abc/edf/acd/ 那麼可以匹配出文字test/
  	可以在正則的最後面加上$來限制
    '''解決路由後面可以隨意亂寫的問題'''
# 由於第一個引數是正則 所以當專案特別大 對應關係特別多的時候要格外的注意是否會出現路由頂替的現象
	小擴充套件:
    可以定製一個主頁面 使用者不攜帶字尾可以直接訪問(掌握)
    url(r'^$',views.home)
  	也可以定義一個尾頁 使用者輸入一個沒有對應關係的直接返回(瞭解)
    url(r'.*',views.error)

無名有名分組

url(r'^test/([0-9]{4})/$', views.test)
"""
路由匹配成功之後就會呼叫檢視函式預設情況下會自動給檢視函式傳遞一個request位置引數
	test(request)
如果路由匹配中使用括號對正則表示式進行了分組 那麼在呼叫檢視函式的時候
會將括號內匹配到的內容當做位置引數傳遞給檢視函式
	test(request,括號內正則表示式匹配到的內容)
	
上述特性django稱之為'無名分組'
"""

url(r'^testadd/(?P<user_id>[0-9]{4})$', views.testadd)
"""
給括號內的正則表示式起別名之後 匹配成功則會講括號內匹配到的內容按照關鍵字引數傳遞給檢視函式
	testadd(request,user_id=括號內正則表示式匹配到的內容)

上述特性django稱之為'有名分組'
"""

# 兩者是否可以混合使用
	url(r'^test/(\d+)/(?P<user_id>[0-9]{4})/$', views.testadd)  # 不可以
  無名有名分組不能混合使用!!! 單個可以重複使用
	url(r'^test/(\d+)/(\d+)/$', views.testadd)   # 可以
  url(r'^test/(?P<a>\d+)/(?P<b>\d+)',views.testadd)  # 可以

反向解析

"""
a標籤的href可以寫網址的全稱 也可以寫字尾
	href='https://www.baidu.com'
	href='/login/'  # 自動補全當前服務的ip和port
		href='127.0.0.1:8000/login/'
"""
1.頁面上有很多a標籤連結了其他路由
2.路由匹配表示式出現了變化 html頁面上的地址全部失效

# 反向解析
	通過反向解析可以獲取到一個結果 該結果可以訪問到一個路由

  步驟1:給對應關係起別名
    url(r'^func666/',views.func,name='func_view')
  步驟2:使用反向解析獲取結果
    前端:
      	{% url 'func_view' %}  # func666/ 結果可以訪問路由
    後端:
      	from django.shortcuts import reverse
      	reverse('func_view')  # func666/ 結果可以訪問路由
# 無名分組反向解析
	步驟1:給對應關係起別名
    url(r'^func666/(\d+)/',views.func,name='func_view')
  步驟2:使用反向解析獲取結果
    '''無法明確括號內正則表示式的內容 需要人為指定'''
    前端:
      	{% url 'func_view' 123 %}  # func666/123/
    後端:
      	from django.shortcuts import reverse
      	reverse('func_view',args=(666,))  # func666/666/
# 有名分組反向解析
	步驟1:給對應關係起別名
    url(r'^func666/(?P<id>\d+)/',views.func,name='func_view')
  步驟2:使用反向解析獲取結果
    '''無法明確括號內正則表示式的內容 需要人為指定'''
    前端:
      	{% url 'func_view' 123 %}  # func666/123/
        {% url 'func_view' id=123 %}  # func666/123/
    後端:
      	from django.shortcuts import reverse
      	reverse('func_view',args=(666,))  # func666/666/
        reverse('func_view',kwargs={'id':1})  # func666/1/
        
"""
疑問:無名有名反向解析中的手動傳值 這個值在實際工作中到底可以是什麼
	一般情況下這個值可以是資料的主鍵值、頁面的頁碼、區域的編號等
"""

路由分發

"""
如果一個django專案特別龐大 裡面有很多應用 每個應用下有很多對應關係 
那麼django自帶的路由層裡面的程式碼就會非常非常的多 如何優化???
	根據應用的不同拆分到不同的應用中

django支援每個應用都可以有自己獨立的
		路由層、模板層、靜態檔案、檢視層(預設)、模型層(預設)
		
上述特效能夠讓django在分組開發上更加的方便、快捷
	所有人都可以在應用中開發完整的專案功能
	最後彙總到一個空的django專案中 然後通過路由分發整合所有人的應用
"""
1.建立多個應用 並去配置檔案中註冊
	INSTALLED_APPS = [
    'app01',
    'app02'
]
2.在多個應用中編寫相同的路由
  urlpatterns = [
    url(r'^index/',views.index111)
]
	urlpatterns = [
    url(r'^index/',views.index)
]
3.路由分發
	總路由
  from django.conf.urls import url, include
  from app01 import urls as app01_urls
	from app02 import urls as app02_urls
  url(r'^app01/',include(app01_urls)),
  url(r'^app02/',include(app02_urls))
  """總路由只負責分發 不負責檢視函式對應"""
  上述程式碼還可以簡寫
  from django.conf.urls import url, include
  url(r'^app01/',include('app01.urls')),
  url(r'^app02/',include('app02.urls'))

名稱空間

1.不同的應用使用了相同的別名 那麼反向解析是否自動識別
	index_view				app01/index/
  index_view				app02/index/
2.驗證發現預設情況下是不會自動識別應用字首的 如何解決反向解析問題
	方式1:名稱空間
    	總路由新增名稱空間
    url(r'^app01/',include('app01.urls',namespace='app01')),
    url(r'^app02/',include('app02.urls',namespace='app02'))
    	應用反向解析自動提示
      	reverse('app01:index_view')
        reverse('app02:index_view')
        {% url 'app01:index_view' %}
        {% url 'app02:index_view' %}
  方式2:只需要確保反向解析的別名在整個專案中不重複即可!!!
    	可以在別名的前面加上應用名的字首
      	url(r'^index/',views.index,name='app01_index_view')
        url(r'^index/',views.index,name='app02_index_view')
"""
名稱空間其實是可有可無的知識 但是在實際工作中還是有不少程式設計師喜歡使用
"""