Frankfurter
Frankfurter es una API gratuita de tipos de cambio para 223 divisas de 104 bancos centrales y fuentes oficiales. Los tipos se actualizan a diario y se remontan a 1948.
La API pública está en api.frankfurter.dev y no necesita clave API. El proyecto es de código abierto, así que también puedes alojarlo tú mismo para tener control total.
¿Trabajas con un agente de IA? Pásale el llms.txt o añade el servidor MCP.
Tipos de cambio
Obtén los últimos tipos de cambio.
curl https://api.frankfurter.dev/v2/ratesCambia la divisa base con base.
curl https://api.frankfurter.dev/v2/rates?base=usdFiltra las divisas de destino con quotes.
curl https://api.frankfurter.dev/v2/rates?quotes=usd,gbpTipos históricos
Consulta los tipos de una fecha concreta.
curl https://api.frankfurter.dev/v2/rates?date=1999-01-04Series temporales
Obtén los tipos de un período con from y to.
curl https://api.frankfurter.dev/v2/rates?from=2026-01-01"es=usdConsejo: Limitar las divisas mantiene las respuestas ligeras. Para rangos de fechas largos, pide NDJSON y recibe los resultados en streaming, línea a línea.
Agrupación
Reduce la resolución de una serie temporal con group. Admite week y month.
curl https://api.frankfurter.dev/v2/rates?from=2026-01-01&group=monthFiltrar por fuente
Limita la consulta a fuentes concretas con providers.
curl https://api.frankfurter.dev/v2/rates?providers=ecb Por defecto, la API combina los tipos de todas las fuentes. Usa providers para obtener los tipos de una fuente concreta o consulta esa fuente directamente con sus propias rutas.
Atribución de fuentes
Añade expand=providers para ver qué fuentes intervienen en cada tipo combinado.
curl https://api.frankfurter.dev/v2/rates?expand=providers Cada fila incluye un array providers con las claves de las fuentes que contribuyen. Las filas de divisas con paridad fija no llevan este campo: esos tipos salen de la paridad, no de los datos de las fuentes.
Salida CSV
Los tipos también están disponibles en CSV. Añade .csv a la ruta o envía la cabecera Accept con text/csv.
curl https://api.frankfurter.dev/v2/rates.csvSalida NDJSON
Para respuestas grandes, pide NDJSON (JSON delimitado por saltos de línea) enviando la cabecera Accept con application/x-ndjson. Cada línea es un objeto JSON independiente, así que puedes procesar series temporales largas en streaming sin cargar toda la respuesta en memoria.
curl https://api.frankfurter.dev/v2/rates?from=2026-01-01Tipo individual
Obtén el tipo de cambio de un solo par de divisas. Si quieres, añade date o providers.
curl https://api.frankfurter.dev/v2/rate/eur/usdDivisas
Obtén las divisas disponibles y qué fuentes las cubren.
curl https://api.frankfurter.dev/v2/currenciesIncluye divisas retiradas con scope.
curl https://api.frankfurter.dev/v2/currencies?scope=allDivisa individual
Obtén los detalles de una divisa y qué fuentes la cubren.
curl https://api.frankfurter.dev/v2/currency/eurFuentes
Lista las fuentes de datos que usa la API.
curl https://api.frankfurter.dev/v2/providersObtén los detalles de una fuente concreta.
curl https://api.frankfurter.dev/v2/providers/ecbTipos por fuente
Consulta los tipos de una fuente concreta directamente. Admite los mismos parámetros que /v2/rates y /v2/rate.
curl https://api.frankfurter.dev/v2/providers/ecb/ratesObtén un solo par de divisas de esa fuente.
curl https://api.frankfurter.dev/v2/providers/ecb/rate/eur/usd Combínalo con date, rangos de fechas (from y to) o agrupación. Los formatos como .csv y ndjson también funcionan aquí.
curl https://api.frankfurter.dev/v2/providers/ecb/rates?date=2024-05-15Conversión
No hay endpoint de conversión. Obtén el tipo y convierte con unas pocas líneas de código.
function convert(base, quote, amount) {
const api = "https://api.frankfurter.dev";
return fetch(`${api}/v2/rate/${base}/${quote}`)
.then((r) => r.json())
.then((d) => (amount * d.rate).toFixed(2));
}
convert("eur", "usd", 10).then((result) =>
alert(`10 EUR = ${result} USD`)
);Errores
La API responde con códigos de estado HTTP estándar y un cuerpo JSON.
{
"status": 422,
"message": "invalid currency: ABC"
}400- Parámetro no válido o petición mal formada.
404- Divisa, tipo de cambio o recurso no encontrado.
422- Petición entendida, pero no se puede procesar.
Self-hosting
Puedes alojar Frankfurter tú mismo con Docker. La guía de despliegue explica la configuración para producción y las claves API.
FAQ
- ¿Para quién es Frankfurter (y para quién no)?
- Funciona bien para facturación SaaS, e-commerce, informes fiscales, sistemas ERP y de contabilidad, e investigación académica con series históricas desde 1948. No está pensado para trading en tiempo real ni para negocios con divisas exóticas sujetas a fuertes oscilaciones intradía.
- ¿La API es gratis para uso comercial?
- Sí. Los tipos en sí se rigen por las condiciones de cada proveedor.
- ¿Tiene la API límites de llamadas?
- No hay cuotas. Las peticiones tienen un rate limit para evitar abusos, pero sin topes diarios ni mensuales. Para volúmenes altos, cachea las respuestas, aloja tu propia instancia o consulta los datasets directamente.
- ¿La API admite GraphQL?
- No. La API REST es tan simple que GraphQL solo añadiría complejidad sin mucho beneficio. Además, rompería la caché en el edge, que es lo que la hace rápida. Usa parámetros de consulta como
base,quotesyfrom/topara obtener exactamente los datos que necesitas. - ¿Se va a retirar la API v1?
- No. La API v1 está obsoleta en favor de v2, pero seguirá disponible indefinidamente. Consulta la documentación de v1. Para datos del Banco Central Europeo, usa /v2/providers/ecb/rates.
- ¿Cuál es la política de privacidad de la API?
- La API no recopila ni registra datos personales, direcciones IP ni URLs de las peticiones. La instancia pública funciona detrás de Cloudflare, que aporta caché y protección DDoS y solo ofrece estadísticas de tráfico agregadas.
- ¿Tengo que declarar la API en las etiquetas de privacidad de la App Store o Google Play?
- No. Como las consultas son anónimas y no se guardan registros de las peticiones, cuentan como datos no recopilados según las directrices de Apple y Google Play.
- ¿Dónde puedo reportar un error o hacer una pregunta?
- Abre una issue para reportar un error, pedir una funcionalidad o sugerir una nueva fuente de datos. Usa Discussions para hacer preguntas o compartir una librería o herramienta que hayas creado con Frankfurter.
- ¿Qué precisión tienen los tipos?
- Para cumplimiento normativo, filtra por una fuente concreta y obtendrás sus tipos de referencia oficiales. Para uso general, los tipos combinados por defecto funcionan bien, aunque los últimos decimales pueden variar a medida que llegan datos nuevos.
- ¿Los tipos son medios, de compra o de venta?
- La API devuelve tipos medios de mercado (mid-market). Si una fuente publica tipos de compra y venta en lugar de un tipo de referencia, Frankfurter guarda ambos y calcula el punto medio.
- ¿Todos los tipos son diarios?
- Casi todos. Algunas fuentes ofrecen observaciones semanales, mensuales o trimestrales. Estas fuentes no entran en el feed combinado. Consúltalas directamente con el filtro
providers. - ¿Por qué se solapan las fechas de algunas divisas antiguas y nuevas?
- Algunas fuentes retrotraen la divisa nueva al período de la antigua (por ejemplo,
TRLtermina en 2010 yTRYempieza en 1996). Guardamos los datos de las fuentes tal cual y solo filtramos los solapamientos al combinarlos. - ¿Por qué Frankfurter?
- Porque el Banco Central Europeo, nuestra fuente de datos original, está en Fráncfort.