تغییر response.request.meta یک شیء Python را تغییر می‌دهد. برای انجام دانلود دیگر باید به Scrapy یک Request دیگر برای زمان‌بندی بدهید.

برای GETی که callback شما صریحاً تصمیم به تلاش دوباره می‌گیرد، کمک‌کنندهٔ عمومی تلاش دوبارهٔ Scrapy می‌تواند حساب تلاش دوباره را همراه درخواست تازه نگه دارد:

from scrapy.downloadermiddlewares.retry import get_retry_request

def retry_through(self, response, proxy_url):
    retry = get_retry_request(
        response.request,
        spider=self,
        reason='choose_another_proxy',
    )
    if retry is None:
        return None
    retry.meta['proxy'] = proxy_url
    retry.headers.pop('Proxy-Authorization', None)
    return retry

این یک کمک‌کنندهٔ spider است. فراخوان باید Request حاصل را وقتی موجود است برگرداند یا yield کند. None یعنی کمک‌کننده تلاش دوبارهٔ دیگری را در محدودهٔ مجاز رد کرده است.

کمک‌کنندهٔ تلاش دوباره درخواست را کپی می‌کند، شمارندهٔ تلاش دوبارهٔ آن را به‌روز می‌کند و رفتار زمان‌بند مناسب برای تلاش دوباره را فراهم می‌کند. yield کردن همان URL به‌عنوان یک درخواست تازهٔ عادی ممکن است در عوض به فیلتر تکرار برخورد کند.

از نشانی پروکسی که HttpProxyMiddleware فعال پشتیبانی می‌کند استفاده کنید. برای تلاش دوبارهٔ درخواست‌های GET عمومی مجاز، یک نامزد HTTP بدون احراز هویت از فهرست پروکسی HTTP می‌تواند proxy_url را فراهم کند. پاک کردن فیلد proxy-authorization که قبلاً پیوست شده از انتقال سرآیند یک واسطهٔ قدیمی به این انتخاب جلوگیری می‌کند؛ بگذارید میان‌افزار در صورت لزوم حساب تازه را از نشانی پروکسی جدید استخراج کند.

این انتخاب در سطح callback را از مدیریت خودکار شکست‌های پیکربندی‌شده توسط RetryMiddleware جدا نگه دارید. تصمیم بگیرید کدام لایه مالک تلاش دوباره است تا عملیات دو بودجهٔ مستقل مصرف نکند. نمونه دربارهٔ کار GET قابل تکرار است، نه وعده‌ای که تکرار یک تراکنش ارسال‌شدهٔ دلخواه ایمن باشد.

مقالات مرتبط