当前位置:   article > 正文

盗墓笔记案例_《盗墓笔记》微信代码

《盗墓笔记》微信代码

目录

目标网址:http://www.daomubiji.com/

数据内容:

scrapy项目

实现分布式的步骤

代码的实现

 Spider.py

1.Python中os.mkdir()与os.makedirs()的区别及用法

2.copy与deepcopy的区别与用法

3.meta传参

4.列表合并

5.正则表达式替换

items.py 

管道保存pipeline.py

settings.py

启动

注意事项:


目标网址:http://www.daomubiji.com/

数据内容:

  1. 书的名称
  2. 章节名称
  3. 文本内容

scrapy项目

  1. 创建项目
  2. 创建爬虫
  3. 定义item
  4. 编写spider
  5. 定义初始请求
  6. 解析响应内容
  7. 定义管道
  8. 运行项目

实现分布式的步骤

  1. 安装:pip install scrapy-redis.
  2. 将爬虫主文件中继承自Scrapy中的scrapy.SpiderCrawlSpider替换成Scrapy-Redis的RedisSpiderRedisCrawlSpider
  3. 初始的start_urls改为redis_kev
  4. settings.py文件中修改Scrapy自带的调度器类和去重类Scrapy-Redis提供的类。
    1. # 调度器 使用scrapy-redis
    2. SCHEDULER = "scrapy redis.scheduler.Scheduler"
    3. # 去重的 使用scrapy-redis
    4. DUPEFILTER_CLASS = "scrapy_redis.dupeŨ lter.RFPDupeFilter"
    5. # 断点续爬 请求持久化
    6. SCHEDULER_PERSIST = True
  5. setting里打开管道
    1. ITEM_PIPELINES = {
    2. 'dmbj.pipelines.DmbjPipeline': 300,
    3. # 数据保存到redis
    4. 'scrapy_redis.pipelines.RedisPipeline': 400,
    5. }

代码的实现

 Spider.py

  1. import scrapy
  2. from dmbj.items import DmbjItem
  3. import re, os
  4. from copy import deepcopy
  5. # redis要导入的内容
  6. from scrapy_redis.spiders import RedisSpider
  7. class SpiderSpider(RedisSpider):
  8. name = 'spider'
  9. # allowed_domains = ['daomubiji.com']
  10. # start_urls = ['http://daomubiji.com/']
  11. # redis要写成这个
  12. redis_key = 'dmbj'
  13. def parse(self, response):
  14. """一级爬取"""
  15. text = response.text
  16. html = response.xpath('//ul[@class="sub-menu"]//a')
  17. for i in html:
  18. item = DmbjItem()
  19. # 书名
  20. item['book_name'] = i.xpath('./text()').get()
  21. # 连接
  22. book_link = i.xpath('./@href').get()
  23. # 书名记得替换特殊字符,预防引发爬取时变成转义字符
  24. book_path = re.sub(r'[\\\/\:\*\?\"\<\>\|]', '_', item['book_name'])
  25. # 书本存放路径
  26. dirpath = f'./noval/{book_path}'
  27. # 每本书一个文件见存放
  28. if not os.path.exists(dirpath):
  29. os.makedirs(dirpath)
  30. # 发送请求到下一级爬取 记得用深拷贝
  31. yield scrapy.Request(url=book_link, callback=self.second_parse, meta={'item': deepcopy(item)})
  32. def second_parse(self, response):
  33. """二级爬取"""
  34. # 接受上一个参数的传参
  35. item = response.meta.get('item')
  36. article_list = response.xpath('//div[@class="excerpts"]//article')
  37. for i in article_list:
  38. # 章节名字
  39. item['chapter_title'] = i.xpath('./a/text()').get()
  40. # 章节链接
  41. content_link = i.xpath('./a/@href').get()
  42. yield scrapy.Request(url=content_link, callback=self.third_parse, meta={'item': deepcopy(item)})
  43. def third_parse(self,response):
  44. """三级爬取"""
  45. item = response.meta.get('item')
  46. content = response.xpath('//article[@class="article-content"]/p/text()').getall()
  47. # 每个段落用换行代替
  48. item['content'] = '\n'.join(content)
  49. yield item

设计知识点:

1.Python中os.mkdir()与os.makedirs()的区别及用法

首先说os.mkdir(path),他的功能是一级一级的创建目录,前提是前面的目录已存在,如果不存在会报异常。

  1. import os
  2.  
  3. os.mkdir('d:\hello')    #  正常
  4. os.mkdir('d:\hello\hi') #  正常
  5.  
  6. #  如果d:\hello目录不存在
  7. #  则os.mkdir('d:\hello\hi')执行失败

然后是os.makedirs(path),可以一次创建多级目录,中间目录不存在也能正常的创建。

  1. import os
  2.  
  3. os.makedirs('d:\hello')    #  正常
  4. os.makedirs('d:\hello\hi') #  正常
  5.  
  6. #  如果d:\hello目录不存在
  7. #  则os.makedirs('d:\hello\hi')  #  仍然正常

2.copy与deepcopy的区别与用法

参考这篇博客:copy与deepcopy的区别

3.meta传参

上一级爬虫发送

yield scrapy.Request(url=content_link, callback=self.third_parse, meta={'item': deepcopy(item)})

下级爬虫接受 

item = response.meta.get('item')

4.列表合并

每个段落用换行合并

  1. # 每个段落用换行代替
  2. item['content'] = '\n'.join(content)

5.正则表达式替换

  1. # 书名记得替换特殊字符,预防引发爬取时变成转义字符
  2. book_path = re.sub(r'[\\\/\:\*\?\"\<\>\|]', '_', item['book_name'])

items.py 

  1. import scrapy
  2. class DmbjItem(scrapy.Item):
  3. # define the fields for your item here like:
  4. # name = scrapy.Field()
  5. # 书名
  6. book_name = scrapy.Field()
  7. # 章节名
  8. chapter_title = scrapy.Field()
  9. # 章节内容
  10. content = scrapy.Field()

管道保存pipeline.py

  1. import re
  2. class DmbjPipeline:
  3. def open_spider(self,spider):
  4. pass
  5. def process_item(self, item, spider):
  6. # 替换字符
  7. self.book_name = re.sub(r'[\\\/\:\*\?\"\<\>\|]', '_', item['book_name'])
  8. self.chapter_title = re.sub(r'[\\\/\:\*\?\"\<\>\|]', '_', item['chapter_title'])
  9. # 创建文件
  10. self.f = open(f'./noval/{self.book_name}/{self.chapter_title}.txt','w',encoding='utf-8')
  11. # 写入
  12. self.f.write(item["content"])
  13. return item
  14. def close_spider(self,spider):
  15. self.f.close()

settings.py

  1. # 调度器 使用scrapy_redis
  2. SCHEDULER = "scrapy_redis.scheduler.Scheduler"
  3. # 去重 使用scrapy_redis
  4. DUPEFILTER_CLASS = "scrapy_redis.dupefilter.RFPDupeFilter"
  5. # 断点续爬 请求持久化
  6. SCHEDULER_PERSIST = True
  7. ITEM_PIPELINES = {
  8. 'dmbj.pipelines.DmbjPipeline': 300,
  9. # 数据保存到redis
  10. 'scrapy_redis.pipelines.RedisPipeline': 400,
  11. }

启动

需要打开redis.py,而且创建redis列表,和起始地址

然后开启多个终端模拟多台电脑运行即可

注意事项:

python3.10之后要做出的修改,在spiders.py的源代码里面

from collections import Iterable from collections.abc import Iterable

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/Monodyee/article/detail/232461
推荐阅读
相关标签
  

闽ICP备14008679号