Integrations

Oxylabs + CaptchaAI:数据中心代理集成

代理和验证码识别是两件事:代理负责更换出口 IP、分散抓取流量,从源头降低验证码触发率;验证码真正弹出时,再交给 CaptchaAI 提交任务、拿回 token。把 Oxylabs 的代理网络和 CaptchaAI 的识别接口串起来,就能在受验证码保护的站点上稳定抓取。

Oxylabs 覆盖 200 万+ 数据中心 IP 和 1 亿+ 住宅 IP,胜在稳定与企业级线路。下面用 Python 演示怎么把两者接到一起。提醒一句:只采集你有权采集的数据,遵守目标站点 robots 协议与网络安全法、数据安全法、个人信息保护法(PIPL)。

Oxylabs 提供哪些代理产品

先对齐产品线,选型时好对号入座。

产品 IP 规模 速度 适用场景
数据中心代理 200 万+ 极快 高并发、速度优先
住宅 IP 代理 1 亿+ 中等 验证码敏感的站点
ISP 代理 住宅级线路 电商、社交平台
移动 IP 代理 2000 万+ 较慢 移动端专属目标
SERP 抓取 API 托管式 Google/Bing 搜索结果

用 Python 集成 Oxylabs 与 CaptchaAI

基础请求:requests 走代理,验证码交给 CaptchaAI

核心逻辑就两步:

  1. fetch_page 通过 Oxylabs 出口取回页面;
  2. 发现 reCAPTCHA 就用 solve_recaptcha 提交 sitekey 与页面地址,每 5 秒轮询一次 res.php,直到拿回 token。
import requests
import time

OXYLABS_USER = "customer-USERNAME"
OXYLABS_PASS = "PASSWORD"
OXYLABS_ENDPOINT = "pr.oxylabs.io:7777"

CAPTCHAAI_KEY = "YOUR_API_KEY"
CAPTCHAAI_URL = "https://ocr.captchaai.com"

# Residential QA 测试会话
proxies = {
    "http": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@{OXYLABS_ENDPOINT}",
    "https": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@{OXYLABS_ENDPOINT}",
}


def fetch_page(url, country=None):
    """Fetch page through Oxylabs proxy."""
    user = OXYLABS_USER
    if country:
        user += f"-cc-{country}"

    proxy = {
        "http": f"http://{user}:{OXYLABS_PASS}@{OXYLABS_ENDPOINT}",
        "https": f"http://{user}:{OXYLABS_PASS}@{OXYLABS_ENDPOINT}",
    }

    return requests.get(
        url,
        proxies=proxy,
        headers={
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) "
            "AppleWebKit/537.36 Chrome/126.0.0.0 Safari/537.36"
        },
        timeout=30,
    )


def solve_recaptcha(site_url, sitekey):
    """Solve via CaptchaAI."""
    resp = requests.post(f"{CAPTCHAAI_URL}/in.php", data={
        "key": CAPTCHAAI_KEY,
        "method": "userrecaptcha",
        "googlekey": sitekey,
        "pageurl": site_url,
        "json": 1,
    })
    data = resp.json()
    if data["status"] != 1:
        raise Exception(f"Submit: {data['request']}")

    task_id = data["request"]

    for _ in range(60):
        time.sleep(5)
        resp = requests.get(f"{CAPTCHAAI_URL}/res.php", params={
            "key": CAPTCHAAI_KEY,
            "action": "get",
            "id": task_id,
            "json": 1,
        })
        data = resp.json()
        if data["request"] == "CAPCHA_NOT_READY":
            continue
        if data["status"] == 1:
            return data["request"]
        raise Exception(f"Solve: {data['request']}")

    raise TimeoutError("Timeout")

googlekeypageurljson=1 等参数名保持原样,别翻译,否则接口对不上。

用粘性会话固定同一个出口 IP

抓取常要在同一 IP 上先取页面、再带 token 提交表单。Oxylabs 用 -sessid- 锁定粘性会话,整段流程固定在同一出口 IP。

def get_oxylabs_sticky_proxy(session_id, country=None):
    """Create Oxylabs sticky session (same IP)."""
    user = OXYLABS_USER + f"-sessid-{session_id}"
    if country:
        user += f"-cc-{country}"

    proxy_url = f"http://{user}:{OXYLABS_PASS}@{OXYLABS_ENDPOINT}"
    return {"http": proxy_url, "https": proxy_url}


# CAPTCHA workflow with sticky IP
import random, string
session = "".join(random.choices(string.ascii_lowercase, k=8))
proxy = get_oxylabs_sticky_proxy(session, country="us")

# All requests use the same IP
resp = requests.get("https://staging.example.com/qa-form", proxies=proxy)
# ... solve CAPTCHA ...
resp = requests.post("https://target.com/submit", proxies=proxy, data={
    "g-recaptcha-response": token,
})

结合 Oxylabs Web Scraper API 渲染与 CaptchaAI 识别

有些站点渲染后才出现验证码,普通请求拿不到完整 DOM。先用 Oxylabs Web Scraper API 渲染,从返回 HTML 正则提取 sitekey,再交给 CaptchaAI:

def scrape_with_oxylabs_api(url):
    """Use Oxylabs Web Scraper API for rendering, CaptchaAI for CAPTCHAs."""
    resp = requests.post(
        "https://realtime.oxylabs.io/v1/queries",
        auth=(OXYLABS_USER, OXYLABS_PASS),
        json={
            "source": "universal",
            "url": url,
            "render": "html",
            "browser_instructions": [
                {"type": "wait", "wait_time_s": 3},
            ],
        },
    )

    result = resp.json()
    html = result["results"][0]["content"]

    # Check for CAPTCHA in rendered HTML
    import re
    sitekey_match = re.search(r'data-sitekey="([^"]+)"', html)

    if sitekey_match:
        sitekey = sitekey_match.group(1)
        token = solve_recaptcha(url, sitekey)
        return {"html": html, "captcha_solved": True, "token": token}

    return {"html": html, "captcha_solved": False}

数据中心 IP 还是住宅 IP:按验证码触发率选

两类 IP 的取舍很直接:

  • 数据中心 IP:快、成本低,但更易被风控识别,验证码触发率高。
  • 住宅 IP:更接近真实用户,触发验证码少,代价是速度慢一些。

实用策略是:验证码敏感的站点走住宅 IP,其余走数据中心 IP,弹出的验证码统一由 CaptchaAI 兜底。举个常见场景:跨境电商选品或海外 SERP 采集量大、预算敏感(按美元计价),多优先数据中心 IP 抢速度;这类国际站点常挂 reCAPTCHA 或 Turnstile(不像国内多用 GeeTest(极验)),正好由 CaptchaAI 负责识别。

# Datacenter: Fast but higher CAPTCHA rate
DC_PROXY = {
    "http": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@dc.pr.oxylabs.io:10000",
    "https": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@dc.pr.oxylabs.io:10000",
}

# Residential: Slower but lower CAPTCHA rate
RES_PROXY = {
    "http": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@pr.oxylabs.io:7777",
    "https": f"http://{OXYLABS_USER}:{OXYLABS_PASS}@pr.oxylabs.io:7777",
}


def smart_proxy_selection(url, captcha_sensitive=True):
    """Pick proxy type based on target site sensitivity."""
    if captcha_sensitive:
        return RES_PROXY  # Less likely to trigger CAPTCHA
    return DC_PROXY  # Faster, CaptchaAI handles any CAPTCHAs

并发抓取管道:多线程批量处理

CaptchaAI 按线程计费,天然适合并发。用 ThreadPoolExecutor 开 5 线程,每个 URL 分配独立粘性会话;命中 sitekey 就识别,完成后线程接下一个任务。

from concurrent.futures import ThreadPoolExecutor, as_completed

def process_url(url):
    session = "".join(random.choices(string.ascii_lowercase, k=8))
    proxy = get_oxylabs_sticky_proxy(session, country="us")

    try:
        resp = requests.get(url, proxies=proxy, timeout=30)

        import re
        match = re.search(r'data-sitekey="([^"]+)"', resp.text)

        if match:
            token = solve_recaptcha(url, match.group(1))
            return {"url": url, "status": "solved"}
        return {"url": url, "status": "no_captcha"}

    except Exception as e:
        return {"url": url, "status": "error", "error": str(e)}


urls = ["https://site1.com", "https://site2.com", "https://site3.com"]

with ThreadPoolExecutor(max_workers=5) as executor:
    futures = {executor.submit(process_url, u): u for u in urls}
    for future in as_completed(futures):
        print(future.result())

max_workers 别超过套餐的线程数,否则任务会排队等待。

常见问题排查

症状 可能原因 处理方式
代理返回 403 出口 IP 被列入黑名单 换用住宅 IP,或轮换出口
认证失败 接口地址写错 数据中心用 dc.pr.oxylabs.io:10000,住宅用 pr.oxylabs.io:7777
粘性会话失效 默认 10 分钟过期 换一个新的 session ID
每个页面都弹验证码 数据中心 IP 被识别 改用住宅 IP
响应变慢 住宅网络延迟高 接受延迟,或改用 ISP 代理

常见问题

CaptchaAI 支持哪些验证码类型?

支持 reCAPTCHA v2/v3(含 Enterprise 与隐形版)、Cloudflare Turnstile 与 Challenge、GeeTest v3、图片/OCR、九宫格与 BLS;CaptchaFox、Friendly Captcha、Lemin 为测试版。hCaptcha 与 FunCaptcha 暂不支持,GeeTest v4 即将支持。

提交 token 时必须用同一个出口 IP 吗?

最好保持一致。风控常把 token 与会话、IP 绑定,中途换 IP 可能让 token 失效;用粘性会话固定出口 IP 走完整段流程最稳。

CaptchaAI 怎么计费?

按线程计费,不按次数:BASIC $15/月(5 线程)、STANDARD $30(15 线程)、ADVANCE $90(50 线程),往上到 ENTERPRISE $300(200 线程)及 VIP 档。每线程当月识别次数不限,并发能力由线程数决定。

相关指南

把 Oxylabs 的代理基础设施和 CaptchaAI 的验证码识别接到一起 —— 免费获取 API Key

该文章已禁用评论。