邂逅Django - 目录
✅ Part 1:【邂逅Django】—— (一)创立我的项目
✅ Part 2:【邂逅Django】—— (二)数据库配置
️ Part 3:【邂逅Django】—— (三)视图
️ Part 4:【邂逅Django】—— (四)表单和通用视图
️ Part 5:【邂逅Django】—— (五)欠缺界面(自定义界面和款式)
️ Part 6:【邂逅Django】—— (六)自定义治理界面
️ Part 7:【邂逅Django】—— (七)自动化测试
前言
本系列文章,在Django
官网文档教程的根底模板下,进行了肯定的改良和删除,增加了一些本人的见解。
心愿大家看完该系列文章后,对Django
可能有一个清晰的意识。
路漫漫兮其修远兮,吾将上下而求索!
Django
==官网文档==:https://www.djangoproject.com/
❗ ❗ ❗ 学习过程中,多看官网文档,能够解决很多问题 ❗ ❗ ❗
本教程应用poetry
对我的项目环境进行治理。
相干poetry
的装置与应用,请参考【Python - 虚拟环境】我的项目的启动,从隔离开发环境开始 - SegmentFault 思否
我的项目地址:https://github.com/CoderBerryRabbit/MeetDjango
一、视图概述
Django
中的视图概念是【一类具备雷同性能和模板的网页汇合】。比方,在一个博客利用中,可能会创立如下视图:
- 博客首页 —— 展现最近的几项内容
- 内容详情页 —— 具体展现某项内容
- 以年为单位的归档页 —— 展现选中的年份里各个月份创立的内容
- 以月为单位的归档页 —— 展现选中的月份里各天创立的内容
- 以天为单位的归档页 —— 展现选中天里创立的所有内容
- 评论处理器 —— 用于响应内容增加评论的操作
而在投票利用中,须要以下几个视图:
- 问题索引页 —— 展现最近的几个投票问题
- 问题详情页 —— 展现某个投票的问题和不带后果的选项列表
- 问题后果页 —— 展现某个投票的后果
- 投票处理器 —— 用于响应用户为某个问题投票的操作
在Django
中,网页和其余内容都是从视图派生而来的。每一个视图体现为一个Python
函数(对于基于类的视图来说,体现为一个办法)。Django
会依据用户申请的URL
来抉择应用哪个视图。
为了将URL
和视图关联起来,Django
应用URLconfs
来配置。URLconf
将URL
映射到视图。
二、编写视图
# polls/views.pyfrom django.shortcuts import renderfrom django.http import HttpResponsedef index(request): return HttpResponse("Hello, world. You're at the polls index.")def detail(request, question_id): return HttpResponse(f"You're looking at question {question_id}")def results(request, question_id): response = "You're looking at the results of question {}" return HttpResponse(response.format(question_id))def vote(request, question_id): return HttpResponse("You're voting on question %s." % question_id)
三、增加url
# polls/urls.pyfrom django.urls import pathfrom . import viewsurlpatterns = [ path("", views.index, name="index"), path("<int:question_id>/", views.detail, name="detail"), path("<int:question_id>/results/", views.results, name="results"), path("<int:question_id>/vote/", views.vote, name="vote"),]
启动Django
开发服务器,能够在浏览器输出以下URL
进行查看:
index
- http://127.0.0.1:8000/polls/detail
- http://127.0.0.1:8000/polls/1/results
- http://127.0.0.1:8000/polls/1/results/vote
- http://127.0.0.1:8000/polls/1/vote/
四、写一个真正有用的视图
每个视图要做两件事:返回一个蕴含被申请页面内容的HttpResponse
对象,或者抛出一个异样。
视图能够从数据库里读取记录,能够应用一个模板引擎,或者其余能用Python
实现的事。
# pools/views.pyfrom django.shortcuts import renderfrom django.http import HttpResponsefrom .models import Questiondef index(request): latest_question_list = Question.objects.order_by("-pub_date")[:5] output = ", ".join([q.question_text for q in latest_question_list]) return HttpResponse(output)def detail(request, question_id): return HttpResponse(f"You're looking at question {question_id}")def results(request, question_id): response = "You're looking at the results of question {}" return HttpResponse(response.format(question_id))def vote(request, question_id): return HttpResponse(f"You're voting on question {question_id}")
在查看之前,能够创立一些Question
的数据。
启动Django
服务器,在浏览器输出http://127.0.0.1:8000/polls/
进行查看。
五、自定义模板
5.1 模板目录阐明
首先,在polls
目录下创立一个templates
目录。Django
会在这个目录里查找模板文件。
在settings.py
配置文件中,TEMPLATES
配置项形容了Django
如何载入和渲染模板。默认设置了DjangoTemplates
后端,并将APP_DIRS
设置为True
。这一选项将会让DjangoTemplates
在每个INSTALLED_APPS
文件夹下寻找templates
子目录。
这就是为什么没有进行DIRS
的设置,Django
也能正确找到polls
的模板地位的起因。
阐明:尽管能够将模板文件间接放在polls/templates
文件夹中(而不是再建设一个polls
子文件夹),然而这样做不太好。Django
会抉择第一个匹配的模板文件,如果有一个模板文件和另一个利用中的指标文件重名,Django
没有方法辨别它们。咱们须要Django
抉择正确的模板,最好的办法就是把它们放入各自的命名空间中,也就是把这些模板放入一个和本身利用重名的子文件夹里。
5.2 创立模板文件
// polls/templates/polls/index.html{% if latest_question_list %} <ul> {% for question in latest_question_list %} <li><a href="/polls/{{ question.id }}">{{ question.question_text }}</a></li> {% endfor %} </ul>{% endif %}
# polls/templates/polls/detail.html<h1>{{ question.question_text }}</h1><ul> {% for choice in question.choice_set.all %} <li>{{ choice.choice_text }}</li> {% endfor %}</ul>
5.3 应用模板
# polls/views.pyfrom django.shortcuts import renderfrom django.http import HttpResponsefrom django.template import loaderfrom .models import Questiondef index(request): latest_question_list = Question.objects.order_by("-pub_date")[:5] template = loader.get_template("polls/index.html") context = {"latest_question_list": latest_question_list} return HttpResponse(template.render(context, request))
开启Django
服务器,输出http://127.0.0.1:8000/polls/进行查看。
5.4 应用模板(一个快捷函数):render()
from django.http import HttpResponsefrom django.shortcuts import renderfrom django.template import loaderfrom .models import Questiondef index(request): latest_question_list = Question.objects.order_by("-pub_date")[:5] context = {"latest_question_list": latest_question_list} return render(request, "polls/index.html", context)
应用render
,不再须要导入loader
和HttpResponse
。不过如果还有其余函数(比方detail
、results
和vote
)须要用到的话,就须要放弃HttpResponse
的导入。
5.5 抛出404谬误
# polls/views.pyfrom django.http import HttpResponse, Http404from django.shortcuts import renderfrom django.template import loaderfrom .models import Questiondef detail(request, question_id): try: question = Question.objects.get(pk=question_id) except Question.DoesNotExist: raise Http404("Question does not exist") return render(request, "polls/detail.html", {"question": question})
开启Django
服务器,输出http://127.0.0.1:8000/polls/1/或http://127.0.0.1:8000/polls/100/进行查看。
一个快捷函数:get_object_or_404()
# polls/views.pyfrom django.http import HttpResponse, Http404from django.shortcuts import render, get_object_or_404from django.template import loaderfrom .models import Questiondef detail(request, question_id): question = get_object_or_404(Question, pk=question_id) return render(request, "polls/detail.html", {"question": question})
六、取出模板中的硬编码URL
在polls/index.html
中,链接硬编码:
<li><a href="/polls/{{ question.id }}">{{ question.question_text }}</a></li>
问题在于,硬编码和强耦合的链接,对于一个蕴含很多利用的我的项目来说,批改起来十分困难。然而,在polls.urls
的url()
函数中,通过name
参数为URL
定义了命名,能够应用{% url %}
标签代替它:
<li><a href="{% url "detail" question.id %}">{{ question.question_text }}</a></li>
这个标签的工作形式是,在polls.urls
模块的URL
定义中寻找具备指定名字的条目。
如果想扭转投票详情视图的URL
,比方想改成polls/specifics/12/
,不必在模板里批改任何货色(包含其余模板),只有在polls/urls.py
里略微批改以下就能够:
path("specifics/<int:question_id>/", views.detail, name="detail")
七、为URL
增加命名空间
在一个实在的Django
我的项目中,可能会有五个、十个、二十个,甚至更多利用。Django
如何分辨重命名的URL
呢?
在根URLconf
中增加命名空间。在polls/urls.py
文件中稍作批改,加上app_name
设置命名空间:
# polls/urls.pyfrom django.urls import pathfrom . import viewsapp_name = "polls"urlpatterns = [ path("", views.index, name="index"), path("<int:question_id>/", views.detail, name="detail"), path("<int:question_id>/results/", views.results, name="results"), path("<int:question_id>/vote/", views.vote, name="vote"),]
当初编辑polls/index.html
,批改:
<li><a href="{% url 'detail' question.id %}">{{ question.question_text }}</a></li>
批改为指向具备命名空间的具体视图:
<li><a href="{% url 'polls:detail' question.id %}">{{ question.question_text }}</a></li>
总结
本文简略介绍了Django
模板、自定义模板,以及模板和URL
之间的映射关系。