
Aloísio Vítor
Image Processing Expert
Publicado Oct 23, 2026
Actualizado Oct 23, 2026 · min de lectura

Un navegador autohospedado puede navegar hasta la página correcta y aun así dejar tu flujo de trabajo detenido en un CAPTCHA. Si ejecutas Steel localmente, agregar el indicador de resolución del servicio en la nube no es suficiente: las implementaciones local y en la nube tienen capacidades diferentes.
Esta guía muestra dónde encaja un resolvedor de CAPTCHA en Steel Browser autohospedado, con una pequeña verificación de conexión en Python. El ejemplo usa una página de desarrollo local y la clave pública de prueba de reCAPTCHA de Google. No se dirige a un sitio web de terceros ni requiere un modelo de IA.
Steel Browser es una API de navegador para desarrolladores que construyen agentes web y aplicaciones de automatización. Gestiona una sesión de navegador que los clientes pueden controlar mediante herramientas de automatización conocidas. El repositorio oficial de Steel documenta el autohospedaje y las conexiones desde Playwright, Puppeteer y Selenium.
Para un desarrollador que ejecuta un flujo de trabajo de formulario autorizado, la división del trabajo es directa. Steel suministra el navegador. Playwright navega e interactúa con la página. Un resolvedor de CAPTCHA gestiona un desafío compatible cuando aparece. Tu flujo de trabajo luego comprueba si la aplicación aceptó la acción prevista.
Este tutorial utiliza el SDK CapSolver Core para ese paso de CAPTCHA. El SDK puede inspeccionar una página de Playwright y exponer una operación de resolución separada. No hay necesidad de añadir un LLM solo para conectar estos componentes.
El caso útil es un trabajo de navegador autohospedado que ya necesita una operación de CAPTCHA. Para pruebas rutinarias de software que te pertenece, la configuración de prueba del proveedor de CAPTCHA puede ser suficiente. Usa la ruta del resolvedor cuando tu flujo de trabajo autorizado realmente lo necesite, en lugar de hacer que cada navegación del navegador dependa de una solicitud de pago.
Steel Local no incluye la resolución de CAPTCHA incorporada del producto en la nube. La matriz de características local versus nube de Steel distingue explícitamente ambas implementaciones.
Esa distinción afecta a la implementación. Un tutorial de la nube puede habilitar la resolución durante la creación de la sesión, mientras que una integración autohospedada debe aportar la operación que falta. No asumas que un campo de configuración de la nube activa una función en el servidor local.
La ruta usada aquí es:
websocketUrl de esa sesión.Evita lanzar un navegador independiente en el paso tres. Un segundo navegador no sería la sesión devuelta por Steel, lo que hace fácil inspeccionar una página mientras tu trabajo real espera en otra.
Empieza con una instancia dedicada y en ejecución de Steel Local y Python 3.12. La configuración verificada usó Steel API 0.5.3 desde la revisión de repositorio 8362bbd, Playwright 1.64.0 y capsolver-core 0.1.1 en macOS.
Sigue las instrucciones de configuración local del repositorio para tu implementación. Para el servidor basado en código fuente utilizado aquí, la API se inició con HOST=127.0.0.1, PORT=3300 y CDP_REDIRECT_PORT=9323. Estos son los puertos elegidos para el entorno de prueba, no valores predeterminados obligatorios. Mantén tu API de desarrollo accesible solo desde el cliente previsto.
Instala las dependencias de Python en un entorno aislado:
python -m pip install "playwright==1.64.0" "capsolver-core==0.1.1" "httpx==0.28.1"
Steel inicia el navegador, por lo que este cliente no lanza otra instancia de Chromium. El método de conexión CDP de Playwright se adjunta a un navegador basado en Chromium existente y expone su contexto predeterminado.
El cliente también necesita acceso a la dirección WebSocket devuelta. Si Steel se ejecuta en un contenedor o en otra máquina, confirma que la dirección sea accesible desde Python; 127.0.0.1 se refiere a la máquina que realiza la conexión.
No se necesita una credencial de CapSolver para la comprobación de detección de abajo. La resolución real requiere tu propia clave de API válida y recursos de cuenta. La resolución de pago, la escritura de tokens de vuelta y la aceptación por parte de la aplicación no se ejecutaron para esta guía. Mantén ese paso de validación separado en tu lista de comprobaciones de despliegue.
El script crea una sesión real de Steel, se conecta a su navegador y lee un widget de desarrollo mediante el SDK oficial. Guárdalo como steel_sdk_check.py y ejecútalo con Python.
El ejemplo usa por defecto un servidor local en el puerto 3300. Define STEEL_URL si tu servidor usa otra dirección. Usa una instancia dedicada: la creación y liberación de sesión cambian la sesión de navegador activa de esa instancia.
La página se suministra mediante una ruta de Playwright, por lo que no se necesita un servidor web en el puerto 8765. El script del widget de Google aún requiere acceso a la red. La clave de sitio pública está documentada en la guía de pruebas de reCAPTCHA de Google y está pensada para desarrollo, no producción.
import asyncio
import json
import os
import httpx
from capsolver_core import create_capsolver
from playwright.async_api import async_playwright
STEEL_URL = os.environ.get("STEEL_URL", "http://127.0.0.1:3300")
TEST_URL = "http://127.0.0.1:8765/"
HTML = """<!doctype html><html><head><title>Steel CAPTCHA check</title></head>
<body><h1>Owned development page</h1>
<div class="g-recaptcha" data-sitekey="6LeIxAcTAAAAAJcZVRqyHh71UMIEGNQ_MXjiZKhI"></div>
<script src="https://www.google.com/recaptcha/api.js" async defer></script>
</body></html>"""
async def main():
async with httpx.AsyncClient(base_url=STEEL_URL, timeout=90) as api:
response = await api.post("/v1/sessions", json={"headless": True})
response.raise_for_status()
session = response.json()
try:
async with async_playwright() as playwright:
browser = await playwright.chromium.connect_over_cdp(session["websocketUrl"])
try:
context = browser.contexts[0]
page = await context.new_page()
await page.route(TEST_URL, lambda route: route.fulfill(
content_type="text/html", body=HTML))
await page.goto(TEST_URL)
await page.wait_for_function(
"() => !!window.___grecaptcha_cfg && "
"Object.keys(window.___grecaptcha_cfg.clients || {}).length > 0",
timeout=30000)
async with create_capsolver() as cap:
infos = await cap.get_captcha_info(page)
result = [{"type": info.type.value,
"url": info.website_url,
"site_key": info.website_key} for info in infos]
print(json.dumps({"session_id": session["id"],
"captcha_parameters": result}))
assert result and result[0]["type"] == "reCaptchaV2"
finally:
await browser.close()
finally:
released = await api.post(f"/v1/sessions/{session['id']}/release")
released.raise_for_status()
print(json.dumps({"released": released.json().get("success")}))
if __name__ == "__main__":
asyncio.run(main())
La comprobación ejecutada devolvió un descriptor reCaptchaV2 con la URL de la página local y la clave pública de prueba del sitio. La respuesta final de liberación devolvió true. Estas observaciones verifican la sesión real de Steel, la conexión CDP, el acceso a la página y la ruta de lectura de parámetros del SDK.
No establecen que se resolviera un CAPTCHA de pago. La clave de desarrollo no es un desafío de producción y el script deliberadamente no solicita ningún token de solución.
El código mantiene la página en el contexto de navegador existente de Steel. Su limpieza cierra la conexión del cliente y pide al servidor que libere la sesión incluso si la detección falla. Si lo adaptas a un servicio compartido, da a un componente la responsabilidad de la vida de la sesión en lugar de permitir que trabajos no relacionados liberen el trabajo de otros.
Añade la llamada de resolución después de que la página de tu aplicación autorizada haya cargado su CAPTCHA compatible, mientras la conexión del navegador y el cliente del SDK siguen abiertos. Sustituye el elemento de desarrollo local por el flujo de trabajo de tu propia aplicación; no uses la clave de prueba como entrada de producción.
Crea el cliente del SDK con la opción documentada api_key, cargando la credencial desde tu configuración de secretos aprobada. CapSolver gestiona la solicitud de desafío; Steel sigue siendo propietario de la sesión de navegador.
La siguiente línea es la llamada oficial intacta en modo navegador. Requiere una clave de API configurada, y la ejecución de pago a través de esta conexión Steel no se probó en este tutorial:
results = await cap.solve_on_page(page)
Mantén la llamada dentro del contexto de cliente activo. Pegarla después de la limpieza del ejemplo se referiría a un navegador y cliente cerrados.
Inspecciona cada resultado devuelto antes de continuar. El SDK informa de un error, una posible solution y si se produjo escritura de vuelta mediante filled. Un resultado vacío o una solución ausente no son evidencia de que tu aplicación haya superado su CAPTCHA.
El modo de token documentado del Core SDK cubre reCAPTCHA v2/v3 y Cloudflare Turnstile. No asumas que la misma llamada resuelve todos los tipos de desafíos enumerados en el resto de la API de CapSolver. La documentación de tareas de reCAPTCHA v2 proporciona los requisitos específicos de tarea para esa ruta compatible.
El flujo de trabajo solo está completo cuando la aplicación alcanza su estado previsto. Una respuesta de token, un campo rellenado y un envío de formulario exitoso son observaciones distintas.
Para una aplicación que controlas, elige una señal de éxito concreta, como su mensaje de confirmación o la respuesta esperada. Espera esa señal tras la acción normal del formulario. Si no aparece, inspecciona la respuesta de la aplicación en lugar de enviar solicitudes de resolución repetidas sin entender el fallo.
Mantén la identidad de la página estable durante la operación. No navegues fuera, cierres la pestaña ni liberes la sesión mientras una resolución está en curso. Si la aplicación recarga el widget, inspecciona de nuevo el desafío actual en lugar de reutilizar parámetros de un estado anterior de la página.
El glosario de CAPTCHA explica el concepto de verificación, mientras que la guía sobre tokens y cookies de CAPTCHA ayuda a distinguir diferentes salidas. Ni una cookie de navegador ni una cadena de token deben sustituir la comprobación de éxito de tu aplicación.
Empieza a solucionar problemas en la operación fallida más temprana para que los problemas de conexión no se conviertan en solicitudes de resolución innecesarias.
| Síntoma | Qué comprobar |
|---|---|
| Fallo al crear la sesión | Confirma que la API de Steel se esté ejecutando e inspecciona el estado HTTP y el registro del servidor. |
| Fallo en la conexión CDP | Comprueba que websocketUrl sea accesible desde el proceso de Python y que pertenezca a la sesión actual. |
| El widget nunca se inicializa | Comprueba el acceso del navegador al script de desarrollo de Google y confirma que se cargó la página esperada. |
| La detección no devuelve descriptores | Inspecciona la página actual y el tipo de CAPTCHA compatible antes de intentar una resolución de pago. |
| Se devuelve una solución pero el flujo de trabajo se bloquea | Comprueba la escritura de vuelta, la acción normal de la aplicación y la respuesta de la aplicación. |
| Otro trabajo pierde su sesión de navegador | Revisa la propiedad de las sesiones y las llamadas de liberación antes de compartir la instancia local. |
Mantén pequeños los registros de diagnóstico. Registra la etapa y un error redactado, no claves de API, tokens de respuesta ni el almacenamiento completo del navegador. Prueba primero una sola página y añade comportamiento de reintento solo después de identificar un fallo temporal que razonablemente pueda arreglar un reintento.
Una integración de Steel Local necesita una transferencia clara desde la página de navegador gestionada a la operación de CAPTCHA. La comprobación de conexión funcional establece esa transferencia sin hacer una solicitud de pago. Antes de usarla en producción, valida la resolución con tu propia credencial y verifica el resultado de la aplicación en un entorno autorizado.
Mantén la sesión abierta para el trabajo que posee y libérala cuando ese trabajo termine. Esto te da un límite útil tanto para la solución de problemas como para futuras actualizaciones de paquetes.
Conecta CapSolver en el paso de CAPTCHA compatible dentro de tu flujo de trabajo con Steel. Empieza con la ruta de detección verificada y después valida tu operación con credenciales antes de aumentar la carga de trabajo.
Prueba CapSolver. Usa el código de bonificación CAP26 para un 5% de bonificación bajo las condiciones de la campaña.

P: ¿Steel Browser autohospedado resuelve CAPTCHAs automáticamente?
No. La comparación oficial de Steel no lista resolución de CAPTCHA incorporada para Steel Local. La función de resolución del producto en la nube es una capacidad separada.
P: ¿Necesito una cuenta de Steel Cloud para este ejemplo?
No. El ejemplo se conecta a una instancia local en ejecución. Tú sigues siendo responsable de iniciar y operar esa instancia.
P: ¿Por qué conectarse por CDP en lugar de lanzar Chromium de Playwright?
CDP conecta Python al navegador gestionado por Steel. Lanzar otro navegador crearía una sesión separada de la que este ejemplo pretende usar.
P: ¿La comprobación de detección gasta créditos de CapSolver?
La verificación solo lee parámetros del widget y no realiza ninguna solicitud de resolución de pago. La llamada de resolución separada requiere una credencial válida de CapSolver.
P: ¿Se ha probado aquí todo el flujo de resolución de pago?
No. La ejecución real verificó la creación de la sesión, la conexión CDP, la detección del SDK y la liberación. La resolución de pago, el rellenado de datos y la aceptación por parte de la aplicación aún requieren una prueba separada con credenciales.
P: ¿Es esto una asociación oficial con Steel o una integración nativa?
No. Este es un ejemplo de conexión probado que utiliza la interfaz pública del navegador de Steel y el SDK oficial de CapSolver. No establece una asociación ni una garantía de compatibilidad para futuras versiones.

Aloísio Vítor
Image Processing Expert
Interpreting the visual signals behind web workflows.
SOBRE EL AUTOR
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.
