Django项目: 5.新闻主页

Posted tmclri

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Django项目: 5.新闻主页相关的知识,希望对你有一定的参考价值。

一、功能需求分析

1.功能

  1. 轮播图

  2. 推荐文章列表

  3. 文章标签导航

  4. 文章列表

  5. 分页

二、模型设计

根据功能分析,我们需要如下表

1.表和字段分析

  1. 文章分类表

  2. 文章表

  3. 文章评论表

  4. 推荐文章表

  5. 轮播图表

2.模型定义

定义一个基类模型,抽取公共字段

# 在utils目录下,创建一个models.py文件,在其中定义一个基类模型
from django.db import models


class BaseModel(models.Model):
    """
    基类,公共字段
    """
    create_time = models.DateTimeField(创建时间, auto_now_add=True)
    update_time = models.DateTimeField(更新时间, auto_now=True)
    is_delete = models.BooleanField(逻辑删除, default=False)

    class Meta:
        # 抽象类,用于继承,迁移时不会创建
        abstract = True

定义其他模型

# 在news目录下的models.py文件中定义如下数据模型
from django.db import models
from utils.models import BaseModel


class Tag(BaseModel):
    """
    文章分类标签模型
    """
    name = models.CharField(标签名, max_length=64, help_text=标签名)

    class Meta:
        ordering = [-update_time, -id]      # 排序
        db_table = "tb_tag"                     # 指明数据库表名
        verbose_name = "文章标签"                # 在admin站点中显示的名称
        verbose_name_plural = verbose_name      # 显示的复数名称

    def __str__(self):
        return self.name


class News(BaseModel):
    """
    文章模型
    """
    title = models.CharField(标题, max_length=150, help_text=标题)
    digest = models.CharField(摘要, max_length=200, help_text=摘要)
    content = models.TextField(内容, help_text=内容)
    clicks = models.IntegerField(点击量, default=0, help_text=点击量)
    image_url = models.URLField(图片url, default=‘‘, help_text=图片url)
    tag = models.ForeignKey(Tag, on_delete=models.SET_NULL, null=True)

    author = models.ForeignKey(user.User, on_delete=models.SET_NULL, null=True)

    class Meta:
        ordering = [-update_time, -id]  # 排序
        db_table = "tb_news"  # 指明数据库表名
        verbose_name = "新闻"  # 在admin站点中显示的名称
        verbose_name_plural = verbose_name  # 显示的复数名称

    def __str__(self):
        return self.title


class Comments(BaseModel):
    """
    评论模型
    """
    content = models.TextField(内容, help_text=内容)
    author = models.ForeignKey(user.User, on_delete=models.SET_NULL, null=True)
    news = models.ForeignKey(News, on_delete=models.CASCADE)

    class Meta:
        ordering = [-update_time, -id]  # 排序
        db_table = "tb_comments"  # 指明数据库表名
        verbose_name = "评论"  # 在admin站点中显示的名称
        verbose_name_plural = verbose_name  # 显示的复数名称

    def __str__(self):
        return <评论>.format(self.id)


class HotNews(BaseModel):
    """
    推荐文章表
    """
    news = models.OneToOneField(News, on_delete=models.CASCADE)
    priority = models.IntegerField(优先级, help_text=优先级)

    class Meta:
        ordering = [-update_time, -id]  # 排序
        db_table = "tb_hotnews"  # 指明数据库表名
        verbose_name = "热门新闻"  # 在admin站点中显示的名称
        verbose_name_plural = verbose_name  # 显示的复数名称

    def __str__(self):
        return <热门新闻>.format(self.id)


class Banner(BaseModel):
    """
    轮播图
    """
    image_url = models.URLField(轮播图url, help_text=轮播图url)
    priority = models.IntegerField(优先级, help_text=优先级)

    news = models.OneToOneField(News, on_delete=models.CASCADE)

    class Meta:
        ordering = [priority, -update_time, -id]  # 排序
        db_table = "tb_banner"  # 指明数据库表名
        verbose_name = "轮播图"  # 在admin站点中显示的名称
        verbose_name_plural = verbose_name  # 显示的复数名称

    def __str__(self):
        return <轮播图>.format(self.id)

三、文章标签导航功能

1.接口设计

  1. 接口说明:

    类目说明
    请求方法 GET
    url定义 /
    参数格式 无参数
  2. 返回结果

    返回新闻页面,直接在模板渲染

2.后端代码

# 在news/views.py文件中定义如下视图
from django.shortcuts import render

from .models import Tag


def index(request):
    """
    新闻首页视图
    :param request:
    :return:
    """

    tags = Tag.objects.only(id, name).filter(is_delete=False)
    return render(request, news/index.html,
                  context=
                      tags: tags
                  )

导入tag测试数据,或者直接用Navicat软件在tb_tag表中添加数据(数据见下方代码中引号里的内容,共6个),,,因为前段设置的原因,必须要跟我的内容一样,后面会用到

# insert news tag data

INSERT INTO tb_tag(name, create_time, update_time, is_delete) values
(Python基础, now(), now(), 0),
(Python高级, now(), now(), 0),
(Python函数, now(), now(), 0),
(PythonGUI, now(), now(), 0),
(Linux教程, now(), now(), 0),
(Python框架, now(), now(), 0);

3.前端代码

# 修改templates/news/index.html中 news-nav部分代码如:
        <!--  news-nav start-->
          <nav class="news-nav">
              <ul class="clearfix">
                  <li class="active"><a href="javascript:void(0)">最新资讯</a></li>
                    % for tag in tags %
                        <li><a href="javascript:void(0)" data-id=" tag.id "> tag.name </a>
                  </li>
                    % endfor %
              </ul>
          </nav>
        <!--  news-nav end -->

四、新闻列表功能

1.业务流程分析

  1. 判断前端传递标签分类id是否为空,是否为整数,是否超过范围

  2. 判断前端传递当前文章页数是否为空,是否为整数,是否超过范围

2.接口设计

接口说明:

类目说明
请求方法 GET
url定义 /news/
参数格式 查询参数

参数说明:

参数名类型是否必须描述
tag 整数 标签分类id
page 整数 当前文章页数

返回结果:


    "errno": "0", 
     "errmsg": "", 
    "data": 
        "total_pages": 61,
        "news": [
            
                id: xxx,
                "digest": "在python用import或者from...import或者from...import...as...来导入相应的模块,作用和使用方法与C语言的include头文件类似。其实就是引入...",
                "title": "import方法引入模块详解",
                "author": "python",
                "image_url": "/media/jichujiaochen.jpeg",
                "tag_name": "Python基础",
                "update_time": "2018年12月17日 14:48"
            ,
            
                id: xxx
                "digest": "如果你原来是一个php程序员,你对于php函数非常了解(PS:站长原来就是一个php程序员),但是现在由于工作或者其他原因要学习python,但是p...",
                "title": "给曾经是phper的程序员推荐个学习网站",
                "author": "python",
                "image_url": "/media/jichujiaochen.jpeg",
                "tag_name": "Python基础",
                "update_time": "2018年12月17日 14:48"
            
        ]
    

3.后端代码

在项目根目录下创建一个media文件夹,用于存放新闻图片以及用户上传文件。

# 在settings.py文件中添加
# 媒体文件配置
MEDIA_URL = /media/
MEDIA_ROOT = os.path.join(BASE_DIR, media)

django在调试模式下提供静态文件服务,为了能够返回media中的媒体文件还需在根urls.py中做如下配置

# 在根urls.py中加上static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
from django.urls import path, include
from django.conf import settings
from django.conf.urls.static import static

urlpatterns = [
    path(‘‘, include(news.urls)),
    path(‘‘, include(verification.urls)),
    path(user/, include(user.urls))
] + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)

导入测试数据,为了测试数据的导入,请确保表名一致

# 在xshell中导入测试数据,在xshell中通过rz命令,将tb_news_20181217.sql文件上传到虚拟机

mysql -u 用户名 -p -D 数据库名 < tb_news_20181217.sql

 

以上是关于Django项目: 5.新闻主页的主要内容,如果未能解决你的问题,请参考以下文章

新闻网站项目django--首页

新闻网站项目django--注册页

django学习笔记二:一个项目多个App项目搭建

如何在 Django 中放置指向网站主页的链接/网址?

Django - 创建一个没有扩展请求处理的主页面(不直接到模板)

django 一个项目多个App项目搭建