Documentación de la API
Envía una URL y tu proxy. Orpheus detecta el desafío anti-bot, lo supera y te devuelve la página — con una sesión que puedes reutilizar en las siguientes peticiones.
Inicio rápido
- Inicia sesión en la consola y crea una clave de API en la pestaña Claves de API. Cópiala: solo se muestra una vez.
- Ten a mano un proxy residencial o ISP sticky (que mantenga la misma IP de salida al menos 10 minutos).
- Llama a
POST /v1/fetchcon la URL y el proxy.
curl -X POST https://orpheus-api.lapetiteagora.fr/v1/fetch \ -H "Authorization: Bearer $LPA_KEY" \ -H "Content-Type: application/json" \ -d '{ "url": "https://www.example.com/", "proxy": "http://user:pass@proxy.example:8080" }'
import os, requests resp = requests.post( "https://orpheus-api.lapetiteagora.fr/v1/fetch", headers={"Authorization": f"Bearer {os.environ['LPA_KEY']}"}, json={ "url": "https://www.example.com/", "proxy": "http://user:pass@proxy.example:8080", }, timeout=70, ) page = resp.json() print(page["status"], page["solved"], page["session_id"])
const resp = await fetch("https://orpheus-api.lapetiteagora.fr/v1/fetch", { method: "POST", headers: { Authorization: `Bearer ${process.env.LPA_KEY}`, "Content-Type": "application/json", }, body: JSON.stringify({ url: "https://www.example.com/", proxy: "http://user:pass@proxy.example:8080", }), }); const page = await resp.json(); console.log(page.status, page.solved, page.session_id);
Pon en tu cliente un timeout de unos 70 segundos: superar un desafío puede llevar unos segundos, a veces más.
Autenticación
Cada petición lleva tu clave de API en el header Authorization:
Authorization: Bearer lpa_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Las claves se crean y se revocan en la consola. Trátalas como contraseñas: guárdalas en el servidor, nunca en un navegador ni en un repositorio público. Una clave revocada, o una cuenta suspendida, recibe 401 invalid_key de inmediato.
Obtener una página
Cuerpo de la petición (JSON)
| Campo | Tipo | Descripción |
|---|---|---|
urlobligatorio | string | La página que quieres obtener, en http o https. |
proxy | string | Obligatorio para iniciar una sesión. http://user:pass@host:port, https://… o socks5://…. Omítelo (o envía el mismo valor) cuando pases un session_id. |
session_id | string | Reutiliza una sesión devuelta por una llamada anterior. Consulta Sesiones. |
method | string | GET (por defecto), POST, PUT, PATCH, DELETE, HEAD u OPTIONS. |
headers | object | Headers adicionales de la petición, como cadenas {"Name": "value"}. Los headers del navegador (User-Agent, client hints…) ya vienen puestos. |
body | string | Cuerpo de la petición para POST/PUT/PATCH. |
body_encoding | string | text (por defecto) o base64 para un cuerpo binario. |
cookies | object · array | Cookies que se añaden a la sesión antes de la petición. Consulta Cookies. |
preset | string | Huella del navegador, fijada al crear la sesión. Por defecto chrome-latest-windows (mantenla salvo que sepas por qué cambiarla). |
Respuesta
La API responde 200 en cuanto el sitio de destino ha respondido — sea cual sea el estado que devuelva el sitio. Ese estado lo lees en status.
{
"status": 200,
"headers": { "content-type": ["text/html; charset=utf-8"] },
"body": "<!doctype html>…",
"encoding": "text",
"url": "https://www.example.com/",
"session_id": "s_Ij4oudr1bYPzUA8U3sdlACAf",
"solved": ["datadome"],
"cookies": [{ "name": "datadome", "value": "…", "domain": ".example.com", "path": "/" }],
"elapsed_ms": 2343
}| Campo | Descripción |
|---|---|
status | Estado HTTP devuelto por el sitio de destino. |
headers | Headers de la respuesta; cada valor es una lista de cadenas. |
body · encoding | La página. encoding es text (UTF-8) o base64 para contenido binario (imágenes, PDF…). |
url | URL final, después de las redirecciones. |
session_id | Reenvíalo para mantener la misma identidad. También se devuelve con la mayoría de los errores. |
solved | Protecciones superadas durante esta llamada: akamai, datadome, incapsula, kasada, cloudflare, ticketmaster. Vacío cuando no había nada que superar. |
cookies | Todas las cookies de la sesión después de la llamada. |
elapsed_ms | Tiempo empleado por nuestra parte, incluida la resolución. |
Sesiones
Las cookies anti-bot están ligadas a la identidad de navegador que las obtuvo: IP, huella, almacén de cookies. Una sesión conserva esa identidad por ti, así que un desafío superado una vez sigue superado.
- La primera llamada (con un
proxy, sinsession_id) crea una sesión y devuelve susession_id. - Envía ese
session_iden las siguientes llamadas: mismo proxy, misma huella, mismas cookies. Las páginas siguientes suelen llegar en unos cientos de milisegundos, consolved: []. - Una sesión caduca tras 30 minutos sin peticiones. Cada petición la prolonga.
- Una sesión conserva su proxy toda su vida. Enviar un
proxydistinto con unsession_iddevuelve409 proxy_mismatch: inicia una sesión nueva en su lugar. - Una petición a la vez por sesión. Una segunda petición simultánea espera hasta 10 segundos y luego recibe
409 session_busy. Para ir más rápido, usa varias sesiones en paralelo, cada una con su propio proxy.
import os, requests API = "https://orpheus-api.lapetiteagora.fr/v1/fetch" HEADERS = {"Authorization": f"Bearer {os.environ['LPA_KEY']}"} def fetch(**payload): r = requests.post(API, headers=HEADERS, json=payload, timeout=70) data = r.json() if r.status_code != 200: raise RuntimeError(data["error"]) return data # 1. Primero la página de inicio: crea la sesión y supera el desafío home = fetch(url="https://www.shop.example/", proxy="http://user:pass@proxy.example:8080") # 2. Luego la página del producto, con la misma identidad product = fetch( url="https://www.shop.example/product/42", session_id=home["session_id"], headers={"Referer": "https://www.shop.example/"}, ) print(product["status"], product["solved"])
# 1. Página de inicio: apunta el session_id de la respuesta curl -s -X POST https://orpheus-api.lapetiteagora.fr/v1/fetch \ -H "Authorization: Bearer $LPA_KEY" -H "Content-Type: application/json" \ -d '{"url":"https://www.shop.example/","proxy":"http://user:pass@proxy.example:8080"}' # 2. Página del producto en la misma sesión curl -s -X POST https://orpheus-api.lapetiteagora.fr/v1/fetch \ -H "Authorization: Bearer $LPA_KEY" -H "Content-Type: application/json" \ -d '{"url":"https://www.shop.example/product/42","session_id":"s_…", "headers":{"Referer":"https://www.shop.example/"}}'
Errores
Los errores usan un estado distinto de 200 y siempre la misma forma. Cuando existe una sesión, se incluye su session_id.
{
"error": { "code": "proxy_blocked", "message": "…" },
"session_id": "s_…"
}| Estado | Código | Qué hacer |
|---|---|---|
| 400 | invalid_request | Corrige la petición: falta url, falta proxy para una sesión nueva, campo no válido, dirección privada o inaccesible. |
| 401 | invalid_key | Clave ausente, incorrecta o revocada, o cuenta suspendida. |
| 402 | quota_exceeded | Cuota mensual alcanzada. Se reinicia el día 1 (UTC). |
| 404 | session_not_found | La sesión caducó (30 min de inactividad) o se cerró. Inicia una nueva. |
| 409 | proxy_mismatch | Una sesión conserva su proxy. Inicia una sesión nueva para otro proxy. |
| 409 | session_busy | Otra petición está usando esta sesión. Espera o usa otra sesión. |
| 413 | response_too_large | La página supera los 5 MB. |
| 422 | proxy_blocked | El sitio ha bloqueado esta IP. Cambia de proxy e inicia una sesión nueva. |
| 429 | too_many_concurrent | Demasiadas peticiones en curso para tu cuenta. Reintenta cuando termine alguna. |
| 502 | challenge_failed | No se pudo superar el desafío. Reintenta una vez; si persiste, cambia de proxy. |
| 502 | solver_error · transport_error | Problema temporal del solver o de la red (a menudo el proxy). Reintenta tras una breve espera. |
| 504 | timeout | No hubo respuesta a tiempo. Reintenta; la sesión sigue siendo utilizable. |
| 500 | internal_error | Problema nuestro. Reintenta y avísanos si persiste. |
Regla práctica para reintentar: reintenta los 429, 502, 504 y 500 con un backoff corto. Nunca reintentes un 422 en la misma sesión: cambia de proxy.
Límites
| Límite | Valor |
|---|---|
| Peticiones mensuales (beta) | 20.000 por cuenta, se reinician el día 1 (UTC). Cuenta toda llamada a /v1/fetch que llegue al sitio, aunque luego falle la resolución; las llamadas rechazadas de entrada (400, 401, 402, 404, 409, 429) no cuentan. |
| Peticiones simultáneas | 5 por cuenta por defecto (consulta tu pestaña Cuenta). |
| Tiempo por petición | Unos 55 segundos, resolución incluida. |
| Tamaño de la respuesta | 5 MB de contenido de la página. |
| Duración de una sesión | 30 minutos después de la última petición. |
| Cookies | 50 por petición, 4096 caracteres por valor. |
El consumo, los desafíos superados y tus últimas peticiones están en la consola.
Otros endpoints
Peticiones usadas este mes, tu cuota y el desglose diario de los últimos 30 días (peticiones, éxitos, errores, bytes, resoluciones por protección).
curl -s https://orpheus-api.lapetiteagora.fr/v1/usage -H "Authorization: Bearer $LPA_KEY"Cierra una sesión de inmediato (si no, caduca sola). Devuelve {"deleted": true}, o 404 si ya no existe.
curl -s -X DELETE https://orpheus-api.lapetiteagora.fr/v1/sessions/s_… -H "Authorization: Bearer $LPA_KEY"Buenas prácticas
- Solo proxies sticky. Un proxy rotativo cambia de IP entre peticiones e invalida las cookies que acabas de obtener. Apunta a sesiones de 10 minutos o más.
- Una sesión por identidad. Reutilízala para todas las páginas de un mismo recorrido; abre más sesiones (con más proxies) para escalar.
- Navega con naturalidad. Carga primero la página de inicio o de categoría y luego la del producto con un header
Referer. Los accesos directos a páginas profundas se marcan más a menudo. - No machaques una sola sesión. Supera el desafío con una petición y sigue; evita ráfagas desde la misma IP.
- Ante
proxy_blocked, aparca la sesión y su proxy durante un tiempo; una IP quemada sigue quemada. - Respeta los sitios a los que accedes. Eres responsable de cumplir sus condiciones y las leyes que te aplican.