La resolución secuencial es sencilla. La resolución paralela es rápida. La elección correcta depende de su volumen, infraestructura y tolerancia a la complejidad. Esta guía compara ambos enfoques conCaptchaAIy le ayuda a elegir la estrategia correcta.
Comparación cabeza a cabeza
| factores | secuencial | paralelo |
|---|---|---|
| Rendimiento (reCAPTCHA v2, mediana de 15 s) | ~240/hour | ~10,000+/hour |
| Complejidad del código | Sencillo | Moderado a complejo |
| Manejo de errores | Sencillo | Requiere aislamiento de errores concurrentes |
| Uso de memoria | Mínimo (~30 MB) | Escala con simultaneidad (~100–500 MB) |
| Costo API por resolución | Lo mismo | Lo mismo |
| Dificultad de depuración | fácil | Más difícil (condiciones de carrera, cronometraje) |
| Conservación del pedido | orientativo | Requiere seguimiento explícito |
| Lo mejor para | < 500 soluciones/day | > 500 resuelve/day |
Resolución secuencial
Cómo funciona
Un CAPTCHA a la vez: envíe → espere → consulta → obtenga el resultado → a continuación.
# sequential_solver.py
import os
import time
import requests
API_KEY = os.environ.get("CAPTCHAAI_KEY", "YOUR_API_KEY")
def solve_sequential(tasks):
"""Solve CAPTCHAs one by one."""
results = []
session = requests.Session()
for task in tasks:
# Submit
resp = session.get("https://ocr.captchaai.com/in.php", params={
"key": API_KEY,
"method": "userrecaptcha",
"googlekey": task["sitekey"],
"pageurl": task["pageurl"],
"json": "1",
})
result = resp.json()
if result.get("status") != 1:
results.append({"error": result.get("request")})
continue
task_id = result["request"]
time.sleep(15)
# Poll
token = None
for _ in range(25):
poll = session.get("https://ocr.captchaai.com/res.php", params={
"key": API_KEY, "action": "get",
"id": task_id, "json": "1",
})
poll_result = poll.json()
if poll_result.get("status") == 1:
token = poll_result["request"]
break
if poll_result.get("request") != "CAPCHA_NOT_READY":
break
time.sleep(5)
results.append({"token": token} if token else {"error": "timeout"})
return results
# 10 tasks sequentially → ~150 seconds total
tasks = [{"sitekey": "SITEKEY", "pageurl": "https://example.com"}] * 10
start = time.time()
results = solve_sequential(tasks)
print(f"Completed in {time.time() - start:.0f}s")
Cuando lo secuencial tiene sentido
- Flujos de trabajo de una sola página: completar un formulario a la vez
- Depuración y desarrollo: flujo de ejecución claro
- Bajo volumen — < 500 soluciones/day no justifica la complejidad paralela
- Tareas que dependen del orden: cuando los resultados de la resolución deben usarse en secuencia
Resolución paralela
Cómo funciona
Envíe todos los CAPTCHA a la vez y realice una consulta para obtener resultados al mismo tiempo:
# parallel_solver.py
import os
import asyncio
import aiohttp
API_KEY = os.environ.get("CAPTCHAAI_KEY", "YOUR_API_KEY")
async def solve_one(session, sitekey, pageurl, semaphore):
"""Solve a single CAPTCHA within concurrency limits."""
async with semaphore:
# Submit
async with session.get("https://ocr.captchaai.com/in.php", params={
"key": API_KEY, "method": "userrecaptcha",
"googlekey": sitekey, "pageurl": pageurl, "json": "1",
}) as resp:
result = await resp.json(content_type=None)
if result.get("status") != 1:
return {"error": result.get("request")}
task_id = result["request"]
await asyncio.sleep(15)
# Poll
for _ in range(25):
async with session.get("https://ocr.captchaai.com/res.php", params={
"key": API_KEY, "action": "get",
"id": task_id, "json": "1",
}) as resp:
poll_result = await resp.json(content_type=None)
if poll_result.get("status") == 1:
return {"token": poll_result["request"]}
if poll_result.get("request") != "CAPCHA_NOT_READY":
return {"error": poll_result.get("request")}
await asyncio.sleep(5)
return {"error": "timeout"}
async def solve_parallel(tasks, max_concurrent=50):
"""Solve CAPTCHAs in parallel with concurrency control."""
semaphore = asyncio.Semaphore(max_concurrent)
connector = aiohttp.TCPConnector(limit=max_concurrent)
async with aiohttp.ClientSession(connector=connector) as session:
coros = [
solve_one(session, t["sitekey"], t["pageurl"], semaphore)
for t in tasks
]
return await asyncio.gather(*coros)
# 10 tasks in parallel → ~20 seconds total
import time
tasks = [{"sitekey": "SITEKEY", "pageurl": "https://example.com"}] * 10
start = time.time()
results = asyncio.run(solve_parallel(tasks))
print(f"Completed in {time.time() - start:.0f}s")
Ejemplo paralelo de JavaScript
// parallel_solver.js
const axios = require('axios');
const https = require('https');
const API_KEY = process.env.CAPTCHAAI_KEY || 'YOUR_API_KEY';
const agent = new https.Agent({ keepAlive: true, maxSockets: 50 });
const api = axios.create({ baseURL: 'https://ocr.captchaai.com', httpsAgent: agent });
async function solveOne(sitekey, pageurl) {
const submit = await api.get('/in.php', {
params: { key: API_KEY, method: 'userrecaptcha', googlekey: sitekey, pageurl, json: '1' },
});
if (submit.data.status !== 1) return { error: submit.data.request };
await new Promise(r => setTimeout(r, 15000));
for (let i = 0; i < 25; i++) {
const poll = await api.get('/res.php', {
params: { key: API_KEY, action: 'get', id: submit.data.request, json: '1' },
});
if (poll.data.status === 1) return { token: poll.data.request };
if (poll.data.request !== 'CAPCHA_NOT_READY') return { error: poll.data.request };
await new Promise(r => setTimeout(r, 5000));
}
return { error: 'timeout' };
}
(async () => {
const tasks = Array.from({ length: 10 }, () => ({
sitekey: 'SITEKEY', pageurl: 'https://example.com',
}));
const start = Date.now();
const results = await Promise.all(tasks.map(t => solveOne(t.sitekey, t.pageurl)));
console.log(`Completed in ${((Date.now() - start) / 1000).toFixed(0)}s`);
console.log(`Solved: ${results.filter(r => r.token).length}/${tasks.length}`);
agent.destroy();
})();
Rendimiento por nivel de simultaneidad
| Resoluciones concurrentes | Rendimiento estimado/hour | Memoria (Python) | Complejidad |
|---|---|---|---|
| 1 (secuencial) | 240 | 30 megas | Bajo |
| 10 | 2.400 | 50 megas | Bajo |
| 25 | 6.000 | 80 megas | Medio |
| 50 | 10,000+ | 120 megas | Medio |
| 100 | 18.000+ | 200 megas | Alto |
Basado en reCAPTCHA v2 con un tiempo medio de resolución de 15 segundos.
Enfoque híbrido
Utilice secuencial para el flujo de trabajo y paralelo para la resolución de CAPTCHA:
# Process 10 URLs sequentially, but solve their CAPTCHAs in a parallel batch
urls = get_next_batch() # 10 URLs
captcha_params = [extract_sitekey(url) for url in urls] # Sequential extraction
tokens = asyncio.run(solve_parallel(captcha_params, max_concurrent=10)) # Parallel solving
for url, result in zip(urls, tokens):
submit_form(url, result.get("token")) # Sequential submission
Solución de problemas
| Problema | causa | Solución |
|---|---|---|
| Paralelo más lento de lo esperado | Semáforo demasiado restrictivo | Aumentar max_concurrent |
| Fallos aleatorios en paralelo | Corrupción estatal compartida | Estado aislado por corrutina/promise |
| Resultados desordenados | asyncio.gather preserva el orden |
Utilice el seguimiento de índice si es necesario |
API devuelve ERROR_NO_SLOT_AVAILABLE |
Demasiados envíos simultáneos | Agregar un pequeño retraso entre envíos |
Preguntas frecuentes
¿Puedo cambiar de secuencial a paralelo sin cambiar la estructura de mi código?
Sí, si extrae la lógica de resolución en una función independiente. El único cambio es ajustar las llamadas en asyncio.gather (Python) o Promise.all (JavaScript).
¿La resolución paralela cuesta más?
No. CaptchaAI cobra por hilo (con resoluciones ilimitadas por hilo), no por solicitud simultánea más allá de su plan. La resolución paralela tiene el mismo costo de suscripción que la secuencial: simplemente se alcanza el total más rápido.
¿Cuál es la máxima concurrencia práctica?
La mayoría de las configuraciones obtienen rendimientos decrecientes por encima de 100 soluciones simultáneas. Más allá de eso, concéntrese en optimizar los parámetros de resolución en lugar de agregar simultaneidad.
Próximos pasos
Elija la estrategia que coincida con su volumen:obtenga su clave API CaptchaAI.
Guías relacionadas:
- Resolución CAPTCHA paralela
- 10.000 tareas por hora
- Optimización de memoria y CPU