Scarnox · Blog

Scrapen zonder geblokkeerd te worden: een praktische gids met code

Geblokkeerd worden tijdens scraping betekent meestal een van drie dingen: je stuurde te veel requests te snel, je client zag er helemaal niet uit als een browser of als een bekende bot, of je IP-adres staat op een lijst die de site minder vertrouwt. Je kunt alle drie verkleinen met een paar gewoonten: merk de blokkade vroeg op, vertraag wanneer de site terugduwt, houd een consistente en eerlijke identiteit aan, en gebruik proxies alleen waar dat past. Deze gids behandelt elk daarvan met werkende code. Gebruik hem voor sites die je mag scrapen.

Herken een blokkade

Een blokkade ziet er niet altijd uit als een foutpagina. Let op:

Log bij elke fout de statuscode en een korte steekproef van de body. Een blokkade die je niet in je logs ziet, kun je ook niet oplossen.

Trek je terug met retries

Wanneer de site zegt "vertraag", moet je code meer dan een beetje vertragen. Exponentiële backoff, met een limiet op het aantal pogingen, is de standaardaanpak. Het respecteert ook Retry-After wanneer de site die stuurt:

import time
import requests

session = requests.Session()
session.headers.update({
    "User-Agent": "ExampleBot/1.0 (+https://example.com/bot)",
    "Accept-Language": "en-US,en;q=0.9",
})

def polite_get(url: str, max_attempts: int = 4) -> requests.Response:
    delay = 2.0
    resp = None
    for _ in range(max_attempts):
        resp = session.get(url, timeout=30)
        if resp.status_code not in (429, 503):
            return resp
        retry_after = resp.headers.get("Retry-After", "")
        wait = float(retry_after) if retry_after.isdigit() else delay
        time.sleep(wait)
        delay *= 2
    return resp  # nog steeds geblokkeerd: geef het laatste antwoord terug aan de aanroeper

resp = polite_get("https://example.com/products?page=1")
print(resp.status_code, len(resp.text))

Let op wat de functie niet doet. Ze probeert een 403 niet opnieuw, en ze wisselt niet door identiteiten om langs één blokkade te komen. Een 403 is een beslissing om te stoppen, geen puzzel om op te lossen.

Diagnosticeer een blokkade stap voor stap

Wanneer een run begint te falen, werk je deze controles af voordat je iets anders verandert:

  1. Bekijk de eerste mislukte URL en zijn statuscode. Een blokkade begint meestal op een specifiek punt, niet willekeurig.
  2. Vergelijk de aanvraagfrequentie in de minuten vóór de eerste fout. Een uitbarsting is de meest voorkomende oorzaak.
  3. Controleer of de fout aan één pad, één sectie of één tijdstip van de dag is gekoppeld.
  4. Haal dezelfde URL één keer met de hand op in een gewone browser. Laadt de browser hem, dan zit het verschil in je requestpatroon. Is de browser ook geblokkeerd, dan levert de site de pagina voorlopig niet aan jou.
  5. Pas pas daarna de code aan. Vertraag eerst, voeg backoff als tweede toe, en bekijk je identiteit als laatste.

Als je meerdere dingen tegelijk verandert, weet je niet meer welke iets heeft geholpen.

Houd een consistente, eerlijke identiteit

Scrapers worden geblokkeerd wanneer hun identiteit tussen requests verandert, of wanneer die niet overeenkomt met de rest van het verkeer. Eén sessie met één duidelijke User-Agent is de eenvoudigste stabiele identiteit. Noem je bot, voeg een contactlink toe en stuur alleen de headers die een gewone client zou sturen. User-Agents wijzigen om eruit te zien als veel verschillende bezoekers is een vorm van ontwijking, en dat maakt een blokkade eerder waarschijnlijker dan minder waarschijnlijk.

Als een site verschillende inhoud toont aan browsers en aan gewone HTTP-clients, gebruik dan voor die pagina's een echte browser en houd dezelfde snelheidslimiet aan. Dat is een legitieme route, en het houdt het requestpatroon redelijk.

Gebruik proxies met zorg

Een proxy verandert het adres waarvan een request komt. Het is een hulpmiddel voor legitieme behoeften, zoals testen vanuit een specifieke regio op een site die je mag testen, of het spreiden van belasting over je eigen infrastructuur. Het is geen manier om een limiet te ontlopen die de site voor jou heeft gesteld. Het formaat van een proxy is het formaat dat de proxy-tasktypes gebruiken:

proxies = {
    "http": "http://user:pass@proxy.example.net:8000",
    "https": "http://user:pass@proxy.example.net:8000",
}
resp = session.get("https://example.com/products", proxies=proxies, timeout=30)

Het kiezen van een proxytype is een aparte vraag, behandeld in residentiële versus datacenter-proxies en roterende proxies voor scraping.

Wanneer de blokkade een captcha wordt

Sommige sites beantwoorden een snelheidsprobleem met een captcha in plaats van een harde blokkade. De verstandige volgorde is: stop, vertraag, controleer de regels opnieuw, en overweeg pas daarna een solve. Voor PopularCaptcha-widgets geeft de live API van Scarnox een token terug dat je in het veld h-captcha-response indient. Voor andere captchatypen controleer je de live lijst, want ondersteuning voor reCAPTCHA, Cloudflare Turnstile, GeeTest, AWS WAF en Arkose komt binnenkort beschikbaar. De uitgebreide gids is webscraping en captchas.

Als je blokkades op een site begint te zien, is de oorzaak bijna altijd het requestpatroon. Captchas vermijden bij scraping behandelt de gewoonten die dat voorkomen.

Scrape verantwoord

Volgende stappen