Scarnox · Blog

Een PopularCaptcha oplossen in Python (werkend voorbeeld, 2026)

Als je Python-script op een PopularCaptcha is gestuit, heb je geen browserfarm of eigen model nodig. Je hebt de sitekey van de pagina, één POST-verzoek en het token dat terugkomt.

Deze gids brengt je in ongeveer vijf minuten van nul naar een werkend token: haal een API-sleutel op, vind de sitekey, vraag het token aan, dien het in bij het formulier, en behandel de foutgevallen die opduiken wanneer een script zonder toezicht draait. Mislukte solves zijn gratis, dus een retry kost je alleen tijd.

Scarnox lost PopularCaptcha vandaag op, proxyless of met je eigen proxy. Andere captchatypen zoals reCAPTCHA, Cloudflare Turnstile en AWS WAF komen binnenkort, dus elk voorbeeld hier gebruikt PopularCaptcha. Het overzicht van captchatypen legt uit hoe de andere verschillen.

1. Haal een API-sleutel op

Maak een account aan en begin met gratis proefkrediet, zonder creditcard. Je API-sleutel staat op het dashboard. Houd hem uit je broncode en lees hem uit een omgevingsvariabele:

export SCARNOX_KEY="scarnox_YOURAPIKEY"

2. Vind de sitekey

Open de pagina met de captcha, open DevTools, en zoek in het Elements-paneel naar data-sitekey. PopularCaptcha-sitekeys zijn UUID's:

<div class="h-captcha" data-sitekey="10000000-ffff-ffff-ffff-000000000001"></div>

Geen data-sitekey in de HTML? De widget is waarschijnlijk door JavaScript gerenderd. Kijk in het Network-tabblad naar het configuratieverzoek van de widget; de queryparameter sitekey daarvan is wat je nodig hebt. Andere manieren om hem te vinden behandelen de iframe-URL en onzichtbare widgets.

Stuur de URL van de pagina die de widget toont als site_url. De host is het belangrijkst, maar de volledige paginaurl is de veilige keuze.

3. Vraag een token aan

import os
import requests

API_URL = "https://api.scarnox.com/api/tasks/create"
API_KEY = os.environ["SCARNOX_KEY"]

def solve_captcha(sitekey: str, page_url: str) -> str:
    r = requests.post(
        API_URL,
        headers={"Authorization": f"Bearer {API_KEY}"},
        json={
            "captcha_type": "PopularCaptchaTaskProxyless",
            "site_key": sitekey,
            "site_url": page_url,
        },
        timeout=185,  # de aanroep blokkeert tot het token klaar is
    )
    data = r.json()
    if data.get("errorId") != 0:
        raise RuntimeError(f"{data.get('errorCode')}: {data.get('errorDescription')}")
    return data["solution"]["token"]

if __name__ == "__main__":
    token = solve_captcha("10000000-ffff-ffff-ffff-000000000001", "https://example.com/signup")
    print(token[:40], "...")

Dat is de hele integratie. Er is geen pollinglus en geen tweede "resultaat ophalen"-aanroep. Het verzoek keert terug wanneer het token klaar is, dus de ene instelling die telt is een timeout die lang genoeg is voor een trage solve. Gebruik ongeveer 185 seconden.

Een geslaagd antwoord heeft errorId op 0, met het token onder solution.token. Elke andere errorId betekent dat de solve mislukt is, en het antwoord bevat een errorCode en een errorDescription die vertellen waarom.

4. Dien het token in

Het token gaat waar de site het captchaantwoord verwacht. Voor PopularCaptcha is dat bijna altijd een formulierveld genaamd h-captcha-response. Veel sites accepteren ook g-recaptcha-response, dus stuur beide:

import requests

def sign_up(session: requests.Session, form_url: str, email: str, sitekey: str) -> requests.Response:
    token = solve_captcha(sitekey, form_url)
    return session.post(form_url, data={
        "email": email,
        "h-captcha-response": token,
        "g-recaptcha-response": token,
    }, timeout=30)

Twee details zijn hier belangrijk. Echte sites controleren meestal ook de sessiecookies van het laden van de pagina, dus laad het formulier met dezelfde requests.Session voordat je post. En post naar de action-URL van het formulier, die niet altijd de paginaurl is.

Los vlak voor het verzenden op. Het token verloopt binnen ongeveer twee minuten, dus haal het niet aan het begin van een lange taak op en houd het niet vast. Als de site het token weigert, open dan het formulier in DevTools en controleer de namen van de verborgen velden.

5. Fouten afhandelen

Mislukte solves zijn gratis, dus een retry kost alleen tijd. Sommige fouten lukken bij een retry toch nooit, dus herhaal niet blindelings. Controleer elke keer errorId, log errorCode en errorDescription, en probeer alleen de tijdelijke fouten opnieuw.

Netwerkfouten vragen om eigen afhandeling, omdat requests een fout gooit voordat er een antwoord bestaat:

import requests

try:
    token = solve_captcha(sitekey, page_url)
except requests.RequestException as exc:
    print("netwerkprobleem, later opnieuw proberen:", exc)
except RuntimeError as exc:
    print("solve geweigerd:", exc)

De gids over foutafhandeling bevat een volledig retrybeleid met backoff en jitter.

Veelgemaakte fouten

Probeer het gratis

Maak een account aan en begin met gratis proefkrediet, zonder creditcard. Draai het voorbeeld hierboven tegen een formulier dat van jou is voordat je het in een grotere taak verwerkt. Voor wat oplossen op volume kost, zie actuele prijzen.

Elke solve loggen

Log per solve één regel: de sitekey, de host van de pagina, de errorId, de errorCode bij een fout, en hoe lang de aanroep duurde. Laat de API-sleutel en eventuele proxywachtwoorden weg. Die regels vertellen je of een trage run traag is door de pagina, de proxy of de solver. Ze zijn ook het eerste wat je nodig hebt als je een supportverzoek opent.

Oplossen in een lus

Als je script veel captchas na elkaar oplost, houd de lus eenvoudig. Los op, verstuur, controleer het resultaat, en ga pas daarna verder. Los niet vooraf op en zet tokens niet in de wachtrij, want elk verloopt binnen ongeveer twee minuten. Een korte pauze tussen solves op dezelfde site houdt je aanvraagfrequentie dicht bij wat een mens zou produceren.

Volgende stappen