Guía · API de placas

Cómo integrar una API de placas de Ecuador

Publicado el

Una API de placas permite incorporar datos básicos de un vehículo a una aplicación de flotas, seguros, compraventa o verificación documental sin obligar a tu equipo a consultar cada placa manualmente.

En esta guía integraremos la ficha básica del vehículo. El ejemplo evita datos personales y muestra cómo normalizar la placa, autenticar la solicitud, leer el JSON y responder ante errores temporales.

Qué endpoint usar para una consulta vehicular

Usa GET /api/v1/placas/{placa}/vehiculo para obtener marca, modelo, año, color, clase, servicio y fechas de matriculación disponibles. Es un buen punto de partida cuando no necesitas información adicional.

La documentación también presenta endpoints separados para otras consultas vehiculares. Selecciona solo los datos que correspondan a tu producto y a la finalidad informada al usuario.

Cómo preparar la placa y la API key

  • Genera una API key y mantenla como variable de entorno en el backend.
  • Convierte la placa a mayúsculas y elimina espacios o guiones antes de construir la URL.
  • Codifica el valor como un segmento de URL y no formes rutas con texto sin validar.
  • Usa un valor ficticio en pruebas y evita almacenar consultas completas en logs.

Ejemplos para consultar una placa desde código

Los cuatro ejemplos consultan la misma ficha básica. Sustituye ABC1234 por la placa normalizada que necesites procesar.

EndpointGET /api/v1/placas/{placa}/vehiculo

El ejemplo usa un identificador ficticio. Reemplázalo por el dato que necesitas consultar.

Solicitud
curl --request GET "https://api.ecuadorapi.com/api/v1/placas/ABC1234/vehiculo" \
  --header "Authorization: Bearer $ECUADORAPI_KEY" \
  --header "Accept: application/json" \
  --fail-with-body \
  --max-time 60
const response = await fetch("https://api.ecuadorapi.com/api/v1/placas/ABC1234/vehiculo", {
  headers: {
    Authorization: "Bearer " + process.env.ECUADORAPI_KEY,
    Accept: "application/json",
  },
  signal: AbortSignal.timeout(60_000),
})
const contentType = response.headers.get("content-type") ?? ""
const body = contentType.includes("json")
  ? await response.json().catch(() => null)
  : null

if (!response.ok || body?.error) {
  throw new Error(body?.message ?? "Request failed: " + response.status)
}

if (!body || !("data" in body)) {
  throw new Error("API returned an invalid response")
}

const result = body.data
// Use result in your server-side flow. Avoid logging personal responses.
import os, requests

response = requests.get(
    "https://api.ecuadorapi.com/api/v1/placas/ABC1234/vehiculo",
    headers={
        "Authorization": f"Bearer {os.environ['ECUADORAPI_KEY']}",
        "Accept": "application/json",
    },
    timeout=60,
)
content_type = response.headers.get("content-type", "")

try:
    body = response.json() if "json" in content_type else None
except requests.exceptions.JSONDecodeError:
    body = None

if not response.ok or (isinstance(body, dict) and body.get("error")):
    message = body.get("message") if isinstance(body, dict) else None
    raise RuntimeError(message or f"Request failed: {response.status_code}")

if not isinstance(body, dict) or "data" not in body:
    raise RuntimeError("API returned an invalid response")

data = body["data"]
# Use data in your server-side flow. Avoid logging personal responses.
$ch = curl_init("https://api.ecuadorapi.com/api/v1/placas/ABC1234/vehiculo");
curl_setopt($ch, CURLOPT_HTTPHEADER, [
    "Authorization: Bearer " . getenv("ECUADORAPI_KEY"),
    "Accept: application/json",
]);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 60);
$rawBody = curl_exec($ch);

if ($rawBody === false) {
    $transportError = curl_error($ch);
    curl_close($ch);
    throw new RuntimeException("Request transport failed: " . $transportError);
}

$statusCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
$body = json_decode($rawBody, true);

if (!is_array($body)) {
    throw new RuntimeException("API returned invalid JSON");
}

if ($statusCode >= 400 || ($body["error"] ?? false)) {
    throw new RuntimeException(
        ($body["message"] ?? null) ?: "Request failed: " . $statusCode
    );
}

if (!array_key_exists("data", $body)) {
    throw new RuntimeException("API returned an invalid response");
}

$data = $body["data"];
// Use $data in your server-side flow. Avoid logging personal responses.

Respuesta de ejemplo · 200 OK

JSON ficticio con la misma estructura que devuelve la API. Verlo o copiarlo no consume saldo.

{
  "data": {
    "plate": "ABC1234",
    "camv_cpn": "T01234567",
    "brand": "CHEVROLET",
    "model": "AVEO ACTIVO 1.6",
    "year": 2018,
    "color": "PLATEADO",
    "vehicle_class": "AUTOMOVIL",
    "service": "PARTICULAR",
    "engine_cc": 1600,
    "country": "ECUADOR",
    "last_registration_date": "2025-04-16",
    "registration_expiry_date": "2026-04-16",
    "fetched_at": "2026-06-20T16:00:00Z"
  },
  "error": null,
  "message": null
}
Ver campos, precio vigente y referencia del endpoint

Campos principales de la respuesta

  • data.plate identifica la placa asociada a la ficha.
  • data.brand, data.model y data.year describen el vehículo.
  • data.color, data.vehicle_class y data.service ayudan a contrastar sus características básicas.
  • data.last_registration_date y data.registration_expiry_date pueden ser null cuando no existe una fecha confirmada.
  • data.fetched_at indica cuándo se obtuvo la información presentada por la API.

Cómo manejar errores y reintentos

  • 400: revisa el formato y la normalización del identificador.
  • 401, 402 o 403: comprueba la API key, el saldo y el estado de la cuenta según el mensaje recibido.
  • 404: no se encontraron datos; no asumas que el vehículo no existe sin revisar el valor enviado.
  • 429: respeta Retry-After y evita reintentos simultáneos.
  • 502 o 503: usa espera progresiva con un número máximo de intentos.

Buenas prácticas para una integración vehicular

  • Compara la placa devuelta con la solicitada antes de guardar el resultado.
  • Tolera campos null y cambios no destructivos en la respuesta.
  • Conserva la API key solo en el servidor y rótala si llega a exponerse.
  • Consulta el precio vigente en la documentación antes de estimar costos por volumen.
Continúa con la integración
Consulta el contrato de la ficha básica, su precio vigente y el ejemplo actualizado.

Preguntas frecuentes

Respuestas rápidas sobre esta guía.

Más guías

Continúa explorando otros temas relacionados.

Ver todas las guías