我用Python实现了一个小说网站雏形

324 阅读5分钟
原文链接: mp.weixin.qq.com

前言

前段时间做了一个爬取妹子套图的小功能,小伙伴们似乎很有兴趣,为了还特意组建了一个Python兴趣学习小组,来一起学习。十个python九个爬,在大家的印象中好像Python只能做爬虫。然而并非如此,Python 也可以做Web开发,接下来给大家展示一下如何做一个小说站点。

相关软件

软件 版本 功能 地址
Python 3.7.1 脚本语言 https://www.python.org/
Django 2.1.3 Web框架 https://www.djangoproject.com/
PyCharm 2018.2.4 可视化开发工具 http://www.jetbrains.com/pycharm/

环境搭建说明:

http://www.runoob.com/python3/python3-install.html

爬取数据

做一个小说网站,内容是必须的,首先我们爬取一本小说《星辰变》到数据库。

创建一个简单的数据库表:

  1. CREATE TABLE `novel` (

  2.   `id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自增主键',

  3.   `title` varchar(100) NOT NULL COMMENT '标题',

  4.   `content` text NOT NULL COMMENT '内容',

  5.   PRIMARY KEY (`id`)

  6. ) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8

安装数据库驱动以及连接池:

  1. # 数据库驱动

  2. pip install pymysql

  3. # 数据库连接池

  4. pip install DBUtils

代码实现:

  1. # -*- coding: UTF-8 -*-

  2. # 导入requests库

  3. import requests

  4. # 导入文件操作库

  5. import codecs

  6. from bs4 import BeautifulSoup

  7. import sys

  8. import mysql_DBUtils

  9. from mysql_DBUtils import MyPymysqlPool

  10. import importlib

  11. importlib.reload(sys)

  12. # 给请求指定一个请求头来模拟chrome浏览器

  13. headers = {

  14.    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/54.0.2840.99 Safari/537.36'}

  15. server = 'http://www.biquge.cm'

  16. # 星辰变地址

  17. book = 'http://www.biquge.cm/2/2042/'

  18. # 定义DB

  19. mysql = MyPymysqlPool("dbMysql")

  20. # 获取章节内容

  21. def get_contents(chapter):

  22.    req = requests.get(url=chapter)

  23.    html = req.content

  24.    html_doc = str(html, 'gbk')

  25.    bf = BeautifulSoup(html_doc, 'html.parser')

  26.    texts = bf.find_all('div', id="content")

  27.    # 获取div标签id属性content的内容 \xa0 是不间断空白符  

  28.    content = texts[0].text.replace('\xa0' * 4, '\n')

  29.    return content

  30. # 写入数据库

  31. def write_db(chapter, content):

  32.    sql = "INSERT INTO novel (title, content) VALUES(%(title)s, %(content)s);"

  33.    param = {"title": chapter, "content": content}

  34.    mysql.insert(sql, param)

  35. # 主方法

  36. def main():

  37.    res = requests.get(book, headers=headers)

  38.    html = res.content

  39.    html_doc = str(html, 'gbk')

  40.    # 使用自带的html.parser解析

  41.    soup = BeautifulSoup(html_doc, 'html.parser')

  42.    # 获取所有的章节

  43.    a = soup.find('div', id='list').find_all('a')

  44.    print('总章节数: %d ' % len(a))

  45.    for each in a:

  46.        try:

  47.            chapter = server + each.get('href')

  48.            content = get_contents(chapter)

  49.            chapter = each.string

  50.            write_db(chapter, content)

  51.        except Exception as e:

  52.            print(e)

  53.    mysql.dispose()

  54. if __name__ == '__main__':

  55.    main()

更多代码详见:

https://gitee.com/52itstyle/Python/tree/master/Day04

创建Web

Django 是一个开放源代码的Web应用框架,由 Python 写成。采用了 MVC 的框架模式,即模型M,视图V和控制器C。它最初是被开发来用于管理劳伦斯出版集团旗下的一些以新闻内容为主的网站的,即是CMS(内容管理系统)软件。

Django 框架的核心组件有:

  • 用于创建模型的对象关系映射

  • 为最终用户设计的完美管理界面

  • 一流的 URL 设计

  • 设计者友好的模板语言

  • 缓存系统。

创建项目

  1. # 安装Web框架

  2. pip install Django

  3. # 创建一个项目

  4. python  django-admin.py startproject itstyle

  5. # 切换目录

  6. cd itstyle

  7. # 创建App

  8. python manage.py startapp novel

一般一个项目有多个app, 当然通用的app也可以在多个项目中使用,然后启动服务:

  1. # 默认端口是8000

  2. python manage.py runserver

如果提示端口被占用,可以用其它端口:

  1. python manage.py runserver 8001

项目结构

最终代码,如下:

  1. │  manage.py

  2. │  

  3. ├─novel

  4. │  │  settings.py  # 基础配置

  5. │  │  urls.py     # URL映射

  6. │  │  wsgi.py

  7. │  │  __init__.py

  8. │  │  

  9. │          

  10. ├─templates             # 相关页面

  11. │      novel.html        # 章节

  12. │      novel_list.html    # 小说首页

  13. │      

  14. ├─utils

  15. │  │  dbMysqlConfig.cnf     # 数据库配置参数

  16. │  │  encoder.py          # 编码类

  17. │  │  mysql_DBUtils.py      # 数据库连接池

  18. │          

  19. └─view

  20.    │  index.py   # 后台业务        

要点备注

RESTful 风格

控制器 urls.py

  1. from django.conf.urls import url

  2. from django.urls import path

  3. from view import index

  4. urlpatterns = [

  5.    # 《星辰变》首页List

  6.    path('', index.main),  # new

  7.    # 章节页面 正则匹配

  8.    path('chapter/<int:novel_id>/', index.chapter),    # new

  9. ]

代码实现

  1. from django.http import HttpResponse

  2. from django.shortcuts import render

  3. import utils.mysql_DBUtils

  4. from utils.mysql_DBUtils import MyPymysqlPool

  5. from utils.encoder import MyEncoder

  6. import json

  7. mysql = MyPymysqlPool("dbMysql")

  8. # 《星辰变》章节列表

  9. def main(request):

  10.    # 这里读取10条,待优化分页

  11.    sql = "SELECT id,title FROM novel LIMIT 10;"

  12.    result = mysql.getAll(sql)

  13.    # 中文转码

  14.    result = json.dumps(result, cls=MyEncoder, ensure_ascii=False, indent=4)

  15.    result = json.loads(result)

  16.    context = {'novel_list': result}

  17.    return render(request, 'novel_list.html',  context)

  18. '''

  19. 单个章节访问

  20. 此处 novel_id 对应 urls.py 中的 <int:novel_id>

  21. 你可以访问:http://localhost:8000/chapter/1/

  22. '''

  23. def chapter(request, novel_id):

  24.    sql = "SELECT title,content FROM novel where id = %(id)s;"

  25.    param = {"id": novel_id}

  26.    result = mysql.getOne(sql, param)

  27.    result['title'] = result['title'].decode('utf-8')

  28.    result['content'] = result['content'].decode('utf-8')

  29.    context = {'novel': result}

  30.    return render(request, 'novel.html', context)

列表展示

基于后端返回的数据,在前台进行展示,这里你可以把它想象成Java中的Struts2标签或者JSTL标签,当然也有点Vue的意思:

  1. {% for novel in novel_list %}

  2.    <a href="/chapter/{{novel.id}} "><li>{{ novel.title }}</li></a>

  3. {% endfor %}

小结

至此,一个简单的Web项目雏形已经完成,当然还有很多需要优化的地方,阅读原文,关注小编的码云,持续更新。

往期精彩回顾

点击图片查看更多推荐内容

↓↓↓

我用Python爬取了妹子网100G的套图

Python学习爬取你的第一张图片

温馨提示

如果你喜欢本文,觉得对周围的小伙伴有所帮助,请分享到朋友圈,你的支持就是小编最大的动力!