API Tutorials

GeeTest Slide CAPTCHA Parametreleri ve API Kılavuzu

GeeTest v3 slide entegrasyonlarının çoğu tek bir nedenle başarısız olur: challenge değeri gönderilmeden önce süresi dolar. Bu doğrulama iki parçadan oluşur — oturumdan oturuma değişmeyen gt hesap kimliği ve her oturumda yeniden üretilip saniyeler içinde bayatlayan challenge. Aşağıda bu iki değeri sayfadan nasıl çıkaracağınızı, in.php uç noktasına method=geetest ile nasıl göndereceğinizi ve dönen validate ile seccode alanlarını hedef sitenin doğrulama uç noktasına nasıl ileteceğinizi çalışan Python örnekleriyle görürsünüz.


GeeTest v3 nasıl çalışır?

GeeTest v3, kullanıcıdan bir yapboz parçasını kaydırıp boşluğa oturtmasını isteyen bir slide (kaydırma) doğrulamasıdır. Sunucu tarafında akış tek bir kaydırma hareketinden ibaret değildir; iki değerle çalışır:

  • gt — sitenin sabit GeeTest hesap kimliği. Her istekte aynı kalır, bir kez okuyup önbelleğe alabilirsiniz.
  • challenge — her oturumda yeniden üretilen, saniyeler içinde bayatlayan tek kullanımlık dize. Her çözüm için taze alınmalıdır.

Doğru çözüm, bu iki değerin birlikte, doğru sırada ve zamanında gönderilmesine bağlıdır. CaptchaAI, GeeTest v3'ü resmî olarak destekler ve çözümü genellikle 10–20 saniye içinde tamamlar. Ücretlendirme thread bazlıdır; GeeTest başına ek ücret yoktur. Düşük hacimli entegrasyon testleri için BASIC ($15/ay, 5 thread) yeterlidir, eşzamanlı çözüm ihtiyacınız arttıkça thread sayısını yükseltirsiniz.

Türkiye'de GeeTest v3'e en çok e-ticaret ve etkinlik/bilet platformlarının QA test akışlarında ve yetkili veri toplama süreçlerinde rastlanır. Kazıdığınız veride kişisel veri varsa bunun KVKK kapsamına girdiğini unutmayın; CaptchaAI'yi yalnızca yetkiniz olan test ve veri toplama iş akışlarında kullanın.


Üç adımda GeeTest v3 akışı

Entegrasyonun mantığı, hangi dilde çalışırsanız çalışın aynı üç adıma dayanır. Aşağıdaki Python örnekleri bu sırayı izler:

  1. Çıkar — hedef sayfadan gt ve taze challenge değerlerini okuyun.
  2. Çöz — bu değerleri in.php uç noktasına gönderin ve res.php'yi sorgulayarak challenge, validate, seccode üçlüsünü alın.
  3. Gönder — üç değeri hedef sitenin doğrulama uç noktasına iletin.

Adımlar arasındaki gecikmeyi olabildiğince kısa tutun: birinci adımla ikinci adım arasında saniyeler geçerse challenge bayatlar ve çözüm reddedilir.


GeeTest v3 parametreleri

Gönderime giren alanlar şunlardır — ilk üçü zorunlu, api_server yalnızca özel uç nokta kullanan sitelerde gerekir:

Parametre Gerekli Açıklama
gt Evet GeeTest hesap kimliği (32 karakterlik onaltılık). Sayfa kaynağında veya API yanıtında bulunur
challenge Evet Oturuma özel challenge dizesi. Her çözüm için taze olmalı
pageurl Evet CAPTCHA'yı gösteren sayfanın tam URL'si
api_server Hayır Özel GeeTest API sunucusu alt alanı

Parametreleri sayfadan çıkarma

Aşağıdaki fonksiyon önce HTML kaynağından gt değerini yakalamayı, ardından register-slide uç noktasından challenge değerini okumayı dener. İkisinden biri gömülü değilse ağ isteklerine düşer:

# extract_geetest_params.py
import requests
import re
import json


def extract_geetest_v3(page_url, session=None):
    """Extract GeeTest v3 gt and challenge from a page."""
    if session is None:
        session = requests.Session()
        session.headers["User-Agent"] = (
            "Mozilla/5.0 (Windows NT 10.0; Win64; x64) "
            "AppleWebKit/537.36 Chrome/125.0.0.0 Safari/537.36"
        )

    resp = session.get(page_url, timeout=15)
    html = resp.text

    # Method 1: Extract gt from HTML
    gt_match = re.search(r'gt["\']?\s*[:=]\s*["\']([a-f0-9]{32})', html)
    gt = gt_match.group(1) if gt_match else None

    # Method 2: Find API endpoint that returns challenge
    api_match = re.search(r'(https?://[^"\']+register-slide[^"\']*)', html)

    challenge = None
    if api_match:
        api_url = api_match.group(1)
        api_resp = session.get(api_url, timeout=10)
        try:
            data = api_resp.json()
            challenge = data.get("challenge")
            gt = gt or data.get("gt")
        except json.JSONDecodeError:
            pass

    if not challenge:
        # Try embedded challenge
        ch_match = re.search(r'challenge["\']?\s*[:=]\s*["\']([a-f0-9]+)', html)
        challenge = ch_match.group(1) if ch_match else None

    return {"gt": gt, "challenge": challenge, "pageurl": page_url}


# Usage
params = extract_geetest_v3("https://staging.example.com/qa-login")
print(f"gt: {params['gt']}")
print(f"challenge: {params['challenge']}")

GeeTest'i CaptchaAI'ye gönderme

gt, challenge ve pageurl değerlerini in.php uç noktasına method=geetest ile gönderin; ardından res.php'yi çözüm hazır olana dek sorgulayın. Gönderim başarılıysa dönen request alanı görev kimliğidir:

# solve_geetest.py
import requests
import time
import os


def solve_geetest(gt, challenge, pageurl, api_server=None):
    """Solve GeeTest v3 slide CAPTCHA via CaptchaAI."""
    api_key = os.environ["CAPTCHAAI_API_KEY"]

    payload = {
        "key": api_key,
        "method": "geetest",
        "gt": gt,
        "challenge": challenge,
        "pageurl": pageurl,
        "json": 1,
    }

    if api_server:
        payload["api_server"] = api_server

    # Submit
    resp = requests.post(
        "https://ocr.captchaai.com/in.php",
        data=payload,
        timeout=30,
    )
    result = resp.json()

    if result.get("status") != 1:
        raise RuntimeError(f"Submit failed: {result.get('request')}")

    task_id = result["request"]

    # Poll — GeeTest typically solves in 10-20 seconds
    time.sleep(10)
    for _ in range(30):
        resp = requests.get("https://ocr.captchaai.com/res.php", params={
            "key": api_key,
            "action": "get",
            "id": task_id,
            "json": 1,
        }, timeout=15)
        data = resp.json()

        if data.get("status") == 1:
            return data["request"]  # Returns challenge, validate, seccode
        if data["request"] != "CAPCHA_NOT_READY":
            raise RuntimeError(data["request"])
        time.sleep(5)

    raise TimeoutError("GeeTest solve timeout")

Çözümü hedef siteye gönderme

Çözüm üç değer döndürür: challenge, validate ve seccode. Bu üçünü birlikte hedef sitenin doğrulama uç noktasına göndermeniz gerekir — biri eksikse doğrulama reddedilir:

# submit_solution.py
import json


def submit_geetest_solution(session, validation_url, solution, original_challenge):
    """Submit GeeTest solution to the target site."""
    # Parse solution if string
    if isinstance(solution, str):
        solution = json.loads(solution)

    payload = {
        "geetest_challenge": solution.get("challenge", original_challenge),
        "geetest_validate": solution.get("validate", ""),
        "geetest_seccode": solution.get("seccode", ""),
    }

    resp = session.post(validation_url, data=payload, timeout=30)
    return resp


# Complete flow
def full_geetest_flow(page_url, validation_url):
    import requests
    from extract_geetest_params import extract_geetest_v3

    session = requests.Session()
    session.headers["User-Agent"] = (
        "Mozilla/5.0 (Windows NT 10.0; Win64; x64) "
        "AppleWebKit/537.36 Chrome/125.0.0.0 Safari/537.36"
    )

    # Step 1: Extract parameters
    params = extract_geetest_v3(page_url, session)
    print(f"gt: {params['gt']}, challenge: {params['challenge'][:16]}...")

    # Step 2: Solve
    solution = solve_geetest(
        params["gt"], params["challenge"], params["pageurl"],
    )
    print("Solved!")

    # Step 3: Submit
    resp = submit_geetest_solution(
        session, validation_url, solution, params["challenge"],
    )
    print(f"Validation response: {resp.status_code}")
    return resp

challenge tazeliği neden kritik?

challenge oturuma özeldir ve hızla geçersiz olur. Sayfayı bir kez açıp challenge değerini kodun ilerleyen adımlarında yeniden kullanmaya çalışmak, entegrasyonlarda gördüğümüz en yaygın hatadır. Her çözümden hemen önce taze bir challenge alın:

# fresh_challenge.py
import time


def get_fresh_challenge(session, register_url):
    """Always fetch a fresh challenge before solving."""
    resp = session.get(register_url, timeout=10)
    data = resp.json()

    challenge = data.get("challenge")
    if not challenge:
        raise ValueError("No challenge returned")

    return challenge


def solve_with_fresh_challenge(session, gt, register_url, pageurl):
    """Ensure challenge is fresh before submitting to CaptchaAI."""
    challenge = get_fresh_challenge(session, register_url)

    # Submit immediately — don't let it expire
    solution = solve_geetest(gt, challenge, pageurl)
    return solution

Altın kural: challenge değerini çıkarıp saniyeler içinde CaptchaAI'ye gönderin. Bayat bir challenge her zaman başarısız olur.


Özel API sunucusu (api_server)

Bazı siteler varsayılan api.geetest.com yerine özel bir GeeTest alt alanı kullanır. Bu durumlarda api_server parametresini geçmezseniz çözüm reddedilebilir:

# The api_server parameter specifies a custom GeeTest backend
# Default: api.geetest.com
# Custom examples: api-na.geetest.com, api.geetest.com/ajax-custom

solution = solve_geetest(
    gt="abc123...",
    challenge="def456...",
    pageurl="https://staging.example.com/qa-login",
    api_server="api-na.geetest.com",  # North America endpoint
)

Doğru alt alanı bulmak için sayfanın ağ isteklerinde api-*.geetest.com çağrılarını inceleyin ve gördüğünüz değeri aynen api_server olarak geçin.


gt veya challenge sayfada görünmüyorsa

Modern sitelerin çoğu bu değerleri düz HTML'e gömmez; JavaScript çalıştıktan sonra bir XHR isteğiyle yükler. requests ile boş sonuç alıyorsanız şu sırayı izleyin:

  • Önce tarayıcının ağ sekmesinde register-slide veya gettype çağrılarını arayın; gt ve challenge çoğunlukla bu yanıtların JSON gövdesindedir.
  • Değer yalnızca sayfa render edildikten sonra oluşuyorsa, kayıt isteğini gerçek bir tarayıcıda tetiklemek için Selenium kullanın ve JSON yanıtını okuyun.
  • İsteği yakaladıktan sonra çözümü yine yukarıdaki solve_geetest fonksiyonuyla yapın — tarayıcı yalnızca taze challenge üretmek içindir.

Bu yaklaşım, gt parametresi bulunamadığında en sık işe yarayan yoldur ve challenge tazeliğini de korur.


Sorun giderme

Sorun Sebep Çözüm
ERROR_CAPTCHA_UNSOLVABLE Bayat challenge Göndermeden hemen önce taze bir challenge alın
validate boş dönüyor Yanlış GeeTest sürümü Bu akış GeeTest v3 içindir; site v4 kullanıyorsa ayrı bir akış gerekir
Çözüm site tarafından reddedildi seccode eksik Üç alanın da (challenge, validate, seccode) gönderildiğinden emin olun
gt parametresi bulunamadı JavaScript ile yükleniyor Kayıt uç noktası için XHR yanıtlarını kontrol edin veya Selenium kullanın

Yayına almadan önce kontrol listesi

Entegrasyonu production'a taşımadan önce şu maddeleri gözden geçirin:

  • challenge her çözümden hemen önce yeniden alınıyor mu?
  • Üç değer (challenge, validate, seccode) hedef siteye eksiksiz gönderiliyor mu?
  • Özel uç nokta kullanan siteler için api_server doğru ayarlandı mı?
  • CAPTCHAAI_API_KEY ortam değişkeni koda gömülmek yerine güvenli şekilde okunuyor mu?

SSS

CaptchaAI GeeTest v4'ü destekliyor mu?

Hayır. CaptchaAI şu anda yalnızca GeeTest v3'ü çözer; GeeTest v4 desteği çok yakında sunulacak. Bu rehberdeki method=geetest akışı v3 içindir.

Sürekli ERROR_CAPTCHA_UNSOLVABLE alıyorum, sorun ne?

Neredeyse her zaman bayat challenge yüzündendir. challenge değerini çıkardıktan sonra saniyeler içinde CaptchaAI'ye gönderin; kod içinde bekletilen ya da yeniden kullanılan bir challenge başarısız olur.

GeeTest v3 çözümü ne kadar sürer ve maliyeti nedir?

Çözüm genellikle 10–20 saniye içinde tamamlanır. CaptchaAI thread bazlı ücretlendirdiği için GeeTest başına ek ücret yoktur; BASIC ($15/ay, 5 thread) ile başlayabilirsiniz.

gt değeri sayfa kaynağında yoksa ne yapmalıyım?

gt çoğu zaman JavaScript ile yüklenir. Sayfanın ağ isteklerinde register-slide veya api-*.geetest.com çağrılarını inceleyin ya da değeri render sonrası okumak için Selenium kullanın.

api_server parametresini ne zaman kullanmalıyım?

Yalnızca site varsayılan api.geetest.com dışında bir uç nokta kullanıyorsa. Ağ isteklerinde api-na.geetest.com gibi bir alt alan görüyorsanız aynısını api_server olarak geçin.


İlgili Kılavuzlar


GeeTest parametrelerine hâkim olun — CaptchaAI ile başlayın.

Bu makale için yorumlar devre dışı bırakılmıştır.