flawopen.com/Referencia/FastAPI SQL Injection
¿FastAPI evita SQL Injection de forma predeterminada?
Pydantic comprueba que un valor coincida con el tipo declarado; no reescribe SQL ni convierte una cadena de Python en un parámetro de base de datos. Un name: str validado sigue siendo texto controlado por quien llama a la API. Piensa en la validación como revisar la etiqueta de un paquete: identifica el tipo de valor recibido, mientras que la parametrización mantiene el valor separado de las instrucciones SQL. Mantén fija la plantilla de consulta y pasa los valores aparte mediante SQLAlchemy.
Patrón vulnerable y seguro en FastAPI
# Comprobar que sea string no hace segura la entrada dentro de la sintaxis SQL
@app.get("/users")
def get_users(name: str, db: Session = Depends(get_db)):
query = text(f"SELECT * FROM users WHERE name = '{name}'")
return db.execute(query).fetchall()
# :name es un parámetro; el valor se pasa por separado
@app.get("/users")
def get_users(name: str, db: Session = Depends(get_db)):
query = text("SELECT * FROM users WHERE name = :name")
return db.execute(query, {"name": name}).fetchall()
Lo que la parametrización no cubre
Un parámetro enlaza un valor, no el nombre de una tabla o columna, un operador SQL ni el sentido del ordenamiento. Si una solicitud debe elegir el campo de orden, asigna esa opción a una lista permitida fija de expresiones de columnas SQLAlchemy; nunca insertes en SQL la cadena recibida. La parametrización tampoco sustituye la autorización: limita las filas que la persona puede leer y concede a la cuenta de base de datos solo los privilegios que necesita el endpoint.
Lista de prevención
- ✓Nunca interpoles datos de solicitudes en
text()de SQLAlchemy ni en una cadena ejecutada directamente por la base de datos. - ✓Usa parámetros con nombre y pasa sus valores por separado, por ejemplo
db.execute(query, {"name": name}). - ✓Para tablas, columnas u ordenamientos dinámicos, asigna la entrada a una lista permitida fija de expresiones SQLAlchemy conocidas.
- ✓Comprueba la autorización por fila por separado y concede a la cuenta de base de datos solo los privilegios necesarios para el endpoint.
- ✓Prefiere expresiones
select()de SQLAlchemy cuando sean claras; usar el ORM no vuelve seguro el SQL sin procesar inseguro.
Referencias
- FastAPI — bases de datos SQL (relacionales)
- SQLAlchemy — envío de parámetros y SQL textual
- OWASP — prevención de SQL Injection