• python 全栈开发,Day81(博客系统个人主页,文章详情页)


    一、个人主页

    随笔分类

    需求:查询当前站点每一个分类的名称以及对应的文章数

    完成这个需求,就可以展示左侧的分类

    它需要利用分组查询,那么必须要会基于双下划线的查询。

    基于双下划线的查询,简单来讲,就是用join。将多个表拼接成一张表,那么就可以单表操作了!

    表关系图

    图中箭头开始的英文字母表示关联字段

    按照箭头方向查询,表示正向查询,否则为反向查询

    分解步骤:

    先来查询每一个分类的名称以及对应的文章数

    看上面的关系图,以Category表为基础表来查询Article表对应的文章数,需要用到反向查询。

    记住一个原则,正向查询使用字段,反向查询使用表名

    修改views.py,导入相关表和聚合函数

    from django.shortcuts import render,HttpResponse,redirect
    from django.contrib import auth
    from blog.models import Article,UserInfo,Blog,Category,Tag
    from django.db.models import Sum,Avg,Max,Min,Count
    # Create your views here.
    def login(request):
    
    </span><span style="color: #0000ff;">if</span> request.method==<span style="color: #800000;">"</span><span style="color: #800000;">POST</span><span style="color: #800000;">"</span><span style="color: #000000;">:
        user</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">user</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        pwd</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">pwd</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;"> 用户验证成功,返回user对象,否则返回None</span>
        user=auth.authenticate(username=user,password=<span style="color: #000000;">pwd)
        </span><span style="color: #0000ff;">if</span><span style="color: #000000;"> user:
            </span><span style="color: #008000;">#</span><span style="color: #008000;"> 登录,注册session</span>
            <span style="color: #008000;">#</span><span style="color: #008000;"> 全局变量 request.user=当前登陆对象(session中)</span>
    

    auth.login(request,user)
    return redirect("/index/")

    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">login.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    

    def index(request):
    article_list
    =Article.objects.all()
    return render(request,"index.html",{"article_list":article_list})

    def logout(request): # 注销
    auth.logout(request)
    return redirect("/index/")

    def homesite(request,username):
    """
    查询
    :param request:
    :param username:
    :return:
    """
    # 查询当前站点的用户对象
    user=UserInfo.objects.filter(username=username).first()
    if not user:
    return render(request,"not_found.html")
    # 查询当前站点对象
    blog=user.blog

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    
    ret </span>= Category.objects.values(<span style="color: #800000;">"</span><span style="color: #800000;">pk</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>,<span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(ret)
    
    dict </span>= {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span><span style="color: #000000;">:blog,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list,
            }
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    解释:

    pk表示主键

    上面这句sql表示以Category表id来分组,得到分类名以及统计数

    多添加几篇文章,给另外一个用户也添加几篇文章

    访问个人站点:http://127.0.0.1:8000/xiao/

    查看Pycharm控制台输出:

    <QuerySet [{'c': 1, 'title': 'python'}, {'c': 1, 'title': 'ajax'}, {'c': 2, 'title': 'django'}, {'c': 2, 'title': 'linux运维'}]>

    上面得到了所有文章的分类以及文章数。

    再来查询当前站点每一个分类的名称以及对应的文章数

    思路:只需要对Category表进行筛选,过滤中当前站点用户的分类

    在homesite视图函数中,已经有一个当前站点的blog对象。

    在Category模型表中,有一个blog属性,它和blog是一对多关系。那么只需要blog=blog,就可以了

    修改视图函数homesite的ret变量

    ret = Category.objects.filter(blog=blog).annotate(c=Count("article__title")).values("title","c")

    注意:等式左边的blog表示Category模型表的blog属性,实际上就是blog_id字段

    等式右边的是blog变量,它是一个model对象。那么blog=blog,就可以查询出,当前站点的分类了!

    刷新网页,查看Pycharm控制台输出:

    <QuerySet [{'title': 'python', 'c': 1}, {'title': 'ajax', 'c': 1}, {'title': 'django', 'c': 2}]

    既然结果出来了,模板就可以渲染了

    修改homesite视图函数,完整代码如下:

    from django.shortcuts import render,HttpResponse,redirect
    from django.contrib import auth
    from blog.models import Article,UserInfo,Blog,Category,Tag
    from django.db.models import Sum,Avg,Max,Min,Count
    # Create your views here.
    def login(request):
    
    </span><span style="color: #0000ff;">if</span> request.method==<span style="color: #800000;">"</span><span style="color: #800000;">POST</span><span style="color: #800000;">"</span><span style="color: #000000;">:
        user</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">user</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        pwd</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">pwd</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;"> 用户验证成功,返回user对象,否则返回None</span>
        user=auth.authenticate(username=user,password=<span style="color: #000000;">pwd)
        </span><span style="color: #0000ff;">if</span><span style="color: #000000;"> user:
            </span><span style="color: #008000;">#</span><span style="color: #008000;"> 登录,注册session</span>
            <span style="color: #008000;">#</span><span style="color: #008000;"> 全局变量 request.user=当前登陆对象(session中)</span>
    

    auth.login(request,user)
    return redirect("/index/")

    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">login.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    

    def index(request):
    article_list
    =Article.objects.all()
    return render(request,"index.html",{"article_list":article_list})

    def logout(request): # 注销
    auth.logout(request)
    return redirect("/index/")

    def homesite(request,username):
    """
    查询
    :param request:
    :param username:
    :return:
    """
    # 查询当前站点的用户对象
    user=UserInfo.objects.filter(username=username).first()
    if not user:
    return render(request,"not_found.html")
    # 查询当前站点对象
    blog=user.blog
    print(blog,type(blog))

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    
    cate_list </span>= Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(cate_list)
    
    dict </span>= {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span><span style="color: #000000;">:blog,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">cate_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:cate_list
            }
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    修改homesite.html

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    
    &lt;style&gt;
        *<span style="color: #000000;"> {
            margin: 0;
            padding: 0;
        }
    
        .header {
             </span>100%<span style="color: #000000;">;
            height: 59px;
            background</span>-color: <span style="color: #008000;">#</span><span style="color: #008000;">369;</span>
    

    }

        .header .title {
            line</span>-<span style="color: #000000;">height: 59px;
            color: white;
            font</span>-<span style="color: #000000;">weight: lighter;
            margin</span>-<span style="color: #000000;">left: 20px;
            font</span>-<span style="color: #000000;">size: 18px;
        }
    
        .left_region {
            margin</span>-<span style="color: #000000;">top: 10px;
        }
    
        .info {
            margin</span>-<span style="color: #000000;">top: 10px;
            color: darkgray;
    
        }
    
        h5 a {
            color: </span><span style="color: #008000;">#</span><span style="color: #008000;">105cb6;</span>
            font-<span style="color: #000000;">size: 14px;
            font</span>-<span style="color: #000000;">weight: bold;
            text</span>-<span style="color: #000000;">decoration: underline;
        }
    
    </span>&lt;/style&gt;
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">stylesheet</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/css/bootstrap.css</span><span style="color: #800000;">"</span>&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/js/jquery.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/js/bootstrap.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        Panel content
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        Panel content
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;
    
            &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                {</span>% <span style="color: #0000ff;">for</span> article <span style="color: #0000ff;">in</span> article_list %<span style="color: #000000;">}
    
                    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_item clearfix</span><span style="color: #800000;">"</span>&gt;
                        &lt;h5&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ article.title }}&lt;/a&gt;&lt;/h5&gt;
                        &lt;div&gt;
    
                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                        &lt;/div&gt;
                        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;img src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/img/icon_comment.gif</span><span style="color: #800000;">"</span> alt=<span style="color: #800000;">""</span>&gt;&lt;<span style="color: #000000;">a
                                href</span>=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                        &lt;/div&gt;
                    &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;
    
        &lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    values_list返回的是一个元组,所以模板中,直接用cate.0就可以取到分类名

    刷新网页,效果如下:

    我的标签

    我的标签和随笔的查询语句是类似的,换一个表名,就可以了!

    先在admin后台为不同的用户,添加标签

    由于admin后台无法直接将博客表和标签表做对应关系,所以只能手动绑定关系。

    使用navicat打开blog_article2tag表

    注意:以实际情况为准

     

    修改homesite视图函数,查询我的标签

    def homesite(request,username):
        """
        查询
        :param request:
        :param username:
        :return:
        """
        # 查询当前站点的用户对象
        user=UserInfo.objects.filter(username=username).first()
        if not user:
            return render(request,"not_found.html")
        # 查询当前站点对象
        blog=user.blog
        print(blog,type(blog))
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(cate_list)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;">我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(tag_list)
    
    dict </span>= {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span><span style="color: #000000;">:blog,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">cate_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:cate_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">tag_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:tag_list,
            }
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    刷新网页,查看Pycharm控制台

    <QuerySet [('python全栈', 2)]>

    修改homesite.html,开始渲染网页

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    
    &lt;style&gt;
        *<span style="color: #000000;"> {
            margin: 0;
            padding: 0;
        }
    
        .header {
             </span>100%<span style="color: #000000;">;
            height: 59px;
            background</span>-color: <span style="color: #008000;">#</span><span style="color: #008000;">369;</span>
    

    }

        .header .title {
            line</span>-<span style="color: #000000;">height: 59px;
            color: white;
            font</span>-<span style="color: #000000;">weight: lighter;
            margin</span>-<span style="color: #000000;">left: 20px;
            font</span>-<span style="color: #000000;">size: 18px;
        }
    
        .left_region {
            margin</span>-<span style="color: #000000;">top: 10px;
        }
    
        .info {
            margin</span>-<span style="color: #000000;">top: 10px;
            color: darkgray;
    
        }
    
        h5 a {
            color: </span><span style="color: #008000;">#</span><span style="color: #008000;">105cb6;</span>
            font-<span style="color: #000000;">size: 14px;
            font</span>-<span style="color: #000000;">weight: bold;
            text</span>-<span style="color: #000000;">decoration: underline;
        }
    
    </span>&lt;/style&gt;
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">stylesheet</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/css/bootstrap.css</span><span style="color: #800000;">"</span>&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/js/jquery.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/js/bootstrap.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        Panel content
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;
    
            &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                {</span>% <span style="color: #0000ff;">for</span> article <span style="color: #0000ff;">in</span> article_list %<span style="color: #000000;">}
    
                    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_item clearfix</span><span style="color: #800000;">"</span>&gt;
                        &lt;h5&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ article.title }}&lt;/a&gt;&lt;/h5&gt;
                        &lt;div&gt;
    
                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                        &lt;/div&gt;
                        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;img src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/img/icon_comment.gif</span><span style="color: #800000;">"</span> alt=<span style="color: #800000;">""</span>&gt;&lt;<span style="color: #000000;">a
                                href</span>=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                        &lt;/div&gt;
                    &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;
    
        &lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    刷新网页,效果如下:

    注意:如果网页数据没有展示,请一定要查看数据库是否有对应的记录!

    日期归档

    查看Article表的create_time字段

    注意:它的时间后面,有很多小数点。每一条是不一样的,所以不能直接分组,否则没有意义!

    要实现这个功能,有3个小知识点:

    • 1.dateformat
    • 2.extra
    • 3.单表分组查询

    dateformat

    DATE_FORMAT() 函数用于以不同的格式显示日期/时间数据。

    每个数据库都有日期/时间 处理的函数,在MySQL中,叫dateformat。SQLite中,叫strftime

    举例:

    #截取年月日
    mysql> select date_format("2018-07-11 06:39:07",'%Y-%m-%d') as date;
    +------------+
    | date       |
    +------------+
    | 2018-07-11 |
    +------------+
    1 row in set (0.00 sec)
    

    #截取年月
    mysql> select date_format("2018-07-11 06:39:07",'%Y-%m') as date;
    +---------+
    | date |
    +---------+
    | 2018-07 |
    +---------+
    1 row in set (0.00 sec)

    View Code

    extra

    有些情况下,Django的查询语法难以表达复杂的where子句,对于这种情况, Django 提供了extra()QuerySet修改机制 。它能在QuerySet生成的SQL从句中注入新子句,extra可以指定一个或多个参数,例如select、where或tables。 这些参数都不是必须的,但是至少要使用一个。

    语法:

    extra(select=None, where=None, params=None, 
          tables=None, order_by=None, select_params=None)

    select参数

    select参数可以在select从句中添加其他字段信息,它应该是一个字典,存放着属性名到 SQL 从句的映射。

    举例:

    修改homesite视图函数,增加几行代码

    def homesite(request,username):
        """
        查询
        :param request:
        :param username:
        :return:
        """
        # 查询当前站点的用户对象
        user=UserInfo.objects.filter(username=username).first()
        if not user:
            return render(request,"not_found.html")
        # 查询当前站点对象
        blog=user.blog
        print(blog,type(blog))
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(cate_list)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;">我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(tag_list)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">测试日期</span>
    test_date = Article.objects.filter(comment_count=0).extra(select={<span style="color: #800000;">'</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">'</span>: <span style="color: #800000;">"</span><span style="color: #800000;">create_time &gt; '2017-09-05'</span><span style="color: #800000;">"</span><span style="color: #000000;">})
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(test_date)
    </span><span style="color: #0000ff;">for</span> i <span style="color: #0000ff;">in</span><span style="color: #000000;"> test_date:
        </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(i.y_m_date)
    
    dict </span>= {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span><span style="color: #000000;">:blog,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">cate_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:cate_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">tag_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:tag_list,
            }
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    大概意思就是,查询创建时间大于2017-09-05的记录

    刷新网页,查看Pycharm控制台输出:

    1
    1
    1

    如果条件成立,返回1。否则返回0

    需要注意的是:此时已经给Article表增加一个临时字段y_m_date。它在内存中,每次使用extra查询才会存在!

    单表分组查询

    查询当前用户的所有文章,根据日期归档

    def homesite(request,username):
        """
        查询
        :param request:
        :param username:
        :return:
        """
        # 查询当前站点的用户对象
        user=UserInfo.objects.filter(username=username).first()
        if not user:
            return render(request,"not_found.html")
        # 查询当前站点对象
        blog=user.blog
        print(blog,type(blog))
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(cate_list)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;">我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(tag_list)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;">日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #0000ff;">print</span><span style="color: #000000;">(date_list)
    
    dict </span>= {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span><span style="color: #000000;">:blog,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">cate_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:cate_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">tag_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:tag_list,
            </span><span style="color: #800000;">"</span><span style="color: #800000;">date_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:date_list,
            }
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    解释:

    SQLite的日期格式化使用strftime,它使用2个%号来区分。

    user=user  等式左边的user是Article模型表的user属性,也就是user_id。等式右边的user是UserInfo表的model对象!

    刷新页面,查看Pychram控制台输出:

    <QuerySet [('2018/07', 4)]>

    修改homesite.html,开始渲染网页

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    
    &lt;style&gt;
        *<span style="color: #000000;"> {
            margin: 0;
            padding: 0;
        }
    
        .header {
             </span>100%<span style="color: #000000;">;
            height: 59px;
            background</span>-color: <span style="color: #008000;">#</span><span style="color: #008000;">369;</span>
    

    }

        .header .title {
            line</span>-<span style="color: #000000;">height: 59px;
            color: white;
            font</span>-<span style="color: #000000;">weight: lighter;
            margin</span>-<span style="color: #000000;">left: 20px;
            font</span>-<span style="color: #000000;">size: 18px;
        }
    
        .left_region {
            margin</span>-<span style="color: #000000;">top: 10px;
        }
    
        .info {
            margin</span>-<span style="color: #000000;">top: 10px;
            color: darkgray;
    
        }
    
        h5 a {
            color: </span><span style="color: #008000;">#</span><span style="color: #008000;">105cb6;</span>
            font-<span style="color: #000000;">size: 14px;
            font</span>-<span style="color: #000000;">weight: bold;
            text</span>-<span style="color: #000000;">decoration: underline;
        }
    
    </span>&lt;/style&gt;
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">stylesheet</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/css/bootstrap.css</span><span style="color: #800000;">"</span>&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/js/jquery.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/js/bootstrap.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> date <span style="color: #0000ff;">in</span> date_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ date.0 }}({{ date.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;
    
            &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                {</span>% <span style="color: #0000ff;">for</span> article <span style="color: #0000ff;">in</span> article_list %<span style="color: #000000;">}
    
                    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_item clearfix</span><span style="color: #800000;">"</span>&gt;
                        &lt;h5&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ article.title }}&lt;/a&gt;&lt;/h5&gt;
                        &lt;div&gt;
    
                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                        &lt;/div&gt;
                        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;img src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/img/icon_comment.gif</span><span style="color: #800000;">"</span> alt=<span style="color: #800000;">""</span>&gt;&lt;<span style="color: #000000;">a
                                href</span>=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                        &lt;/div&gt;
                    &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;
    
        &lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    刷新网页,效果如下:

    左侧面板添加链接

    接下来,需要点击左边的分类、标签、归档,显示相关的文章

    访问博客园左侧的分类、标签、归档,方法它有一个规律

    标签:

    http://www.cnblogs.com/用户名/tag/标签名/

    分类:

    https://www.cnblogs.com/用户名/category/分类id.html

    归档:

    https://www.cnblogs.com/用户名/archive/年/月.html

    修改urls.py,增加3个路径。注意要导入re_path模块

    re_path('(?P<username>w+)/category/(?P<params>.*)', views.homesite),
    re_path('(?P<username>w+)/tag/(?P<params>.*)', views.homesite),
    re_path('(?P<username>w+)/achrive/(?P<params>.*)', views.homesite),

    仔细观察个人站点网页的布局

    发现,点击不同的分类、标签、归档。红色区域和绿色区域始终不变,只有紫色区域在变动。变动区域取决于article_list变量!

    那么个人站点首页、分类、标签、归档这4种url可以共用一个视图函数homesite模板以及视图函数。

    重新修改urls.py,完整代码如下:

    from django.contrib import admin
    from django.urls import path,re_path
    

    from blog import views
    urlpatterns
    = [
    path(
    'admin/', admin.site.urls),
    path(
    'login/', views.login),
    path(
    'index/', views.index),
    path(
    'logout/', views.logout),
    path(
    '', views.index),

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 跳转</span>
    re_path(<span style="color: #800000;">'</span><span style="color: #800000;">(?P&lt;username&gt;w+)/(?P&lt;condition&gt;category|tag|achrive)/(?P&lt;params&gt;.*)/$</span><span style="color: #800000;">'</span><span style="color: #000000;">, views.homesite),
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 个人站点</span>
    re_path(<span style="color: #800000;">'</span><span style="color: #800000;">(?P&lt;username&gt;w+)/$</span><span style="color: #800000;">'</span><span style="color: #000000;">, views.homesite),
    

    ]

    View Code

    那么问题来了,访问个人站点时,不需要额外的参数。

    访问分类/标签/归档 这2个类别是,必须要2个额外的变量。分别是类别、类别参数。

    homesite视图函数,如果分别接收呢?答案是,使用**kwargs,它可以接收可变的关键字参数,至少1个或者多个参数!

    修改homesite.html,增加一个网页图标,否则待会测试时,会有2次请求。

    如果网页没有图标,每次会请求一次网络请求,请求favicon.ico

    在title标签下面,增加一行

    <link rel="shortcut icon" href="https://common.cnblogs.com/favicon.ico" type="image/x-icon" />

    修改homesite视图函数

    def homesite(request,username,**kwargs):
        """
        查询
        :param request:
        :param username:
        :return:
        """
        print("kwargs", kwargs)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点的用户对象</span>
    user=UserInfo.objects.filter(username=<span style="color: #000000;">username).first()
    </span><span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> user:
        </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">not_found.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点对象</span>
    blog=<span style="color: #000000;">user.blog
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    article_list=Article.objects.filter(user__username=<span style="color: #000000;">username)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(cate_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;">我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(tag_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;">日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(date_list)</span>
    
    dict = {"blog":blog, "article_list":article_list, "cate_list":cate_list, "tag_list":tag_list, "date_list":date_list, }
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    访问个人站点: http://127.0.0.1:8000/xiao/

    Pycharm控制台输出:kwargs {}

    访问个人分类python: http://127.0.0.1:8000/xiao/category/python/

    Pycharm控制台输出:kwargs {'params': 'python/', 'condition': 'category'}

    访问个人标签: http://127.0.0.1:8000/xiao/tag/python全栈/

    Pycharm控制台输出:kwargs {'params': 'python全栈/', 'condition': 'tag'}

    访问个人归档: http://127.0.0.1:8000/xiao/achrive/2018/07

    Pycharm控制台输出:kwargs {'params': '2018/07', 'condition': 'achrive'}

    注意:要带上用户名,否则出现404错误

    那么,只需要判断kwargs变量,就可以区分了!

    修改homesite视图函数

    def homesite(request,username,**kwargs):
        """
        查询
        :param request:
        :param username:
        :return:
        """
        print("kwargs", kwargs)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点的用户对象</span>
    user=UserInfo.objects.filter(username=<span style="color: #000000;">username).first()
    </span><span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> user:
        </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">not_found.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点对象</span>
    blog=<span style="color: #000000;">user.blog
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    <span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> kwargs:
        article_list </span>= Article.objects.filter(user__username=<span style="color: #000000;">username)
    
    </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
        condition </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">condition</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        params </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">params</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;">判断分类、随笔、归档</span>
        <span style="color: #0000ff;">if</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">category</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(category__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">elif</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">tag</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(tags__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
            year, month </span>= params.split(<span style="color: #800000;">"</span><span style="color: #800000;">/</span><span style="color: #800000;">"</span><span style="color: #000000;">)
            article_list </span>= Article.objects.filter(user__username=username).filter(create_time__year=<span style="color: #000000;">year,
                                                                                  create_time__month</span>=<span style="color: #000000;">month)
    </span><span style="color: #008000;">#</span><span style="color: #008000;">随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(cate_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;">我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(tag_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;">日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(date_list)</span>
    
    dict = {"blog":blog, "article_list":article_list, "cate_list":cate_list, "tag_list":tag_list, "date_list":date_list, "username":username, }
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,dict)</pre>
    
    View Code

    修改homesite.html

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <link rel="shortcut icon" href="https://common.cnblogs.com/favicon.ico" type="image/x-icon"/>
    
    &lt;style&gt;
        *<span style="color: #000000;"> {
            margin: 0;
            padding: 0;
        }
    
        .header {
             </span>100%<span style="color: #000000;">;
            height: 59px;
            background</span>-color: <span style="color: #008000;">#</span><span style="color: #008000;">369;</span>
    

    }

        .header .title {
            line</span>-<span style="color: #000000;">height: 59px;
            color: white;
            font</span>-<span style="color: #000000;">weight: lighter;
            margin</span>-<span style="color: #000000;">left: 20px;
            font</span>-<span style="color: #000000;">size: 18px;
        }
    
        .left_region {
            margin</span>-<span style="color: #000000;">top: 10px;
        }
    
        .info {
            margin</span>-<span style="color: #000000;">top: 10px;
            color: darkgray;
    
        }
    
        h5 a {
            color: </span><span style="color: #008000;">#</span><span style="color: #008000;">105cb6;</span>
            font-<span style="color: #000000;">size: 14px;
            font</span>-<span style="color: #000000;">weight: bold;
            text</span>-<span style="color: #000000;">decoration: underline;
        }
    
    </span>&lt;/style&gt;
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">stylesheet</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/css/bootstrap.css</span><span style="color: #800000;">"</span>&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/js/jquery.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/js/bootstrap.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="/{{ username }}/category/{{ cate.0 }}">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/tag/{{ tag.0 }}</span><span style="color: #800000;">"</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> date <span style="color: #0000ff;">in</span> date_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/achrive/{{ date.0 }}</span><span style="color: #800000;">"</span>&gt;{{ date.0 }}({{ date.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;
    
            &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                {</span>% <span style="color: #0000ff;">for</span> article <span style="color: #0000ff;">in</span> article_list %<span style="color: #000000;">}
    
                    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_item clearfix</span><span style="color: #800000;">"</span>&gt;
                        &lt;h5&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ article.title }}&lt;/a&gt;&lt;/h5&gt;
                        &lt;div&gt;
    
                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                        &lt;/div&gt;
                        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;img src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/img/icon_comment.gif</span><span style="color: #800000;">"</span> alt=<span style="color: #800000;">""</span>&gt;&lt;<span style="color: #000000;">a
                                href</span>=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                        &lt;/div&gt;
                    &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;
    
        &lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    访问个人站点:http://127.0.0.1:8000/xiao/

    效果如下:

    主题切换

    查看blog_blog表,有2条记录

    theme对应主题的css文件

    在homesite.html中的style标签定义了一些样式。现在需要分离出来!

    每一个用户有自己的标题颜色,比如xiao用默认的蓝色,zhang用绿色

    在static中新建css目录,在css中新建文件夹theme,新建3个css文件,其中common.css是公共样式!

    common.css

    * {
        margin: 0;
        padding: 0;
    }
    

    .header {
    100%;
    height: 59px;
    background
    -color: #369;
    }

    .header .title {
    line-height: 59px;
    color: white;
    font
    -weight: lighter;
    margin
    -left: 20px;
    font
    -size: 18px;
    }

    .left_region {
    margin-top: 10px;
    }

    .info {
    margin-top: 10px;
    color: darkgray;

    }

    h5 a {
    color: #105cb6;
    font-size: 14px;
    font
    -weight: bold;
    text
    -decoration: underline;
    }

    View Code

    xiao.css

    .header {
         100%;
        height: 59px;
        background-color: #369;
    }
    View Code

    zhang.css

    .header {
         100%;
        height: 59px;
        background-color: green;
    }
    View Code

    修改homesite.html,修改head部分,完整代码如下:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <link rel="shortcut icon" href="https://common.cnblogs.com/favicon.ico" type="image/x-icon"/>
        {#公共样式#}
        <link rel="stylesheet" href="/static/css/theme/common.css">
        {#个人站点主题样式#}
        <link rel="stylesheet" href="/static/css/theme/{{ blog.theme }}">
    
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">stylesheet</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/css/bootstrap.css</span><span style="color: #800000;">"</span>&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/js/jquery.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    &lt;script src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/bootstrap/js/bootstrap.js</span><span style="color: #800000;">"</span>&gt;&lt;/script&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="/{{ username }}/category/{{ cate.0 }}">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/tag/{{ tag.0 }}</span><span style="color: #800000;">"</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> date <span style="color: #0000ff;">in</span> date_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/achrive/{{ date.0 }}</span><span style="color: #800000;">"</span>&gt;{{ date.0 }}({{ date.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;
    
            &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                {</span>% <span style="color: #0000ff;">for</span> article <span style="color: #0000ff;">in</span> article_list %<span style="color: #000000;">}
    
                    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_item clearfix</span><span style="color: #800000;">"</span>&gt;
                        &lt;h5&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;{{ article.title }}&lt;/a&gt;&lt;/h5&gt;
                        &lt;div&gt;
    
                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                        &lt;/div&gt;
                        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;img src=<span style="color: #800000;">"</span><span style="color: #800000;">/static/img/icon_comment.gif</span><span style="color: #800000;">"</span> alt=<span style="color: #800000;">""</span>&gt;&lt;<span style="color: #000000;">a
                                href</span>=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                            </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                        &lt;/div&gt;
                    &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;
    
        &lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    使用谷歌浏览器登录xiao的用户,进入个人主页

    使用火狐浏览器登录zhang的用户

     

    进入个人主页,发现标题颜色没有换过来

    进入admin后台,点击users表,找到zhang用户,发现它没有绑定个人站点。

    因为使用命令创建用户时,blog_id字段,默认为空!

    手动绑定一下

    再次刷新页面,效果如下:

    文章详情

    由于文章详情页,功能繁多,必须专门做一个视图才行。

    修改urls.py,增加路径article_detail

    urlpatterns = [
        path('admin/', admin.site.urls),
        path('login/', views.login),
        path('index/', views.index),
        path('logout/', views.logout),
        path('', views.index),
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;">文章详情</span>
    re_path(<span style="color: #800000;">'</span><span style="color: #800000;">(?P&lt;username&gt;w+)/articles/(?P&lt;article_id&gt;d+)/$</span><span style="color: #800000;">'</span><span style="color: #000000;">, views.article_detail),
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 跳转</span>
    re_path(<span style="color: #800000;">'</span><span style="color: #800000;">(?P&lt;username&gt;w+)/(?P&lt;condition&gt;category|tag|achrive)/(?P&lt;params&gt;.*)/$</span><span style="color: #800000;">'</span><span style="color: #000000;">, views.homesite),
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 个人站点</span>
    re_path(<span style="color: #800000;">'</span><span style="color: #800000;">(?P&lt;username&gt;w+)/$</span><span style="color: #800000;">'</span><span style="color: #000000;">, views.homesite),
    

    ]

    View Code

    由于文章详情页的左测和标题部分是通用的,需要用到模板继承

    模板继承

    新建base.html,将homesite.html的代码复制过来,删除多余的部分。增加block

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        {#公共样式#}
        <link rel="stylesheet" href="/static/css/theme/common.css">
        {#个人站点主题样式#}
        <link rel="stylesheet" href="/static/css/theme/{{ blog.theme }}">
        {#bootstrap#}
        <link rel="stylesheet" href="/static/bootstrap/css/bootstrap.css">
        <script src="/static/js/jquery.js"></script>
        <script src="/static/bootstrap/js/bootstrap.js"></script>
    
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">shortcut icon</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">https://common.cnblogs.com/favicon.ico</span><span style="color: #800000;">"</span> type=<span style="color: #800000;">"</span><span style="color: #800000;">image/x-icon</span><span style="color: #800000;">"</span> /&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    <div class="left_region">
    <div class="panel panel-success">
    <div class="panel-heading">
    <h3 class="panel-title">随笔分类</h3>
    </div>
    <div class="panel-body">
    {
    % for cate in cate_list %}
    <p><a href="/{{ username }}/category/{{ cate.0 }}">{{ cate.0 }}({{ cate.1 }})</a></p>
    {
    % endfor %}

                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/tag/{{ tag.0 }}</span><span style="color: #800000;">"</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
                    </span>&lt;/div&gt;
    
                &lt;/div&gt;
                &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
                        &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
                    &lt;/div&gt;
                    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                        {</span>% <span style="color: #0000ff;">for</span> date <span style="color: #0000ff;">in</span> date_list %<span style="color: #000000;">}
                            </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/achrive/{{ date.0 }}</span><span style="color: #800000;">"</span>&gt;{{ date.0 }}({{ date.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
                        {</span>% endfor %<span style="color: #000000;">}
    
                    </span>&lt;/div&gt;
                &lt;/div&gt;
            &lt;/div&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">col-md-9</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
    
           {</span>% block content %<span style="color: #000000;">}
           
           {</span>% endblock %<span style="color: #000000;">}
    
        </span>&lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    修改homesite.html

    {% extends "base.html" %}
    

    {% block content %}
    <div class="article_list">
    {
    % for article in article_list %}
    <div class="article_item clearfix">
    <h5><a href="/{{ username }}/articles/{{ article.pk }}">{{ article.title }}</a></h5>
    <div>

                          &lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">small desc </span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                              {{ article.desc }}
                          </span>&lt;/span&gt;
    
                      &lt;/div&gt;
                      &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">info small pull-right</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
                            发布于 </span>&lt;span&gt;{{ article.create_time|date:<span style="color: #800000;">'</span><span style="color: #800000;">Y-m-d H:i</span><span style="color: #800000;">'</span> }}&lt;/span&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                           </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-comment</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;评论({{ article.comment_count }})&lt;/a&gt;&amp;nbsp;&amp;<span style="color: #000000;">nbsp;
                           </span>&lt;span <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">glyphicon glyphicon-thumbs-up</span><span style="color: #800000;">"</span>&gt;&lt;/span&gt;&lt;a href=<span style="color: #800000;">""</span>&gt;点赞({{ article.up_count }})&lt;/a&gt;
                      &lt;/div&gt;
                 &lt;/div&gt;
                    &lt;hr&gt;<span style="color: #000000;">
                {</span>% endfor %<span style="color: #000000;">}
            </span>&lt;/div&gt;<span style="color: #000000;">
    

    {% endblock %}

    View Code

    增加article_detail.html

    {% extends "base.html" %}
    

    {% block content %}

    </span>&lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">article_info</span><span style="color: #800000;">"</span>&gt;
        &lt;h4 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">text-center</span><span style="color: #800000;">"</span>&gt;{{ article_obj.title }}&lt;/h4&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">content</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
            {{ article_obj.content }}
        </span>&lt;/div&gt;
    &lt;/div&gt;<span style="color: #000000;">
    

    {% endblock %}

    View Code

    修改article_detail视图函数

    def article_detail(request,username,article_id):
        user = UserInfo.objects.filter(username=username).first()
        # 查询当前站点对象
        blog = user.blog
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询指定id的文章</span>
    article_obj=Article.objects.filter(pk=<span style="color: #000000;">article_id).first()
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(cate_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;"> 我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(tag_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;"> 日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(date_list)</span>
    
    dict = {"blog": blog, "article_obj": article_obj, "cate_list": cate_list, "tag_list": tag_list, "date_list": date_list, "username": username, }
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">'</span><span style="color: #800000;">article_detail.html</span><span style="color: #800000;">'</span>,dict)</pre>
    
    View Code

    刷新网页,点击左侧的一个分类,效果如下:

    点击右边的一篇文章

    关于内容部分,为什么是html标签。这些暂时不处理,后面会讲到如何处理!

    查看article_detail和homesite 这2个视图函数,有重复的代码。在编程的过程中,最好不要出现重复代码,怎么办呢?使用函数封装!

    函数封装

    修改views.py,增加函数get_query_data。删掉article_detail和homesite 这2个视图函数中的重复代码,完整代码如下:

    from django.shortcuts import render,HttpResponse,redirect
    from django.contrib import auth
    from blog.models import Article,UserInfo,Blog,Category,Tag
    from django.db.models import Sum,Avg,Max,Min,Count
    # Create your views here.
    def login(request):
    
    </span><span style="color: #0000ff;">if</span> request.method==<span style="color: #800000;">"</span><span style="color: #800000;">POST</span><span style="color: #800000;">"</span><span style="color: #000000;">:
        user</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">user</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        pwd</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">pwd</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;"> 用户验证成功,返回user对象,否则返回None</span>
        user=auth.authenticate(username=user,password=<span style="color: #000000;">pwd)
        </span><span style="color: #0000ff;">if</span><span style="color: #000000;"> user:
            </span><span style="color: #008000;">#</span><span style="color: #008000;"> 登录,注册session</span>
            <span style="color: #008000;">#</span><span style="color: #008000;"> 全局变量 request.user=当前登陆对象(session中)</span>
    

    auth.login(request,user)
    return redirect("/index/")

    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">login.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    

    def index(request):
    article_list
    =Article.objects.all()
    return render(request,"index.html",{"article_list":article_list})

    def logout(request): # 注销
    auth.logout(request)
    return redirect("/index/")

    def get_query_data(request,username):
    user
    = UserInfo.objects.filter(username=username).first()
    # 查询当前站点对象
    blog = user.blog

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 随笔分类</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(cate_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;"> 我的标签</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(tag_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;"> 日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(date_list)</span>
    
    dict = {"blog": blog, "cate_list": cate_list, "tag_list": tag_list, "date_list": date_list, "username": username, }
    </span><span style="color: #0000ff;">return</span> dict <span style="color: #008000;">#</span><span style="color: #008000;">返回字典</span>
    

    def homesite(request,username,**kwargs):
    """
    查询
    :param request:
    :param username:
    :return:
    """
    print("kwargs", kwargs)

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点的用户对象</span>
    user=UserInfo.objects.filter(username=<span style="color: #000000;">username).first()
    </span><span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> user:
        </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">not_found.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点对象</span>
    blog=<span style="color: #000000;">user.blog
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    <span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> kwargs:
        article_list </span>= Article.objects.filter(user__username=<span style="color: #000000;">username)
    
    </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
        condition </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">condition</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        params </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">params</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;">判断分类、随笔、归档</span>
        <span style="color: #0000ff;">if</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">category</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(category__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">elif</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">tag</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(tags__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
            year, month </span>= params.split(<span style="color: #800000;">"</span><span style="color: #800000;">/</span><span style="color: #800000;">"</span><span style="color: #000000;">)
            article_list </span>= Article.objects.filter(user__username=username).filter(create_time__year=<span style="color: #000000;">year,
                                                                                  create_time__month</span>=<span style="color: #000000;">month)
    dict </span>= get_query_data(request,username)  <span style="color: #008000;">#</span><span style="color: #008000;">调用函数</span>
    dict[<span style="color: #800000;">'</span><span style="color: #800000;">article_list</span><span style="color: #800000;">'</span>] = article_list  <span style="color: #008000;">#</span><span style="color: #008000;"> 增加一个key</span>
    <span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span><span style="color: #000000;">,dict)
    

    def article_detail(request,username,article_id):
    content_text
    = get_query_data(request,username) #调用函数
    #查询指定id的文章
    article_obj = Article.objects.filter(pk=article_id).first()
    content_text[
    'article_obj'] = article_obj # 增加一个key

    <span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">'</span><span style="color: #800000;">article_detail.html</span><span style="color: #800000;">'</span>,content_text)</pre>
    
    View Code

    注意:get_query_data必须要在2个视图函数的上面,否则无法调用!

    重新访问网页,效果如下:

    封装函数,有一个局限性,如果新增变量,需要增加字典key-value。由于继承模板时,变量是不会继承的。所以引用的视图函数,必须重新传值才可以渲染。那么可不可以,将模板和数据包装成一个模板,作为一个整体。其他模板继承时,就是一个已经渲染过的模板呢?

    答案是有的,那就是inclusion_tag

    包含标签(Inclusion tags)

    Django过滤器和标签功能很强大,而且支持自定义标签,很是方便;其中一种标签是Inclusion tags,即包含标签
    包含标签(Inclusion tags)通过渲染其他的模板来展示内容,这类标签的用途在于一些相似的内容的展示,并且返回的内容是渲染其他模板得到的内容。

    自定义标签必须在应用名目录下创建templatetags目录。注意:此目录名必须叫这个名字,不可改变。

    在templatetags目录下,创建my_tags.py,这个文件名,是可以随便的

    先来增加一个乘法的标签

    from django import template
    

    register=template.Library()

    @register.simple_tag
    def mul_tag(x,y):

    </span><span style="color: #0000ff;">return</span> x*y</pre>
    
    View Code

    修改article_detail.html,调用这个自定义标签

    {% extends "base.html" %}
    

    {% block content %}
    {
    % load my_tags %}
    <p>{% mul_tag 2 7 %}</p>
    <div class="article_info">
    <h4 class="text-center">{{ article_obj.title }}</h4>
    <div class="content">
    {{ article_obj.content }}
    </div>
    </div>

    {% endblock %}

    View Code

    必须重启django项目,否则模板无法引用自定义标签!

    必须重启django项目,否则模板无法引用自定义标签!

    必须重启django项目,否则模板无法引用自定义标签!

    随便访问一篇文章,出现一个14,说明调用成功了

    那么这个my_tags,如何渲染左侧的分类,标签,归档呢?

    新建标签get_query_data,必须返回一个字典

    将视图函数中的相关代码,复制过来即可。

    from django import template
    

    register=template.Library()

    @register.simple_tag
    def mul_tag(x,y):

    </span><span style="color: #0000ff;">return</span> x*<span style="color: #000000;">y
    

    from blog.models import Category,Tag,Article,UserInfo
    from django.db.models import Count,Avg,Max

    @register.inclusion_tag("left_region.html")
    def get_query_data(username):
    user
    = UserInfo.objects.filter(username=username).first()
    # 查询当前站点对象
    blog = user.blog

    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点每一个分类的名称以及对应的文章数</span>
    cate_list = Category.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(cate_list)</span>
    
    <span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前站点每一个标签的名称以及对应的文章数</span>
    tag_list = Tag.objects.filter(blog=blog).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">article__title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 日期归档</span>
    date_list = Article.objects.filter(user=user).extra(select={<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>: <span style="color: #800000;">"</span><span style="color: #800000;">strftime('%%Y/%%m',create_time)</span><span style="color: #800000;">"</span><span style="color: #000000;">}).values(
        </span><span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>).annotate(c=Count(<span style="color: #800000;">"</span><span style="color: #800000;">title</span><span style="color: #800000;">"</span>)).values_list(<span style="color: #800000;">"</span><span style="color: #800000;">y_m_date</span><span style="color: #800000;">"</span>, <span style="color: #800000;">"</span><span style="color: #800000;">c</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> print(date_list)</span>
    
    <span style="color: #0000ff;">return</span> {<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span>:blog,<span style="color: #800000;">"</span><span style="color: #800000;">username</span><span style="color: #800000;">"</span>:username,<span style="color: #800000;">"</span><span style="color: #800000;">cate_list</span><span style="color: #800000;">"</span>:cate_list,<span style="color: #800000;">"</span><span style="color: #800000;">tag_list</span><span style="color: #800000;">"</span>:tag_list,<span style="color: #800000;">"</span><span style="color: #800000;">date_list</span><span style="color: #800000;">"</span>:date_list}</pre>
    
    View Code

    @register.inclusion_tag("left_region.html") 表示将返回结果渲染给left_region.html

    如果在模板中有调用left_redig.html,那么这个文件,就会渲染,是渲染后的html文件!

    在templates中新建文件left_region.html

    <div class="left_region">
        <div class="panel panel-success">
            <div class="panel-heading">
                <h3 class="panel-title">随笔分类</h3>
            </div>
            <div class="panel-body">
                {% for cate in cate_list %}
                    <p><a href="/{{ username }}/category/{{ cate.0 }}">{{ cate.0 }}({{ cate.1 }})</a></p>
                {% endfor %}
    
        </span>&lt;/div&gt;
    &lt;/div&gt;
    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-warning</span><span style="color: #800000;">"</span>&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
            &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;我的标签&lt;/h3&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
            {</span>% <span style="color: #0000ff;">for</span> tag <span style="color: #0000ff;">in</span> tag_list %<span style="color: #000000;">}
                </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/tag/{{ tag.0 }}</span><span style="color: #800000;">"</span>&gt;{{ tag.0 }}({{ tag.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
            {</span>% endfor %<span style="color: #000000;">}
        </span>&lt;/div&gt;
    &lt;/div&gt;
    &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel panel-info</span><span style="color: #800000;">"</span>&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-heading</span><span style="color: #800000;">"</span>&gt;
            &lt;h3 <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-title</span><span style="color: #800000;">"</span>&gt;日期归档&lt;/h3&gt;
        &lt;/div&gt;
        &lt;div <span style="color: #0000ff;">class</span>=<span style="color: #800000;">"</span><span style="color: #800000;">panel-body</span><span style="color: #800000;">"</span>&gt;<span style="color: #000000;">
            {</span>% <span style="color: #0000ff;">for</span> date <span style="color: #0000ff;">in</span> date_list %<span style="color: #000000;">}
                </span>&lt;p&gt;&lt;a href=<span style="color: #800000;">"</span><span style="color: #800000;">/{{ username }}/achrive/{{ date.0 }}</span><span style="color: #800000;">"</span>&gt;{{ date.0 }}({{ date.1 }})&lt;/a&gt;&lt;/p&gt;<span style="color: #000000;">
            {</span>% endfor %<span style="color: #000000;">}
    
        </span>&lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    View Code

    修改base.html,将<div class="col-md-3"></div> 中的内容部分,改为引用get_query_data标签

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        {#公共样式#}
        <link rel="stylesheet" href="/static/css/theme/common.css">
        {#个人站点主题样式#}
        <link rel="stylesheet" href="/static/css/theme/{{ blog.theme }}">
        {#bootstrap#}
        <link rel="stylesheet" href="/static/bootstrap/css/bootstrap.css">
        <script src="/static/js/jquery.js"></script>
        <script src="/static/bootstrap/js/bootstrap.js"></script>
    
    &lt;link rel=<span style="color: #800000;">"</span><span style="color: #800000;">shortcut icon</span><span style="color: #800000;">"</span> href=<span style="color: #800000;">"</span><span style="color: #800000;">https://common.cnblogs.com/favicon.ico</span><span style="color: #800000;">"</span> type=<span style="color: #800000;">"</span><span style="color: #800000;">image/x-icon</span><span style="color: #800000;">"</span>/&gt;
    

    </head>
    <body>
    <div class="header">
    <p class="title">{{ blog.title }}</p>
    </div>

    <div class="container-fluid">
    <div class="row">
    <div class="col-md-3">
    {
    #加载自定义标签模块#}
    {% load my_tags %}
    {
    #调用get_query_data标签,它返回left_region.html,是已经被渲染过的文件#}
    {% get_query_data username %}
    </div>
    <div class="col-md-9">

            {</span>% block content %<span style="color: #000000;">}
    
            {</span>% endblock %<span style="color: #000000;">}
    
        </span>&lt;/div&gt;
    &lt;/div&gt;
    

    </div>

    </body>
    </html>

    View Code

    此时刷新网页,效果同上!

    修改views.py中的视图函数,删除get_query_data!

    删除homesite和article_detail两个视图函数多余的代码

    from django.shortcuts import render,HttpResponse,redirect
    from django.contrib import auth
    from blog.models import Article,UserInfo,Blog,Category,Tag
    from django.db.models import Sum,Avg,Max,Min,Count
    # Create your views here.
    def login(request):
    
    </span><span style="color: #0000ff;">if</span> request.method==<span style="color: #800000;">"</span><span style="color: #800000;">POST</span><span style="color: #800000;">"</span><span style="color: #000000;">:
        user</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">user</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        pwd</span>=request.POST.get(<span style="color: #800000;">"</span><span style="color: #800000;">pwd</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;"> 用户验证成功,返回user对象,否则返回None</span>
        user=auth.authenticate(username=user,password=<span style="color: #000000;">pwd)
        </span><span style="color: #0000ff;">if</span><span style="color: #000000;"> user:
            </span><span style="color: #008000;">#</span><span style="color: #008000;"> 登录,注册session</span>
            <span style="color: #008000;">#</span><span style="color: #008000;"> 全局变量 request.user=当前登陆对象(session中)</span>
    

    auth.login(request,user)
    return redirect("/index/")

    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">login.html</span><span style="color: #800000;">"</span><span style="color: #000000;">)
    

    def index(request):
    article_list
    =Article.objects.all()
    return render(request,"index.html",{"article_list":article_list})

    def logout(request): # 注销
    auth.logout(request)
    return redirect("/index/")

    def query_current_site(request,username): # 查询当前站点的博客标题
    # 查询当前站点的用户对象
    user = UserInfo.objects.filter(username=username).first()
    if not user:
    return render(request, "not_found.html")
    # 查询当前站点对象
    blog = user.blog
    return blog

    def homesite(request,username,**kwargs):
    """
    查询
    :param request:
    :param username:
    :return:
    """
    print("kwargs", kwargs)

    blog </span>=<span style="color: #000000;"> query_current_site(request,username)
    
    </span><span style="color: #008000;">#</span><span style="color: #008000;"> 查询当前用户发布的所有文章</span>
    <span style="color: #0000ff;">if</span> <span style="color: #0000ff;">not</span><span style="color: #000000;"> kwargs:
        article_list </span>= Article.objects.filter(user__username=<span style="color: #000000;">username)
    </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
        condition </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">condition</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        params </span>= kwargs.get(<span style="color: #800000;">"</span><span style="color: #800000;">params</span><span style="color: #800000;">"</span><span style="color: #000000;">)
        </span><span style="color: #008000;">#</span><span style="color: #008000;">判断分类、随笔、归档</span>
        <span style="color: #0000ff;">if</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">category</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(category__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">elif</span> condition == <span style="color: #800000;">"</span><span style="color: #800000;">tag</span><span style="color: #800000;">"</span><span style="color: #000000;">:
            article_list </span>= Article.objects.filter(user__username=username).filter(tags__title=<span style="color: #000000;">params)
        </span><span style="color: #0000ff;">else</span><span style="color: #000000;">:
            year, month </span>= params.split(<span style="color: #800000;">"</span><span style="color: #800000;">/</span><span style="color: #800000;">"</span><span style="color: #000000;">)
            article_list </span>= Article.objects.filter(user__username=username).filter(create_time__year=<span style="color: #000000;">year,
                                                                                  create_time__month</span>=<span style="color: #000000;">month)
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">"</span><span style="color: #800000;">homesite.html</span><span style="color: #800000;">"</span>,{<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span>:blog,<span style="color: #800000;">"</span><span style="color: #800000;">username</span><span style="color: #800000;">"</span>:username,<span style="color: #800000;">"</span><span style="color: #800000;">article_list</span><span style="color: #800000;">"</span><span style="color: #000000;">:article_list})
    

    def article_detail(request,username,article_id):
    blog
    = query_current_site(request,username)

    </span><span style="color: #008000;">#</span><span style="color: #008000;">查询指定id的文章</span>
    article_obj = Article.objects.filter(pk=<span style="color: #000000;">article_id).first()
    
    </span><span style="color: #0000ff;">return</span> render(request,<span style="color: #800000;">'</span><span style="color: #800000;">article_detail.html</span><span style="color: #800000;">'</span>,{<span style="color: #800000;">"</span><span style="color: #800000;">blog</span><span style="color: #800000;">"</span>:blog,<span style="color: #800000;">"</span><span style="color: #800000;">username</span><span style="color: #800000;">"</span>:username,<span style="color: #800000;">'</span><span style="color: #800000;">article_obj</span><span style="color: #800000;">'</span>:article_obj})</pre>
    
    View Code

    注意:get_query_data标签只是定义了左侧的标签!那么homesite和article_detail两个视图函数,需要知道当前站点的博客标题。

    所以需要专门定义个函数,来获取博客标题!

    修改article_detail.html,删除测试的自定义标签

    {% extends "base.html" %}
    

    {% block content %}
    <div class="article_info">
    <h4 class="text-center">{{ article_obj.title }}</h4>
    <div class="content">
    {{ article_obj.content }}
    </div>
    </div>

    {% endblock %}

    View Code

    重新访问个人站点,随便乱点,效果同上!

    Inclusion tags的优点:

    1.不用在视图函数中return字典

    2.数据和样式结合在一起,返回一个渲染后的html

    详情页显示html代码问题

    访问一篇博客详情,比如:

    http://127.0.0.1:8000/xiao/articles/5/

    效果如下:

    那么django响应给浏览器的,真的是原来的html代码吗?

    修改id为5的文章记录,修改content字段的数据,先备份一下,改成一个h1标签。

    刷新网页,效果如下:

    打开浏览器控制台-->network,查看这次请求的响应体

    发现代码被转义了!那么是谁转义了呢?当然是....

    注意:这不是浏览器的锅,是django转义的,这是它的安全策略做的。遇到html或者js代码,会自动转义!

    那么我们不要django转义呢?使用safe过滤器即可!

    修改article_detail.html中的代码

    {{ article_obj.content|safe }}

    重新刷新页面,效果如下:

    注意:这样有一个安全隐患!

    举例:将内容修改为一段js代码

    重新刷新页面,它会有一个提示框

    注意:它只会弹一次。如果是下面这段代码呢?

    <script>for (var i = 0; i < 99999; i++) {alert("hello");}</script>

    数据库记录如下:

    刷新页面试试?不用想了,你今天啥事不用干,疯狂的点击吧!

    那么既要网页安全,又需要网站展示真实的内容,怎么办呢?

    答案就是:数据库不存储html代码即可!存html和js代码时,需要做特殊处理。

    后面讲到富文本编辑器,会讲到。完美解决这个问题!


    参考资料:

    Django 基础教程

    转载声明:
    作者:肖祥
    出处: https://www.cnblogs.com/xiao987334176/

  • 相关阅读:
    CentOS 7.X 关闭SELinux
    删除或重命名文件夹和文件的方法
    centos7-每天定时备份 mysql数据库
    centos7 tar.gz zip 解压命令
    MySQL5.6/5.7/8.0版本授权用户远程连接
    下载CentOS7系统
    使用js实现tab页签切换效果
    sql优化常用的几种方法
    mysql 多表联查的快速查询(索引)
    【图论】强连通分量+tarjan算法
  • 原文地址:https://www.cnblogs.com/bqwzx/p/10198769.html
Copyright © 2020-2023  润新知