1. 解析库beautifulsoup
1.1 介绍
BeautifulSoup是一个可以从HTML或XML文件中提取数据的Python库 .
官方文档 : https : / / www . crummy . com / software / BeautifulSoup / bs4 / doc / index . zh . html
1.2 解析库
Python2 . 7.3 之前的版本和Python3中 3.2 .2 之前的版本 , 必须安装lxml或html5lib ,
因为那些Python版本的标准库中内置的HTML解析方法不够稳定 .
解析器 使用方法 优势 劣势 Python标准库 BeautifulSoup(markup, “html.parser”) Python的内置标准库执行速度适中文档容错能力强 Python 2.7.3 or 3.2.2)前 的版本中文档容错能力差 lxml HTML 解析器 BeautifulSoup(markup, “lxml”) 速度快文档容错能力强 需要安装C语言库 lxml XML 解析器 BeautifulSoup(markup, [“lxml”, “xml”])``BeautifulSoup(markup, “xml”) 速度快唯一支持XML的解析器 需要安装C语言库 html5lib BeautifulSoup(markup, “html5lib”) 最好的容错性以浏览器的方式解析文档生成HTML5格式的文档 速度慢不依赖外部
安装BeautifulSoup4与解析器 :
pip install BeautifulSoup4
pip install lxml
pip install html5lib
生成节点 Tag对象 :
from bs4 import BeautifulSoup
soup = BeautifulSoup ( 需要解析的字符串 , 使用的解析器 )
1.3 容错处理
文档的容错能力 : 指的是在html代码不完整的情况下 , 使用该模块可以识别该错误。
使用BeautifulSoup解析上述代码 , 能够得到一个 BeautifulSoup 的对象 , 并能按照标准的缩进格式的结构输出 .
from bs4 import BeautifulSoup
html_doc = """
<html><head><title>页面标题</title></head>
<body>
<p class="title"><b>标题</b></p>
<p class="story">开始,
<a href="https://www.baidu.com" class="sister" id="link1">A</a>
<a href="https://www.baidu.come" class="sister" id="link2">B</a> 中间
<a href="https://www.baidu.com" class="sister" id="link3">C</a>
结束.</p>
<p class="story">...</p>
"""
soup = BeautifulSoup( html_doc, 'lxml' )
res = soup. prettify( )
print ( res)
1.4 遍历文档树
遍历文档树 : 即直接通过标签名字选择 , 特点是选择速度快 , 但如果存在多个相同的标签则只返回第一个 .
* 多个相同标签只返回第一个 , 第一个算遍历 , 其他的都不算 !
1. 获取标签对象
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. p)
print ( soup. body. p)
2. 获取标签名称
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. name)
3. 获取标签的属性
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. attrs)
print ( soup. body. p. attrs[ 'class' ] )
print ( soup. body. p[ 'class' ] )
4. 获取标签的内容
* 1. 文本内容
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. text)
print ( soup. body. p. get_text( ) )
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. next_sibling. next_sibling. text)
"""
开始,
A
B 中间
C
结束.
"""
如果tag包含了多个子节点 , tag就无法确定
. string 方法应该调用哪个子节点的内容 , . string 的输出结果是 None .
如果只有一个子节点那么就输出该子节点的文本,比如下面的这种结构 , . string 返回为None ,
但 . strings就可以找到所有文本 , 值是一个生成器 .
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. string)
print ( soup. body. p. next_sibling. next_sibling. string)
print ( soup. body. p. strings)
print ( list ( soup. body. p. strings) )
print ( list ( soup. body. p. next_sibling. next_sibling. strings) )
soup = BeautifulSoup( html_doc, 'lxml' )
for line in soup. body. p. next_sibling. next_sibling. stripped_strings:
print ( line)
"""
开始,
A
B
中 间
C
结束.
"""
5. 嵌套选择
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. head. title. text)
print ( soup. body. a. text)
6. 子节点&子孙节点
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. contents)
print ( soup. body. p. children)
for i, child in enumerate ( soup. p. children) :
print ( i, child)
print ( soup. p. descendants)
for i, child in enumerate ( soup. p. descendants) :
print ( i, child)
7. 父节点&祖先节点
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. a. parent)
print ( soup. a. parents)
for a in soup. a. parents:
print ( a, '\n' )
8. 兄弟节点
* 空行被算成一个兄弟 .
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. a. next_sibling)
print ( soup. body. a. previous_sibling)
print ( list ( soup. body. a. next_siblings) )
print ( soup. body. a. previous_siblings)
1.5 搜索文档树
1. 五种过滤器
五种过滤器 : 字符串 , 正则表达式 , 列表 , True / False , 函数方法
* 1. 字符串过滤 ( )
find ( ) : 找到一个就放回
find_all ( ) : 找多个
. . .
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. find( 'p' ) )
print ( soup. find( name= 'p' ) )
print ( soup. find( class_= 'title' ) )
print ( soup. find( attrs= { 'class' : 'title' } ) )
print ( soup. find( id = "link1" ) )
print ( soup. find( attrs= { 'id' : 'link1' } ) )
print ( soup. find( href= "https://www.baidu.com" ) )
print ( soup. find( id = "link1" , class_= 'sister' ) )
print ( soup. find_all( name= 'p' ) )
* 2. 正则表达式
import re
soup = BeautifulSoup( html_doc, 'lxml' )
re_t = re. compile ( '^t' )
print ( soup. find( class_= re_t) )
* 3. 列表
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. find_all( class_= [ 'title' , 'sister' ] ) )
* 4. True / False
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. find( id = True ) )
print ( soup. p. find( id = False ) )
print ( soup. find( href= True ) )
* 5. 自定义函数
soup = BeautifulSoup( html_doc, 'lxml' )
def has_class_but_no_id ( tag) :
return tag. has_attr( 'class' ) and not tag. has_attr( 'id' )
print ( soup. body. find_all( has_class_but_no_id) )
* 6. limit 参数与 recursive参数
limit : 限制条数
recursive : 当前层级查询不到 , 递归查询 ( 默认开启 )
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. find_all( name= 'p' , limit= 1 ) )
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. find_all( name= 'b' , recursive= False ) )
2. css选择器
select 返回的是列表形式 .
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. select( '#link1' ) )
print ( soup. select( 'body>p>b' ) )
print ( soup. select( 'body p b' ) )
1.6 修改文档树
* 1. 修改标签名称
soup = BeautifulSoup( html_doc, 'lxml' )
soup. body. p. name = 'h3'
print ( soup. body. h3. name)
* 2. 修改属性值
soup = BeautifulSoup( html_doc, 'lxml' )
soup. body. p[ 'class' ] = 'c1'
print ( soup. body. p. attrs)
* 3. 修改值
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. string)
soup. body. p. string = 'xxx'
print ( soup. body. p. string)
* 4. 添加值
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p. string)
soup. body. p. string = 'xxx'
soup. body. p. append( 'abcd' )
print ( soup. body. p. string)
print ( soup. body. p. text)
* 5. 删除标签
soup = BeautifulSoup( html_doc, 'lxml' )
print ( soup. body. p)
soup. body. p. decompose( )
print ( soup. body. p)
2. 宝塔面板与JumpServer堡垒机
2.1 宝塔面板
宝塔 : 宝塔面板是一款支持windows和linux系统的服务器管理软件 , 可通过Web端管理服务器 , 提升运维效率 .
使用宝塔前: 手工输入命令安装各类软件 , 操作起来费时费力并且容易出错 .
而且需要记住很多Linux的命令,非常复杂 .
使用宝塔后: 2 分钟装好面板 , 一键管理服务器 , 鼠标点几下就能替代以前的复杂繁多命令 ,
操作简单 , 看一眼就会使用 . ( 图形化替代命令行操作 )
2.2 JumpServer堡垒机
JumpServer跳板机 / 堡垒机 : 是一类可作为跳板批量操作远程设备的网络设备 ,
提供了认证、授权、审计和自动化运维等功能 . . .
jumpserver组件说明
jumpserver堡垒机由以下三个部分组成:
* 1. jumpserver
jumpserver是jumpserver的核心组件 , 是一个使用Python的django开发的管理后台 , 支持restful API .
* 2. coco
coco是SSH Server和Web Terminal Server的组件,提供SSH和WebSocket接口 , 使用paramiko和flask开发 .
* 3. luna
luna是Web Terminal Server的前端 , 前端页面均由该项目提供 , 主要负责页面后台的渲染 .
3. 使用bs4库爬虫实例
网站 : https : / / www . autohome . com . cn / news / 2 /#liststart
需要获取 : 标题 , 图片 , 简介 , 链接
使用BeautifulSoup , 从HTML文件中提取数据 .
* 1. 分析网站
import requests
res = requests. get( 'https://www.autohome.com.cn/news/1/#liststart' )
print ( res. text)
得到的ul信息中有文章也有广告 .
有h3标签的是文字 , 没有h3标签的广告获取是空li标签 .
广告
空标签
文章链接与封面路由
* 2. 使用BeautifulSoup获取html的ul数据 .
import requests
from bs4 import BeautifulSoup
res = requests. get( 'https://www.autohome.com.cn/news/1/#liststart' )
soup = BeautifulSoup( res. text, 'html.parser' )
ul = soup. find( class_= 'article' )
print ( ul)
* 3. 查询ul标签下所有的li标签
import requests
from bs4 import BeautifulSoup
res = requests. get( 'https://www.autohome.com.cn/news/1/#liststart' )
soup = BeautifulSoup( res. text, 'html.parser' )
ul = soup. find( class_= 'article' )
li_list = ul. find_all( name= 'li' )
print ( li_list)
* 4. 获取标题 , 图片 , 简介 , 链接的信息 .
import requests
from bs4 import BeautifulSoup
res = requests. get( 'https://www.autohome.com.cn/news/1/#liststart' )
soup = BeautifulSoup( res. text, 'html.parser' )
ul = soup. find( class_= 'article' )
li_list = ul. find_all( name= 'li' )
for li in li_list:
title = li. find( name= 'h3' )
if title:
title = title. text
article_url = 'https:' + li. find( 'a' ) . attrs. get( 'href' )
img_url = li. find( name= 'img' ) . attrs. get( 'src' )
img_url = img_url if img_url. startswith( 'https:' ) else 'https:' + img_url
desc = li. find( 'p' ) . text
print (
f"""
标题: { title} ,
文章链接: { article_url} ,
封面: { img_url} ,
简介: { desc}
"""
)
4. 创建代理池
* 1. 分析免费代理网站
地址 : http : / / www . 66 ip . cn / 1. html
import requests
url = 'http://www.66ip.cn/1.html'
res = requests. get( url)
res. encoding = res. apparent_encoding
print ( res. text)
* 2. 获取ip表单
import requests
from bs4 import BeautifulSoup
url = 'http://www.66ip.cn/1.html'
res = requests. get( url)
res. encoding = res. apparent_encoding
soup = BeautifulSoup( res. text, 'lxml' )
print ( soup. find_all( name= 'table' ) [ - 1 ] )
< table width = ' 100%' border = " 2px" cellspacing = " 0px" bordercolor = " #6699ff" >
< tr>
< td> ip</ td>
< td> 端口号</ td>
< td> 代理位置</ td>
< td> 代理类型</ td>
< td> 验证时间</ td>
</ tr>
< tr>
< td> 165.225.20.14</ td>
< td> 10605</ td>
< td> 宁夏回族自治区中卫市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日06时 验证</ td>
</ tr>
< tr>
< td> 8.215.27.71</ td>
< td> 3128</ td>
< td> 吉林省辽源市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日04时 验证</ td>
</ tr>
< tr>
< td> 103.155.54.245</ td>
< td> 84</ td>
< td> 广西壮族自治区桂林市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日02时 验证</ td>
</ tr>
< tr>
< td> 183.245.6.120</ td>
< td> 8080</ td>
< td> 云南省保山市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日00时 验证</ td>
</ tr>
</ table>
* 3. 获取表单中tr的标签信息
import requests
from bs4 import BeautifulSoup
url = 'http://www.66ip.cn/1.html'
res = requests. get( url)
res. encoding = res. apparent_encoding
soup = BeautifulSoup( res. text, 'lxml' )
table = soup. find_all( name= 'table' ) [ - 1 ]
for tr in table. children:
print ( tr)
* table . children 获取table下说有的子标签 , 行号算一个标签 ! ! !
正常的标签 : < ! -- < class 'bs4.element.Tag' > -- >
空的标签 : < ! -- < class 'bs4.element.NavigableString' > -- >
< tr>
< td> ip</ td>
< td> 端口号</ td>
< td> 代理位置</ td>
< td> 代理类型</ td>
< td> 验证时间</ td>
</ tr>
< tr>
< td> 165.225.20.14</ td>
< td> 10605</ td>
< td> 宁夏回族自治区中卫市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日06时 验证</ td>
</ tr>
< tr>
< td> 8.215.27.71</ td>
< td> 3128</ td>
< td> 吉林省辽源市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日04时 验证</ td>
</ tr>
< tr>
< td> 103.155.54.245</ td>
< td> 84</ td>
< td> 广西壮族自治区桂林市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日02时 验证</ td>
</ tr>
< tr>
< td> 183.245.6.120</ td>
< td> 8080</ td>
< td> 云南省保山市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日00时 验证</ td>
</ tr>
* 4. 获取表单中tr的标签信息 ( 剔除空行标签 )
import requests
import bs4
from bs4 import BeautifulSoup
url = 'http://www.66ip.cn/1.html'
res = requests. get( url)
res. encoding = res. apparent_encoding
soup = BeautifulSoup( res. text, 'lxml' )
table = soup. find_all( name= 'table' ) [ - 1 ]
for tr in table. children:
if isinstance ( tr, bs4. element. Tag) :
print ( tr)
* 5. 获取表单中的td标签
. . .
for tr in table. children:
if isinstance ( tr, bs4. element. Tag) :
for td in tr. children:
print ( td)
print ( '----' )
< td> ip</ td>
< td> 端口号</ td>
< td> 代理位置</ td>
< td> 代理类型</ td>
< td> 验证时间</ td>
----
< td> 165.225.20.14</ td>
< td> 10605</ td>
< td> 宁夏回族自治区中卫市</ td>
< td> 高匿代理</ td>
< td> 2022年06月17日06时 验证</ td>
* 6. 正则匹配获取ip与端口
import requests
import bs4
from bs4 import BeautifulSoup
import re
url = 'http://www.66ip.cn/1.html'
res = requests. get( url)
res. encoding = res. apparent_encoding
soup = BeautifulSoup( res. text, 'lxml' )
table = soup. find_all( name= 'table' ) [ - 1 ]
ip_port_list = [ ]
for tr in table. children:
if isinstance ( tr, bs4. element. Tag) :
re_ip = re. compile ( r'^\d+.\d+.\d+.\d+$' )
ip = tr. find( text= re_ip)
re_port = re. compile ( r'^\d+$' )
port = tr. find( text= re_port)
if ip and port:
http_type_list = [ 'http' , 'https' ]
ip_port = ip + ":" + port
for http_type in http_type_list:
try :
res = requests. get( 'https://www.baidu.com/' , proxies= { http_type: ip_port} , timeout= 10 )
if res. status_code == 200 :
ip_port_list. append( ( http_type, ip_port) )
print ( 'ok' )
except Exception as e:
pass
print ( ip_port_list)
"""
[('http', '52.236.90.60:3128'),
('http', '165.225.20.14:10605'),
('http', '8.215.27.71:3128'),
('http', '103.155.54.245:84'),
('http', '183.245.6.120:8080')]
"""
5. 第三链接池项目
* 1. 下载项目
项目地址 : https : / / github . com / jhao104 / proxy_pool
* 2. 解压并打来项目
* 3. 安装依赖 : pip install -r requirements . txt
# 安装不上就换成国内源
APScheduler = = 3.2 .0 # 定时任务框架
werkzeug = = 0.15 .5 # Python的WSGI规范的实用函数库
Flask = = 1.0
requests = = 2.20 .0
click = = 7.0 # 用于快速创建命令行
gunicorn = = 19.9 .0 # Python WSGI UNIX的HTTP服务器
lxml # lxml是XML和HTML的解析器
redis
* 4. 更新配置 ( 配置好redis库即可 )
HOST = "0.0.0.0"
PORT = 5010
DB_CONN = 'redis://:127.0.0.1:6379/0'
PROXY_FETCHER = [
"freeProxy01" ,
"freeProxy02" ,
]
* 5. 启动项目
如果已经具备运行条件 , 可用通过proxyPool . py启动
程序分为 : schedule 调度程序 和 server Api服务
# 都在Terminal 中输入命令
# 1. 启动调度程序 ( 获取免费代理 )
python proxyPool . py schedule
# 2. 启动webApi服务
python proxyPool . py server
启动报错 : ( 更新 Flask Jinja2 )
pip uninstall Flask Jinja2
pip install Flask Jinja2
启动调度后获取免费代理
* 6. 测试
* 7. 随机获取一个请求
* 8. 请求api介绍
启动web服务后 , 默认配置下会开启 http : / / 127.0 .0 .1 : 5010 的api接口服务 :
api method Description params / GET api介绍 None /get GET 随机获取一个代理 可选参数: ?type=https
过滤支持https的代理 /pop GET 获取并删除一个代理 可选参数: ?type=https
过滤支持https的代理 /all GET 获取所有代理 可选参数: ?type=https
过滤支持https的代理 /count GET 查看代理数量 None /delete GET 删除代理 ?proxy=host:ip
* 删除代理 ?proxy = host : ip = = > 官方文旦写的不好理解了 , 应该是 ?proxy = ip : port
* 9. 新建一个项目 , 在项目中使用
import requests
def get_proxy ( ) :
return requests. get( "http://127.0.0.1:5010/get/" ) . json( )
def delete_proxy ( proxy) :
requests. get( "http://127.0.0.1:5010/delete/?proxy={}" . format ( proxy) )
def getHtml ( ) :
retry_count = 5
proxy = get_proxy( ) . get( "proxy" )
while retry_count > 0 :
try :
html = requests. get( 'http://www.baidu.com' , proxies= { "http" : "http://{}" . format ( proxy) } )
return html
except Exception:
retry_count -= 1
delete_proxy( proxy)
return None
html = getHtml( )
print ( html. status_code)
6. 打码平台使用
只演示图片验证码 :
* 1. 将验证码下载到本地
* 2. 将验证码上传到打码平台 ( 将图片验证码给别人识别 , 全国有几十台服务器 , 有六千多工人 , 24 小时轮班 . . . )
* 3. 打码平台放回验证码
验证码识别平台 : http : / / www . chaojiying . com /
* 1. 注册一个账户
* 2. 下载Demo实例代码包
* 3. 解压代码包
Chaojiying_Python
| -a . jpg 验证码图片
| -chaojiying . py 实例代码
* 4. 生成软件id
* 5. 获取积分
* 6. 打开项目测试
import requests
from hashlib import md5
class Chaojiying_Client ( object ) :
def __init__ ( self, username, password, soft_id) :
self. username = username
password = password. encode( 'utf8' )
self. password = md5( password) . hexdigest( )
self. soft_id = soft_id
self. base_params = {
'user' : self. username,
'pass2' : self. password,
'softid' : self. soft_id,
}
self. headers = {
'Connection' : 'Keep-Alive' ,
'User-Agent' : 'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0)' ,
}
def PostPic ( self, im, codetype) :
"""
im: 图片字节
codetype: 题目类型 参考 http://www.chaojiying.com/price.html
"""
params = {
'codetype' : codetype,
}
params. update( self. base_params)
files = { 'userfile' : ( 'ccc.jpg' , im) }
r = requests. post( 'http://upload.chaojiying.net/Upload/Processing.php' , data= params, files= files,
headers= self. headers)
return r. json( )
def PostPic_base64 ( self, base64_str, codetype) :
"""
im: 图片字节
codetype: 题目类型 参考 http://www.chaojiying.com/price.html
"""
params = {
'codetype' : codetype,
'file_base64' : base64_str
}
params. update( self. base_params)
r = requests. post( 'http://upload.chaojiying.net/Upload/Processing.php' , data= params, headers= self. headers)
return r. json( )
def ReportError ( self, im_id) :
"""
im_id:报错题目的图片ID
"""
params = {
'id' : im_id,
}
params. update( self. base_params)
r = requests. post( 'http://upload.chaojiying.net/Upload/ReportError.php' , data= params, headers= self. headers)
return r. json( )
if __name__ == '__main__' :
chaojiying = Chaojiying_Client( 'q18177' , 'q18177' , '93518' )
im = open ( 'a.jpg' , 'rb' ) . read( )
print ( chaojiying. PostPic( im, 1902 ) )
* 7. 查看结果pic_str是验证码
7. 打码平台使用案例
* 1. 分析登入 ( 输入一个错误的密码 , 不然看不到请求就跳转了 )
登入地址 : http : / / www . aa7a . cn / user . php? & ref = http % 3 A % 2 F % 2 Fwww . aa7a . cn % 2 F
获取验证码图片
* 这个网站的验证码就是不检验的 , 一下找不到合适的网站测试
import requests
from bs4 import BeautifulSoup
res = requests. get( 'http://www.aa7a.cn/user.php?&ref=http%3A%2F%2Fwww.aa7a.cn%2F' )
soup = BeautifulSoup( res. text, 'lxml' )
url = soup. find( id = 'login_img_checkcode' ) [ 'src' ]
code_url = 'http://www.aa7a.cn/' + url
print ( code_url)
* 2. 登入触发事件
数据提交地址 : http : / / www . aa7a . cn / user . php
提交数据 :
username : 1360012768 @ qq . com
password : zxc12dasdasd
captcha : asda
remember : 1
ref : http : / / www . aa7a . cn
act : act_login
import requests
from bs4 import BeautifulSoup
from chaojiying import Chaojiying_Client
res = requests. get( 'http://www.aa7a.cn/user.php?&ref=http%3A%2F%2Fwww.aa7a.cn%2F' )
soup = BeautifulSoup( res. text, 'lxml' )
url = soup. find( id = 'login_img_checkcode' ) [ 'src' ]
code_url = 'http://www.aa7a.cn/' + url
chaojiying = Chaojiying_Client( 'q18177354117' , 'q18177354117' , '935180' )
res = requests. get( code_url)
code_dict = chaojiying. PostPic( res. content, 1902 )
print ( code_dict. get( 'pic_str' ) )
data = {
'username' : '[email protected] ' ,
'password' : 'zxc123456' ,
'captcha' : code_dict. get( 'pic_str' ) ,
'remember' : 1 ,
'ref' : 'http://www.aa7a.cn/' ,
'act' : 'act_login' ,
}
res = requests. post( 'http://www.aa7a.cn/user.php' , data= data)
print ( res. text)
8. bs4爬虫小说
* 1. 分析小说章节名称
地址 : https : / / www . au26 . com / shu / 3414 /
分析小说章节名称 , 文章内容 .
末尾还有两种广告 !
* 2. 爬虫程序
import requests
from bs4 import BeautifulSoup
import re
res = requests. get( 'https://www.au26.com/shu/3414/' )
soup = BeautifulSoup( res. text, 'lxml' )
name = soup. h1. text
id_list = soup. find( id = 'list' )
chapter_re_href = re. compile ( r'(.*?).html' )
chapter_re_text = re. compile ( r'第\d+章.*' )
list_a = id_list. find_all( href= chapter_re_href, text= chapter_re_text)
chapter_list = [ ]
for chapter in list_a:
if chapter in chapter_list:
index = chapter_list. index( chapter)
chapter_list. pop( index)
chapter_list. append( chapter)
chapter_list. append( chapter)
print ( chapter_list)
with open ( f' { name} .txt' , mode= 'wt' , encoding= 'utf-8' ) as wf:
for chapter in chapter_list:
chapter_name = chapter. text
chapter_url = 'https://www.au26.com/' + chapter. get( 'href' )
res = requests. get( chapter_url)
soup = BeautifulSoup( res. text, 'lxml' )
content = soup. find( id = 'content' ) . text
str1 = '喜欢大明王侯请大家收藏:(www.au26.com)大明王侯笔趣阁备用站更新速度最快。 '
str2 = '&&ahref=http:www.&&;起点中文网www.欢迎广大书友光临阅读,最新、最快、最火的连载作品尽在起点原创!'
pure_content = content. strip( str1) . strip( str2)
wf. write( chapter_name + '\n' )
wf. write( pure_content + '\n' )