gpt4 book ai didi

python - 即使有未处理的异常,有没有办法强制 Scrapy 进入 parse 方法?

转载 作者:太空宇宙 更新时间:2023-11-04 01:28:21 24 4
gpt4 key购买 nike

我有一个使用 Scrapy 的相当复杂的多进程程序。它在大约 95% 的时间里工作得很好,但偶尔我会在 Twisted 访问导致 DNSLookupError/TCPTimedOutError 的错误站点时收到未处理的异常。

这不是问题,但不幸的是,这些错误导致 Scrapy 跳过 BaseSpider 解析方法,我在其中设置了一个队列来处理响应。由于它跳过了队列,我无法确定跳过了哪些 URL。

有没有办法始终确保每个 Scrapy 请求都以该解析方法结束?我所需要的只是一种访问那些失败的响应对象并将它们放入队列的方法。

这是我的爬虫代码的一个例子:

class SeerSpider(BaseSpider):
"""Scrapy-based html retrieval system."""

name = "SeerSpider"

def __init__(self, spider_queue, url_list):
self.queue = spider_queue
self.allowed_domains = []
self.start_urls = []
for url in url_list:
self.allowed_domains.append(str(urlparse(url).netloc))
self.start_urls.append(url)
super(SeerSpider, self).__init__()

def parse(self, response):
"""Extracts information from each website in start_urls."""
self.queue.put(response)

如您所见,它非常基础。

稍后,队列是这样处理的:

while True:
response = spider_queue.get()
### DO STUFF HERE ###
results_queue.put(result)

然后……

while True:
try:
result = results_queue.get(True, 60)
except:
print 'HALP', sys.exc_info()
result = ['ERROR']
self.results.append(result)
counter -= 1
if counter <= 0 or self.exit == True:
for process in process_list:
process.terminate()
break

我在队列超时中添加了一个临时解决方案,这样它就不会在等待队列中不存在的项目时无限期挂起。如果我能保证某种响应对象将进入 start_urls 列表中每个 URL 的队列,它会解决我所有的问题。

谢谢

最佳答案

我想通了,中间件是对的,但是是下载器中间件而不是scrapy中间件。在我使用 process_exception 方法实现了一个下载器中间件之后,我设法让它工作了。

代码在这里:

class SpiderFailSignal(object):

def process_exception(self, request, exception, spider):
response = Response(request.url, status=666, body='error')
spider.queue.put(response)
return response

然后我添加了

settings.overrides['DOWNLOADER_MIDDLEWARES'] = {'seerspider.SpiderFailSignal': 901}

它奏效了。

尽管如此,一旦 scrapy spider_idle 信号被触发,我也最终向队列添加了一个虚拟值,然后创建了一个 if 语句以在遇到该项目时退出队列。所以这两个解决方案一起 = 全部修复。

关于python - 即使有未处理的异常,有没有办法强制 Scrapy 进入 parse 方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15933231/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com