Захват кодов статуса http с помощью программы scrapy

Я новичок в скрапе. Я пишу паука, предназначенного для проверки длинного списка URL-адресов на наличие кодов состояния сервера и, при необходимости, на какие URL-адреса они перенаправляются. Важно, если есть цепочка редиректов, мне нужно знать код состояния и url при каждом переходе. Я использую response.meta['redirect_urls'] для захвата URL-адресов, но не знаю, как захватить коды состояния - похоже, для него нет мета-ключа ответа.

Я понимаю, что мне, возможно, потребуется написать какое-то пользовательское промежуточное ПО для предоставления этих значений, но я не совсем понимаю, как регистрировать коды состояния для каждого прыжка и как получить доступ к этим значениям из паука. Я посмотрел, но не могу найти пример того, как кто-то это делает. Если кто-нибудь может указать мне в правильном направлении, это было бы очень признательно.

Например,

    items = []
    item = RedirectItem()
    item['url'] = response.url
    item['redirected_urls'] = response.meta['redirect_urls']     
    item['status_codes'] = #????
    items.append(item)

Редактировать— Основываясь на отзывах от warawauk и активной помощи парней на IRC-канале (freenode #scrappy), мне удалось это сделать. Я считаю, что это немного хакерски, поэтому любые комментарии по улучшению приветствуются:

(1) Отключите промежуточное программное обеспечение по умолчанию в настройках и добавьте свое собственное:

DOWNLOADER_MIDDLEWARES = {
    'scrapy.contrib.downloadermiddleware.redirect.RedirectMiddleware': None,
    'myproject.middlewares.CustomRedirectMiddleware': 100,
}

(2) Создайте свой CustomRedirectMiddleware в файле middlewares.py. Он наследуется от основного класса промежуточного программного обеспечения перенаправления и захватывает перенаправление:

class CustomRedirectMiddleware(RedirectMiddleware):
    """Handle redirection of requests based on response status and meta-refresh html tag"""

    def process_response(self, request, response, spider):
        #Get the redirect status codes
        request.meta.setdefault('redirect_status', []).append(response.status)
        if 'dont_redirect' in request.meta:
            return response
        if request.method.upper() == 'HEAD':
            if response.status in [301, 302, 303, 307] and 'Location' in response.headers:
                redirected_url = urljoin(request.url, response.headers['location'])
                redirected = request.replace(url=redirected_url)

                return self._redirect(redirected, request, spider, response.status)
            else:
                return response

        if response.status in [302, 303] and 'Location' in response.headers:
            redirected_url = urljoin(request.url, response.headers['location'])
            redirected = self._redirect_request_using_get(request, redirected_url)
            return self._redirect(redirected, request, spider, response.status)

        if response.status in [301, 307] and 'Location' in response.headers:
            redirected_url = urljoin(request.url, response.headers['location'])
            redirected = request.replace(url=redirected_url)
            return self._redirect(redirected, request, spider, response.status)

        if isinstance(response, HtmlResponse):
            interval, url = get_meta_refresh(response)
            if url and interval < self.max_metarefresh_delay:
                redirected = self._redirect_request_using_get(request, url)
                return self._redirect(redirected, request, spider, 'meta refresh')


        return response

(3) Теперь вы можете получить доступ к списку перенаправлений в вашем пауке с помощью

request.meta['redirect_status']
10
задан reportingmonkey 13 June 2012 в 15:29
поделиться