Una API de web scraping se encarga de las partes difíciles de recopilar páginas web por ti: elige el proxy, ejecuta el navegador cuando una página lo necesita, reintenta los fallos y te devuelve el HTML o los datos que has pedido. Envías una sola solicitud con una URL; el servicio se ocupa de todo lo que hay entre tú y el sitio.
Este tutorial te lleva desde tu primera solicitud hasta un pequeño scraper fiable, usando la Web Scraping API de Shifter como ejemplo. Los pasos y patrones son los mismos para la mayoría de servicios de este tipo. Si antes quieres conocer el contexto de lo que ocurre detrás de la solicitud, nuestro artículo explicativo sobre cómo funciona una web scraping API lo cubre.
Paso 1: consigue una clave de API
Cada solicitud se autentica con una clave de API. En el panel de Shifter, abre Web Scraping API, luego API Keys, y copia una clave activa.
Mantén la clave fuera de tu código. Guárdala en una variable de entorno, para que nunca acabe en un repositorio o una captura de pantalla:
export SHIFTER_SCRAPER_KEY="your-key-here"
Paso 2: haz tu primera solicitud
La API es un único endpoint, https://scrape.shifter.io/v1. Pasa tu clave y la página que quieres como parámetros de consulta:
curl "https://scrape.shifter.io/v1?api_key=$SHIFTER_SCRAPER_KEY&url=https://example.com"
La respuesta es el HTML de la página, obtenido a través de los proxies de la API. Eso es todo lo que necesita una solicitud básica.
Paso 3: activa el renderizado de JavaScript cuando la página lo necesite
Muchos sitios modernos envían una página casi vacía y construyen el contenido en el navegador con JavaScript. Si el HTML que recibes no tiene los datos que puedes ver en tu navegador, añade render_js=1. La API entonces carga la página en un navegador headless y devuelve el resultado renderizado. En Shifter, una solicitud renderizada cuesta lo mismo que una normal.
Dos ajustes relacionados ayudan con las páginas lentas:
wait_for_cssespera hasta que aparece un elemento específico antes de devolver la respuesta, de modo que no recibas la página antes de que sus datos se hayan cargado.timeoutda más tiempo a los sitios lentos.
El renderizado es más lento que una obtención normal, así que úsalo solo para páginas que lo necesiten. Nuestra guía sobre scraping de sitios con mucho JavaScript explica cómo detectarlo.
Paso 4: obtén JSON en lugar de HTML
Analizar el HTML tú mismo es donde fallan la mayoría de los scrapers. En su lugar, describe los campos que quieres con extract_rules: un objeto JSON que relaciona cada nombre de campo con un selector CSS y lo que debe devolver de él.
output | Devuelve |
|---|---|
text | El texto del elemento |
html | El HTML interno del elemento |
@href, @src y similares | El valor de un atributo |
Por ejemplo, {"title": {"selector": "h1", "output": "text"}} devuelve {"title": "Example Domain"} para example.com. Muchas páginas también incrustan sus datos como JSON estructurado de forma nativa; nuestra guía sobre extraer JSON-LD en lugar de analizar HTML muestra cómo usarlo.
Paso 5: gestiona los errores correctamente
Todo scraper se encuentra con fallos: sitios lentos, páginas que no renderizan, demasiadas solicitudes a la vez. La API te indica qué ha ido mal con el código de estado, y la respuesta correcta depende de cuál recibas:
| Estado | Significado | Qué hacer |
|---|---|---|
200 | Éxito | Usa la respuesta |
400, 401, 403 | Un problema con tu solicitud, clave o funciones del plan | Corrígelo; reintentar no ayudará |
408 | El sitio de destino agotó el tiempo de espera | Reintenta, quizá con un timeout más alto |
422 | La página no se pudo renderizar | Reintenta; comprueba que el sitio funciona en un navegador normal |
429 | Demasiadas solicitudes simultáneas para tu plan | Espera, luego reintenta |
500 | Un error interno | Reintenta tras una breve pausa |
En Shifter, las solicitudes fallidas no se cobran; pagas un crédito por cada respuesta exitosa. La API también reintenta internamente algunos fallos antes de responder, y esos cuentan como una sola llamada.
Juntándolo todo
Aquí tienes un pequeño asistente en Python que envuelve los cinco pasos: lee la clave del entorno, añade renderizado y extracción cuando se lo pides, reintenta los errores que merece la pena reintentar con una pausa creciente, y se detiene de inmediato en los que necesitan una corrección.
import json
import os
import time
import requests
API = "https://scrape.shifter.io/v1"
RETRY = {408, 422, 429, 500} # worth another try after a pause
STOP = {400, 401, 403} # fix the request; retrying will not help
def scrape(url, render_js=False, extract_rules=None, attempts=3, session=None, wait=2.0):
"""Fetch one page through the Web Scraping API; returns text, or parsed JSON with extract_rules."""
session = session or requests.Session()
params = {"api_key": os.environ["SHIFTER_SCRAPER_KEY"], "url": url}
if render_js:
params["render_js"] = 1
if extract_rules:
params["extract_rules"] = json.dumps(extract_rules)
for attempt in range(1, attempts + 1):
response = session.get(API, params=params, timeout=120)
if response.status_code == 200:
return response.json() if extract_rules else response.text
if response.status_code in STOP or attempt == attempts or response.status_code not in RETRY:
raise RuntimeError(f"{url}: HTTP {response.status_code} {response.text[:200]}")
time.sleep(wait * attempt) # back off a little more each time
Usándolo:
from scrape_api import scrape
html = scrape("https://example.com")
data = scrape("https://example.com", extract_rules={"title": {"selector": "h1", "output": "text"}})
print(data["title"])
Hemos probado la construcción de solicitudes, los reintentos y las condiciones de parada del asistente frente a respuestas simuladas para cada uno de los códigos de estado anteriores.
Si eres nuevo en la lógica de reintentos, nuestra guía sobre reintentos y backoff para scrapers web explica por qué la pausa crece con cada intento.
Paso 6: escala
Una vez que las solicitudes individuales funcionan, tres cosas importan a medida que creces:
- Concurrencia. Envía varias solicitudes a la vez con un pool de hilos o un cliente asíncrono. Cada plan tiene un límite de concurrencia (de 20 a 500 solicitudes a la vez en Shifter, según el plan); mantente por debajo de él y trata el
429como una señal para ir más despacio. - Ubicación y tipo de proxy. Usa el parámetro
countrypara obtener una página tal como aparece en un país concreto. En los planes Growth y superiores,premium_proxyenruta las solicitudes a través de IPs residenciales para sitios que bloquean el tráfico de centros de datos. - Sesiones. Para flujos de varios pasos, un
session_idmantiene la misma IP y las mismas cookies entre solicitudes.
Cuando los datos empiezan a fluir, guárdalos en algún lugar donde puedas consultarlos. Nuestra guía sobre llevar datos de una web scraping API a SQL cubre un flujo limpio desde la respuesta hasta la tabla.
Errores comunes de principiantes
- Codificar la clave de API directamente. Usa una variable de entorno o un gestor de secretos.
- Renderizarlo todo. Prueba primero con una solicitud normal; renderiza solo las páginas que lo necesiten.
- Reintentarlo todo. Un
401fallará siempre. Reintenta solo los errores que puedan tener éxito más tarde. - Analizar el HTML a mano. Usa reglas de extracción o JSON incrustado cuando puedas.
- Ignorar los límites de concurrencia. Demasiadas solicitudes en paralelo producen
429, no velocidad.
Preguntas frecuentes
¿Qué es una web scraping API?
Un servicio que obtiene páginas web por ti a través de sus propios proxies y navegadores, gestiona los reintentos y bloqueos, y devuelve el HTML o los datos extraídos en respuesta a una única solicitud.
¿Necesito saber programar para usar una web scraping API?
Un poco. Una sola solicitud funciona desde la línea de comandos con curl, pero la mayoría de proyectos reales usan un pequeño script en Python u otro lenguaje para enviar solicitudes, gestionar errores y almacenar los resultados.
¿Cuándo debería activar el renderizado de JavaScript?
Cuando el HTML devuelto sin renderizar carece de contenido que puedes ver en tu navegador. Muchos sitios construyen sus páginas con JavaScript, y el renderizado devuelve la página tal como la mostraría un navegador.
¿Las solicitudes fallidas cuestan créditos?
En Shifter, no. Se te cobra un crédito por cada respuesta exitosa, y las solicitudes fallidas, incluidos los errores del sitio de destino, son gratuitas.
En resumen
Usar una web scraping API se reduce a unos pocos hábitos: mantén la clave en el entorno, empieza con solicitudes normales y añade el renderizado solo donde sea necesario, pide JSON con reglas de extracción en lugar de analizar HTML, reintenta solo los errores que puedan tener éxito más tarde, y respeta la concurrencia de tu plan. El asistente anterior cubre todo esto en unas veinte líneas. Los planes y límites están en la página de precios de Web Scraping API.