我正在构建一个scrapy项目,其中我有多个蜘蛛(每个域都有一个蜘蛛).现在,要删除的URL来自用户给定的查询.所以基本上我不需要做广泛的抓取甚至跟踪链接.将会有一个接一个的网址,我只需要使用选择器提取.所以我在想是否可以将URL传递给scrapy蜘蛛可以消耗的消息队列,我会没事的.但我无法弄明白.我检查过
https://github.com/darkrho/scrapy-redis
但我觉得它不适合我的目的,因为我需要多个队列(每个蜘蛛一个队列).正如我开始学习的那样,一种方法似乎是覆盖蜘蛛中的start_requests方法.但在这里,我不知道该怎么做(python和scrapy的新手).我可以将它视为任何普通的python脚本,并将方法用于使用(任意)消息队列吗?此外,我需要24*7运行的蜘蛛,并在队列上有请求时刮擦.我想我应该使用信号并在某处提升DontCloseSpider异常.但是我在哪里这样做?我很丢失.请帮忙.
这是我正在看的场景:
用户 - >查询 - >来自abc.com的网址 - > abc-spider
-> url from xyz.com -> xyz-spider -> url from ghi.com -> ghi-spider
现在每个网址都有相同的东西要为每个网站抓取.所以我有选择器在每个蜘蛛中这样做.我需要的是,这只是一个用户场景.当有多人用户时,会有多个不相关的网址进入同一个蜘蛛.所以它会是这样的:
query1,query2,query3
abc.com - > url_abc1,url_abc2,url_abc3
xyz.com - > url_xyz1,url_xyz2,url_xyz3
ghi.com - > url_ghi1,url_ghi2,url_ghi3
因此,对于每个网站,这些网址将动态发送,并将其推送到各自的消息队列中.现在,对于网站而言,每个蜘蛛都必须使用各自的队列,并在消息队列上有请求时向我提供已删除的项目
这是一种非常常见且(IMO)将scrapy构建为数据管道的优秀方法; 我一直这样做.
你想要覆盖蜘蛛的start_requests()
方法是正确的.如果您定义了start_requests()以及start_urls变量,我不知道scrapy的行为如何,但如果您使用动态源(如数据库),我建议您使用start_requests().
一些示例代码,未经测试但应该给您正确的想法..如果您需要更多信息,请告诉我.它还假设您的队列由另一个进程填充.
class ProfileSpider( scrapy.Spider ): name = 'myspider' def start_requests( self ): while( True ): yield self.make_requests_from_url( self._pop_queue() ) def _pop_queue( self ): while( True ): yield self.queue.read()
这会将您的队列公开为生成器.如果要最小化空循环量(因为队列在很多时候可能是空的),您可以在_pop_queue循环中添加睡眠命令或指数退避.(如果队列为空,请休眠几秒钟并尝试再次弹出.)
假设您的代码中没有发生致命错误,我认为这不应该因为循环/生成器的构造而终止.