url函数详解
url()函数在urls.py文件中可以说是最重要的函数,属于核心。主要功能就是利用正则表达式匹配对应的url并且指明处理函数。下面详细讲解这部分的应用。我们从参数着手,先讲解基础用法,然后在用示例展示一些高级用法。
url有四个参数,分别是两个必选参数:regex、view和两个可选参数:kwargs、name。下面分别介绍。
regex
regex代表一个正则表达式,凡是与regex匹配的URL请求都会执行到url()函数中对应的第二个参数view代表的视图函数中。需要注意的是:正则表达式不会匹配URL中的域名和查询参数,如:http://192.168.1.10:8000/article/?page=1,Django只找article/。正则表达式在URLconf模块加载时就编译好了,所以在匹配的时候速度是很快的。
正则表达式中遇到的一些情况:
1. 正则表达式字符串的开头字母“r”。它告诉Python这是个原始字符串,不需要处理里面的反斜杠(转义字符)。在普通Python字符串中,反斜杠用于特殊字符的转义。当你用r把它标示为一个原始字符串后,Python不再视其中的反斜杠为转义字符。
2. url中常用的正则表达式符号:除了^ 和 $ 表示以开头和结尾外还有一些正则表达式符号可能会用到:
view
Django匹配正则表达式成功后,就会找到相应的视图函数进行处理。这个函数通常写在views中,关于views的详细内容我们后面会views部分还会讲解。
kwargs
kwargs就是一个字典类型的参数,它的使用方式如:
url(r'^archive /(d{4})/$', archive, {'dict':True}),
这里的kwargs 就是{'summary': True},可以直接向视图函数对应的传参,相当于字典方式传参。另外还有一种方式为位置传参,即(d{4})的部分。注意第一个括号中的内容会传给视图函数的第二个参数(第一个是request),第二个括号部分传给第三个,以此类推。
视图函数中就是这样使用接收相应参数:
def archive(request, archive_id, dict):
name
name是为了提高模版的灵活性。Djangotemplate中经常会有一些url的标识,如: <a href="/login"class="head">请登录<span>|</span></a> 这种硬编码的方式,模版难以维护。内建标签url,{% url path.to.some_view%}可以返回视图函数对应的URL(相对域名的绝对路径),比如url(r^/account/$’, views.index, name=index),使用{% url view.index%}将返回/accout/,这样做可以方便修改。
Include的使用
Include函数对应返回值可以用作url函数的第二个参数,作为url的引用。例如:
# urls.py
from django.conf.urls import *
urlpatterns = patterns('',
(r'^blog/', include('myapp.urls')),
)
表示url blog/ 对应的转入inner函数继续进行url处理,通常就是我们所说的app内的url文件
#app内urls.py
from django.conf.urls import *
urlpatterns = patterns('',
(r'^archive/$', 'mysite.views.archive'), 对应的url实际是 blog/archive/
(r'^about/$', 'mysite.views.about'),
(r'^rss/$', 'mysite.views.rss'),
)
如果在上一层url加入第三个参数字典,则表示在其下一层所有的url中都加入此字典,如下两个代码等价:
第一个:
# urls.py
from django.conf.urls.defaults import *
urlpatterns = patterns('',
(r'^blog/', include('inner'), {'blogid': 3}),
)
# inner.py
from django.conf.urls.defaults import *
urlpatterns = patterns('',
(r'^archive/$', 'mysite.views.archive'),
(r'^about/$', 'mysite.views.about'),
(r'^rss/$', 'mysite.views.rss'),
)
第二个
# urls.py
from django.conf.urls.defaults import *
urlpatterns = patterns('',
(r'^blog/', include('inner')),
)
# inner.py
from django.conf.urls.defaults import *
urlpatterns = patterns('',
(r'^archive/$', 'mysite.views.archive', {'blogid': 3}),
(r'^about/$', 'mysite.views.about', {'blogid': 3}),
(r'^rss/$', 'mysite.views.rss', {'blogid': 3}),
)
如果在上一层想表达什么都不匹配直接进入下一层匹配的时候用如下代码:
(r'^', include('myapp.urls')), 即相当于直接匹配app中url对应的正则表达式匹配
)
调试模式
在url中经常用到一些调试模式,决定有些url是否执行:
if settings.DEBUG:
urlpatterns += patterns('',
(r'^debuginfo/$', views.debug),
)
重用命名组
上面我们讲到向视图函数中传参,位置传参不需要指定视图函数中参数的名称,但是通过下面的用法P?<参数名> 的方式可以强行指定视图函数中必须对应那个名称的参数
urlpatterns = patterns('',
(r'^articles/(?P<year>\d{4})/$', views.year_archive),
(r'^articles/(?P<year>\d{4})/(?P<month>\d{2})/$',views.month_archive),
)
不同的url对应相同的处理函数
实际这种情况也经常发生,我们可以通过url的第三个参数传入使用模板的名字,这样不同的url对应相同的函数,使用不同模板。
urlpatterns = patterns('',
(r'^foo/$', views.foobar_view, {'template_name': 'template1.html'}),
(r'^bar/$', views.foobar_view, {'template_name': 'template2.html'}),
)