【python】-- Django路由系统(网址关系映射)、视图、模板
Django路由系统(网址关系映射)、视图、模板
一、路由系统(网址关系映射)
1、单一路由对应:
一个url对应一个视图函数(类)
urls.py:
url(r'^test', views.test),
#url(r'^home', views.Test.as_view()), views.py:
def test(request):
print(request.method)
return render(request, "home.html")
"""
class Test(View): def get(self, request):
print(request.method)
return render(request, "home.html") def post(self, request):
print(request.method)
return render(request, "home.html")
"""
2、基于正则路由对应:
多个url对应一个视图
urls.py
# 多个url对应一个视图函数,不过在给视图函数传参时,要根据对应形参位置进行传参
url(r'^detail-(\d+)-(\d+).html', views.detail),
# 多个url对应一个视图函数,推荐这种写法,在正则匹配完毕后进行了分组分配,在传参时就可以形参位置变化也没有关系
url(r'^detail-(?P<nid>\d+)-(?P<uid>\d+).html', views.detail), views.py:
#普通传参
def detail(request, nid, uid):
print(nid, uid)
return HttpResponse("%s - %s" % (nid, uid))
#args传参
def detail(request, *args, **kwargs):
print(args[0], args[1])
return HttpResponse("%s - %s" % (args[0], args[1]))
#kwargs传参
def detail(request, *args, **kwargs):
print(kwargs["nid"], kwargs["uid"])
return HttpResponse("%s - %s" % (kwargs["nid"], kwargs["uid"]))
3、name:
对URL路由关系进行命名,以后可以根据此名称生成自己想要的URL
urls.py:
url(r'^url_1/', views.index, name='i1'),
url(r'^url_2/(\d+)/(\d+)/', views.index, name='i2'),
url(r'^url_3/(?P<pid>\d+)/(?P<nid>\d+)/', views.index, name='i3'), views.py:
from django.urls import reverse
def func(request, *args, **kwargs):
url1 = reverse('i1') # url_1/
url2 = reverse('i2', args=(1,2,)) # url_2/1/2/
url3 = reverse('i3', kwargs={'pid': 1, "nid": 9}) # url_3/1/9/ xxx.html: {% url "i1" %} # url_1/
{% url "i2" 1 2 %} # url_2/1/2/
{% url "i3" pid=1 nid=9 %} # url_3/1/9/ PS:
# 显示当前的URL
request.path_info
4、多级路由:
多级路由目的避免有多个app时,在project urls.py的路由(网址)因路径名称一致而引起的冲突
#project/urls.py:
from django.conf.urls import url, include
from django.contrib import admin
urlpatterns = [
url(r'^app1/', include("app1.urls")),
url(r'^app2/', include("app2.urls")),
] #app01/urls.py:
from django.conf.urls import url
from app1 import views
urlpatterns = [
url(r'^test', views.test),
] #app02/urls.py:
from django.conf.urls import url
from app2 import views
urlpatterns = [
url(r'^test', views.test),
]
5、默认值
在路由关系映射的同时,添加额外参数,views.py中的对应函数可接受参数使用
#urls.py:
url(r'^test', views.url_test, {"value": 3}), #views.py:
def url_test(request, value):
print(value)
return HttpResponse("OK")
6、命令空间
在project的urls.py中定义namespace后,在views中的函数会根据指定namespace生成url
6.1.、project.urls.py
from django.conf.urls import url, include urlpatterns = [
url(r'^app1/', include("app1.urls", namespace='name_1')),
url(r'^app2/', include("app1.urls", namespace='name_2')),
]
6.2、app1.urls.py
from django.conf.urls import url
from app1 import views app_name = "app1" # 如果在project urls.py中定义namespace,那在这里就要定义一下app_name urlpatterns = [
url(r'^test$', views.url_test, name='i1'),
]
6.3、app1.views.py
from django.shortcuts import reverse, HttpResponse def url_test(request):
url_1 = reverse("name_1:i1")
url_2 = reverse("name_2:i1")
print(url_1, url_2)
return HttpResponse("OK")
二、视图
1、FBV&CBV
1.1、 FBV (Function Base VIew)在view(视图)中基于函数编写逻辑
#urls.py:
url(r'^test', views.test), # FBV function base view #views.py:
def test(request):
if request.method == "GET":
return render(request, 'test.html')
1.2、CBV(Class Base Viev)在view(视图)中基于类编写逻辑
#urls.py;
url(r'^home', views.Test.as_view()), # CBV class base view .as_view() Test没有view所以在views.py中Test类中继承Django的View #views.py:
from django.views import View class Test(View): # 调用父类中的dispatch方法,并重写
def dispatch(self, request, *args, **kwargs): # 通过dispatch的反射可以找到如:get、post方法的起始点
print("before")
result = super(Test, self).dispatch(request, *args, **kwargs)
return result def get(self, request):
print(request.method)
return render(request, "home.html") def post(self, request):
print(request.method)
return render(request, "home.html")
2、HTML from表单提交数据的提取示例:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<form action="/test" method="POST" enctype="multipart/form-data"><!--enctypes属性没有的话,默认提交的是字符串,无法实现文件上传-->
<p>
<input type="text" name="user" placeholder="用户名" />
</p>
<p>
<input type="password" name="pwd" placeholder="密码" />
</p>
<p>
男:<input type="radio" name="gender" value="1"/>
女:<input type="radio" name="gender" value="2"/>
张扬:<input type="radio" name="gender" value="3"/>
</p>
<p>
男:<input type="checkbox" name="favor" value="11"/>
女:<input type="checkbox" name="favor" value="22"/>
张扬:<input type="checkbox" name="favor" value="33"/>
</p>
<p>
<select name="city" multiple>
<option value="sh">上海</option>
<option value="bj">北京</option>
<option value="tj">天津</option>
</select>
</p>
<p>
<input type="file" name="file"/>
</p> <input type="submit" value="提交"/>
</form>
</body>
</html>
test.html
def test(request):
if request.method == "GET":
return render(request, 'test.html')
elif request.method == "POST":
# text
v = request.POST.get('pwd') # 获取input输入框输入的value
print(v)
# radio
v0 = request.POST.get('gender') # 获取radio的value
print(v0)
# checkbox
v1 = request.POST.getlist('favor') # 获取checkbox多选情况下的value
print(v1)
# select
v2 = request.POST.getlist('city') # 获取select下拉框multiple情况下的value
print(v2)
# file
obj = request.FILES.get('file') # 获取上传文件并保存
print(obj, type(obj), obj.name)
import os
file_path = os.path.join('upload', obj.name)
f = open(file_path, mode="wb")
for i in obj.chunks(): # chunks()利用生成器,每次只加载部分上传的文件,直至加载完毕
f.write(i)
f.close()
return redirect("/test")
else:
# PUT,DELETE,HEAD,OPTION...
return redirect("/test")
3、查看views.py中的request封装的信息
from django.core.handlers.wsgi import WSGIRequest
request.environ
request.environ['HTTP_USER_AGENT']
三、模板
1、模板的特殊语言
视图中函数:
def func(request):
return render(request, "index.html", {'current_user': "QQ"}) index.html:
<html>
..
<body>
<div>{{current_user}}</div>
</body>
</html>
变量名
视图函数:
def func(request):
return render(request, "index.html", {'current_user': "QQ", 'user_list': ['', '']}) index.html:
< html >
..
< body >
< div > {{current_user}} < / div >
< ul >
{ %for row in user_list %} <!--for循环中嵌套if判断>
{ % if row == "" %} <!--if判断>
< li > {{row}} < / li >
{ % endif %} <!--结束if判断>
{ % endfor %} <!--结束for循环>
< / ul >
< / body >
< / html >
for循环,if判断
视图函数:
def func(request):
return render(request, "index.html", {
'current_user': "QQ",
'user_list': ['',''],
'user_dict': {'k1': 'v1', 'k2': 'v2'}}) index.html:
< html >
..
< body >
<div>{{current_user}}</div>
<a> {{ user_list.1 }} </a>
<a> {{ user_dict.k1 }} </a>
<a> {{ user_dict.k2 }} </a>
< / body >
< / html > 索引
索引
试图函数:
USER_DICT = {
"k1": "value1",
"k2": "value2",
"k3": "value3",
"k4": "value4"
} def for_dict(request):
return render(request, "index.html", {"user_dict": USER_DICT}) index.html:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
</head>
<body>
<ul>
{%for key in user_dict.keys%} <!--循环获取key-->
<li>
{{key}}
</li>
{%endfor%}
</ul>
<ul>
{%for value in user_dict.values%} <!--循环获取value-->
<li>
{{value}}
</li>
{%endfor%}
</ul>
<ul>
{%for key,value in user_dict.items%} <!--循环获取key,value-->
<li>
{{key}}--{{ value }}
</li>
{%endfor%}
</ul>
</body>
</html> for循环字典
for循环字典
<!--表示当前循环的执行次数的整数计数器。这个计数器是从1开始的,所以在第一次循环时forloop.counter 将会被设置为1-->
{% for item in todo_list %}
<p>{{ forloop.counter }}: {{ item }}</p>
{% endfor %} ps:<!--forloop.counter0 类似于 forloop.counter ,但是它是从0计数的。第一次执行循环时这个变量会被设置为0-->
forloop.counter
<!--布尔值类型,在第一次执行循环时该变量为True-->
{% for object in objects %}
{% if forloop.first %}<li class="first">{% else %}<li>{% endif %}
{{ object }}
</li>
{% endfor %}
forloop.first
<!--布尔值,在最后一次执行循环时被置为True-->
{% for link in links %}
{{ link }}
{% if not forloop.last %}
|
{% endif %}
{% endfor %} #结果:
Link1 | Link2 | Link3 | Link4
forloop.last
2、模板的继承
父模板:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>{% block title %} {% endblock %}</title> <!--定义标题继承位置-->
<link rel="stylesheet" href="/static/commons.css" />
<style>
.pg-header{
height: 50px;
background-color: seashell;
color: green;
}
</style>
{% block css %} {% endblock %} # <!--定义CSS继承位置-->
</head>
<body>
<div class="pg-header">oms</div>
{%block content%}{%endblock%} <!--定义内容继承位置-->
<script src="/static/jquery.js"></script>
{%block js%}{%endblock%} <!--定义JavaScript继承位置-->
</body>
</html>
子模板:
{% extends 'master.html' %} <!--声明继承的文件--> {% block title %}用户管理{% endblock %} <!--在继承文件的头部位置放入值--> {% block content %} <!--在继承文件的内容位置放入值-->
<h1>用户管理</h1>tou
<ul>
{% for i in u %}
<li>{{ i }}</li>
{% endfor %}
</ul> {% block css %} <!--在继承文件的CSS位置放入自己特有的CSS-->
<style>
body{
background-color: red;
}
</style>
{% endblock %} {% block js %} <!--在继承文件的CSS位置放入自己特有的js-->
<script></script>
{% endblock %}
3、模板的引用
{% include 'tag.html' %} <!--直接include想要导入的HTML文本-->
4、自定义simple_tag
Django提供的模板方法(类似于python的内置函数),以供我们在使用模板的时候,更加方便的对数据进行操作。
{{ k1|lower }} # 将所有字母都变为小写
{{ k1|first|upper }} # 将首字母变为大写
{{ k1|truncatewords:"30" }} # 取变量k1的前30个字符
{{ item.createTime|date:"Y-m-d H:i:s" }} # 将时间转为对应格式显示
当然Django提供的方法是有限的,无法满足我们所有的需求,这个时候就需要自定制更加符合我们自己需求的方法(函数),步骤如下:
- a.在settings中注册APP
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'app',
]
settings.py中注册app
- b.在app下创建templatetags目录(templatetags目录名称不可变)
- c.在templatetags目录下定义test.py文件(py文件名任意)
- d.在test.py文件中定义自定制函数
from django import template
from django.utils.safestring import mark_safe register = template.Library() #创建创建template对象 register @register.simple_tag #利用register中对象的simple_tagz函数装饰自定义函数
def addition(a1,a2):
return a1 + a2
自定义函数
- e.在模板中引用自定义方法(函数)
{% load test %} <!--导入刚刚定义的py文件名称-->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title></title>
</head>
<body>
{% addition 2 5 %} <!--导入刚刚定义的函数(方法),参数用空格隔开-->
</body>
</html>
在模板中引用方法
5、自定义filter
步骤与自定义simple_tag步骤一致,只是在引用自定义函数中用的装饰器和模板中的引用方式不同:
- a、b、c、步骤一致
- d.在test.py文件中定义自定制函数
from django import template
from django.utils.safestring import mark_safe register = template.Library() #创建创建template对象 register @register.filter #利用register中对象的filter函数装饰自定义函数
def addition(a1,a2):
return a1 + str(a2)
自定义函数
- e.在模板中引用自定义方法(函数)
{% load test %} <!--导入刚刚定义的py文件名称-->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title></title>
</head>
<body>
{{ 2|addition:30 }} <!--导入刚刚定义的函数(方法){{ 参数1|addition:参数2 }}-->
</body>
</html>
在模板中引用方法
PS:自定义simple_tag和自定义filter的区别。
- 自定义simple_tag装饰的函数可以传入任意数量的参数,但自定filter只能传入两个参数(间接传入多个参数办法:就是将第二个参数通过"args1,args2,args3"的形式传入,然后通过split()解析获取)
- 自定义simple_tag装饰的函数不能用于模板if条件,但自定filter用于if条件
【python】-- Django路由系统(网址关系映射)、视图、模板的更多相关文章
- python django 路由系统
URL配置 基本格式: from django.conf.urls import url urlpatterns = [ url(正则表达式, views ...
- Python学习---Django路由系统【all】
Django URL (路由系统) Django URL (路由系统): URL配置(URLconf)就像Django 所支撑网站的目录.它的本质是URL模式以及要为该URL模式调用的视图函数之间的映 ...
- Django路由系统
django路由系统 简而言之,django的路由系统作用就是使views里面处理数据的函数与请求的url建立映射关系.使请求到来之后,根据urls.py里的关系条目,去查找到与请求对应的处理方法,从 ...
- Django 路由系统
Django 路由系统 基本格式 from django.conf.urls import url urlpatterns = [ url(正则表达式, views视图函数,参数,别名), ] 参数说 ...
- Django路由系统-分组命名匹配
Django路由系统 分组命名匹配 在上述基本配置示例中,使用了简单的正则表达式分组匹配来捕获URL中的值并以位置参数的形式传递给视图,例如url(r'^articles/([0-9]{4})/( ...
- Django路由系统-URLconf配置、正则表达式简述
Django路由系统 1.11版本官方文档 URL配置就像是Django项目的目录,它的本质是URL与URL调用的函数之间的映射表,Django会根据URL配置,在遇到一个URL时,就去执行相应的 ...
- python 终极篇 --- django 路由系统
URL配置 基本格式: from django.conf.urls import url urlpattern ...
- Django 路由系统URL 视图views
一.Django URL (路由系统) URL配置(URLconf)就像Django 所支撑网站的目录.它的本质是URL模式以及要为该URL模式调用的视图函数之间的映射表:你就是以这种方式告诉Djan ...
- python的Web框架:Django路由系统以及模板导入
Django的路由系统 当一个请求来到时 当一个请求来到时 1.首先到项目目录下的urls.py(根URLconf模块)中,查找路由规则: 2.根URELcof模块,里面定义了 urlpatterns ...
随机推荐
- Redis 3.2.8 集群模式+Sentinel多Master部署
环境准备CentOS 7.3redis1 172.18.1.101:7001 masterredis2 172.18.1.102:7002 masterredis3 172.18.1.103:7003 ...
- Java之旅(2)—反射
1. 概念 反射就是将java类中的各种成分映射成对应的java类.之前我们已经讲过了Class类,也明确了一个java类中用一个Class类的对象来表示,一个类中的组成部分有:成员变量,方法 ...
- 檢查php文件中是否含有bom的php文件
原文链接: http://www.cnblogs.com/Athrun/archive/2010/05/27/1745464.html 另一篇文章:<关于bom.php>,http://h ...
- 小程序排错(redis导致)
小程序突然出问题,题库加载不了,程序正常,测试环境同样环境,同样代码都正常,但是线上数据秒过期,怀疑redis过期时间设置有问题,但是检查配置没问题,写入数据带过期时间也正常. redis设置key: ...
- 关于Xilinx FPGA JTAG下载时菊花链路中的芯片数量
关于Xilinx FPGA JTAG下载时菊花链路中的芯片数量 emesjx | 2014-08-13 13:13:30 阅读:1793 发布文章 当一个系统中含有多片(2片以上)Xil ...
- HNU 13411 Reverse a Road II(最大流+BFS)经典
Reverse a Road II Time Limit: 10000ms, Special Time Limit:25000ms, Memory Limit:65536KB Total submit ...
- mysql存在就更新,不存在就新增
INSERT INTO newest_log_operation( ACTION, OPERATION, KEY_VALUE, BUS_KEY, CONTENT, USER_ID, VERSIO ...
- Python 安装 MaxMind GeoLite City
1.先安装 geoip c library geoip c library >= 1.4.6 installed on your machine. >= 1.4.6 installed ...
- UML结构体系简介
一.UML的结构 UML有3种基本的构造块,分别是事物(元素).关系和图.事物是UML中重要的组成部分.关系把事物紧密联系在一起.图是很多有相互相关的事物的组. 二.UML的事物 UML中的事物也称为 ...
- select option 不可以选
<select> <option>Volvo</option> <option>Saab</option> <option disab ...