Cambiar del nivel gratuito de Brave Search API a Scavio requiere aproximadamente 15 minutos de cambios de código y elimina el límite de 2000 consultas/mes que bloquea la mayoría de las cargas de trabajo de producción. Este tutorial lo guía paso a paso a través de la migración: asignar campos de respuesta de Brave a equivalentes de Scavio, actualizar sus llamadas HTTP, ajustar el manejo de errores y validar que su lógica descendente funcione con el nuevo formato de respuesta.
Requisitos previos
- Integración existente de Brave Search API que desea migrar
- Clave API de Scavio (250 créditos gratuitos al mes en scavio.dev)
- Python 3.9+ o Node.js 18+
Guia paso a paso
Paso 1: Audite su uso actual de Brave Search
Antes de migrar, audite cómo llama actualmente a Brave API. Tenga en cuenta el punto final, los encabezados, los parámetros de consulta y los campos de respuesta que utiliza realmente su código. La mayoría de las integraciones solo utilizan el título, la URL y la descripción de los resultados de búsqueda web, lo que facilita la migración.
# Typical Brave Search API call you are replacing
import requests
BRAVE_API_KEY = 'your_brave_key'
resp = requests.get(
'https://api.search.brave.com/res/v1/web/search',
headers={'X-Subscription-Token': BRAVE_API_KEY},
params={'q': 'best crm for startups 2026', 'count': 10}
)
data = resp.json()
for result in data.get('web', {}).get('results', []):
print(result['title'], result['url'], result.get('description', ''))Paso 2: Asignar campos de respuesta de Brave a equivalentes de Scavio
Scavio devuelve resultados en una matriz orgánica en lugar de web.results. Los nombres de los campos difieren ligeramente: Brave usa una descripción mientras que Scavio usa un fragmento. Cree un mapeo para que pueda actualizar todas las referencias de una sola vez.
# Field mapping: Brave -> Scavio
# data.web.results -> data.organic
# result.title -> item.title (same)
# result.url -> item.url (same)
# result.description -> item.snippet
# result.extra_snippets -> (not applicable)
# params.q -> json body: query
# params.count -> json body: num
# header X-Subscription-Token -> header x-api-keyPaso 3: Reemplazar la llamada API
Cambie la solicitud Brave GET por una solicitud POST de Scavio. La API de Scavio utiliza un cuerpo JSON en lugar de parámetros de consulta y un encabezado x-api-key en lugar de X-Subscription-Token.
import requests
SCAVIO_API_KEY = 'your_scavio_api_key'
def search(query, num=10):
resp = requests.post(
'https://api.scavio.dev/api/v1/search',
headers={'x-api-key': SCAVIO_API_KEY},
json={'query': query, 'num': num}
)
resp.raise_for_status()
data = resp.json()
return [
{
'title': item.get('title', ''),
'url': item.get('url', ''),
'description': item.get('snippet', ''),
}
for item in data.get('organic', [])
]Paso 4: Actualizar el manejo de errores y los límites de velocidad
Brave devuelve 429 cuando alcanzas el límite de nivel gratuito. Scavio devuelve códigos de error HTTP estándar e incluye encabezados de límite de velocidad. Actualice su lógica de reintento para leer el encabezado restante de x-ratelimit y retroceda antes de alcanzar el límite en lugar de después.
import time
def search_with_retry(query, num=10, max_retries=3):
for attempt in range(max_retries):
resp = requests.post(
'https://api.scavio.dev/api/v1/search',
headers={'x-api-key': SCAVIO_API_KEY},
json={'query': query, 'num': num}
)
if resp.status_code == 200:
return resp.json()
if resp.status_code == 429:
wait = 2 ** attempt
print(f'Rate limited, waiting {wait}s...')
time.sleep(wait)
continue
resp.raise_for_status()
raise Exception('Max retries exceeded')Paso 5: Validar la paridad de salida
Ejecute ambas API en paralelo en una muestra de consultas y compare los resultados para verificar que su lógica descendente funcione correctamente. Verifique que los títulos, las URL y las descripciones estén completos y que su código de análisis maneje el nuevo formato sin errores.
test_queries = [
'best crm for startups 2026',
'python web scraping tutorial',
'saas pricing page examples',
]
for q in test_queries:
results = search(q, num=5)
print(f'Query: {q}')
print(f' Results: {len(results)}')
for r in results:
assert r['title'], 'Missing title'
assert r['url'], 'Missing url'
print(f' - {r["title"][:60]}')
print()Ejemplo en Python
import requests
import time
SCAVIO_API_KEY = 'your_scavio_api_key'
def search(query, num=10, max_retries=3):
for attempt in range(max_retries):
resp = requests.post(
'https://api.scavio.dev/api/v1/search',
headers={'x-api-key': SCAVIO_API_KEY},
json={'query': query, 'num': num}
)
if resp.status_code == 200:
data = resp.json()
return [
{
'title': item.get('title', ''),
'url': item.get('url', ''),
'description': item.get('snippet', ''),
}
for item in data.get('organic', [])
]
if resp.status_code == 429:
time.sleep(2 ** attempt)
continue
resp.raise_for_status()
raise Exception('Max retries exceeded')
# Validate migration
test_queries = [
'best crm for startups 2026',
'python web scraping tutorial',
'saas pricing page examples',
]
for q in test_queries:
results = search(q, num=5)
print(f'Query: {q} -> {len(results)} results')
for r in results:
print(f' {r["title"][:60]}')Ejemplo en JavaScript
const SCAVIO_API_KEY = 'your_scavio_api_key';
async function search(query, num = 10, maxRetries = 3) {
for (let attempt = 0; attempt < maxRetries; attempt++) {
const resp = await fetch('https://api.scavio.dev/api/v1/search', {
method: 'POST',
headers: { 'x-api-key': SCAVIO_API_KEY, 'Content-Type': 'application/json' },
body: JSON.stringify({ query, num }),
});
if (resp.ok) {
const data = await resp.json();
return (data.organic || []).map(item => ({
title: item.title || '',
url: item.url || '',
description: item.snippet || '',
}));
}
if (resp.status === 429) {
await new Promise(r => setTimeout(r, 2 ** attempt * 1000));
continue;
}
throw new Error(`API error: ${resp.status}`);
}
throw new Error('Max retries exceeded');
}
async function main() {
const testQueries = [
'best crm for startups 2026',
'python web scraping tutorial',
'saas pricing page examples',
];
for (const q of testQueries) {
const results = await search(q, 5);
console.log(`Query: ${q} -> ${results.length} results`);
for (const r of results) {
console.log(` ${r.title.slice(0, 60)}`);
}
}
}
main();Salida esperada
Query: best crm for startups 2026 -> 5 results
The 10 Best CRMs for Startups in 2026 - Detailed Comparison
...
Query: python web scraping tutorial -> 5 results
...
Query: saas pricing page examples -> 5 results
...