天下难事必作於易。天下大事必作於细。是以圣人终不为大,故能成其大

——老子《道德经》


本节内容

  • HTML页面的渲染
  • 使用页面模板
  • 异常处理
  • 超链接路径处理
  • 路由命名空间

1. HTML页面渲染

在之前的章节中,我们使用的视图,都是临时在函数HttpResponse中添加的字符串,这样的数据明显不符合我们网页的需要,一个网页中那么多的文字、图片、视频音频等等数据,如果按照字符串的方式来处理的话明显不是很现实

网页开发有独立的技术进行处理,通常使用HTML/CSS/JavaScript/JQuery进行网页部分的开发,当然,大家如果这些技术稍有遗憾的话,可以上网多找资料学习一下的哦~~

接下来,上干货:渲染第一个HTML页面

1.1 渲染HTML网页
  • polls/应用目录下,创建一个名称为templates/文件夹,在文件夹中,创建一个名称为index.html的网页,添加如下内容
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>投票模块首页</title>
<link rel="stylesheet" href="">
</head>
<body>
<h1>投票模块首页</h1>
</body>
</html>
  • 修改polls/views.py中的index函数,如下:
from django.template import loader
from django.http import HttpResponse
# 定义首页处理函数
def index(request):
# 获取模板页面
temp = loader.get_template("index.html")
# 保存数据的上下文对象
context = {}
# 渲染视图
return HttpResponse(temp.render(context, request))
  • OK,接下来,启动服务,访问以下http://localhost:8000/polls,看看结果哦

注意:通常情况下,我们会将要使用的html网页,保存在应用的templates/文件夹下,因为django在视图处理函数中,通过loader.get_template()函数进行加载的时候,会默认从templates/文件夹下进行搜索查询。此时,你明白为什么要创建一个templates/文件夹了ma?

1.2. 渲染网页的快捷方式

上述代码中,将一个HTML网页做成了视图模板,在我们的web项目中可以使用了,但是操作过程比较麻烦:

首先需要通过loader对象的get_template()函数加载网页

然后还有一个保存数据的上下文对象

最后需要通过HttpResonse函数进行渲染才能给浏览器查看到。

Django为了方便我们进行HTML网页视图模板的处理,提供了一个快捷进行网页模板渲染的方式:render()

上干货:修改上面的index函数中的视图处理的代码:

from django.shortcuts import render
# 修改首页处理函数
def index(request):
# 返回渲染视图对象
return render(request, "index.html", {})

Bingo!这个世界清净了。赶紧试试吧!!!

2. 使用页面模板

目前来说,HTML网页已经正常的显示在我们的浏览器中

此时有个非常重要的问题需要解决,什么问题呢?我们Django中定义的数据,怎么展示到HTML网页中呢?

如果,如果我说,这里的HTML网页中,可以写类似python代码!惊不惊喜意不意外!

此处应播放 类似爱情

在template/文件夹下的html网页,可以在一对特殊的符号中编写类似python的模板语法的代码,这个符号就是{%这里可以写类似python的模板语法的代码%}

同时,在html页面中,可以通过一对双大括号,来访问python对象的属性,如{{question.question_text}}

干货来袭,改造首页处理函数和首页index.html


改造首页处理函数,查询所有的对象,然后保存到上下文对象中

from django.template import loader
from .models import Question
# 处理首页的函数
def index(request):
questionList = Question.objects.order_by("-pub_date")
return render(request, "index.html", {"question_list" : questionList})

改造首页index.html,用于展示所有查询到的问题

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>投票模块首页</title>
<link rel="stylesheet" href="">
</head>
<body>
<h1>投票模块首页</h1>
{%if question_list%}
<ul>
{%for question in question_list%}
<li><a href="/polls/{{qustion.id}}">{{question.question_text}}</a></li>
{%endfor%}
</ul>
{%else%}
<p>没有要处理的问题</p>
{%endif%}
</body>
</html>

Bingo!接下来,重启一下项目,然后在浏览器中访问一下看看吧

3. 异常处理

软件开发,总是一个问题接着一个问题,一个Bug跟着一堆Bug;尤其是需求变动频繁的情况下,看着需求经理和产品经理,心理已经默默的将满清十八大酷刑轮了好几遍!

不过,话说回来,不就是应该变动这么快的需求,要求这么严格的产品,软件开发才造就了高薪么。

那么问题来了!如果我们前面写的项目,用户访问了不存在的问题编号,会出现什么问题呢?来吧来吧~看看先!

3.1. 异常的出现——潜在Bug

首先改造detail函数和对应的视图页面detail.html

改造detail函数如下:

# 定义和页面的绑定关系
def detail(request, question_id):
# 根据主键编号查询一个问题对象
question = Question.objects.get(pk=question_id)
return render(request, "details.html", {"question":question})

改造detail.html函数

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<title>详细问题展示</title>
<link rel="stylesheet" href="">
</head>
<body>
<h1>详细问题展示页面</h1>
{%if question%}
<p>问题编号:{{question.id}}</p>
<p>问题描述:{{question.question_text}}</p>
{%else%}
<p>没有问题</p>
{%endif%}
</body>
</html>

此时,入门在访问问题详细页面时,如果修该浏览器中的id编号,会出现如下的异常

3.2. 处理异常

页面出现的异常情况,我们有一些特殊的状态处理方式,如常规情况下在HTTP协议中有一些特殊的状态编码,如404表示访问的资源不存在,500表示服务器内部错误等等,在Django中,我们也可以这么干

首先,捕获到用户访问的数据不存在的异常,然后抛出一个异常对象

改造polls/views.py中的detail函数如下:

from django.http import Http404
# 问题详情函数
def detail(requst, question_id):
try:
question = Question.objects.get(pk=question_id)
except Question.DoesNotExist:
raise Http404("您要找的问题不存在,问题编号:%s" % question_id)
return render(request, "detail.html", {"question": question})

此时,如果我们重新访问一个不存在的编号:

3.3. 针对web异常的快捷处理方式

通常情况下,类似查询数据访问对应的模板页面,无非就两种情况,有或者没有。有就返回数据,没有就返回404,针对两种结果,django封装了一个好玩的函数来进行处理

# 获取对象,如果对象不存在就抛出404异常
get_object_or_404()

我们改造一下detail视图处理函数

# 引入需要的模块
from django.shortcuts import render, get_object_or_404
# 改造函数
def detail(request, question_id):
#查询对象,如果不存在就抛出异常
question = get_object_or_404(Question, pk=question_id)
return render(request, "detail.html", {"question":question})

3.4. 补充:关于开发模式和生产模式

在我们目前的章节中,默认是使用开发模式【就是适合代码开发的软件环境,有更多的错误提示信息】,包括页面的展示也是使用的开发模式的错误提示

在进行项目发布时,需要将开发模式转换成生产模式【适合实际使用的软件环境,错误提示或者错误引起的软件的乱码等都会隐藏】

将开发模式转换成生成模式

修改mysite/settings.py配置文件

# 关闭调试【关闭开发模式】
DEBUG = False
# 一旦修改成生产模式,需要在ALLOWED_HOST中添加允许访问的主机列表
ALLOWED_HOSTS = ["localhost", "127.0.0.1"]

此时我们如果访问错误页面,就会出现下面这样的风格

4. 超链接路径处理

在前面的案例项目中,在页面部分使用的是硬编码的形式进行了超链接路径指定

<li><a href="/polls/{{question_id}}">{{question.question_text}}</a></li>

这样的形式并不是特别适合实际项目开发,会出现各种路径维护的问题(如模块路径更换、路由路径更新会造成大量的项目改造非常麻烦),所以可以使用路由指定的形式来记性处理,如下:

# 使用url进行路由指定即可,避免了硬编码造成的问题
<li><a href="{%url 'detail' question_id%}"></a></li>

注意,这里的url编码配置,和urls.py文件中的配置必须对应

5.路由命名空间

第4节我们对路由从硬编码改造成了配置实现的方式,方便了项目中的操作

但是,此时我们只有一个模块应用,当项目中出现多个模块的应用,同时多个模块应用下又有重名的路由时,这样的配置方式同样是有问题的:

|-- mysite/
|-- polls/
|-- templates/
|--details.html
|-- ......
|-- ....
|-- shop/
|-- templates/
|-- details.html
|-- ......
|-- ....

路由配置如下:

polls/urls.py
--------------------------
urlpatterns = [
....
url(r"^(?P<detail_id>\d+)$", views.detail, name="detail"),
....
]
***************************************************************
shop/urls.py
--------------------------
urlpatterns = [
....
url(r"^(?P<goods_id>\d+)$", views.detail, name="detail"),
....
]

此时,我们如果在页面中,通过前面的编码的方式,就会出现非常不明确的跳转方式

<li><a href="{%url 'detail' question_id%}"></a></li>
# ?问题?你是要跳转大polls/detial还是shop/detail呢?

Bingo!此时就是我们路由的命名空间登场了,在urls.py模块中,增加一个app_name来定义一个路由的命名空间,后续的路由操作,可以通过命名空间的形式来指定路径了。

修改路由配置如下:

polls/urls.py
--------------------------
app_name="polls"
urlpatterns = [
....
url(r"^(?P<detail_id>\d+)$", views.detail, name="detail"),
....
]
***************************************************************
shop/urls.py
--------------------------
app_name="shop"
urlpatterns = [
....
url(r"^(?P<goods_id>\d+)$", views.detail, name="detail"),
....
]

然后我们就可以这样用了

# 这是跳转到polls的detaild的链接【命名空间:路由名称】
<li><a href="{%url 'polls:detail' question_id%}"></a></li>

【7】Django网页视图模板处理的更多相关文章

  1. 五、Django之视图和模板-Part 3

    一.概述 一个视图就是一个页面,通常提供特定的功能,使用特定的模版.列如:在一个博客应用中,你可能会看到下列视图: 博客主页:显示最新发布的一些内容 每篇博客的详细页面:博客的永久链接 基于年的博客页 ...

  2. python Django教程 之模板渲染、循环、条件判断、常用的标签、过滤器

    python3.5 manage.py runserver python Django教程 之模板渲染.循环.条件判断.常用的标签.过滤器 一.Django模板渲染模板 1. 创建一个 zqxt_tm ...

  3. Django之视图

    Django之视图   Django的View(视图) 一个视图函数(类),简称视图,是一个简单的Python 函数(类),它接受Web请求并且返回Web响应. 响应可以是一张网页的HTML内容,一个 ...

  4. Django的视图层简介

    Django的视图层 视图函数 所谓视图函数,其实就是我们Django项目中各个应用中的views.py文件中定义的每个用来处理URL路由映射到这里的逻辑函数.一个视图函数简称视图,它是个简单的Pyt ...

  5. 【笔记】Django的视图

    [笔记]Django的视图 Python Django  Django的View(视图) 一个视图函数(类),简称视图,是一个简单的Python 函数(类),它接受Web请求并且返回Web响应. 响应 ...

  6. 03 Django之视图函数

    一.Django的视图函数view 一个视图函数(类),简称视图,是一个简单的Python函数(类),它接受WEB请求并返回Web响应. 响应可以是一张网页的HTML内容,一个重定向,一个404错误, ...

  7. 【Django】 视图层说明

    [Django视图层] 视图层的主要工作是衔接HTTP请求,Python程序和HTML模板,使他们能够有机互相合作从模型层lou到数据并且反馈.说到视图层的工作就有以下几个方面要说 ■ URL映射 对 ...

  8. Django基本视图

    Django基本视图 下面这三个类也许不能提供项目所需的所有的功能,这些应用于基于类的视图或Mixins情形下. 大多数Django的内建视图继承于其他基于类的视图或者各种mixins中,因为继承链是 ...

  9. Django通用视图APIView和视图集ViewSet的介绍和使用

    原 Django通用视图APIView和视图集ViewSet的介绍和使用 2018年10月21日 14:42:14 不睡觉假扮古尔丹 阅读数:630   1.APIView DRF框架的视图的基类是 ...

随机推荐

  1. CodeForces 16B Burglar and Matches(贪心)

    B. Burglar and Matches time limit per test 0.5 second memory limit per test 64 megabytes input stand ...

  2. uefi bios安装ubuntu16.04 (win10和ubuntu双系统)

    哎呀,没事闲的装双系统,按照晚上的教程装半天也没成功,后来才知道是自己电脑的问题,当然也有那些过时的博客的问题! ultraiso制作ubuntu u盘启动盘  http://www.cr173.co ...

  3. openstack Aio env deubg

  4. MSP430 使用时 RST引脚一定拉高

    因为这次省去了RESET按键,RST没做任何处理,程序下载完之后插上电池无法运行,最终原因:RST引脚没有拉高.呼呼切记啊

  5. 为什么要使用XHTML?

    XHTML 是什么? XHTML 指可扩展超文本标签语言(EXtensible HyperText Markup Language). XHTML 的目标是取代 HTML. XHTML 与 HTML ...

  6. MVVMLight消息通知实现机制详解(一)

    最近对委托.事件的订阅使用的太多,订阅与被订阅之间的绑定约束非常...麻烦,所以翻了下MVVMLight源码找出这段可以拿出来用的部分,详情见下: 一.开发中遇到的问题: 场景1:ClassA中存在事 ...

  7. js判断ie6的代码

    var isIE=!!window.ActiveXObject; var isIE6=isIE&&!window.XMLHttpRequest; var isIE8=isIE& ...

  8. 聪明的kk --- 搜索超时

    二话没说上去搜索 , 果不其然 华丽超时 . #include<stdio.h> #include<string.h> #include<math.h> #incl ...

  9. 51nod 1340 差分约束

    思路: 带未知量的Floyd 很强 http://yousiki.net/index.php/archives/87/ //By SiriusRen #include <bits/stdc++. ...

  10. 【知识总结】线性筛_杜教筛_Min25筛

    首先感谢又强又嘴又可爱脸还筋道的国家集训队(Upd: WC2019 进候选队,CTS2019 不幸 rk6 退队)神仙瓜 ( jumpmelon ) 给我讲解这三种筛法~~ 由于博主的鸽子属性,这篇博 ...