Como FastAPI está basado en la especificación de OpenAPI, sus APIs pueden ser descritas en un formato estándar que muchas herramientas entienden.
Esto hace fácil generar documentación actualizada, librerías cliente (SDKs) en múltiples lenguajes, y testing o flujos de automatización que se mantienen sincronizados con tu código.
En esta guía, aprenderás cómo generar un SDK de TypeScript para tu backend de FastAPI.
Una opción versátil es el OpenAPI Generator, que soporta muchos lenguajes de programación y puede generar SDKs desde tu especificación OpenAPI.
Para clientes TypeScript, Hey API es una solución construida específicamente, que proporciona una experiencia optimizada para el ecosistema de TypeScript.
Puedes descubrir más generadores de SDK en OpenAPI.Tools.
Consejo
FastAPI genera automáticamente especificaciones de OpenAPI 3.1, así que cualquier herramienta que uses debe soportar esta versión.
Notá que las path operations definen los modelos que usan para el payload de request y el payload de response, usando los modelos Item y ResponseMessage.
Una vez que tenemos una app de FastAPI con los modelos, podemos usar Hey API para generar un cliente TypeScript. La forma más rápida de hacerlo es vía npx.
...eso es porque el generador del cliente usa el operation ID interno de OpenAPI para cada path operation.
OpenAPI requiere que cada operation ID sea único en todas las path operations, así que FastAPI usa el nombre de la función, el path, y el método/operación HTTP para generar ese operation ID, porque de esa manera puede asegurar que los operation IDs sean únicos.
Pero te mostraré cómo mejorar eso a continuación. 🤓
Operation IDs Personalizados y Mejores Nombres de Métodos¶
Puedes modificar la manera en que estos operation IDs son generados para hacerlos más simples y tener nombres de métodos más simples en los clientes.
En este caso, tendrás que asegurar que cada operation ID sea único de alguna otra manera.
Por ejemplo, podrías asegurar que cada path operation tenga un tag, y luego generar el operation ID basado en el tag y el nombre de la path operation (el nombre de la función).
FastAPI usa un ID único para cada path operation, que se usa para el operation ID y también para los nombres de cualquier modelo personalizado necesario, para requests o responses.
Puedes personalizar esa función. Toma una APIRoute y retorna un string.
Por ejemplo, aquí se usa el primer tag (probablemente tendrás solo un tag) y el nombre de la path operation (el nombre de la función).
Luego puedes pasar esa función personalizada a FastAPI como el parámetro generate_unique_id_function:
Generar un Cliente TypeScript con Operation IDs Personalizados¶
Ahora, si generas el cliente de nuevo, verás que tiene los nombres de métodos mejorados:
Como ves, los nombres de métodos ahora tienen el tag y luego el nombre de la función, ahora no incluyen información del path de la URL y la operación HTTP.
Preprocesar la Especificación OpenAPI para el Generador de Clientes¶
El código generado todavía tiene algo de información duplicada.
Ya sabemos que este método está relacionado con los items porque esa palabra está en ItemsService (tomado del tag), pero todavía tenemos el nombre del tag como prefijo en el nombre del método también. 😕
Probablemente todavía querremos mantenerlo para OpenAPI en general, ya que eso asegurará que los operation IDs sean únicos.
Pero para el cliente generado, podríamos modificar los operation IDs de OpenAPI justo antes de generar los clientes, solo para hacer esos nombres de métodos más bonitos y limpios.
Podríamos descargar el JSON de OpenAPI a un archivo openapi.json y luego podríamos remover ese tag prefijado con un script como este:
Con eso, los operation IDs serían renombrados de cosas como items-get_items a simplemente get_items, de esa manera el generador del cliente puede generar nombres de métodos más simples.
Generar un Cliente TypeScript con el OpenAPI Preprocesado¶
Como el resultado final ahora está en un archivo openapi.json, necesitas actualizar tu ubicación de entrada:
Al usar los clientes generados automáticamente, obtendrías autocompletado para:
Métodos.
Payloads de request en el body, query parameters, etc.
Payloads de response.
También tendrías errores en línea para todo.
Y cuando actualices el código del backend, y regeneres el frontend, tendría cualquier nueva path operation disponible como métodos, las viejas removidas, y cualquier otro cambio se reflejaría en el código generado. 🤓
Esto también significa que si algo cambió, se reflejará en el código del cliente automáticamente. Y si compilas el cliente, dará error si tienes alguna discrepancia en los datos usados.
Así que, detectarías muchos errores muy temprano en el ciclo de desarrollo en lugar de tener que esperar a que los errores le aparezcan a tus usuarios finales en producción y luego intentar debuggear dónde está el problema. ✨