Django学习记录(十二):Django by example -- Blog(八)
PyxYuYu opened this issue · 0 comments
PyxYuYu commented
The land did not move, but moved. The sea was not still, yet was still.
0x01 Django
- Build a Blog Application
-
Creating templates for your views
- 编辑
post/list.html
,继承blog/base.html
{% extends "blog/base.html" %} {% block title %}My Blog{% endblock %} {% block content %} <h1>My Blog</h1> {% for post in posts %} <h2> <a href="{{ post.get_absolute_url }}"> {{ post.title }} </a> </h2> <p class="date"> Published {{ post.publish }} by {{ post.author }} </p> {{ post.body|truncatewords:30|linebreaks }} {% endfor %} {% endblock %}
{% extends %}
: 继承的标签,继承blog/base.hteml
,之前的两处block
,title
和content
填入相应的内容post.body
: 显示内容的地方用了两个过滤标签,一个是截断truncatewords:30
,一个是换行符linebreaks
- 编辑
post/detail.html
,同样继承blog/base.html
{% extends "blog/base.html" %} {% block title %}{{ post.title }}{% endblock %} {% block content %} <h1>{{ post.title }}</h1> <p class="date"> Published {{ post.publish }} by {{ post.author }} </p> {{ post.body|linebreaks }} {% endblock %}
- 注意:
- 发布的文章必须属性是
published
views.py
中publish__year
等的双下划线
代表属性的意思
- 发布的文章必须属性是
- 编辑
-
Adding pagination
Django
有一个内建的控制分页类来管理文章页数- 编辑
views.py
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger def post_list(request): object_list = Post.published.all() paginator = Paginator(object_list, 3) #每页3篇文章 page = request.GET.get('page') try: posts = paginator.page(page) except PageNotAnInteger: posts = paginator.page(1) except EmptyPage: posts = paginator.page(paginator.num_pages) return render(request, 'blog/post/list.html', {'page': page, 'posts': posts})
paginator.page(self, number)
: 返回第number
页的数据内容- 不是整数就返回第一页,超过了最后一页的范围,就返回最后一页
- 创建一个
pagination.html
模板,可以导入到任何其他模板中 - 在
templates
文件夹下创建
<div class="pagination"> <span class="step-links"> <% if page.has_previous %> <a href="?page={{ page.previous_page_number }}">Previous</a> <% endif %> <span class="current"> Page {{ page.number }} of {{ page.paginator.num_pages }}. </span> {% if page.has_next %} <a href="?page={{ page.next_page_number }}">Next</a> {% endif %} </span> </div>
- 这个模板中用了
page
对象 - 返回到
blog/post/list.html
中,将上面的模板导入
{% block content %} ... {% include "pagination.html" with page=posts %} {% endblock %}
- 注意:
pagination.html
文件放在templates
文件夹根目录下
-
Using class-based views
- 利用
Django
自带的基类来实现post_list
- 编辑
views.py
from django.views.generic import ListView class PostListView(ListView): queryset = Post.published.all() context_object_name = 'posts' paginate_by = 3 template_name = 'blog/post/list.html'
- 指定了一个
QuerySet
来接受所有的objects
- 自定义查询结果命名为
context_object_name
,默认为object_list
- 分页结果显示3篇每页
- 用指定的模板,默认为
blog/post_list.html
- 之后,
urls.py
中需要注释掉之前的post_list URL pattern
,增加
url(r'^$', views.PostListView.as_view(), name='post_list')
- 为了保证控制分页的模板继续工作,
blog/posts/list.html
中的with page=posts
需要更改
{% include "pagination.html" with page=page_obj %}
Django
中的ListView
基类选择页面的参数名为page_obj
- 注意:使用
class
类 来实现了 之前的def post_list
函数功能
- 利用
-
ListView
类是显示对象列表,其中最重要的get
和post
,实际对应http
中的get
和post
方法,as_view()
方法是处理request-response
过程的接入点,在urls.py
中会被调用,dispatch()
方法就是上面提到的get
和post
方法
-