Movatterモバイル変換


[0]ホーム

URL:


Saltar a contenido
Join theFastAPI Cloud waiting list 🚀
Follow@fastapi onX (Twitter) to stay updated
FollowFastAPI onLinkedIn to stay updated
Subscribe to theFastAPI and friends newsletter 🎉
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor
sponsor

Seguridad - Primeros pasos

🌐 Traducción por IA y humanos

Esta traducción fue hecha por IA guiada por humanos. 🤝

Podría tener errores al interpretar el significado original, o sonar poco natural, etc. 🤖

Puedes mejorar esta traducciónayudándonos a guiar mejor al LLM de IA.

Versión en inglés

Imaginemos que tienes tu API debackend en algún dominio.

Y tienes unfrontend en otro dominio o en un path diferente del mismo dominio (o en una aplicación móvil).

Y quieres tener una forma para que el frontend se autentique con el backend, usando unusername ypassword.

Podemos usarOAuth2 para construir eso conFastAPI.

Pero vamos a ahorrarte el tiempo de leer la larga especificación completa solo para encontrar esos pequeños fragmentos de información que necesitas.

Usemos las herramientas proporcionadas porFastAPI para manejar la seguridad.

Cómo se ve

Primero solo usemos el código y veamos cómo funciona, y luego volveremos para entender qué está sucediendo.

Creamain.py

Copia el ejemplo en un archivomain.py:

fromtypingimportAnnotatedfromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:Annotated[str,Depends(oauth2_scheme)]):return{"token":token}
🤓 Other versions and variants

Tip

Prefer to use theAnnotated version if possible.

fromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:str=Depends(oauth2_scheme)):return{"token":token}

Ejecútalo

Información

El paquetepython-multipart se instala automáticamente conFastAPI cuando ejecutas el comandopip install "fastapi[standard]".

Sin embargo, si usas el comandopip install fastapi, el paquetepython-multipart no se incluye por defecto.

Para instalarlo manualmente, asegúrate de crear unentorno virtual, activarlo, y luego instalarlo con:

$pipinstallpython-multipart

Esto se debe a queOAuth2 utiliza "form data" para enviar elusername ypassword.

Ejecuta el ejemplo con:

$fastapidevmain.py<span style="color: green;">INFO</span>:     Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)

Revisa

Ve a la documentación interactiva en:http://127.0.0.1:8000/docs.

Verás algo así:

¡Botón de autorización!

Ya tienes un nuevo y brillante botón de "Authorize".

Y tupath operation tiene un pequeño candado en la esquina superior derecha que puedes pulsar.

Y si lo haces, tendrás un pequeño formulario de autorización para escribir unusername ypassword (y otros campos opcionales):

Nota

No importa lo que escribas en el formulario, aún no funcionará. Pero llegaremos allí.

Esto por supuesto no es el frontend para los usuarios finales, pero es una gran herramienta automática para documentar interactivamente toda tu API.

Puede ser utilizada por el equipo de frontend (que también puedes ser tú mismo).

Puede ser utilizada por aplicaciones y sistemas de terceros.

Y también puede ser utilizada por ti mismo, para depurar, revisar y probar la misma aplicación.

El flujopassword

Ahora retrocedamos un poco y entendamos qué es todo eso.

El "flujo"password es una de las formas ("flujos") definidas en OAuth2, para manejar la seguridad y la autenticación.

OAuth2 fue diseñado para que el backend o la API pudieran ser independientes del servidor que autentica al usuario.

Pero en este caso, la misma aplicación deFastAPI manejará la API y la autenticación.

Así que, revisémoslo desde ese punto de vista simplificado:

  • El usuario escribe elusername ypassword en el frontend, y presionaEnter.
  • El frontend (ejecutándose en el navegador del usuario) envía eseusername ypassword a una URL específica en nuestra API (declarada contokenUrl="token").
  • La API verifica eseusername ypassword, y responde con un "token" (no hemos implementado nada de esto aún).
    • Un "token" es solo un string con algún contenido que podemos usar luego para verificar a este usuario.
    • Normalmente, un token se establece para que expire después de algún tiempo.
      • Así que, el usuario tendrá que volver a iniciar sesión más adelante.
      • Y si el token es robado, el riesgo es menor. No es como una llave permanente que funcionará para siempre (en la mayoría de los casos).
  • El frontend almacena temporalmente ese token en algún lugar.
  • El usuario hace clic en el frontend para ir a otra sección de la aplicación web frontend.
  • El frontend necesita obtener más datos de la API.
    • Pero necesita autenticación para ese endpoint específico.
    • Así que, para autenticarse con nuestra API, envía unheaderAuthorization con un valor deBearer más el token.
    • Si el token contienefoobar, el contenido delheaderAuthorization sería:Bearer foobar.

OAuth2PasswordBearer deFastAPI

FastAPI proporciona varias herramientas, en diferentes niveles de abstracción, para implementar estas funcionalidades de seguridad.

En este ejemplo vamos a usarOAuth2, con el flujoPassword, usando un tokenBearer. Hacemos eso utilizando la claseOAuth2PasswordBearer.

Información

Un token "bearer" no es la única opción.

Pero es la mejor para nuestro caso de uso.

Y podría ser la mejor para la mayoría de los casos de uso, a menos que seas un experto en OAuth2 y sepas exactamente por qué hay otra opción que se adapta mejor a tus necesidades.

En ese caso,FastAPI también te proporciona las herramientas para construirlo.

Cuando creamos una instance de la claseOAuth2PasswordBearer pasamos el parámetrotokenUrl. Este parámetro contiene la URL que el cliente (el frontend corriendo en el navegador del usuario) usará para enviar elusername ypassword a fin de obtener un token.

fromtypingimportAnnotatedfromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:Annotated[str,Depends(oauth2_scheme)]):return{"token":token}
🤓 Other versions and variants

Tip

Prefer to use theAnnotated version if possible.

fromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:str=Depends(oauth2_scheme)):return{"token":token}

Consejo

AquítokenUrl="token" se refiere a una URL relativatoken que aún no hemos creado. Como es una URL relativa, es equivalente a./token.

Porque estamos usando una URL relativa, si tu API estuviera ubicada enhttps://example.com/, entonces se referiría ahttps://example.com/token. Pero si tu API estuviera ubicada enhttps://example.com/api/v1/, entonces se referiría ahttps://example.com/api/v1/token.

Usar una URL relativa es importante para asegurarse de que tu aplicación siga funcionando incluso en un caso de uso avanzado comoDetrás de un Proxy.

Este parámetro no crea ese endpoint /path operation, pero declara que la URL/token será la que el cliente deberá usar para obtener el token. Esa información se usa en OpenAPI, y luego en los sistemas de documentación interactiva del API.

Pronto también crearemos la verdaderapath operation.

Información

Si eres un "Pythonista" muy estricto, tal vez no te guste el estilo del nombre del parámetrotokenUrl en lugar detoken_url.

Eso es porque está usando el mismo nombre que en la especificación de OpenAPI. Para que si necesitas investigar más sobre cualquiera de estos esquemas de seguridad, puedas simplemente copiarlo y pegarlo para encontrar más información al respecto.

La variableoauth2_scheme es una instance deOAuth2PasswordBearer, pero también es un "callable".

Podría ser llamada como:

oauth2_scheme(some,parameters)

Así que, puede usarse conDepends.

Úsalo

Ahora puedes pasar eseoauth2_scheme en una dependencia conDepends.

fromtypingimportAnnotatedfromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:Annotated[str,Depends(oauth2_scheme)]):return{"token":token}
🤓 Other versions and variants

Tip

Prefer to use theAnnotated version if possible.

fromfastapiimportDepends,FastAPIfromfastapi.securityimportOAuth2PasswordBearerapp=FastAPI()oauth2_scheme=OAuth2PasswordBearer(tokenUrl="token")@app.get("/items/")asyncdefread_items(token:str=Depends(oauth2_scheme)):return{"token":token}

Esta dependencia proporcionará unstr que se asigna al parámetrotoken de lapath operation function.

FastAPI sabrá que puede usar esta dependencia para definir un "security scheme" en el esquema OpenAPI (y en los docs automáticos del API).

Detalles técnicos

FastAPI sabrá que puede usar la claseOAuth2PasswordBearer (declarada en una dependencia) para definir el esquema de seguridad en OpenAPI porque hereda defastapi.security.oauth2.OAuth2, que a su vez hereda defastapi.security.base.SecurityBase.

Todas las utilidades de seguridad que se integran con OpenAPI (y los docs automáticos del API) heredan deSecurityBase, así es comoFastAPI puede saber cómo integrarlas en OpenAPI.

Lo que hace

Irá y buscará en el request ese headerAuthorization, verificará si el valor esBearer más algún token, y devolverá el token como unstr.

Si no ve un headerAuthorization, o el valor no tiene un tokenBearer, responderá directamente con un error de código de estado 401 (UNAUTHORIZED).

Ni siquiera tienes que verificar si el token existe para devolver un error. Puedes estar seguro de que si tu función se ejecuta, tendrá unstr en ese token.

Puedes probarlo ya en los docs interactivos:

Todavía no estamos verificando la validez del token, pero ya es un comienzo.

Resumen

Así que, en solo 3 o 4 líneas adicionales, ya tienes alguna forma primitiva de seguridad.


[8]ページ先頭

©2009-2026 Movatter.jp