// docs / rest api
REST API
Bearer-authenticated JSON API for scan automation, scan status, and findings. Passive scans are available through REST; active scans are available for paid plans only after the domain is verified and explicitly authorized in the dashboard.
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/scansEnqueues a passive scan by default. For verified domains with active authorization, paid plans can request active mode. Returns immediately with a queued scan id; poll GET /api/v1/scans/[scanId] until 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.
