python爬虫时用redis去重的多种方式(增量爬虫用到)

什么是增量爬虫

爬虫过程中,常常要对目标网站的新数据进行抓取,遇到已经爬过的网页需要进行过滤。本文介绍用redis数据库的高效去重。

逻辑是:

方法一:把所有爬过的url都放在redis中,以后每次爬取链接之前,先把url添加进去,如果能添加进去,说明是没爬过的,如果添加不进去,说明该链接有爬取过。

方法二:有时可以把请求的response进行哈希,然后保存,其他的逻辑同方法一。

普通爬取时,核心的代码逻辑是:

import hashlib
import redis


def get_md5(val):
    """把目标数据进行哈希,用哈希值去重更快"""
    md5 = hashlib.md5()
    md5.update(val.encode('utf-8'))
    return md5.hexdigest()


def add_url(url):
    red = redis.Redis(host='106.1xxx', password='redixxxx', port=6379, db=0)
    res = red.sadd('TEST:urlset', get_md5(url)) # 注意是 保存set的方式
    if res == 0:  # 若返回0,说明插入不成功,表示有重复
        return False
    else:
        return True


if __name__ == '__main__':
    print(add_url('https://www.taobao.com'))

scrapy中,去重的核心代码是:(这里也是先对url进行判断,没爬过的才爬取)

主脚本的代码示例:

import scrapy
from scrapy.linkextractors import LinkExtractor
from scrapy.spiders import CrawlSpider, Rule
from redis import Redis
from TestProgram.items import TestProgramItem
class TestSpider(CrawlSpider):
    name = 'ttt'
    # allowed_domains = ['www.xxx.com']
    start_urls = ['https://www.xxx.html']

    rules = (
        Rule(LinkExtractor(allow=r'/index.php/\d+\.html'), callback='parse_item', follow=True),
    )

    def parse_item(self, response):
        conn = Redis(host='127.0.0.1',port=6379)
        detail_url_list= response.xpath('//li[@class="c/@href').extract()
        for url in detail_url_list:
            ex = conn.sadd('test_url',url)
            #等于1 的时候 说明数据还没有存储到redis中  等于0 的时候 说明redis中已经存在该数据
            if ex == 1:
                yield scrapy.Request(url=url,callback=self.parse_detail)
            else:
                print("无数据更新")
    def parse_detail(self,response):
        item = TestProgramItem()
        item['name']=response.xpath('/html/bo/text()').extract_first()
        item['age']=response.xpath('/html/bo/text()').extract_first()
        yield item

pipeline中的脚本示例:(因为在主脚本中已经过滤了,这里就不用其他的操作,正常操作即可)

from redis import Redis
class TestProramPipeline(object):
    conn = None
    def open_spider(self,spider):
        self.conn = Redis(host='127.0.0.1',port=6379)

    def process_item(self, item, spider):
        self.conn.lpush('movie_data',item)
        return item

 

  • 2
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值