martes, 25 de marzo de 2025

馃憠 Autenticaci贸n de APIs en Flask con JWT (JSON Web Tokens)

Despu茅s de implementar autenticaci贸n con sesiones en Flask, es momento de aprender una alternativa moderna y escalable: JWT (JSON Web Tokens). Ideal para APIs RESTful.

En este post aprender谩s:
✔️ Qu茅 es JWT y para qu茅 se usa
✔️ C贸mo generar y verificar tokens en Flask
✔️ Proteger rutas con decoradores
✔️ Ejemplo pr谩ctico paso a paso

馃搶 JWT es ampliamente usado en APIs modernas por su seguridad y portabilidad.


1️⃣ ¿Qu茅 es JWT?

JWT (JSON Web Token) es un est谩ndar para transmitir informaci贸n de forma segura entre dos partes.

馃搶 Se compone de 3 partes codificadas en base64:

  • Header (tipo y algoritmo)

  • Payload (datos del usuario)

  • Signature (clave secreta)

✅ Es 煤til para autenticar usuarios sin necesidad de sesiones.


2️⃣ Instalar dependencias

pip install flask flask_sqlalchemy pyjwt

Tambi茅n usaremos werkzeug.security para manejar contrase帽as:

from werkzeug.security import generate_password_hash, check_password_hash

3️⃣ Generar el token JWT al iniciar sesi贸n

import jwt from datetime import datetime, timedelta from flask import Flask, request, jsonify app = Flask(__name__) app.config["SECRET_KEY"] = "clave_super_segura" def generar_token(usuario_id): payload = { "usuario_id": usuario_id, "exp": datetime.utcnow() + timedelta(hours=1) } token = jwt.encode(payload, app.config["SECRET_KEY"], algorithm="HS256") return token

4️⃣ Ruta de Login para devolver un JWT

@app.route("/login", methods=["POST"]) def login(): datos = request.json usuario = Usuario.query.filter_by(email=datos["email"]).first() if usuario and check_password_hash(usuario.password, datos["password"]): token = generar_token(usuario.id) return jsonify({"token": token}) return jsonify({"error": "Credenciales inv谩lidas"}), 401

馃搶 Salida esperada:

{ "token": "eyJhbGciOiJIUzI1NiIsInR..." }

5️⃣ Proteger rutas con un decorador personalizado

from functools import wraps def token_requerido(f): @wraps(f) def decorador(*args, **kwargs): token = request.headers.get("Authorization") if not token: return jsonify({"error": "Token requerido"}), 403 try: datos = jwt.decode(token, app.config["SECRET_KEY"], algorithms=["HS256"]) usuario = Usuario.query.get(datos["usuario_id"]) except: return jsonify({"error": "Token inv谩lido o expirado"}), 403 return f(usuario, *args, **kwargs) return decorador

6️⃣ Ruta protegida usando el token

@app.route("/perfil") @token_requerido def perfil(usuario): return jsonify({ "usuario": usuario.username, "email": usuario.email })

✅ Si el token es v谩lido, se accede al perfil del usuario autenticado.


7️⃣ C贸mo enviar el token desde el cliente

馃搶 En las peticiones protegidas, se debe incluir el token:

GET /perfil HTTP/1.1 Authorization: eyJhbGciOiJIUzI1NiIsInR...

✅ Esto permite que el backend valide al usuario sin usar cookies ni sesiones.


馃殌 Conclusi贸n

✅ JWT es ideal para autenticar usuarios en APIs REST.
✅ Protege tus rutas con decoradores y claves secretas.
✅ A diferencia de Flask-Login, JWT es stateless, perfecto para microservicios.

馃搶 Pr贸ximo post: C贸mo refrescar tokens JWT y controlar expiraci贸n.

馃搨 C贸digo en GitHub: github.com/josecodetech
馃帴 Tutorial en YouTube: https://www.youtube.com/@josecodetech/

馃挰 ¿Ya usaste JWT? ¿Prefieres sesiones o tokens? Cu茅ntamelo 馃憞



No hay comentarios:

Publicar un comentario

Se procedera a revision para su pronta publicacion en caso de que no incumpla las normas de blogger.