背景
抓取古诗文大全_古诗文网的全部内容~
1. 创建
1.1 创建项目
scrapy startproject 项目名称
scrapy startproject gushiwen
1.2 创建模板
scrapy genspider -t crawl 爬虫名称 域名
scrapy genspider -t crawl gushiwen gushiwen.org
此时d:/crawl下自动生成了模板gushiwen.py
2. 定义规则
- LinkExtractor链接提取器:会去起始url响应回来的页面中提取指定的url
- rules元组中存放的是不同的规则解析器(封装好了某种解析规则)
- 规则解析器:根据链接提取器中提取到的链接,根据指定规则提取解析器链接网页中的内容。
参数名 | 参数含义 |
---|---|
allow | 提取符合对应正则表达式的链接 |
deny | 不提取符合对应正则表达式的链接 |
restrict_xpaths | 使用xpath表达式与allow共用作用提取出同时符合对应xpath表达式和对应正则表达式的链接 |
allow_domains | 允许提取的域名,比如我只想提取某个域名下的链接时候会使用 |
deny_domains | 禁止提取的域名,比如我需要限制一定不提取某个域名下的链接时会使用 |
3. 解析页面
明确我们要提取的字段,这里我需要的是体裁、标题、朝代、作者、内容;于是,打开items.py上定义一个类:
然后在模板gushiwen.py中引入该类
from gushiwen.items import GushiwenItem
分析网页,确定每个字段的xpath后,我们就可以在parse_item()方法里面开始提取内容了
def parse_item(self, responAse):
item = GushiwenItem()
divs = response.xpath('//div[@class="sons"]')
nums = len(divs)
for i in range(nums):
d = response.xpath('/html/body/div[2]/div[1]/div['+str(2*i+1)+']')
item["genre"] = ""
try:
item["title"] = d.xpath('./div[1]/p[1]/a/b/text()').extract()[0].strip()
except:
continue
try:
item["dynasty"] = d.xpath('./div[1]/p[2]/a[1]/text()').extract()[0].strip()
except:
continue
try:
item["author"] = d.xpath('./div[1]/p[2]/a[2]/text()').extract()[0]
except:
continue
content = ''
for p in d.xpath('.//div[@class="contson"]//p/text()'):
content = content + p.extract().strip()
if content == '':
content = d.xpath('.//div[@class="contson"]/text()').extract()[0].strip()
item["content"] = content
yield item # 将item提交至管道
4. 保存结果
在管道文件pipelines.py中实现item的处理process_item。这里我是把它写入txt里面,用制表符分割每个字段。我们也可以在这个文件里面多写几个类,诸如写入json文件、csv文件的类,然后调用的时候换成这些类就行。
关键一步:还需要在设置setting.py里面调用pipelines的这个类,setting.py里面已经写好了,我们只需要取消注释就行。
5. 执行爬虫
scrapy crawl 爬虫名称
我在“D:\crawl”路径执行程序没有成功,将模板文件gushiwen.py复制“D:\crawl\gushiwen\gushiwen\spiders”里面,将路径切换到“D:\crawl\gushiwen”执行命令就跑通了:
scrapy crawl gushiwen
程序在跑的时候就有输出文件生成了,等爬完了去验收就ok了!
错误总结
- 一开始不熟悉,我既想提取下一页,但是在allow=sublink那里又把网页规定只能局限在第一页,难怪一直翻页不了。。。后来,我看文言文那里一共有60页,就想把提取下一页的规则解析器注释掉,直接在sublink=“default_4A111111111111A[1-60].aspx”。发现结果还是少了一些,仔细分析才知道并非每个页面都是"default_4A111111111111A开头的,像文言文第40页就不是了。
- 因为提取的内容有些前后自带换行符,以至于我写出的txt文件有些行的正文content字段跳到下一行。本来想手工调整,后来觉得实在太多了,于是在代码里对str字段加上strip()方法就轻松解决了。
- xpath语法要掌握好,一开始//和/分不清,走了不少弯路。建议用xpath时候先学习参考教程最后一篇,少走弯路。
代码
yingtingHuang/scrapy_crawl: scrapy爬虫
https://github.com/yingtingHuang/scrapy_crawl
参考教程
- scrapy框架中crawlspider的使用 - 水痕 - CSDN博客
https://blog.csdn.net/kuangshp128/article/details/80304982 - Scrapy框架的使用之Scrapy通用爬虫 - liukuan73的专栏 - CSDN博客
https://blog.csdn.net/liukuan73/article/details/80459435 - python爬虫之Scrapy框架(CrawlSpider) - 迎风而来 - 博客园
https://www.cnblogs.com/sui776265233/p/9724147.html - XPath 语法
http://www.w3school.com.cn/xpath/xpath_syntax.asp