Django的博客项目创建(5)

利用Django实现的功能如下:
  • Post模型增加保存时生成摘要功能
  • views的视图函数改为视图类
  • 优化评论显示页面
  • 增加页面分页功能
具体实现过程如下:

1.Post模型增加保存时生成摘要功能

在模型保存时,自定义一些功能,此时我们不能重写__init__,应该利用save()进行自定义的初始化操作。在Post模型中,我们需要有能自动生成摘要的功能,以便于在博客列表中显示部分摘要。

...
import markdown
from django.utils.html import strip_tags


class Post(models.Model):
    ...

    def save(self, *args, **kwargs):
        if not self.excerpt:
            md = markdown.Markdown(extensions=[
                'markdown.extensions.extra',
                'markdown.extensions.codehilite',
                ]) 
            self.excerpt = strip_tags(md.convert(self.body)[:20])
        #继承并重写save函数
        super(Post, self).save(*args, **kwargs)

    class Meta:
        #帖子返回时的排序方式,按时间倒序排。
        ordering = ['-created_time']

2.把视图函数改为视图类:
视图类继承了ListView和DetailView等类。与视图函数相比,视图类的代码更简洁方便,并带有许多使用的功能。我们只需要继承相应的功能,然后重写方法,添上我们自定义的内容即可。

...
from .models import Post, Category
from django.views.generic import ListView, DetailView
from comments.forms import CommentForm

class IndexView(ListView):
    model = Post
    template_name = 'blog/index.html'
    context_object_name = 'post_list'
    paginate_by = 1


class PostDetailView(DetailView):
    model = Post
    template_name = 'blog/detail.html'
    #上下文环境对象命名为post,方便在模板中使用        
    context_object_name = 'post'

    #继承父类的get,并增加访问量加1的功能
    def get(self, request, *args, **kwargs):
        response = super(PostDetailView, self).get(request, *args, **kwargs)
        self.object.increase_views()

        return response


    #继承父类的get_object,同时对post.body进行markdown处理
    def get_object(self, queryset=None):
        post = super(PostDetailView, self).get_object(queryset=None)

        post.body = markdown.markdown(post.body, extensions=[
            'markdown.extensions.extra',
        'markdown.extensions.codehilite',
        'markdown.extensions.toc',])
        return post

    #继承父类的get_context_data,并增加form,comment_list到上下文数据context中,这些数据将会在模板中使用
    def get_context_data(self, **kwargs):
        context = super(PostDetailView, self).get_context_data(**kwargs)
        form = CommentForm()
        comment_list = self.object.comment_set.all()
        context.update(
                {
                'form':form,
            'comment_list':comment_list

                }

            )
        return context

def archives(request, year, month):
    post_list = Post.objects.filter(created_time__year=year,
        created_time__month=month).order_by('-created_time')
    return render(request, 'blog/index.html', context={'post_list':post_list})


class CategoryView(ListView):
    model = Post
    template_name = 'blog/index.html'
    context_object_name = 'post_list'


    def get_queryset(self):
        cate = get_object_or_404(Category, pk=self.kwargs.get('pk'))

        #返回当前category对象所对应的post
        return super(CategoryView,self).get_queryset().filter(category=cate).order_by('-created_time')

urls.py的修改:
在views的视图改为视图函数后,相应的url也需要做更改,具体如下:

from django.conf.urls import url,include
from django.contrib import admin

from . import views

app_name = 'blog'

urlpatterns = [
    url(r'^$', views.IndexView.as_view(), name='index'),
    url(r'^(?P<pk>[0-9]+)/$', views.PostDetailView.as_view(), name='detail'),
    url(r'^archives/(?P<year>[0-9]{4})/(?P<month>[0-9]{1,2})/$', views.archives, name='archives'),
    url(r'^category/(?P<pk>[0-9]+)/$', views.CategoryView.as_view(), name='category'),
]

3.优化评论页面:
模板修改,评论的显示页面得到优化。

...
<div class="comment-list-panel">
            <h3>评论列表,共 <span>{{ post.comment_set.count }}</span> 条评论</h3>
            <ul class="comment-list list-unstyled">
                {% for comment in comment_list %}
                    <li class="comment-item">
                        <span class="nickname">{{ comment.name }}</span>
                        <time class="submit-date"
                              datetime="{{ comment.created_time }}">{{ comment.created_time }}</time>
                        <div class="text">
                            {{ comment.text }}
                        </div>
                    </li>
                {% empty %}
                    暂无评论
                {% endfor %}
            </ul>
        </div>

...

4.添加分页功能:
在views中重写get_context_data()方法,并添加自定义方法pagination_data()。

class IndexView(ListView):
    model = Post
    template_name = 'blog/index.html'
    context_object_name = 'post_list'
    #每个分页只有1帖子个内容
    paginate_by = 1
    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        #获得分页的相关数据
        paginator = context.get('paginator')
        page = context.get('page_obj')
        is_paginated = context.get('is_paginated')
        #把分页的相关数据传入方法中,获得处理后的分页数据
        pagination_data = self.pagination_data(paginator, page, is_paginated)
        #分页数据更新到上下文环境中
        context.update(pagination_data)
        return context

    def pagination_data(self, paginator, page, is_paginated):
        if not is_paginated:
            return {}
        left = []
        right = []
        left_has_more = False
        right_has_more = False
        first = False
        last = False
        page_number = page.number
        total_pages = paginator.num_pages
        page_range = paginator.page_range
        if page_number ==1:
            right = page_range[page_number:page_number + 2]
            if right[-1] < total_pages -1:
                right_has_more = True

            if right[-1] <total_pages:
                last = True

        elif page_number == total_pages:
            left = page_range[(page_number-3) if(page_number - 3) > 0 else 0:page_number -1]
            if left[0] > 2:
                left_has_more = True

            if left[0] > 1:
                first = True

        else:
            left = page_range[(page_number-3) if (page_number-3) > 0 else 0: page_number-1]
            right = page_range[page_number:page_number+2]

            if right[-1] < total_pages -1:
                right_has_more = True

            if right[-1] < total_pages:
                last = True

            if left[0] > 2:
                left_has_more = True

            if left[0] > 1:
                first = True

        data = {
            'left':left,
            'right':right,
            'left_has_more':left_has_more,
            'right_has_more':right_has_more,
            'first':first,
            'last':last,

        }
        return data

在index.html中添加分页功能的模板内容,具体如下:

{% if is_paginated %}
        <div class="pagination">
            <ul>
                {% if first %}
                    <li><a href="?page=1">1</a></li>
                {% endif %}
                {% if left %}
                    {% if left_has_more %}
                        <li><span>...</span></li>
                    {% endif %}
                    {% for i in left %}
                        <li><a href="?page={{ i }}">{{ i }}</a></li>
                    {% endfor %}
                {% endif %}
                <li class="current"><a href="?page={{ page_obj.number }}">{{ page_obj.number }}</a></li>
                {% if right %}
                    {% for i in right %}
                        <li><a href="?page={{ i }}">{{ i }}</a></li>
                    {% endfor %}
                    {% if right_has_more %}
                        <li><span>...</span></li>
                    {% endif %}
                {% endif %}
                {% if last %}
                    <li><a href="?page={{ paginator.num_pages }}">{{ paginator.num_pages }}</a></li>
                {% endif %}
            </ul>
        </div>
    {% endif %}

摘要的页面显示效果:
摘要显示效果

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值