So beheben Sie CAPCHA_NOT_READY beim Abfragen eines Ergebnisses

capcha_not_ready - How to Fix CAPCHA_NOT_READY When Polling for a Result

Kurze Antwort: CAPCHA_NOT_READY ist kein Fehler. Es ist die API, die Ihnen mitteilt, dass das Captcha noch gelöst wird und Sie zu früh gefragt haben. An Ihrer Anfrage gibt es nichts zu beheben. Sie brauchen nur den richtigen Polling-Rhythmus und eine Schleife, die weiß, wann sie stoppen muss. Diese Anleitung behandelt beides, plus das Read-once-Verhalten, das aus einem funktionierenden Skript ein verwirrendes macht.

Was CAPCHA_NOT_READY tatsächlich bedeutet

Wenn Sie ein Captcha senden an /in.php erhalten Sie eine ID zurück, keine Antwort. Das Lösen geschieht im Hintergrund. Anschließend pollen Sie /res.php mit dieser ID, bis die Antwort bereit ist.

Bis es so weit ist, gibt jede Abfrage denselben String zurück:

# Poll for the result. Note action=get and the id from /in.php.
curl "http://127.0.0.1:8080/res.php?key=YOUR_API_KEY&action=get&id=CAPTCHA_ID"

# Still working:
CAPCHA_NOT_READY

# Done:
OK|03AGdBq26Sxo...

Und ja, es wird geschrieben CAPCHA, nicht CAPTCHA. Dieser Tippfehler steckt seit Beginn in der 2captcha-API. CapSkip ist Drop-in-kompatibel mit dieser API, daher wird die Falschschreibung bewusst beibehalten. Würde man sie korrigieren, würde jede bestehende Client-Bibliothek, die auf die exakte Zeichenkette prüft, brechen. Übernehmen Sie sie in Ihrem Code exakt so.

Fragen Sie im richtigen Rhythmus ab

Die meisten stoßen ständig darauf, weil sie sofort nach dem Absenden abfragen. Verschiedene Captcha-Typen benötigen sehr unterschiedlich viel Zeit, daher sollte die erste Prüfung nicht bei allen zum selben Zeitpunkt erfolgen.

TypVor der ersten Prüfung wartenWiederholen Sie es dann alle
Bild / Text1 Sekunde5 Sekunden
reCAPTCHA v215 bis 20 Sekunden5 Sekunden
reCAPTCHA v310 bis 15 Sekunden5 Sekunden
GeeTestetwa 5 Sekunden5 Sekunden
Cloudflare Turnstileetwa 5 Sekunden5 Sekunden

Häufiger als alle 5 Sekunden abzufragen lässt nichts schneller lösen. Es verbrennt nur Anfragen.

Eine Polling-Schleife, die endet

Die Shell-Version, die die Struktur klar zeigt:

# Submit, capture the id, give it a head start, then poll.
ID=$(curl -s "http://127.0.0.1:8080/in.php?key=YOUR_API_KEY&method=userrecaptcha&googlekey=YOUR_SITEKEY&pageurl=https://example.com" | cut -d'|' -f2)

sleep 15
while :; do
  RES=$(curl -s "http://127.0.0.1:8080/res.php?key=YOUR_API_KEY&action=get&id=$ID")
  [ "$RES" = "CAPCHA_NOT_READY" ] || break
  sleep 5
done
echo "$RES"

Diese Schleife hat einen erwähnenswerten Fehler: Sie läuft ewig, wenn vorgelagert etwas schiefgeht. Begrenzen Sie sie in echtem Code.

# pip install requests
import time
import requests

BASE = "http://127.0.0.1:8080"

def solve_recaptcha(sitekey, page_url, api_key="YOUR_API_KEY", timeout=180):
    task = requests.get(BASE + "/in.php", params={
        "key": api_key,
        "method": "userrecaptcha",
        "googlekey": sitekey,
        "pageurl": page_url,
        "json": 1,
    }).json()
    task_id = task["request"]

    time.sleep(15)                      # reCAPTCHA needs a head start
    deadline = time.monotonic() + timeout

    while time.monotonic() < deadline:
        res = requests.get(BASE + "/res.php", params={
            "key": api_key,
            "action": "get",
            "id": task_id,
        }).text.strip()

        if res.startswith("OK|"):
            return res.split("|", 1)[1]

        # Anything that is not the pending string is terminal.
        if res != "CAPCHA_NOT_READY":
            raise RuntimeError(res or "empty response: already read, or bad id")

        time.sleep(5)

    raise TimeoutError("gave up after %ss" % timeout)

Drei Dinge machen dies sicher: eine Deadline, damit es nicht hängen bleibt, das Behandeln jedes nicht-ausstehenden Strings als endgültig, damit echte Fehler sofort sichtbar werden, und das genau einmalige Lesen der Antwort.

Oder überspringen Sie die Schleife ganz

Wenn Sie eines der offiziellen SDKs verwenden, ist nichts davon Ihr Problem. Das Polling erfolgt innerhalb des Aufrufs und Sie erhalten das Token direkt zurück, also CAPCHA_NOT_READY erreicht Ihren Code niemals.

# pip install capskip
from capskip import CapSkip

solver = CapSkip(host="127.0.0.1", port=8080)

# Submit and poll happen inside this one call.
result = solver.recaptcha(
    sitekey="YOUR_SITEKEY",
    url="https://example.com/page-with-recaptcha",
)

print(result["code"])   # token, ready to inject
// npm install capskip
const { CapSkip } = require('capskip');

const solver = new CapSkip({ host: '127.0.0.1', port: 8080 });
const result = await solver.recaptcha('YOUR_SITEKEY', 'https://example.com/page-with-recaptcha');

console.log(result.code);
// composer require capskip/capskip
use CapSkip\CapSkip;

$solver = new CapSkip(['host' => '127.0.0.1', 'port' => 8080]);
$result = $solver->recaptcha('YOUR_SITEKEY', 'https://example.com/page-with-recaptcha');

echo $result['code'];
// dotnet add package CapSkip
using CapSkip;

var solver = new CapSkipClient(host: "127.0.0.1", port: 8080);
var result = await solver.RecaptchaAsync("YOUR_SITEKEY", "https://example.com/page-with-recaptcha");

Console.WriteLine(result.Code);

Vollständige Methodensignaturen für alle vier Sprachen finden Sie auf der SDK zum Captcha-Lösen -Seite. Die rohe Schleife oben ist weiterhin das, was Sie für Go, Java, Ruby oder alles ohne offizielles Paket benötigen.

Die Read-once-Falle

Das ist derjenige, der einen Nachmittag verschwendet. Jedes Ergebnis kann nur einmal gelesen werden. Fragen Sie nach einem erfolgreichen Lesen erneut ab, erhalten Sie eine leere Antwort, nicht den Token, den Sie bereits hatten.

Ein leerer Body bedeutet also nicht “wird noch bearbeitet”. Er bedeutet eines von zwei Dingen:

  • Sie haben dieses Ergebnis bereits abgerufen und verworfen
  • Die ID existiert nicht, meist eine verstümmelte oder abgeschnittene ID aus dem Parsen OK|ID

Speichern Sie den Token in dem Moment, in dem Sie ihn erhalten. Fragen Sie ihn nicht erneut ab, um ihn zu “bestätigen”.

Wenn es wirklich ein Problem ist

Wenn CAPCHA_NOT_READY niemals aufgelöst wird, ist die pending-Zeichenkette ein Symptom und nicht die Ursache. Prüfen Sie diese der Reihe nach:

AntwortWas es bedeutetBeheben
ERROR_CAPTCHA_UNSOLVABLEDas Lösen wurde versucht und schlug fehlPrüfen Sie, ob sitekey und pageurl die aktuellen sind, und übermitteln Sie dann erneut
ERROR_WRONG_ID_FORMATDie ID ist keine gültige GanzzahlSie parsen OK|ID falsch. Am Pipe-Zeichen splitten, Feld 2 nehmen
ERROR_GOOGLEKEYDer Sitekey wurde zum Zeitpunkt der Übermittlung abgelehntLesen Sie es erneut von der Live-Seite, nicht aus dem zwischengespeicherten Quellcode
Leerer TextBereits gelesen oder unbekannte IDSpeichern Sie das Ergebnis beim ersten Lesen
Länger als 3 Minuten ausstehendDer Löser läuft nicht oder ist nicht erreichbarBestätigen Sie, dass der Dienst am konfigurierten Port läuft. Siehe das Einrichtungsanleitung

Die vollständige Liste der Fehler-Strings finden Sie in der API-Dokumentation.

Häufig gestellte Fragen

Ist CAPCHA_NOT_READY ein Fehler, den ich loggen sollte?

Nicht als Fehler. Es ist der normale Zustand „in Bearbeitung“, und Sie werden ihn mehrmals pro Lösung sehen. Loggen Sie ihn, wenn überhaupt, auf Debug-Level, sonst begraben Sie echte Fehler unter Rauschen.

Liefert schnelleres Polling die Antwort früher?

Nein. Die Lösezeit ist unabhängig davon, wie oft Sie anfragen. Alle 5 Sekunden ist das dokumentierte Intervall, und alles Schnellere sind verschwendete Anfragen.

Warum wird es CAPCHA und nicht CAPTCHA geschrieben?

Es ist ein alter Tippfehler in der ursprünglichen 2captcha-API, der Teil des Vertrags wurde. CapSkip ist drop-in-kompatibel mit dieser API, sodass der String exakt erhalten bleibt. Die Schreibweise zu korrigieren würde jeden Client zerstören, der darauf prüft.

Kann ich den pending-Status als JSON erhalten?

Ja. Fügen Sie hinzu json=1 zur Anfrage, und die Antworten kommen als Objekt zurück mit status und request Felder statt Klartext. Die pending-Zeichenkette selbst bleibt unverändert.

Zusammenfassung

Geben Sie der Lösung einen Vorsprung vor Ihrer ersten Prüfung, wiederholen Sie alle 5 Sekunden, und behandeln Sie alles außer CAPCHA_NOT_READY als endgültig, begrenzen Sie die Schleife mit einer Frist und lesen Sie das Ergebnis genau einmal. Das ist das gesamte Muster.

Wenn Sie die Schleife lieber gar nicht schreiben möchten, ist CapSkip ein Captcha-Löser der lokal läuft und SDKs für Python, Node.js, PHP und .NET liefert, die das Polling für Sie übernehmen.