scrapy redis爬蟲queue,去重,排程

2021-10-08 02:07:28 字數 2734 閱讀 9014

原始碼:git clone

一、爬蟲佇列: fifoqueue  lifoqueue  priorityqueue

class base(object):

"""per-spider base queue class"""

def __init__(self, server, spider, key, serializer=none):

if serializer is none:

serializer = picklecompat

if not hasattr(serializer, 'loads'):

raise typeerror("serializer does not implement 'loads' function: % r"

% serializer)

if not hasattr(serializer, 'dumps'):

raise typeerror("serializer '% s' does not implement 'dumps' function: % r"

% serializer)

self.server = server

self.spider = spider

self.key = key %

self.serializer = serializer

def _encode_request(self, request):

obj = request_to_dict(request, self.spider)

return self.serializer.dumps(obj)

def _decode_request(self, encoded_request):

obj = self.serializer.loads(encoded_request)

return request_from_dict(obj, self.spider)

def __len__(self):

"""return the length of the queue"""

raise notimplementederror

def push(self, request):

"""push a request"""

raise notimplementederror

def pop(self, timeout=0):

"""pop a request"""

raise notimplementederror

def clear(self):

"""clear queue/stack"""

self.server.delete(self.key)

_encode_request() 和 _decode_request() 方法 對request物件進行序列化和反序列化

實現三種佇列方法:定義子類繼承父類base 並重寫_len() _pop() _push 

二、去重過濾

原始碼檔案是 dupefilter.py

步驟: 利用redis集合  指紋    server 物件的 sadd() 。獲取指紋之後就直接向集合新增指紋,如果新增成功,說明這個指紋原本不存在於集合中,返回值 1。**中最後的返回結果是判定新增結果是否為 0,如果剛才的返回值為 1,那這個判定結果就是 false,也就是不重複,否則判定為重複。

三、排程器

原始檔名稱是 scheduler.py

scrapy-redis 還幫我們實現了配合 queue、dupefilter 使用的排程器 scheduler,原始檔名稱是 scheduler.py。我們可以指定一些配置,如 scheduler_flush_on_start 即是否在爬取開始的時候清空爬取佇列,scheduler_persist 即是否在爬取結束後保持爬取佇列不清除。我們可以在 settings.py 裡自由配置,而此排程器很好地實現了對接

def enqueue_request(self, request):

if not request.dont_filter and self.df.request_seen(request):

self.df.log(request, self.spider)

return false

if self.stats:

self.stats.inc_value('scheduler/enqueued/redis', spider=self.spider)

self.queue.push(request)

return true

def next_request(self):

block_pop_timeout = self.idle_before_close

request = self.queue.pop(block_pop_timeout)

if request and self.stats:

self.stats.inc_value('scheduler/dequeued/redis', spider=self.spider)

return request

enqueue_request() 可以向佇列中新增 request,核心操作就是呼叫 queue 的 push() 操作,還有一些統計和日誌操作。next_request() 就是從佇列中取 request,核心操作就是呼叫 queue 的 pop() 操作,此時如果佇列中還有 request,則 request 會直接取出來,爬取繼續,否則如果隊列為空,爬取則會重新開始

爬蟲基礎 Scrapy Redis分布式爬蟲元件

scrapy是乙個框架,他本身是不支援分布式的。如果我們想要做分布式的爬蟲,就需要借助乙個元件叫做scrapy redis,這個元件正是利用了redis可以分布式的功能,整合到scrapy框架中,使得爬蟲可以進行分布式。可以充分的利用資源 多個ip 更多頻寬 同步爬取 來提高爬蟲的爬行效率。可以充分...

scrapy redis分布式爬蟲

依賴環境 scrapy 1.1 redis 2.8 分布式爬蟲 將乙個專案拷貝到多台電腦上,同時爬取資料。1.必須保證所有電腦上的 是相同的配置。2.在其中一台電腦上啟動redis和mysql的資料庫服務。3.同時將所有的爬蟲專案執行起來。4.在啟動redis和mysql資料庫的電腦上,向redis...

94 爬蟲 scrapy redis實戰(五)

有緣網的資料爬回來了,但是放在redis裡沒有處理。之前我們配置檔案裡面沒有定製自己的item pipelines,而是使用了redispipeline,所以現在這些資料都被儲存在redis的youyuan items鍵中,所以我們需要另外做處理。在scrapy youyuan目錄下可以看到乙個pr...