Python ile DataDome CAPTCHA Nasıl Çözülür (requests)

Python’da bir DataDome CAPTCHA’sını çözmek için 403 engelleme sayfasını okuyup, ondan challenge adresini oluşturup, bu adresi CapSkip DataDome çözücüsü üzerinden datadome() ile gönderip, döndürdüğü çerezle isteğinizi yinelersiniz. Yanıt bir çerezdir, bir form için token değildir ve CapSkip belgeleri, çerezin yalnızca kazanıldığı User-Agent ve IP adresiyle çalıştığını söyler. Bu rehber, bütün döngüyü CapSkip Python SDK ve requests ile yaklaşık 90 satırda çalıştırır. CapSkip, çözüm başına ücret olmadan kendi Windows bilgisayarınızda çalışır; bu yüzden bir yeniden deneme hiçbir şeye mal olmaz.
Neye ihtiyacınız var
- Bir Windows bilgisayarında çalışan CapSkip 3.2.0 veya üzeri. Bu sürüm, kaydırıcı ve cihaz kontrolü için DataDome çözme desteğini ekledi. İlk başlatmayı kurulum kılavuzu adım adım anlatır.
- Python 3.10 veya üzeri ve capskip paketinin 1.5.0 veya üzeri sürümü. Daha eski sürümlerde datadome metodu yoktur. Aşağıdaki kod, capskip 1.5.0 ve requests 2.34.2 ile Python 3.11.7 ve 3.14.0 üzerinde çalıştı. Python 3.10 burada denenmedi.
- Bir PowerShell istemi. Komutlar PowerShell sözdizimini kullanır.
- Sahibi olduğunuz ya da otomatikleştirmenize izin verilen, DataDome arkasındaki bir sayfa.
- Çözücü için bir adres. Local modunda CapSkip 127.0.0.1 üzerinden yalnızca o cihaza yanıt verir. Server modunda ağ adresinizi veya genel IP’nizi dinler, böylece başka bir bilgisayardaki, bir VPS’teki veya barındırılan bir platformdaki script API üzerinden ona erişebilir. İkisi de şurada ayarlanır: bağlantı ayarları.
- Test aşamasını geçtiğinizde görev başına sabit IP’li (sticky) bir proxy. Çerez, onu kazanan IP adresine bağlıdır; bunu 3. Adım açıklar.
Nasıl test edildi: kod, gerçek bir DataDome sitesine karşı değil, benim yazdığım üç sahte (mock) sunucuya karşı çalıştırıldı. Birincisi CapSkip API belgeleri içindeki DataDome bölümünde listelenen denetimleri kopyalar; ikincisi 403 engelleme sayfası veren ve yalnızca CapSkip’in verdiği bir çerezi, verildiği User-Agent ile birlikte kabul eden korumalı bir sitenin, üçüncüsü ise bir forward proxy’nin yerini tutar. SDK, gerçek capskip 1.5.0 idi. Bilgisayarımda CapSkip uygulaması çalışmıyordu, bu yüzden buradaki hiçbir şey gerçek bir çözümün ne kadar sürdüğünü ya da canlı bir DataDome sitesinin neyi kabul ettiğini göstermez. Çerezle ilgili kurallar CapSkip belgelerinden gelir. DataDome’nin kendi çerez belgeleri datadome çerezinin bir yıl geçerli olduğunu söyler ve Domain ya da Path değerinin değiştirilmesine karşı uyarır. Çerezin neye bağlı olduğunu söylemez.
1. Adım: engelleme sayfasını okuyun ve captcha_url adresini oluşturun
DataDome bir isteğe şüpheyle yaklaştığında site, içerik yerine 403 durumuyla (bazen 401) ve küçük bir HTML sayfasıyla yanıt verir. Bu sayfa dd adlı bir script nesnesi barındırır ve challenge’ı geo.captcha-delivery.com üzerinden bir iframe içinde yükler. CapSkip’in ihtiyaç duyduğu şey iframe adresidir ve belgeler ona captcha_url der. Sayfada iframe zaten varsa src değerini olduğu gibi alabilirsiniz. Çoğu engelleme sayfası iframe’i bunun yerine bir script ile oluşturur; bu yüzden aşağıdaki fonksiyon aynı adresi dd nesnesinden derler.
rt değeri yolu belirler. c, /captcha/ altındaki kaydırıcı; i ise /interstitial/ altındaki cihaz kontrolü anlamına gelir. t değeri de önemlidir: fe bir challenge, bv ise sayfayı çeken IP adresini DataDome’nin yasakladığı anlamına gelir. İlk istek sade bir Chrome User-Agent ile gider. Bu dize CapSkip’e hiç gönderilmez, bu yüzden Chrome sürümünün hiçbir şeyle eşleşmesi gerekmez. Canlı bir DataDome sitesinin farklı bir User-Agent’a aynı challenge’ı verip vermediğini test etmedim, bu yüzden o kısmı denenmemiş sayın.
# pip install capskip requests
import json
import re
from urllib.parse import urlencode
import requests
PAGE_URL = "https://www.example.com/" # a page behind DataDome
BROWSER = { # for the first request only; the cookie comes with its own User-Agent
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 "
"(KHTML, like Gecko) Chrome/156.0.0.0 Safari/537.36",
}
def get(headers, via=None):
proxies = {"http": via, "https": via} if via else None
return requests.get(PAGE_URL, headers=headers, proxies=proxies, timeout=30)
def captcha_url_from(resp):
"""Build the challenge address from a DataDome block page, or None."""
if resp.status_code not in (401, 403):
return None
found = re.search(r"var\s+dd\s*=\s*(\{[^}]*\})", resp.text)
if not found:
return None
dd = json.loads(found.group(1).replace("'", '"'))
path = "interstitial" if dd["rt"] == "i" else "captcha"
query = {"initialCid": dd["cid"], "hash": dd["hsh"], "cid": dd["cookie"]}
if dd.get("t"):
query["t"] = dd["t"] # fe is a challenge, bv means the address is banned
query.update(referer=PAGE_URL, s=dd["s"])
for key in ("e", "b"):
if dd.get(key):
query[key] = dd[key]
query["dm"] = "cd"
return f"https://{dd.get('host', 'geo.captcha-delivery.com')}/{path}/?{urlencode(query)}"Fonksiyon, yanıt bir engelleme sayfası değilse None döndürür; böylece bir script “çözülecek bir şey yok” ile “çözüldü” durumunu ayırt edebilir. Her engelleme sayfası yeni bir challenge getirir. Onun captcha_url değerini hemen kullanın ve sonraki görev için eski bir adresi yeniden kullanmak yerine sayfayı yeniden isteyin.
2. Adım: datadome() ile çözün
SDK metodu datadome(captcha_url, pageurl, userAgent, proxy) biçimindedir ve 2Captcha argüman sırasını izler. İlk ikisi zorunludur. CapSkip’te userAgent ve proxy isteğe bağlıdır. Bir User-Agent göndermezseniz CapSkip kendi tarayıcısınınkini kullanır ve sonuçta userAgent olarak döndürür. Gönderirseniz Windows için Chrome olmalı ve CapSkip’in tarayıcısıyla aynı ana sürüme sahip olmalıdır; bu yüzden onu hiç vermemek kolay seçimdir. CapSkip challenge’ı kendi çalıştırdığı gerçek bir tarayıcıda geçtiği için metot, reCAPTCHA’nın kullandığı daha uzun 300 saniyelik zaman aşımıyla bekler. API belgeleri bir çözümün genellikle 3 ila 20 saniye sürdüğünü söyler; ben bir tane ölçmedim.
Proxy, sonraki isteklerinizin kullanacağı proxy’dir. Script’iniz bir proxy üzerinden çıkıyorsa onu verin; istekler CapSkip’i çalıştıran makineden çıkıyorsa hiçbir şey vermeyin. CapSkip bir sunucuda çalışıyorsa o makine sunucudur.
from capskip import CapSkip
# Local mode. In Server mode, use your server's address instead.
solver = CapSkip(host="127.0.0.1", port=8080)
def proxy_arg(proxy_url):
if not proxy_url:
return None # your requests leave from the PC that runs CapSkip
scheme, rest = proxy_url.split("://", 1)
return {"type": scheme.upper(), "uri": rest} # e.g. HTTP, user:pass@ip:port
def solve(captcha_url, proxy_url=None):
# No userAgent argument: CapSkip uses its own browser's and reports it.
return solver.datadome(captcha_url, PAGE_URL, proxy=proxy_arg(proxy_url))Cihaz kontrolü geçilemezse DataDome kaydırıcıya geçer. CapSkip belgelerine göre tek çağrı onu oraya kadar izler, bu yüzden iki challenge için ayrı kod yazmanız gerekmez.
3. Adım: çerezi User-Agent ve IP adresiyle birlikte gönderin
Sonuç, önemli olan dört alanı bulunan bir sözlüktür. code alanı, çerezin DataDome tarafından ayarlandığı hâliyle Max-Age, Domain ve diğer özniteliklerle birlikte tamamıdır; bir çerez deposunun istediği budur. cookie alanı yalnızca datadome ad ve değer çiftidir; bir Cookie başlığının istediği budur. userAgent alanı, onu kazanan User-Agent’tır. proxy alanı yalnızca siz proxy göndermediyseniz ve CapSkip kendi DataDome proxy listesi üzerinden çözdüyse görünür. CapSkip belgeleri, DataDome’nin çerezi başka bir IP adresinden ya da başka bir User-Agent ile reddettiğini söyler; bu yüzden her seferinde aynı User-Agent’ı gönderin ve sonuç bir proxy adlandırıyorsa isteği onun üzerinden gönderin. Bu proxy alanı yalnızca host ve porttur; şema ve giriş bilgisi yoktur. Fonksiyon http:// ekler ve bu yüzden girişi gerekmeyen bir liste proxy’si varsayar. Sizinkinde giriş varsa onu ekleyin.
DataDome sonraki bir yanıtta yerine geçen bir çerez de gönderebilir. Fonksiyon, bir tarayıcının yapacağı gibi en yenisini tutar.
def send_with_cookie(result, proxy_url=None):
# The cookie works only from the address and User-Agent that earned it.
via = proxy_url
if not via and result.get("proxy"):
via = "http://" + result["proxy"] # CapSkip solved through its own list
headers = {"User-Agent": result["userAgent"], "Cookie": result["cookie"]}
resp = get(headers, via)
fresh = resp.cookies.get("datadome") # DataDome may rotate the cookie
if fresh:
headers["Cookie"] = f"datadome={fresh}"
return resp, headers, viaÇerez başlıkta elle ayarlanır, bu yüzden requests onu sizin için yönetmez. Bu bilinçlidir: açık başlık oturum çerez deposunun önüne geçer ve çerezi, User-Agent’ı ve proxy’yi tek bir yerde bir arada tutar. Proxy çalıştırmasının gösterdiği bir şey: şemadan sonraki metin CapSkip’e yazdığınız gibi gider, bu yüzden proxy giriş bilgisini yüzde kodlaması gerektiren karakterlerden uzak tutun. Bir socks5 proxy için requests ayrıca socks ekstrasına ihtiyaç duyar; pip install requests[socks] ile kurulur.
4. Adım: tam çalışan örnek
Son blok, Python’da DataDome CAPTCHA çözme akışını bir araya getirir ve yeniden denemeyi ekler. Dört bloğun hepsini art arda tek bir dosyaya, datadome_demo.py adıyla kaydedin ve python datadome_demo.py ile çalıştırın. Her deneme sayfayı yeniden ister, bu yüzden her seferinde yeni bir challenge gelir. Başarısız bir çözüm ApiException fırlatır ve döngü yeniden dener. Buna rağmen 403 alan bir çerez de döngüyü yeni engelleme sayfasıyla başa döndürür.
from capskip import ApiException
def fetch_protected(proxy_url=None):
for attempt in range(1, 4):
resp = get(BROWSER, proxy_url) # a fresh block page, a fresh challenge
captcha_url = captcha_url_from(resp)
if captcha_url is None:
return resp, BROWSER, proxy_url # no block page on this response
try:
result = solve(captcha_url, proxy_url)
except ApiException as err:
print(f"attempt {attempt}: {err}") # the next attempt gets a new page
continue
resp, headers, via = send_with_cookie(result, proxy_url)
if resp.status_code != 200:
print(f"attempt {attempt}: HTTP {resp.status_code} with the cookie")
continue
return resp, headers, via
raise RuntimeError("DataDome not passed in 3 attempts")
if __name__ == "__main__":
page, headers, via = fetch_protected()
print(page.status_code, page.text[:40])
again = get(headers, via) # reuse the cookie while it lasts
print(again.status_code)SDK, t=bv içeren bir captcha_url adresini hiçbir şey göndermeden önce reddeder, çünkü o adresten yapılan hiçbir çözüm geçemez. Bu ValidationException bir ApiException değildir, bu yüzden döngü onu yakalamaz. Görünür kalmasına izin verin: adresi değiştirip baştan başlamanın işaretidir. CapSkip’in bunun yerine ERROR_PROXY_BANNED olarak bildirdiği bir yasak ise ApiException olarak gelir ve döngü onu aynı adreste yeniden dener; bu yüzden çıktıda bu hatayı görürseniz yeniden çalıştırmadan önce proxy’yi değiştirin. Proxy döndürme kılavuzu proxy’lerin nasıl döndürüleceğini anlatır; CAPTCHA’yı engelden ayırt etme sayfanın hiç de bir challenge olmadığı diğer durumu ele alır.
Mock çalıştırmasında script şöyle davrandı:
| Mock ayarı | Script ne yaptı |
|---|---|
| Kaydırıcı engelleme sayfası, her çözüm yanıtlandı | Bir görev, ardından çerezle 200 durumu ve yeniden kullanımda yine 200 |
| Cihaz kontrolü engelleme sayfası | Aynı kod çalıştı: captcha_url /interstitial/ adresini gösterdi ve sonuç aynıydı |
| İlk iki çözüm reddedildi | İki deneme satırı, ardından üçüncü görevde 200 durumu |
| İlk üç çözüm reddedildi | Üç deneme satırı, ardından RuntimeError |
| Sonuç, CapSkip’in kendi listesinin yaptığı gibi bir proxy adlandırıyor | Çerez isteği o proxy üzerinden gitti ve 200 aldı |
| Çözüme kendi proxy’niz verildi | in.php proxy’yi ve türünü aldı, istekler de onu kullandı |
| t=bv içeren engelleme sayfası | ValidationException, mock CapSkip hiç istek görmedi |
| Farklı bir User-Agent ile gönderilen çerez | Mock site 403 yanıtı verdi |
| Farklı bir IP adresinden gönderilen çerez | CapSkip’in bir proxy üzerinden verdiği çerez proxy olmadan gönderilince mock site 403 yanıtı verdi |
Son iki satır, CapSkip belgelerini izleyen mock’umun kurallarını sınar. Gerçek hizmet hakkında kanıt değildir.
Yaygın hatalar
| Hata | Neden | Düzeltme |
|---|---|---|
| ValidationException | DataDome challenge adresi olmayan bir captcha_url, t=bv içeren bir engelleme sayfası, http ya da https olmayan bir pageurl veya Windows için Chrome olmayan bir userAgent. İleti bunlardan hangisi olduğunu söyler | Adresi yeni bir engelleme sayfasından yeniden oluşturun, yasaklıysa adresi değiştirin ve userAgent argümanını kaldırın |
| ApiException ile ERROR_WRONG_USERAGENT | User-Agent Windows için Chrome ama ana sürümü CapSkip’in tarayıcısından farklı | userAgent göndermeyin ve sonucun bildirdiğini kullanın |
| ERROR_CAPTCHA_UNSOLVABLE içeren ApiException | Challenge geçilemedi | Sayfayı yeniden isteyin ve yeni captcha_url değerini gönderin |
| ApiException ile ERROR_PROXY_BANNED | CapSkip, API belgelerine göre engelleme sayfası t=bv diyen bir görevi reddeder | Proxy’yi değiştirin ve sayfayı yeniden isteyin |
| ApiException ile ERROR_PROXY_CONNECT_REFUSED | CapSkip, proxy üzerinden bağlanamadığında bunu bildirir. Yeniden üretmedim | Proxy adresini, giriş bilgisini ve türünü kontrol edin |
| TimeoutException | CapSkip 300 saniyelik bekleme içinde yanıt vermedi. Bu bir ApiException değildir, bu yüzden döngü onu yakalamaz | CapSkip’in çalıştığını ve çözdüğünü kontrol edin, sonra script’i yeniden çalıştırın |
| NetworkException | CapSkip çalışmıyor ya da host veya port yanlış | CapSkip’i başlatın ve bağlantı ayarlarını kontrol edin |
| Çerezle birlikte hâlâ 403 | İstek başka bir IP adresinden çıktı, başka bir User-Agent kullandı ya da çerezin süresi doldu | Sonucun userAgent ve proxy değerlerini her seferinde gönderin ya da döngüyü yeni engelleme sayfasıyla yeniden çalıştırın |
Çözücüyü bir sunucuda çalıştırmak
Script’in CapSkip’ten iki şeye ihtiyacı var: bir host ve bir port. Local modunda bunlar 127.0.0.1 ve kendi bilgisayarınızdır. Server modunda CapSkip ağ adresinizi veya genel bir IP’yi dinler, böylece başka bir bilgisayardaki, bir VPS’teki veya barındırılan bir platformdaki script aynı API üzerinden ona erişebilir. Host ve port değerlerini CapSkip constructor’ında değiştirin; başka hiçbir şey değişmez. Kararlı uzaktan erişim için statik bir genel IP önerilir. Server modu da kendi donanımınızda çalışır ve çözüm başına ücretlendirme yoktur. Yine de portu her adrese açar, bu yüzden ulaşmaması gereken adresler için bir Windows Firewall engelleme kuralı ekleyin. Çözümün o makinede çalıştığını unutmayın; bu yüzden çerez sunucunun IP adresinden kazanılır. Bir proxy vermezseniz çerezi taşıyan istek de o sunucudan çıkmak zorundadır. Bir proxy kullanıyorsanız aynısını hem çözüme hem isteklerinize verin. Modlar arasında nasıl geçileceğini bağlantı ayarları bölümünde bulabilirsiniz.
FAQ
DataDome çözücü bir token döndürür mü?
Hayır. datadome çerezini döndürür. Bu çerezi, engellenen isteğin Cookie başlığında, aynı User-Agent ile birlikte gönderirsiniz. Doldurulacak bir form alanı yoktur.
DataDome için proxy gerekir mi?
Test için gerekmez. İlk çalıştırma için tek bir IP adresi yeterlidir. CapSkip belgelerine göre çerez yalnızca onu kazanan IP adresinden çalışır; bu yüzden çok sayıda istek göndermeye başladığınızda görev başına bir sticky proxy planlayın ve aynı proxy’yi hem çözüme hem isteklerinize verin.
Bu hem kaydırıcı hem cihaz kontrolü için çalışır mı?
Evet, aynı çağrıyla. Kaydırıcının captcha_url değeri /captcha/ altında, cihaz kontrolününki /interstitial/ altındadır. CapSkip belgeleri, kaydırıcıya yükselen bir cihaz kontrolünün oraya kadar izlendiğini söyler.
Barındırılan bir platform bunu benim CapSkip’ime karşı çalıştırabilir mi?
Evet, Server modu ile. CapSkip’i ağınızı veya genel IP’nizi dinleyecek şekilde ayarlayın, CapSkip constructor’ını o host ve port bilgisine yöneltin; döngü aynı çalışır, tek bir farkla: çözüm artık sunucuda çalışır, bu yüzden çözüme ve isteklerinize aynı proxy’yi verin. Çözücü sizin donanımınızda kalır.
Kısa özet
Python’da bir DataDome CAPTCHA’sını çözmek dört hamle sürer: engelleme sayfasını okuyun, captcha_url adresini oluşturun, datadome() metodunu çağırın ve isteği çerezle, User-Agent ile ve ait olduğu IP adresiyle yineleyin. Kendi makinenizde yeniden denemek ücretsizdir. Bir yerel captcha çözücü ile korumalı bir site size sürekli yeni challenge vermeye devam etse bile her yeniden deneme ücretsizdir. SDK’nın geri kalanı için bkz. Python CAPTCHA çözücü sayfası.
