Django学习记录(十七):Django by example -- Blog(十三)
PyxYuYu opened this issue · 0 comments
PyxYuYu commented
Learn from yesterday, live for today, look to tomorrow.
0x01 Django
- Build a Blog Application
Adding tagging functionality
- 通过导入一个第三方的标签应用来创建一个标签
posts
的方法 django-taggit
这个第三方应用提供了Tag
模型和manager
来简单的导入标签给任何模型- 安装
pip install django-taggit==0.21.3
或者用PyCharm
的管理工具安装 - 在
settings.py
中将django-taggit
添加到INSTALLED_APPS
里
INSTALLED_APPS = ( # ... 'blog', 'taggit', )
- 在
models.py
中添加TaggableManager
标签管理器到Post
模型中
from taggit.managers import TaggableManager class Post(models.Model): # ... tags = TaggableManager()
- 标签管理器允许我们对标签进行增加、检索和移动
- 进行数据迁移,同步到数据库
python manage.py makemigrations blog
python manage.py migrate
- 同步之后,就可以使用
django-taggit
,打开shell
,看看标签管理器的用法python manage.py shell
- 检索
id=1
的post
>>> from blog.models import Post >>>> post = Post.objects.get(id=1)
- 之后就可以给这个
post
增加一些标签,也可以用tags.all()
来验证是否增加成功
>>> post.tags.add('aaa', 'bbb', 'ccc') >>> post.tags.all() [<Tag: aaa>, <Tag: bbb>, <Tag: ccc>]
- 利用
tags.remove(
aaa)
也可以删除指定标签
>>> post.tags.remove('ccc') >>> post.tags.all() [<Tag: aaa>, <Tag: bbb>]
- 运行
python manage.py runserver
后,可以在http://localhost:8000/admin/taggit/tag
页面查看到标签列表,可以看到之前创建的3个标签,被移除的ccc
也在,只是将ccc
移除到post id=1
外 post
编辑页面下面也会出现一个标签字段用于添加标签
- 在模板上面显示标签,编辑
blog/post/list.html
,在post title
后添加
<p class="tags">Tags: {{ post.tags.all|join:", " }}</p>
join
这个模板过滤器{{ list|join:", " }}
用指定分隔符连接列表(这里用逗号连接)- 接下来需要实现一个功能:根据指定的标签列出这些标签所标的
posts
- 编辑
blog/views.py
导入Tag
模型
from taggit.models import Tag def post_list(request, tag_slug=None): object_list = Post.published.all() tag = None if tag_slug: tag = get_object_or_404(Tag, slug=tag_slug) object_list = object_list.filter(tags__in=[tag]) # ... return render(request, 'blog/post/list.html', {'page': page, 'posts': posts, 'tag': tag})
post_list
需要一个tag_slug
参数,默认是None
,从URL
中获取- 在函数内建立了一个查询集,检索所有的公开
posts
,如果有tag_slug
,用get_object_or_404()
获取这个tag
,然后利用个这个标签过滤获得所需要的posts
,最后在render()
中添加tag
传送给模板 - 因为根据
URL
获取tag_slug
,所以修改urls.py
,添加
url(r'^tag/(?P<tag_slug>[-\w]+)/$', views.post_list, name='post_list_by_tag'),
- 接着需要在模板中进行修改,因为之前用的是
Django
的内置类ListView
写的post
列表,所以需要修改blog/post/list.html
{% include "pagination.html" with page=posts %}
- 在
{% for %}
循环上面添加
{% if tag %} <h2>Posts tagged with "{{ tag.name }}"</h2> {% endif %}
- 后面接着显示指定
tag
所过滤出的posts
,修改<p class="tags">
<p class="tags"> Tags: {% for tag in post.tags.all %} <a href="{% url "blog:post_list_by_tag" tag.slug %}"> {{ tag.name }} </a> {% if not forloop.last %} , {% endif %} {% endfor %} </p>
forloop.last
是一个布尔值,在最后一次执行循环是被设置为True
,如果不是最后一次都会输出一个逗号,最后一次,就不会继续执行输出逗号
- 编辑