如何重新安排在scrapy中稍后要抓取​​的403 HTTP状态代码?

时间:2015-12-07 07:33:57

标签: python web-scraping scrapy

根据these说明,我可以看到HTTP 500错误,连接丢失错误等总是被重新安排,但如果重新安排403错误或者只是将它们视为一个错误,我就无法找到任何地方有效响应或在达到重试限制后被忽略。

同样来自同一条指令:

  

在抓取过程中收集失败的页面并重新安排在   最后,一旦蜘蛛完成所有常规爬行(非   失败的)页面。一旦没有更多失败的页面重试,这个   中间件发送一个信号(retry_complete),所以其他扩展可以   连接到那个信号。

这些Failed Pages指的是什么?它们包含403错误吗?

此外,当scrapy遇到HTTP 400状态时,我可以看到引发此异常:

2015-12-07 12:33:42 [scrapy] DEBUG: Ignoring response <400 http://example.com/q?x=12>: HTTP status code is not handled or not allowed

从这个例外情况来看,我认为很明显,HTTP 400响应会被忽略而不会被重新安排。

我不确定403 HTTP状态是否被忽略或重新安排在最后被抓取。 所以我尝试根据these文档重新安排所有具有HTTP状态403的响应。这是我到目前为止所尝试的内容:

在middlewares.py文件中:

def process_response(self, request, response, spider):
    if response.status == 403:
        return request
    else:
        return response

在settings.py中:

RETRY_TIMES = 5
RETRY_HTTP_CODES = [500, 502, 503, 504, 400, 403, 404, 408]

我的问题是:

  1. 这些Failed Pages指的是什么?它们包含403错误吗?
  2. 我是否需要编写process_response来重新安排403错误页面,还是通过scrapy自动重新安排?
  3. scrapy重新安排了什么类型的例外和(HTTP代码)?
  4. 如果我重新安排404错误页面,我是否会进入无限循环或是否有超时,之后不会再进行重新安排?

2 个答案:

答案 0 :(得分:9)

  1. 您可以找到重试here的默认状态。

  2. RETRY_HTTP_CODES文件中向settings.py添加403应处理该请求并重试。

  3. RETRY_HTTP_CODES中的内容已经检查了默认值。

  4. RETRY_TIMES会处理尝试错误页面的次数,默认设置为2,您可以在settings.py文件上覆盖它。

答案 1 :(得分:0)

一种方法是将中间件添加到您的Spider(sourcelinked):

# File: middlewares.py

from twisted.internet import reactor
from twisted.internet.defer import Deferred

DEFAULT_DELAY = 5

class DelayedRequestsMiddleware(object):
    def process_request(self, request, spider):
        delay_s = request.meta.get('delay_request_by', None)
        if not delay_s and response.status != 403:
            return
        delay_s = delay_s or DEFAULT_DELAY

        deferred = Deferred()
        reactor.callLater(delay_s, deferred.callback, None)
        return deferred

在示例中,您可以使用meta键调用延迟:

# This request will have itself delayed by 5 seconds
yield scrapy.Request(url='http://quotes.toscrape.com/page/1/', 
                     meta={'delay_request_by': 5})