程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式師世界 >> 編程語言 >  >> 更多編程語言 >> Python

Django set up ten blog home pages

編輯:Python

Article application model establishment

edit \myblog\article\models.py

The contents are as follows :

import logging
import os
from django.db import models
from django.db.models import F
from django.urls import reverse
from django.utils.safestring import mark_safe
from django.conf import settings
from django.utils.html import strip_tags
from django.contrib.auth import get_user_model
from mdeditor.fields import MDTextField
from system.models import BaseModel
logger = logging.getLogger('django')
User = get_user_model()
class Category(BaseModel):
name = models.CharField(verbose_name=' Category name ', max_length=20, unique=True)
slug = models.SlugField(verbose_name=" classification slug", unique=True)
level = models.IntegerField(verbose_name=" Classification level ", default=1)
parent = models.ForeignKey('self', verbose_name=' Parent navigation ', related_name='parent_category', null=True, blank=True,
on_delete=models.CASCADE, help_text=" Parent navigation can be empty ",
limit_choices_to={
"parent__isnull": True})
show = models.BooleanField(verbose_name=" Whether or not shown ", default=True)
icon = models.CharField(verbose_name=" Navigation icons ", max_length=30, help_text=" Currently, the navigation icon only supports font-awesome", null=True,
blank=True)
order = models.IntegerField(verbose_name=" Serial number ", help_text=" The larger the serial number, the higher the number ", default=1)
class Meta:
db_table = "article_category"
verbose_name = ' The article classification '
verbose_name_plural = verbose_name
ordering = ['-order']
def __str__(self):
return self.name
def save(self, *args, **kwargs):
if self.parent:
self.level = self.parent.level + 1
super(Category, self).save(*args, **kwargs)
class Tag(BaseModel):
name = models.CharField(verbose_name=' Tag name ', max_length=20, unique=True)
slug = models.SlugField(verbose_name=" label slug", unique=True)
show = models.BooleanField(verbose_name=" Whether or not shown ", default=True)
class Meta:
db_table = "article_tag"
verbose_name = ' label '
verbose_name_plural = verbose_name
def __str__(self):
return self.name
def get_article_count(self):
return self.tag_article.count()
class Article(BaseModel):
slug = models.SlugField(verbose_name=" article slug", unique=True)
title = models.CharField(max_length=500, verbose_name=' Article title ')
summary = models.TextField(verbose_name=' Article summary ', help_text=" The system automatically generates a summary ", null=True, blank=True)
content = MDTextField(verbose_name=" Content ", null=True, blank=True)
cover = models.ImageField(verbose_name=" Article cover ", null=True, blank=True)
views = models.IntegerField(verbose_name=' Browse the number ', default=0, editable=False)
loves = models.IntegerField(verbose_name=' Number of likes ', default=0, editable=False)
category = models.ForeignKey(Category, verbose_name=' classification ', on_delete=models.DO_NOTHING,
related_name="category_article", limit_choices_to={
'level__gt': 1},
db_constraint=False, null=True, blank=True)
tags = models.ManyToManyField(Tag, verbose_name=' label ', related_name='tag_article', blank=True,
db_table="sys_article_tag")
show = models.BooleanField(verbose_name=" Whether or not shown ", default=True)
can_comment = models.BooleanField(verbose_name=" Allow comments ", default=True)
auto_summary = models.BooleanField(verbose_name=" Automatically generate summaries ", help_text=" If I don't check it , The summary information will not be automatically generated ", default=True)
place_top = models.BooleanField(verbose_name=" Whether it's at the top ", default=False)
class Meta:
db_table = "article"
verbose_name = " article "
verbose_name_plural = verbose_name
ordering = ["-place_top", "-create_time"]
def __str__(self):
return self.title[:20]
def get_previous_article(self):
previous_article = Article.objects.only("id", "slug").filter(id__lt=self.id).last()
return previous_article
def get_next_article(self):
next_article = Article.objects.only("id", "slug").filter(id__gt=self.id).last()
return next_article
def increase_views(self):
Article.objects.filter(id=self.id).update(views=F('views') + 1)
def increase_loves(self):
Article.objects.filter(id=self.id).update(loves=F('loves') + 1)
def get_tag_list(self):
return self.tags.all()
def show_image(self):
url = os.path.join(settings.MEDIA_URL, self.cover.url)
return mark_safe("<img src='{url}' width=75></a>".format(url=url))
show_image.short_description = " cover "
def save(self, *args, **kwargs):
if self.auto_summary:
summary = strip_tags(self.content).replace(" ", "").replace("\n", "").replace("&nbsp;", " ")
self.summary = summary[:200]
super(Article, self).save(*args, **kwargs)

admin The background configuration

newly added \myblog\article\admin.py

The contents are as follows

from django.contrib.admin import register
from article.models import Article, Tag, Category
from system.admin import BaseModelAdmin
@register(Category)
class CategoryModelAdmin(BaseModelAdmin):
list_display = ['id', 'name', 'slug', 'show', 'parent', 'order']
list_filter = ["show", "level"]
search_fields = ['name', 'slug']
list_editable = ['name', 'slug', 'show', 'order']
@register(Tag)
class TagModelAdmin(BaseModelAdmin):
list_display = ['id', 'name', 'slug', 'show']
search_fields = ['name', 'slug']
list_editable = ['name', 'show']
@register(Article)
class ArticleModelAdmin(BaseModelAdmin):
actions = ["batch_show_action", "batch_hide_action"]
list_display = ['title', 'category', 'views', 'loves', 'can_comment', 'show', 'place_top','show_image']
list_filter = ['title', 'category', 'tags', 'show']
search_fields = ['title', 'content']
list_editable = ['show', 'place_top', 'can_comment']
list_per_page = 10
list_order_field = ["views", "loves"]
filter_horizontal = ("tags",)
preserve_filters = ("category",)
def batch_show_action(self, queryset):
for obj in queryset:
obj.show = True
obj.save()
return None
batch_show_action.short_description = " Batch display the selected "
def batch_hide_action(self, queryset):
for obj in queryset:
obj.show = False
obj.save()
return None
batch_hide_action.short_description = " Batch hide the selected "
def queryset(self):
""" Control that users can only view their own articles ( Except for super Administrators )"""
qs = super().queryset()
if not self.request.user.is_superuser:
qs = qs.filter(creator=self.request.user)
return qs

meditor Routing configuration

edit \myblog\myblog\urls.py

Because in Article The rich text editor application is used in the model django-meditor, So it needs to be in urlpatterns Add the following to the list

path(r'mdeditor/', include('mdeditor.urls')),

Background rendering

Article classification rendering

Article label rendering

[ Failed to transfer the external chain picture , The origin station may have anti-theft chain mechanism , It is suggested to save the pictures and upload them directly (img-ibnEjIsX-1656230280008)(assets/1656127970807.png)]

Article rendering

Article editing renderings

Custom article template labels

newly added \myblog\article\templatetags Module folder

newly added \myblog\article\templatetags\article_tags.py file

Add the following

from django import template
from article.models import Article, Tag
import logging
logger = logging.getLogger('django')
register = template.Library()
@register.simple_tag
def get_article_date_list():
article_date_list = Article.objects.only("id", "slug", "title").filter(show=True).datetimes('create_time', 'month',
order='DESC')
return article_date_list
@register.simple_tag
def get_article_by_date(year, month):
article_list = Article.objects.only("id", "slug", "title").filter(show=True, create_time__year=year,
create_time__month=month)
return article_list
@register.simple_tag
def get_tag_list():
""" Return to the list of tags """
from django.db.models import Count
tag_list = Tag.objects.annotate(article_nums=Count('tag_article')).filter(article_nums__gt=0).order_by('name')
return tag_list
@register.simple_tag
def get_new_article_list():
return Article.objects.only("id", "slug", "title").filter(show=True).order_by('-create_time')[:5]
@register.simple_tag
def get_hot_article_list():
return Article.objects.only("id", "slug", "title").filter(show=True).order_by('-views')[:5]

Custom template context

edit \myblog\system\template_context_processors.py

import logging
from system.models import User
logger = logging.getLogger("django")
def template_context(request):
superuser = User.objects.filter(is_superuser=True).first()
context = {
"superuser": superuser}
return context

edit \myblog\myblog\settings.py, modify TEMPLATES Register your own defined context handler

TEMPLATES = [
{

'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [os.path.join(BASE_DIR, 'templates')]
,
'APP_DIRS': True,
'OPTIONS': {

'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
# hold media Register globally template In the template 
'django.template.context_processors.media',
'system.template_context_processors.template_context',
],
},
},
]

Home page control

Article paging control

To write \myblog\templates\layout\pagination.html

Add the following

{% load system_tags %}
{% if is_paginated %}
<nav aria-label="Page navigation example">
<ul class="pagination justify-content-center my-3 pagination-lg">
{% if page_obj.has_previous %}
<li class="page-item">
<a href="?page={
{ page_obj.previous_page_number }}" aria-label="Previous">
<span aria-hidden="true">&laquo;</span>
</a>
</li>
{% endif %}
{% get_elided_page_range paginator page_obj.number as page_list %}
{% for page in page_list %}
{% ifequal page page_obj.number %}
<li class="page-item active"><span>{
{ page }}</span></li>
{% else %}
{% ifequal page page_obj.paginator.ELLIPSIS %}
<li class="page-item"><span>{
{ page }}</span></li>
{% else %}
<li class="page-item"><a href="?page={
{ page }}&q={
{ query }}">{
{ page }}</a></li>
{% endifequal %}
{% endifequal %}
{% endfor %}
{% if page_obj.has_next %}
<li class="page-item">
<a href="?page={
{ page_obj.next_page_number }}" aria-label="Next">
<span aria-hidden="true">&raquo;</span>
</a>
</li>
{% endif %}
</ul>
</nav>
{% endif %}

design sketch

Article list control

To write \myblog\templates\article\article-query-list.html

Add the following

{% for article in articles %}
<article class="d-block bg-white hvr-float">
<div class="media d-block">
<div class="article-thumb">
<a href="#"><img src="{
{ MEDIA_URL }}{
{ article.cover }}" class="mr-3"></a>
</div>
<div class="media-body py-3 pl-1 overflow-hidden">
<div class="index-article-header">
<a href="#" class="label ">{
{ article.category.name }}<i class="position-absolute c-arrow"></i></a>
<h2 class="d-inline article-title"><a href="#" class="text-dark">{
{ article.title }}</a></h2>
{% if article.place_top %}<span class="new-icon"> Roof placement </span>{% endif %}
</div>
<div class="article-summary">
<p class="text-wrap text-secondary">
{
{ article.summary|truncatechars:170 }}{% if article.summary|length > 150 %}
...{% endif %}</p>
</div>
</div>
<div class="article-relative-meta">
<span class="float-left">
<a href="#"><i class="fa fa-calendar c4"></i>{
{ article.create_time|date:'Y year m month d Japan ' }}</a>
<a href="#"><i class="fa fa-comments c5"></i>{
{ 0 }} Comment on </a>
<a href="#"><i class="fa fa-eye c6"></i>{
{ article.views|default:0 }} read </a>
</span>
<span class="visible-xs float-left">
<a href="#"><i class="fa fa-heart c7"></i>{
{ article.loves|default:0 }} like </a>
<a {% if article.creator.link %}href="{
{ article.creator.link }}"{% endif %}><i class="fa fa-user c8"></i>{% firstof article.creator.nickname article.creator.username %}</a>
</span>
<span class="float-right">
<a class="mr-0" href="#" title=" Read the whole passage "> Read the whole passage <i class="fa fa-chevron-circle-right"></i></a>
</span>
</div>
</div>
</article>
{% empty %}
<div class="d-block bg-white mb-3 text-center" > Articles that haven't been published yet !
</div>
{% endfor %}

design sketch

Home sidebar control

To write \myblog\templates\layout\aside\page_aside.html

Add the following

<aside class="col-lg-4 col-xl-4 hidden-xs hidden-sm" id="aside">
<div class="sidebar" id="sidebar">
{% include 'layout/aside/sentence.html' %}
{% include 'layout/aside/aboutme.html' %}
{% include 'layout/aside/recommendation-article.html' %}
{% include 'layout/aside/article-tag.html' %}
</div>
</aside>

Sidebar Daily Sentence control

To write \myblog\templates\layout\aside\sentence.html

Add the following

{% load system_tags %}
<aside class="mb-2">
<div class="sentence">
<strong> A random sentence </strong>
<h2>{% now "Y year m month d Japan " %}</h2>
<p> What you don't want , Do not to others .</p>
</div>
</aside>

design sketch

Sidebar about my controls

To write \myblog\templates\layout\aside\aboutme.html

Add the following

{% load static %}
<aside class="card about mb-2">
<div class="card-bg"></div>
<div class="card-body text-center p-0">
{% if request.user.is_authenticated %}
<img class="xwcms" src="{
{ MEDIA_URL }}{
{ request.user.avatar }}"/>
<h5 class="card-title text-dark mt-2">{% firstof request.user.nickname request.user.username %}</h5></a>
<p class="card-text mb-2" >{
{ request.user.introduction|default:'' }}</p>
<p>
<a href="#" class="text-reset "><i class="fa fa-user-circle"></i> Modify information </a>
<a href="#" class="text-reset "><i class="fa fa-key"></i> Change Password </a>
<a href="{% url 'sys:logout' %}" class="text-reset "><i class="fa fa-sign-out"></i> Log out </a>
</p>
{% else %}
<a href="#"><img class="xwcms" src="{
{ MEDIA_URL }}{
{ superuser.avatar }}"></a>
<a href="#" class=""><h5 class="card-title text-dark mt-2 superuser">{% firstof superuser.nickname superuser.username %}</h5>
</a>
<p class="card-text mb-2" >{
{ superuser.introduction|default:'' }}</p>
<div class="contact-me text-center">
<a id="link_weixin" href="javascript:;" rel="nofollow" data-toggle="popover" data-trigger="hover click" data-html="true" data-title=" official account " data-content="<img src='{% static '/images/weixin_link.jpg' %}' width='150px' height='150px'>"><i class="fa fa-weixin" aria-hidden="true"></i></a>
<a target="_blank" href="https://github.com/tongyuebin" rel="nofollow"><i class="fa fa-github" aria-hidden="true"></i></a>
<a target="_blank" href="http://mail.qq.com/cgi-bin/qm_share?t=qm_mailme&email={
{ superuser.email }}" rel="nofollow"><i class="fa fa-envelope-o" aria-hidden="true"></i></a>
<a id="link_qq" href="javascript:;" rel="nofollow" data-toggle="popover" data-title=" Blogger QQ" data-trigger="hover click" data-html="true" data-content="<img src='{% static '/images/qq_link.jpg' %}' width='150px' height='150px'>"><i class="fa fa-qq" aria-hidden="true"></i></a>
</div>
</div>
<div class="text-center" >
<a id="bookmark" class="bookmark button--primary button--animated" href="javascript:;" title=" Bookmark " target="_self"><i class="fa fa-bookmark" aria-hidden="true"></i><span class="pl-2"> Bookmark </span></a>
</div>
{% endif %}
</aside>

Effect map is not logged in

Effect drawing after login

Sidebar article recommended controls

To write \myblog\templates\layout\aside\recommendation-article.html

Add the following

{% load article_tags %}
{% get_new_article_list as newArticles %}
{% get_hot_article_list as hotArticles %}
{% if newArticles or hotArticles %}
<aside class="mb-2 py-2 pl-3 recommendation tab-6">
<ul class="nav nav-tabs" role="tablist">
{% if newArticles %}
<li class="nav-item">
<a class="nav-link border-0 text-center text-dark active" data-toggle="tab" href="#new" role="tab" aria-controls="new"> The latest article </a>
</li>
{% endif %}
{% if hotArticles %}
<li class="nav-item">
<a class="nav-link border-0 text-center text-dark" data-toggle="tab" href="#hot" role="tab" aria-controls="hot"> The hottest article </a>
</li>
{% endif %}
</ul>
<div class="tab-content">
<div class="tab-pane active" id="new" role="tabpanel">
<ul class="list-group list-group-flush">
{% for newArticle in newArticles %}
<a class="pl-0 list-group-item text-truncate text-dark " title="{
{ newArticle.title }}" href="#">
<i class="fa fa-book"></i>
{
{ newArticle.title }}
</a>
{% endfor %}
</ul>
</div>
<div class="tab-pane" id="hot" role="tabpanel">
<ul class="list-group list-group-flush">
{% for hotArticle in hotArticles %}
<a class="pl-0 list-group-item text-truncate text-dark " title="{
{ hotArticle.title }}" href="#">
<i class="fa fa-book"></i>
{
{ hotArticle.title }}
</a>
{% endfor %}
</ul>
</div>
</div>
</aside>
{% endif %}

design sketch

Sidebar article label control

newly added \myblog\templates\layout\aside\article-tag.html

The contents are as follows

{% load system_tags %}
{% load article_tags %}
{% get_tag_list as tags %}
{% if tags %}
<aside class="mb-2 py-2 pl-3 aside-article-tag tab-6">
<ul class="nav nav-tabs" role="tablist">
<li class="nav-item">
<a class="nav-link border-0 text-center text-dark active" data-toggle="tab" href="#aside-article-tag" role="tab" aria-controls="aside-article-tag"> Tag cloud </a>
</li>
</ul>
<div class="tab-content pt-2">
<div class="tab-pane active" id="aside-article-tag" role="tabpanel">
<!-- Tag cloud -->
<div class="tags btn-group-sm d-inline-block">
{% for tag in tags %}
<a class="btn btn-sm border rounded-pill" href="{% url 'article:tag' tag.slug %}" data-toggle="tooltip" title=" There is... Under this label {
{ tag.article_nums }} An article ">{
{ tag.name }}</a>
{% endfor %}
</div>
</div>
</div>
</aside>
{% endif %}

design sketch

Homepage template

newly added \myblog\templates\index.html

{% extends 'base.html' %}
{% load static %}
{% block title %}
{
{ title|default:' home page ' }}
{% endblock %}
{% block main %}
<div class="container">
<div class="row">
<section class="col-sm-12 col-md-12 col-lg-8 index" id="main">
{% include 'article/article-query-list.html' %}
{% include 'layout/pagination.html' %}
</section>
{% include 'layout/page_aside.html' %}
</div>
</div>
{% endblock %}

Home view

To write \myblog\article\views.py

Add the following

from django.http import Http404
import logging
from django.views.generic import ListView
from article.models import Article, Tag, Category
logger = logging.getLogger('django')
class ArticleListView(ListView):
template_name = 'index.html'
context_object_name = 'articles'
paginate_by = 10
page_kwarg = 'page'
http_method_names = ['get']
model = Article
queryset = Article.objects.only("id",
"slug",
"title",
"cover",
"summary",
"category__name",
"category_id",
"place_top",
"create_time",
"views",
"loves",
"creator__username")
def get_queryset(self):
qs = super(ArticleListView, self).get_queryset()
qs = qs.filter(**self.kwargs)
if not self.request.user.is_superuser:
qs = qs.filter(show=True)
return qs
def get_context_data(self, **kwargs):
title = " home page "
try:
if 'tags__slug' in self.kwargs.keys(): # Classify articles by tags 
slug = self.kwargs.get('tags__slug')
tag = Tag.objects.get(slug=slug)
title = " Article label archiving :" + tag.name
elif 'category__slug' in self.kwargs.keys():
slug = self.kwargs.get('category__slug')
category = Category.objects.get(slug=slug)
title = " Articles are classified and archived :" + category.name
elif 'create_time__year' in self.kwargs.keys() and 'create_time__month' in self.kwargs.keys(): # Date category article 
title = " The date of the article is filed :" + str(self.kwargs.get("create_time__year")) + "-" + str(
self.kwargs.get("create_time__month"))
kwargs.update({
"title": title})
except Exception as e:
logger.info(e)
raise Http404()
return super(ArticleListView, self).get_context_data(**kwargs)

Routing binding

edit \myblog\article\urls.py

Add the following

from django.urls import path
from article import views
urlpatterns = [
path('category/<slug:category__slug>', views.ArticleListView.as_view(), name='category'),
path('tag/<slug:tags__slug>', views.ArticleListView.as_view(), name='tag'),
path('date/<int:create_time__year>/<int:create_time__month>', views.ArticleListView.as_view(), name='date'),
]

edit \myblog\myblog\urls.py

Add the following

from article.views import ArticleListView
path('', ArticleListView.as_view(), name="index"),

Overall rendering of the home page

Effect map is not logged in

Effect drawing after login


  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式師世界 All Rights Reserved