// docs / rest api
REST API
JSON API autenticado por el portador para la automatización del escaneo, el estado del escaneo y los hallazgos. Los escaneos pasivos están disponibles a través de REST; Los escaneos activos están disponibles para planes pagos solo después de que el dominio esté verificado y autorizado explícitamente en el panel.
Autenticación
Cada solicitud debe llevar un token Bearer en el header Authorization. Los tokens se emiten desde Account → API tokens; el texto plano se te muestra exactamente una vez al crearlos. Revocar un token devuelve 401 en la siguiente llamada.
curl -H "Authorization: Bearer fxv_..." \
https://fixvibe.app/api/v1/scansFormato del token: fxv_ seguido de 43 caracteres base64url. Se almacena en reposo como hash SHA-256; el texto plano nunca se persiste del lado del servidor.
Límites de tasa
Dos ventanas en cada solicitud autenticada: ráfaga de 10 req/sec y estado estable de 60 req/min, ambas asociadas al hash Bearer. La aplicación de cuotas (topes de escaneos por mes) se suma encima; consulta Cuotas y límites.
Paginación
Los endpoints de lista (/api/v1/scans, /api/v1/findings) usan paginación basada en cursor con clave (created_at, id) en orden descendente. Pasa ?cursor=<next_cursor> para obtener la siguiente página. El cursor sigue siendo correcto con escrituras concurrentes (sin desviación por OFFSET).
Formatos de error
Cada error es un objeto JSON con al menos una clave error.
{ "error": "invalid_token" } // 401
{ "error": "forbidden" } // 403
{ "error": "not_found" } // 404
{ "error": "quota_exceeded", "quota": {...} } // 429
{ "error": "rate_limited", "retry_after_seconds": 47 } // 429
{ "error": "invalid_input", "issues": [...] } // 400Endpoints
Iniciar un escaneo
/api/v1/scansPone en cola un análisis pasivo de forma predeterminada. Para dominios verificados con autorización activa, los planes pagos pueden solicitar el modo activo. Regresa inmediatamente con una identificación de escaneo en cola; encuesta GET /api/v1/scans/[scanId] hasta status === "completed".
curl -X POST https://fixvibe.app/api/v1/scans \
-H "Authorization: Bearer fxv_..." \
-H "content-type: application/json" \
-d '{"target":"https://staging.example.com"}'// respuesta 200
{
"id": "8f1c4e2a-8c3a-4b6f-9c0d-9b1e8f3c2a4d",
"status": "queued",
"target": "https://staging.example.com",
"mode": "passive"
}Listar tus escaneos
/api/v1/scansDevuelve los escaneos de la org vinculada al token que llama, del más nuevo al más antiguo. Pagina con ?cursor=. Límite predeterminado 50, máximo 100.
curl -H "Authorization: Bearer fxv_..." \
"https://fixvibe.app/api/v1/scans?limit=25"// respuesta 200
{
"scans": [
{
"id": "8f1c4e2a-...",
"target_url": "https://staging.example.com",
"target_hostname": "staging.example.com",
"mode": "passive",
"status": "completed",
"started_at": "2026-05-07T14:00:00Z",
"completed_at": "2026-05-07T14:00:23Z",
"findings_count": { "critical": 1, "high": 3, "medium": 7, "low": 2, "info": 4 },
"triggered_by": "api",
"created_at": "2026-05-07T14:00:00Z"
}
],
"next_cursor": "2026-05-07T14:00:00Z:8f1c4e2a-..."
}Obtener un escaneo
/api/v1/scans/{scanId}Devuelve el sobre del escaneo + resumen de severidad por categoría de forma predeterminada. Pasa ?include_findings=true para obtener el informe completo (grande en escaneos ruidosos; prefiere el endpoint de hallazgos con filtros).
curl -H "Authorization: Bearer fxv_..." \
https://fixvibe.app/api/v1/scans/8f1c4e2a-8c3a-4b6f-9c0d-9b1e8f3c2a4dListar hallazgos
/api/v1/findingsLista filtrable de hallazgos en todos los escaneos de la org que llama. Filtros: severity=critical,high, check_id=secrets.patterns, since=2026-04-01T00:00:00Z. Paginada por cursor.
curl -H "Authorization: Bearer fxv_..." \
"https://fixvibe.app/api/v1/findings?severity=critical,high&limit=50"// respuesta 200
{
"findings": [
{
"id": "...",
"scan_id": "...",
"check_id": "secrets.js-bundle-sweep",
"severity": "critical",
"title": "Supabase service role key exposed in JS bundle",
"description": "...",
"evidence": { ... },
"remediation": "...",
"cwe_id": "CWE-798",
"created_at": "2026-05-07T14:00:23Z"
}
],
"next_cursor": null
}Especificación OpenAPI
Especificación legible por máquina en /docs/api/openapi (text/yaml). Pásala a tu generador de código favorito (openapi-typescript, openapi-python-client o cualquier toolchain OpenAPI 3.1) para clientes tipados.
