django中的路由
django的视图主要有2种,分别是函数视图和类视图.现在刚开始学习django,我们先学习函数视图(FBV),后面再学习类视图[CBV].
Function BaseView 函数基本视图(FBV)
Class BaseView 类基本视图(CBV)
在django中所有的路由最终都被保存到一个变量 urlpatterns.
, urlpatterns必须声明在主应用下的urls.py总路由中。这是由配置文件settings设置的。
在django运行中,当客户端发送了一个http请求到服务端,服务端的web服务器则会从http协议中提取url地址, 从程序内部找到项目中添加到urlpatterns里面的所有路由信息的url进行遍历匹配。如果相等或者匹配成功,则调用当前url对象的视图方法。
在给urlpatterns路由列表添加路由的过程中,django一共提供了2个函数给开发者注册路由
from django.urls import path # 字符串路由 from django.urls import re_path # 正则路由,会把url地址看成一个正则模式与客户端的请求url地址进行正则匹配 # path和re_path 使用参数一致.仅仅在url参数和接收参数时写法不一样
# path("路由url","视图函数","路由别名"), path("index.html4", views.index4,name="index4" ),
from django.urls import path,re_path from . import views urlpatterns = [ # path("路由url","视图函数","路由别名"), re_path("^index7/(?P<id>\d+)/message/(?P<mobile>1[3-9]\d{9})$", views.index7), ]
视图代码中接收路由的参数.
def index7(request, id, mobile): print("id=%s, mobile=%s" % (id,mobile)) print("type(id)=%s, type(mobile)=%s" % (type(id),type(mobile))) return HttpResponse("ok")
django的url路由加斜杠的问题
在django路由中编写url地址时为了快速查找, 建议最好不加上 / 在路由的后面.当用户访问对应视图的路由时,
加不加斜杠, django都能转换到正确的url地址,这个方式虽然好,但是会导致,我们客户端的静态文件的url路径如果是相对路径,则会被django这个做法导致出现路径正确的情况,所以不要加 斜杠。
re_path("goods/(?P<id>\d+)/", views.index3),
路由转换器
也可以叫路由验证器,有2个作用:把路由参数进行类型转换,也可以起到验证路由匹配的作用(简写正则路由)
内置转换器
文档:https://docs.djangoproject.com/zh-hans/3.2/topics/http/urls/#path-converters
常见的内置路由转换器:
str - 匹配除了 '/' 之外的非空字符串。如果表达式内不包含转换器,则会默认匹配字符串。 int - 匹配 0 或任何正整数。返回一个 int 。 slug - 匹配任意由 ASCII 字母或数字以及连字符和下划线组成的短标签。比如,building-your-1st-django-site 。 uuid - 匹配一个格式化的 UUID 。为了防止多个 URL 映射到同一个页面,必须包含破折号并且字符都为小写。比如,075194d3-6885-417e-a8a8-6c931e272f00。返回一个 UUID 实例。 path - 匹配非空字段,包括路径分隔符 '/' 。它允许你匹配完整的 URL 路径而不是像 str 那样匹配 URL 的一部分。
# 路由中使用 urlpatterns = [ path('sms/<int:mobile>', views.send_sms) ]
自定义转换器
在当前子应用下新建converters.py
"""子应用路由""" from django.urls import path,re_path # 路由使用过程中,django提供了2个函数给我们把url和视图进行绑定映射, # django.urls.path("字符串url地址", 视图函数, name="路由别名") # django.urls.re_path("正则字符串url地址", 视图函数, name="路由别名") from . import views # 自定义路由转换器 class MobileConverter(object): regex = "1[3-9]\d{9}" def to_python(self,value): """把路由上面的内容转换成python数据,并转换类型""" # 将匹配结果传递到视图内部时使用 return value def to_url(self,value): # 将匹配结果用于反向解析传值时使用 return value from django.urls import register_converter # register_converter(路由转换器类名, "使用别名") register_converter(MobileConverter, "mob") urlpatterns = [ # 匹配手机号码的路由参数 # re_path("^sms/(?P<mobile>1[3-9]\d{9})$", views.index7), # 把手机的正则路由匹配改写成路由转换器 # 一般负责的正则路由都会把正则路由编写成路由转换器,写在外部文件中,导包引入使用 path("sms/<mob:mobile>", views.index7), ] # 最终用户访问的视图url地址: # url = 总路由的公共url地址 + 子应用路由的uri地址
自定义路由转换器,实际上就是django在对路由进行数据转换和简写正则路由的实现,这种实现方式是基于不同的转换器类来完成,开发者要实现自定义转换器,需要编写的类必须符合官方要求的3个基本要求:
必须声明属性:regex 和 方法:to_python,to_url
这种实现方式,实际就是对编程领域的设计模式的一种应用。
设计模式,前人总结下来的基于固定业务场景的解决方案就是设计模式。
编程中,设计模式有23种不同设计模式。
其中,我们上面这种就是叫 策略模式/接口模式