RedisCrawlSpider类
这个不陌生吧!跟CrawlSpider类差不多,只不过这个是解决在分布式爬虫的时候实现自动翻页操作。那么我们来看一下演示代码:
# -*- coding: utf-8 -*-
from scrapy.spiders import Rule
from scrapy.linkextractors import LinkExtractor
from scrapy_redis.spiders import RedisCrawlSpider
class MySpider(RedisCrawlSpider):#继承RedisSpider
name = 'myspider_redis' #爬虫的名字
allowed_domains = ['jd.com'] #手动指定allow_domain
redis_key = 'myspider:start_urls'#指定reids中start_urls的键
#------>启动的时候只需要往对应的键中存入url地址,不同服务器的爬虫就会来取该url
#------>所以启动爬虫的命令分为两个步骤:
# 1.scrapy crawl myspider_redis(或者scrapy runspider myspider_redis)让爬虫就绪
# 2.在redis中输入lupsh myspider:start:urls "http://XXXX" 让爬虫从这个url开始爬取
rules = ( #----->和crawl一样,指定url的过滤规则
Rule(LinkExtractor(),callback='parse_page',follow=True)
)
# def __init__(self,*args,**kwargs): #动态的设置allow_domain,一般不需要,直接手动指定即可
# domain=kwargs.pop('domain','')
# self.allowed_domains=filter(None,domain.split(','))
# super(MySpider,self).__init__(*args,**kwargs)
#
def parse_page(self,response):
pass
到这里的话,也是非常的好理解了,跟前面的CrawlSpider一样,那么具体我们通过演示亚马逊图书爬虫,来更好的理解它。
亚马逊图书实战演示
我们的目标地址是:亚马逊图书
我们通过下面的这种方式创建代码:
scrapy startproject amazcon
cd amazon
scrapy genspider -t crawl ama amazon.cn
然后修改继承的父类就可以了,如果不喜欢这种方式,可以手打代码。我们首先就是分析网页的代码,核对我们看到的标签是否存在html源文件中。那么参考代码:
# -*- coding: utf-8 -*-
from scrapy.linkextractors import LinkExtractor
from scrapy.spiders import Rule
from scrapy_redis.spiders import RedisCrawlSpider
class AmaSpider(RedisCrawlSpider):
name = 'ama'
allowed_domains = ['amazon.cn']
# start_urls = ['http://amazon.cn/']
redis_key = 'amazon'
rules = (
#大分类和小分类的url地址
Rule(LinkExtractor(restrict_xpaths=('//div[@aria-live="polite"]/li')),follow=True),
#定位图书详情页的url地址
Rule(LinkExtractor(restrict_xpaths=('//div[@id="mainResults"]/ul/li//h2/..')), callback='parse_book_detail'),
#翻页
Rule(LinkExtractor(restrict_xpaths=('//div[@id="pagn"]')), follow=True),
)
#处理图书详情页,提取部分数据
def parse_book_detail(self, response):
print(response.body.decode())
item = {}
item['book_name']=response.xpath('//h1[@id="title"]/span/text()').extract_first()
item['book_author']=response.xpath('//div[@id="bylineInfo"]/span/a/text()').extract_first()
item['book_img']=response.xpath('//div[@id="ebooks-img-canvas"]/img/@src').extract_first()
item['book_price']=response.xpath('//span[@class="a-color-base"]/span/text()').extract_first()
然后是修改settings文件:
# -*- coding: utf-8 -*-
# Scrapy settings for amazon project
#
# For simplicity, this file contains only settings considered important or
# commonly used. You can find more settings consulting the documentation:
#
# https://doc.scrapy.org/en/latest/topics/settings.html
# https://doc.scrapy.org/en/latest/topics/downloader-middleware.html
# https://doc.scrapy.org/en/latest/topics/spider-middleware.html
BOT_NAME = 'amazon'
SPIDER_MODULES = ['amazon.spiders']
NEWSPIDER_MODULE = 'amazon.spiders'
USER_AGENT = 'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.149 Safari/537.36'
LOG_LEVEL='DEBUG'
ROBOTSTXT_OBEY = False
ITEM_PIPELINES = {
'amazon.pipelines.AmazonPipeline': 300,
'scrapy_redis.pipelines.RedisPipeline':400,
}
#指定哪个去重方法结合request对象去重
DUPEFILTER_CLASS='scrapy_redis.dupefilter.RFPDupeFilter'
#指定scheduler队列
SCHEDULER='scrapy_redis.scheduler.Scheduler'
#队列中的内容是否持久保存,为False的时候,关闭redis的同时会清空redis数据
SCHEDULER_PERSIST=True
REDIS_URL='redis://127.0.0.1:6379'
开启redis服务端,在reids对应的键中添加开始的URL地址:
lpush amazon https://www.amazon.cn/b?ie=UTF8&node=662409051
代码开始运行,发现被反扒,也就是在图书详情页是没有数据的,需要输入验证码了。
腾讯招聘实战演示
为了能够看到具体的效果,我们选择简单的:http://circ.gov.cn/web/site0/tab5240/作为演示,可参考:
# -*- coding: utf-8 -*-
from scrapy.linkextractors import LinkExtractor
from scrapy.spiders import Rule
from scrapy_redis.spiders import RedisCrawlSpider
import re
class AmaSpider(RedisCrawlSpider):
name = 'ama'
allowed_domains = ['circ.gov.cn']
# start_urls = ['http://amazon.cn/']
redis_key = 'amazon'
rules = (
#翻页
Rule(LinkExtractor(allow=r'/web/site0/tab5240/module14430/page\d+\.htm'),follow=True),
#详情页
Rule(LinkExtractor(allow=r'/web/site0/tab5240/info\d+\.htm'), callback='parse_detail'),
)
#处理详情页,提取部分数据
def parse_detail(self, response):
item = {}
item['title'] = re.findall('<!--TitleStart-->(.*?)<!--TitleEnd-->', response.body.decode(), re.S)
item['publish_data'] = re.findall('发布时间:(20\d{2}-\d{2}-\d{2})', response.body.decode(), re.S)[0]
item['content']=response.xpath('//span[@id="zoom"]//p/text()').extract()
item['content']=[i.strip() for i in item['content'] if len(i.strip())>0]
print(item)
我是直接修改了亚马逊图书的代码,爬虫名字没有修改。需要注意的是title是存在两个标签注释之间的,代码没有显示出来,因为它是个注释,所以你需要你自己把两头的注释添加上。
Scrapy爬虫框架在这里就结束了,后续如果有其它需要补充的内容,我会接着修改。
声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。