
Aloísio Vítor
Image Processing Expert

ReCaptchaV2TaskProxyLess, websiteURL y websiteKey, y devuelve gRecaptchaResponse después de un resultado listo.needs_review previenen bucles y alertas de stock engañosas.La recolección de datos de inventario de tienda parece sencilla hasta que una página de retail cambia su comportamiento según la ubicación, requiere un selector de tienda o pausa una sesión del navegador autorizada en un CAPTCHA. Un recolector confiable debe preservar el contexto del producto y la tienda, resolver el punto de verificación a través de la misma sesión y demostrar que la página devolvió un estado real de stock. CapSolver puede servir como infraestructura de CAPTCHA dentro de ese paso de recuperación controlado.
Este guía se centra en un escenario concreto de operaciones de retail: monitorear la disponibilidad pública de productos para planificación de reposición aprobada, calidad de merchandising o notificaciones de stock orientadas al cliente. No asume que una tarea de CAPTCHA exitosa significa que la solicitud de inventario tuvo éxito. El flujo finaliza solo cuando la aplicación objetivo proporciona un resultado de inventario reconocido y el recolector registra suficiente evidencia para distinguir entre "agotado" y "desconocido".
La recolección de datos de inventario de tienda debe devolver un registro pequeño y estable que los sistemas posteriores puedan confiar. Un registro útil contiene el minorista, el identificador de producto canónico, la tienda solicitada o el área postal, la disponibilidad observada, el momento de la observación y la fuente de evidencia. El precio puede incluirse, pero no debe reemplazar un estado de stock explícito.
{
"retailer": "authorized-demo-store",
"product_id": "SKU-4821",
"store_id": "STORE-017",
"postal_area": "10001",
"availability": "in_stock",
"quantity_hint": "limited",
"observed_at": "2026-08-13T09:15:00Z",
"source": "product-page",
"verification": "inventory-label-and-store-id",
"captcha_recovery": "completed"
}
La entrada es una URL de producto más un contexto de tienda permitido. La operación selecciona o confirma la ubicación, detecta un punto de verificación de verificación, lo resuelve cuando está autorizado, lee el estado de inventario y normaliza el resultado. La salida es el registro anterior o un estado terminal como not_found, out_of_stock, needs_review o policy_denied. Nunca convierta un tiempo de espera, un bucle de desafío, una pared de inicio de sesión o una respuesta malformada en out_of_stock; ese error genera señales comerciales falsas.
La FAQ de resolución de CAPTCHA de CapSolver explica los límites del servicio, mientras que la guía de automatización de navegador da un contexto más amplio para mantener el estado de la página. En este caso de usuario, el navegador posee la navegación y la evidencia, CapSolver posee la tarea documentada de CAPTCHA y su aplicación posee la autorización, la política de reintentos y la verificación final.
Un recolector de retail común realiza varias acciones con estado antes de que aparezca el inventario: cargar una página de producto, aceptar una configuración regional, seleccionar una tienda, abrir un panel de recogida o llamar a un punto final de inventario público iniciado por la página. Un CAPTCHA puede aparecer antes de que se renderice la primera página o después de una de esas acciones. Si el recolector lo trata como HTML genérico, los selectores fallan y el trabajo podría escribir un registro vacío o incorrecto.
La respuesta correcta es una transición de estado, no un reintentó ciego. El recolector pasa de collecting a captcha_required, congela el contexto actual del producto y ubicación, recopila solo los campos de desafío documentados y llama al adaptador del proveedor. Una respuesta de proveedor lista mueve el flujo a apply_solution; la aceptación de la aplicación lo mueve a verify_inventory. Un resultado rechazado, un checkpoint repetido, un host inesperado o un plazo agotado lo mueve a needs_review.
Este diseño mantiene separadas tres verdades diferentes:
Solo la tercera verdad permite que el trabajo publique un registro de inventario. Esta separación es especialmente importante cuando un minorista utiliza contenido en caché, redirige entre dominios regionales o actualiza el stock de forma asincrónica después de que se cargue la primera HTML.
Use seis componentes con responsabilidades estrechas.
El registro de alcance enumera los hostnames aprobados, propósitos de recolección, rutas de producto, regiones de tienda, horarios y dueños de contacto. También debe registrar exclusiones: áreas de cuentas autenticadas, portales de empleados, caja, pago, perfiles personales y cualquier ruta que el propietario del sitio o su acuerdo coloque fuera del alcance. Una solicitud que no coincida con el registro se detiene antes de que se abra el navegador.
El navegador establece la configuración regional, selección de tienda, cookies y estado de navegación. Mantenga una verificación de producto dentro de un contexto de navegador. Reutilizar cookies no relacionadas entre tiendas puede crear desplazamiento de ubicación confuso; descartar el contexto durante una recuperación de CAPTCHA puede invalidar la solución. Persista solo los datos mínimos necesarios para el trabajo y límpielos según su política de retención.
El detector busca elementos de widget explícitos, campos de respuesta conocidos, scripts de desafío o una ruta de verificación. También distingue un CAPTCHA de problemas ordinarios como un 404, un diálogo de consentimiento, una tienda no disponible o un error de aplicación. El glosario de CapSolver es útil para mantener la terminología de desafío consistente en registros y manuales de operaciones.
El adaptador recibe una solicitud estrecha que contiene el tipo de desafío, la URL de la página, la clave del sitio y un ID de correlación. Lee la clave de API desde un almacenamiento secreto, crea una tarea, sondea esa misma tarea con un plazo, valida el esquema del resultado y devuelve un éxito o fallo normalizado. No decide qué sitios están permitidos y no escribe datos de inventario.
El extractor mapea la página o respuesta pública a un esquema de inventario estable. Debe preferir identificadores de producto duraderos, IDs de tienda, datos estructurados y texto de disponibilidad explícito sobre posiciones visuales frágiles. Si la página contiene varios modos de cumplimiento, registre la recogida, el envío y la entrega local por separado en lugar de fusionarlos en un booleano.
La capa de evidencia almacena hechos diagnósticos no sensibles: ID de correlación, hostname permitido, ID de producto, ID de tienda, tipo de desafío, ID de tarea del proveedor, tiempo transcurrido, estado final y el selector o campo de respuesta utilizado para la verificación. Debe enmascarar tokens, cookies, claves de API, direcciones y cualquier datos de cliente. Alerte solo en cambios de estado significativos y requiera dos observaciones cuando un resultado transitorio único podría causar ruido operativo.
Antes de implementar la recuperación de CAPTCHA, confirme que tiene permiso para automatizar las páginas de retail seleccionadas y que el propósito de la recolección está documentado. Respete los límites contractuales, la ley aplicable, las instrucciones de robots donde se aplican a su uso y las tasas razonables de solicitud. El Protocolo de Exclusión de Robots describe directivas de rastreador estandarizadas; es una señal dentro de una revisión de autorización más amplia, no un permiso de acceso.
Use estos requisitos previos:
requests e instalado Playwright.Los secretos deben provenir de un entorno gestionado o almacén de secretos. La guía de gestión de secretos de OWASP apoya la separación de credenciales del código de aplicación, registros y artefactos de construcción. No coloque una clave de cliente real, cookie, token resuelto o dirección de cliente en un artículo, prompt, captura de pantalla o ticket de solución de problemas.
El detector debe ejecutarse después de cada acción que pueda desencadenar una página de verificación: navegación inicial, cambio de tienda, apertura del panel de recogida, paginación y refresco de inventario. La detección debe devolver evidencia estructurada en lugar de un booleano simple.
from dataclasses import dataclass
@dataclass(frozen=True)
class CaptchaEvidence:
kind: str
website_url: str
website_key: str
async def detect_recaptcha_v2(page) -> CaptchaEvidence | None:
frame = page.locator('iframe[src*="recaptcha"]')
textarea = page.locator('textarea[name="g-recaptcha-response"]')
if await frame.count() == 0 and await textarea.count() == 0:
return None
key = await page.locator('[data-sitekey]').first.get_attribute('data-sitekey')
if not key:
raise RuntimeError("reCAPTCHA detected without a readable site key")
return CaptchaEvidence(
kind="recaptcha_v2",
website_url=page.url,
website_key=key,
)
La entrada es la página de Playwright ya abierta. La operación comprueba dos señales de widget explícitas y lee la clave del sitio proporcionada por la página. La salida es None o un objeto de evidencia tipado. La función se detiene con un error cuando un desafío es visible pero la clave no puede confirmarse; adivinar una clave o reutilizar una de otra página haría que la recuperación fuera poco confiable.
Antes de llamar al solucionador, valide que page.url aún pertenece al host de retail permitido y que la ejecución actual aún mantiene los identificadores de producto y tienda esperados. Si una redirección conduce a una página de cuenta, caja, flujo de pago o dominio inesperado, deténgase y marque policy_denied. La capacidad técnica no proporciona permiso para acceder a datos privados, restringidos, sensibles o no autorizados.
La guía oficial de tarea reCAPTCHA v2 de CapSolver documenta ReCaptchaV2TaskProxyLess, websiteURL y websiteKey. La API createTask devuelve un taskId; la API getTaskResult devuelve un resultado terminal. Un resultado exitoso de reCAPTCHA v2 incluye solution.gRecaptchaResponse.
import os
import time
import requests
CAPSOLVER_API = "https://api.capsolver.com"
def solve_recaptcha_v2(website_url: str, website_key: str) -> str:
client_key = os.environ["CAPSOLVER_API_KEY"]
created = requests.post(
f"{CAPSOLVER_API}/createTask",
json={
"clientKey": client_key,
"task": {
"type": "ReCaptchaV2TaskProxyLess",
"websiteURL": website_url,
"websiteKey": website_key,
},
},
timeout=30,
).json()
if created.get("errorId") or not created.get("taskId"):
raise RuntimeError(created.get("errorDescription", "createTask failed"))
task_id = created["taskId"]
deadline = time.monotonic() + 120
while time.monotonic() < deadline:
result = requests.post(
f"{CAPSOLVER_API}/getTaskResult",
json={"clientKey": client_key, "taskId": task_id},
timeout=30,
).json()
if result.get("status") == "ready":
token = result.get("solution", {}).get("gRecaptchaResponse")
if not token:
raise RuntimeError("ready result did not contain gRecaptchaResponse")
return token
if result.get("status") == "failed" or result.get("errorId"):
raise RuntimeError(result.get("errorDescription", "CAPTCHA task failed"))
time.sleep(3)
raise TimeoutError("CAPTCHA task exceeded the 120-second deadline")
La entrada de la función es la URL de página verificada y la clave del sitio. La operación crea exactamente una tarea y sondea solo su taskId. La salida es la cadena de token documentada. Las condiciones de detención son explícitas: error de creación de tarea, estado fallido, respuesta lista malformada, tiempo de espera de red o el plazo de 120 segundos. Un reintentó de transporte puede repetir la solicitud HTTP para el mismo resultado de tarea, pero no debe crear en silencio una serie de nuevas tareas cobrables.
Redime tu código de bonificación de CapSolver
¡Aumenta tu presupuesto de automatización instantáneamente!
Usa el código de bonificación CAP26 al recargar tu cuenta de CapSolver para obtener un 5% adicional en cada recarga — sin límites.
Redímelo ahora en tu Panel de CapSolver
La aplicación del token es específica de la página. En una integración autorizada o página de prueba controlada, escriba el token en el campo de respuesta documentado e invoque el camino de devolución de llamada o envío esperado por la página. No copie un token en un nuevo navegador, otra página de producto o un contexto de tienda diferente.
async def apply_recaptcha_token(page, token: str) -> None:
applied = await page.evaluate(
"""
(token) => {
const fields = [...document.querySelectorAll(
'textarea[name="g-recaptcha-response"]'
)];
if (fields.length === 0) return false;
for (const field of fields) {
field.value = token;
field.innerHTML = token;
field.dispatchEvent(new Event('change', { bubbles: true }));
}
return true;
}
""",
token,
)
if not applied:
raise RuntimeError("el campo de respuesta de reCAPTCHA desapareció antes de la aplicación")
Este ejemplo está limitado intencionalmente al campo de respuesta visible en la página actual. Algunas implementaciones también requieren un callback documentado. Inspeccione la página que posee o a la que tiene autorización para probar y conéctese a su contrato de integración real. Nunca invente un nombre de callback. Después de la aplicación, espere a que el widget o la ruta de verificación cambie de estado, luego reanude la acción de inventario una vez.
La verificación del inventario debe vincular el estado observado al producto y tienda solicitados. Un selector que diga "disponible" es insuficiente si la etiqueta de la tienda cambió en silencio o la página del producto redirigió a una variante.
from datetime import datetime, timezone
async def read_inventory(page, expected_sku: str, expected_store: str) -> dict:
sku = (await page.locator('[data-product-sku]').first.get_attribute('data-product-sku'))
store = (await page.locator('[data-store-id]').first.get_attribute('data-store-id'))
label = (await page.locator('[data-inventory-status]').first.inner_text()).strip()
if sku != expected_sku or store != expected_store:
raise RuntimeError("el contexto del producto o tienda cambió durante la recopilación")
normalized = {
"En stock": "en_stock",
"Stock limitado": "limitado",
"Agotado": "agotado",
}.get(label)
if not normalized:
raise RuntimeError(f"etiqueta de inventario no reconocida: {label!r}")
return {
"product_id": sku,
"store_id": store,
"availability": normalized,
"observed_at": datetime.now(timezone.utc).isoformat(),
"verification": "product-store-status",
}
Los selectores son marcadores de posición para una página que controla o tiene permiso para automatizar. La entrada es la página actual más los identificadores esperados. La operación verifica la identidad antes de normalizar la etiqueta. La salida es un registro de inventario verificado. La función se detiene ante elementos faltantes, identificadores cambiados o un estado desconocido. Estas detenciones protegen al sistema de destino de un fallo común: transformar un diseño de página cambiado en un evento falso de agotado.
Para producción, agregue un segundo canal de evidencia cuando esté disponible. Ejemplos incluyen un objeto de producto estructurado, una respuesta XHR iniciada por la página, una etiqueta de tienda del panel de recogida o una verificación de elegibilidad del carrito permitida por su acuerdo. El recolector debe requerir que la evidencia de identidad y disponibilidad coincida, no solicitudes duplicadas simplemente para aumentar la confianza.
Una máquina de estados predecible hace que el flujo de trabajo sea observable y evita la recuperación recursiva.
SCOPED
-> OPEN_PRODUCT
-> CONFIRM_STORE
-> DETECT_CHECKPOINT
-> no challenge: READ_INVENTORY
-> reCAPTCHA v2: CREATE_ONE_TASK
-> ready: APPLY_IN_SAME_SESSION
-> failed/deadline: NEEDS_REVIEW
-> unsupported/ambiguous: NEEDS_REVIEW
-> REPLAY_INVENTORY_ACTION_ONCE
-> VERIFY_PRODUCT + STORE + AVAILABILITY
-> valid: WRITE_RECORD
-> repeated challenge: NEEDS_REVIEW
-> changed context: POLICY_DENIED
El trabajo debe llevar un ID de correlación a través de cada estado. Registre el tiempo de transición y el resultado, pero nunca el token resuelto o la clave del cliente. La FAQ de errores y solución de problemas de CapSolver puede ayudar a los operadores a distinguir entre fallos del proveedor y fallos del navegador y aplicación.
Los síntomas incluyen clave de sitio faltante, una página de verificación inesperada o un widget de familia no reconocida por el adaptador. Capture una captura de pantalla con redacción y el host de nivel superior, luego deténgase. No envíe parámetros adivinados ni trate cada iframe como reCAPTCHA.
Un errorId no nulo, estado fallido, resultado listo mal formado o plazo de sondeo es un fallo en el límite del proveedor. Preserve taskId, descripción de error documentada, tiempo transcurrido y ID de correlación. Vuelva a intentar solo si la clase de error es explícitamente transitoria y el presupuesto restante de tarea lo permite.
El campo de respuesta puede desaparecer porque la página navegó, se volvió a renderizar o cambió el contexto de tienda. No aplique el token a una página de reemplazo automáticamente. Vuelva a ejecutar las verificaciones de alcance y contexto, luego reinicie la verificación de producto único desde un estado limpio o diríjalo a revisión.
El proveedor puede devolver una tarea lista mientras que la página rechaza la solución porque la sesión, el momento de la página, los metadatos del widget o la ruta de callback no coinciden. Clasifíquelo como un fallo de aplicación. Una repetición controlada es suficiente. Si el CAPTCHA se repite, deténgase en lugar de iniciar un bucle.
Si la página carga pero la evidencia de stock está ausente o en conflicto, registre "unknown", no "out_of_stock". Notifique cuando la ambigüedad supere un umbral para un minorista o plantilla, ya que a menudo indica un cambio en la marca en lugar de un evento real de inventario.
La especificación de semántica HTTP ayuda a distinguir el estado de transporte del significado de la aplicación. Un "200 OK" solo describe la respuesta HTTP; no prueba que se haya seleccionado una ubicación, se haya aceptado un CAPTCHA o se haya devuelto el inventario.
La automatización de inventario buena minimiza la recopilación mientras maximiza la confianza. Realice encuestas con una frecuencia justificada por la necesidad comercial y permitida por la fuente. Almacene en caché los metadatos del producto estables. Programa las verificaciones de tienda con jitter dentro de la ventana aprobada, no con solicitudes paralelas estalladas. Use fetches condicionales donde la fuente lo permita y detenga una ejecución cuando la tasa de desafíos o la tasa de error de aplicación aumente inesperadamente.
Siga estos métricos por separado:
No optimice solo por la finalización del solucionador. Una alta tasa de lista con una baja tasa de aceptación de aplicación indica un problema de integración. Una alta tasa de aceptación con una tasa de inventario desconocido en aumento indica un problema del extractor o de la plantilla de página. Las métricas deben orientar a los operadores hacia la capa que posee el fallo.
Cuando los datos generen alertas, deduplique observaciones repetidas y defina una regla de estabilidad. Por ejemplo, notifique en "out_of_stock" solo después de dos verificaciones válidas separadas por el intervalo normal de recopilación, mientras que una transición a "in_stock" puede requerir una observación fresca exitosa. Mantenga la regla visible en la configuración para que los equipos comerciales puedan auditar por qué se envió una alerta.
Pruebe el flujo contra páginas que posea o que esté explícitamente autorizado a automatizar. Use fixtures para estados de inventario ordinarios y una integración de CAPTCHA controlada para pruebas de recuperación.
createTask y confirme que no se escriba ningún registro de inventario.processing hasta el plazo y confirme que solo se haya creado una tarea.gRecaptchaResponse y confirme que falle la validación de esquema.needs_review.La guía para elegir una API de resolución de CAPTCHA proporciona criterios adicionales de evaluación, pero la prueba de aceptación para este caso de uso permanece específico del negocio: el sistema debe devolver el producto correcto, la tienda correcta y la disponibilidad correcta después de una recuperación acotada.
La recopilación de datos de inventario de tienda se vuelve confiable cuando el manejo de CAPTCHA se trata como un estado controlado dentro de un flujo de trabajo verificado de comercio minorista. Preserve el contexto del producto y tienda, cree una tarea documentada, aplique la solución en la misma sesión autorizada, replique la acción de inventario una vez y publique los datos solo después de que pasen las verificaciones de identidad y disponibilidad. CapSolver proporciona la infraestructura de tarea de CAPTCHA; su recolector sigue siendo responsable del alcance, límites de frecuencia, calidad de datos y condiciones de detención.
P: ¿Cuál es la salida mínima para la recopilación de datos de inventario de tienda?
La salida mínima confiable contiene un ID de producto canónico, ID de tienda o región, disponibilidad normalizada, hora de observación y la evidencia utilizada para verificar el estado. Una página en blanco o un punto de control fallido nunca debe convertirse en "agotado".
P: ¿Por qué debe preservarse la misma sesión de navegador durante la recuperación de CAPTCHA?
La misma sesión preserva la página, cookies, selección de producto, selección de tienda y ciclo de vida del widget asociado al punto de control. Mover el resultado a otro contexto puede causar rechazo o asociar la observación a la tienda equivocada.
P: ¿Cuántos intentos de CAPTCHA debe realizar un trabajo de inventario?
Use un pequeño presupuesto explícito: una tarea y una repetición controlada es un valor predeterminado práctico. Un desafío repetido debe ingresar a needs_review para que la integración pueda inspeccionarse sin un bucle costoso o disruptivo.
P: ¿Prueba una tarea lista de CapSolver que el inventario se haya recopilado?
No. Una tarea lista prueba solo que el proveedor devolvió una solución. El navegador debe aceptarla, y la aplicación aún debe devolver un producto, tienda y estado de inventario reconocidos.
P: ¿Puede este flujo recopilar inventario de portales privados de minoristas?
Solo cuando el propietario del portal haya autorizado explícitamente esa automatización y el flujo cumpla con el acuerdo aplicable y la ley. La capacidad técnica no otorga permiso para acceder a datos privados, restringidos, sensibles o no autorizados.
Aprende una arquitectura de raspado web escalable en Rust con reqwest, scraper, raspado asíncrono, raspado con navegador sin cabeza, rotación de proxies y manejo de CAPTCHA conforme.

Automatiza la resolución de CAPTCHA con Nanobot y CapSolver. Utiliza Playwright para resolver reCAPTCHA y Cloudflare autónomamente.
