前言
系列文章目录
视频及资料和课件
链接:https://pan.baidu.com/s/1LCv_qyWslwB-MYw56fjbDg?pwd=1234
提取码:1234
1. 视图(View)
视图就是一个Python函数,被定义在子应用的views.py中。
视图函数的第一个参数就是客户端发送过来的请求,即HttpRequest类型的对象reqeust,包含了所有请求信息。
导入HttpRequest:
from django.http import HttpReques
视图必须返回一个响应,响应是HttpResponse的实例对象或者HttpResponse子类的实例对象,包含返回给请求者的响应信息。
导入HttpResponse:
from django.http import HttpResponse
视图负责接受Web请求HttpRequest,进行逻辑处理,返回Web响应HttpResponse给请求者,响应内容可以是HTML内容,404错误,重定向,json数据…
1.1 定义视图
login/views.py
from django.shortcuts import render from django.http import HttpRequest from django.http import HttpResponse # Create your views here. def index(request): return HttpResponse('index')
2. URL 定义路由
2.1 查找视图的过程
1.请求者在浏览器地址栏中输入URL, 请求到服务器.
2.服务器获取URL信息.
3.然后与编写好的路由规则逐条匹配.
4.如果匹配成功则进入相应的模块进行处理.
5.如果所有的路由规则都没有匹配成功,则返回404错误。
寻找路径会默认进入项目文件项目相关配置文件夹内的urls.py文件中进行查找。
此项配置可以进行修改,但是一般不进行修改。
2.2 定义路由
项目名/urls.py
# 1. urlpatterns 是固定写法,urlpatterns的值为列表 # 2. 在浏览器中输入的路径会和urlpatterns中的每一项顺序进行匹配 # 如果匹配成功,会进入对应的模块,进行后序的处理 # 如果所有都匹配不成功直接返回404 # 3. 请求路径:http://ip:port/path?key=value中http://ip:port/和get、post参数不参与匹配 # 即 path 参与路由匹配 urlpatterns = [ path('admin/', admin.site.urls), ]
添加自己的路由:
from django.contrib import admin from django.urls import path from django.urls import include # 1. urlpatterns 是固定写法,urlpatterns的值为列表 # 2. 在浏览器中输入的路径会和urlpatterns中的每一项顺序进行匹配 # 如果匹配成功,会进入对应的模块,进行后序的处理 # 如果匹配不成功直接返回404 urlpatterns = [ path('admin/', admin.site.urls), # 与‘admin/’匹配失败的向下继续匹配 # 添加自己的路由的写法: # Add a URL to urlpatterns: path('blog/', include('blog.urls')) # 与'index/'匹配,引导到login.urls中 path('index/', include('login.urls')) ]
login/urls.py:
from django.urls import path from login.views import index urlpatterns = [ # 在 项目名.urls中与index/匹配成功进入该模块继续进行匹配 # 匹配成功进入login.views 中的 index 函数进去请求的处理与响应 path('index/', index) ]
index/index/
参与匹配,第一个index/
与项目名.urls中的index/
进行匹配,匹配成功,进入login.urls,第二个index/
参与匹配,匹配成功进入login.views 中的 index 函数
2.3 路由匹配流程图
2.4 在项目的urls.py进行处理函数的匹配
在项目的urls.py进行匹配,不引导到子应用中继续进行路由的匹配。
Function views 1. Add an import: from my_app import views 2. Add a URL to urlpatterns: path('', views.home, name='home')
from django.contrib import admin from django.urls import path from django.urls import include from login.views import index # 1. urlpatterns 是固定写法,urlpatterns的值为列表 # 2. 在浏览器中输入的路径会和urlpatterns中的每一项顺序进行匹配 # 如果匹配成功,会进入对应的模块,进行后序的处理 # 如果匹配不成功直接返回404 urlpatterns = [ path('admin/', admin.site.urls), # path('index/', include('login.urls')) # 直接在项目的urls中进行匹配,不引导到子应用中 path('index/index/', index) ]
引导到子应用中继续匹配,该种写法可以对请求进行分类处理,如有关登录的请求到登录的子应用中进行处理。
2.5 为路由命名
为路由命名,可以用于反解析,通过路由的名字获取对应的路由,避免因为路由的修改,导致其他用到该路由的地方也要进行相应的修改。
book/urls.py:
from django.urls import path from book.views import index urlpatterns = [ path('index/', index, name='index') ]
2.6 reverse反解析
# 使用路由进行页面的跳转 # 登陆成功之后跳转回首页 # return redirect('/index') # 注册成功之后跳转回首页 # return redirect('/index')
如果路由进行了修改,则多处用到该路由的地方也要进行修改。
使用reverse反解析路由,需要先进行导入:
from django.urls import reverse
from django.urls import reverse # 动态获取路由名对应的路由 path = reverse('index') # 使用动态获取的路由进行页面的跳转 # 登陆成功之后跳转回首页 # return redirect(path) # 注册成功之后跳转回首页 # return redirect(path)
使用该方法,即使路由进行了修改,使用到该路由的地方也不用进行修改。
2.7 路由命名空间
在使用include函数定义路由时,可以使用namespace参数定义路由的命名空间。
命名空间的作用:避免不同应用中的路由使用了相同的名字发生冲突,使用命名空间区别开。
项目/urls.py:
子应用的命名空间习惯使用子应用名进行命名。
注意:定义了命名空间,include第一个参数数据类型必须设置为元组类型,且元组需要包含两个元素,第一个元素为’子应用名.urls’,第二个元素为’子应用名’,include第二个参数为命名空间
urlpatterns = [ path('admin/', admin.site.urls), # path('index/', include('login.urls')) # 注意:定义了命名空间,include第一个参数数据类型必须设置为元组类型, # 且元组需要包含两个元素,第一个元素为'子应用名.urls',第二个元素为'子应用名' # include第二个参数为命名空间 path('book/', include(('book.urls', 'book'), namespace='book')) ]
命名空间表示,凡是book.urls中定义的路由,均属于namespace指明的book名下
指定了命名空间后,通过reverse动态获取路由需要使用命名空间:路由名
path = reverse('book:index')
3. 模板(Template)
模板即网页的页面。
3.1 模板使用步骤
- 创建模板
- 设置模板查找路径
- 模板接收视图传入的数据
- 模板发送给客户端
3.2 创建模板
单独创建一个文件夹,用于存放网页页面的文件。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <h1>hello world</h1> <!-- 模板语言 --> <h1>你好,{{name}}</h1> </body> </html>
3.3 设置模板查找路径
'DIRS': [ os.path.join(BASE_DIR, 'template') ], • 1
3.4 模板接收视图传入的数据 & 模板发送给客户端
模板发送给客户端,使用render()函数
# render() 有三个参数 # request template_name context=None # request:当前的请求 # template_name:模板文件 # context:要向模板文件中传递的数据,传递的参数类型为字典
from django.shortcuts import render from django.http import HttpRequest from django.http import HttpResponse # Create your views here. def index(request): # return HttpResponse('index') # render() 有三个参数 # request template_name context=None # request:当前的请求 # template_name:模板文件 # context:要向模板文件中传递的数据,传递的参数类型为字典 # context中的key会与模板文件中需要填充数据的位置进行匹配 context = { 'name': 'ZS' } return render(request, 'index.html', context)
流程图:
4. 案例
经过[Python]Django模型(Model)中的操作,目前模型BookInfo中已经有两个对象数据。
实现:使用模型从数据库中查询数据,并获取页面模板,将查询出来的数据添加到页面模板中,并将最后的页面返回给客户端。
login/views.py:
from django.shortcuts import render from django.http import HttpRequest from django.http import HttpResponse # 导入模型 from login.models import BookInfo # Create your views here. def index(request): # 数据库操作语言: # select * from BookInfo # ORM中查询表中的全部数据使用: # 模型(类).objects.all() books = BookInfo.objects.all() context = { 'books' : books } # 获取页面,将数据放入页面,并返回给客户端 return render(request, 'index.html', context)
后面的文章会进行讲解
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <h1>hello world</h1> <ul> {# 模板语言:遍历数据 #} {% for book in books %} {% books view中传递进来的books %} <li>{{book.name}}</li> {% endfor %} </ul> </body> </html>