Die Beherrschung der FastAPI-Sicherheit: Ein umfassender Leitfaden zu OAuth2 mit Passwort-Hashing und JWT-Bearer-Tokens
Im Zeitalter der digitalen Transformation ist die Sicherung von Webanwendungen von größter Bedeutung geworden. FastAPI ist eines der beliebtesten Frameworks zum Erstellen von APIs mit Python und bietet mehrere Optionen zum Absichern von Endpunkten und Verwalten der Authentifizierung. Dieser umfassende Leitfaden führt Sie durch die Implementierung von OAuth2 mit Passwort-Hashing und JWT-Bearer-Tokens in FastAPI.
Einführung in OAuth2
OAuth2 ist ein weit verbreitetes Autorisierungs-Framework, das Anwendungen ermöglicht, eingeschränkten Zugriff auf Benutzerkonten auf einem HTTP-Dienst zu erhalten. Es funktioniert durch die Delegierung der Benutzerauthentifizierung an einen Drittanbieter, was eine sicherere und effizientere Zugriffskontrolle ermöglicht.
Schlüsselbegriffe von OAuth2
- Ressourceneigentümer: Der Benutzer, der einer Anwendung den Zugriff auf sein Konto autorisiert.
- Client: Die Anwendung, die den Zugriff auf das Benutzerkonto anfordert.
- Autorisierungsserver: Der Server, der Token ausstellt, nachdem der Ressourceneigentümer erfolgreich authentifiziert und die Autorisierung erhalten wurde.
- Ressourcenserver: Der Server, der die Daten des Benutzers speichert und Zugriffstoken für den Ressourcenzugriff akzeptiert.
Einrichten von FastAPI für OAuth2
Wir beginnen mit der Einrichtung einer grundlegenden FastAPI-Anwendung und fügen die notwendigen Bibliotheken zur Implementierung von OAuth2 hinzu.
from fastapi import FastAPI, Depends, HTTPException, status
from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm
from passlib.context import CryptContext
from jose import JWTError, jwt
from pydantic import BaseModel
from datetime import datetime, timedelta
from typing import Optional
Die hier genannten Bibliotheken und Module sind essentiell für die Handhabung von Abhängigkeiten, HTTP-Ausnahmen, Passwort-Hashing und JSON-Web-Tokens (JWT).
Implementierung des Passwort-Hashings
Das Speichern von Klartext-Passwörtern ist niemals eine gute Praxis. Stattdessen hashen wir Passwörter mit passlib
, einer Passwort-Hashing-Bibliothek für Python.
Erstellen einer Passwort-Hashing-Funktion
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
def verify_password(plain_password, hashed_password):
return pwd_context.verify(plain_password, hashed_password)
def get_password_hash(password):
return pwd_context.hash(password)
Hier überprüft verify_password
, ob das Klartext-Passwort mit dem gehashten Passwort übereinstimmt, während get_password_hash
ein Klartext-Passwort hasht.
Erstellen von Modellen und Token-Dienstprogrammen
Wir benötigen Benutzer-Modelle und Dienstprogramme zum Generieren und Dekodieren von JWT-Tokens.
Benutzer- und Token-Modelle
class User(BaseModel):
username: str
class UserInDB(User):
hashed_password: str
class Token(BaseModel):
access_token: str
token_type: str
class TokenData(BaseModel):
username: Optional[str] = None
User
repräsentiert einen Benutzer, UserInDB
enthält das gehashte Passwort, und Token
und TokenData
behandeln JWT-Tokens.
JWT-Dienstprogramme
SECRET_KEY = "secret"
ALGORITHM = "HS256"
ACCESS_TOKEN_EXPIRE_MINUTES = 30
def create_access_token(data: dict, expires_delta: Optional[timedelta] = None):
to_encode = data.copy()
if expires_delta:
expire = datetime.utcnow() + expires_delta
else:
expire = datetime.utcnow() + timedelta(minutes=15)
to_encode.update({"exp": expire})
encoded_jwt = jwt.encode(to_encode, SECRET_KEY, algorithm=ALGORITHM)
return encoded_jwt
Die Funktion create_access_token
generiert JWT-Tokens mit einer Ablaufzeit.
Handhabung von Authentifizierung und Autorisierung
Wir verwenden die OAuth2PasswordBearer- und OAuth2PasswordRequestForm-Klassen zur Handhabung der Authentifizierung.
Abhängigkeitsinjektion für sichere Endpunkte
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="token")
async def get_current_user(token: str = Depends(oauth2_scheme)):
credentials_exception = HTTPException(
status_code=status.HTTP_401_UNAUTHORIZED,
detail="Could not validate credentials",
headers={"WWW-Authenticate": "Bearer"},
)
try:
payload = jwt.decode(token, SECRET_KEY, algorithms=[ALGORITHM])
username: str = payload.get("sub")
if username is None:
raise credentials_exception
token_data = TokenData(username=username)
except JWTError:
raise credentials_exception
user = get_user(fake_users_db, username=token_data.username)
if user is None:
raise credentials_exception
return user
Dieser Code überprüft das JWT-Token und ruft den aktuellen Benutzer aus den Token-Daten ab.
Erstellen von Routen zur Token-Generierung und sicherem Zugriff
app = FastAPI()
@app.post("/token", response_model=Token)
async def login_for_access_token(form_data: OAuth2PasswordRequestForm = Depends()):
user = authenticate_user(fake_users_db, form_data.username, form_data.password)
if not user:
raise HTTPException(
status_code=status.HTTP_401_UNAUTHORIZED,
detail="Incorrect username or password",
headers={"WWW-Authenticate": "Bearer"},
)
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
access_token = create_access_token(
data={"sub": user.username}, expires_delta=access_token_expires
)
return {"access_token": access_token, "token_type": "bearer"}
@app.get("/users/me", response_model=User)
async def read_users_me(current_user: User = Depends(get_current_user)):
return current_user
Der Endpunkt /token
generiert ein JWT-Token, und /users/me
gibt die Daten des aktuell authentifizierten Benutzers zurück.
Schlussfolgerung
Die Implementierung von OAuth2 mit Passwort-Hashing und JWT-Bearer-Tokens in FastAPI bietet eine robuste Sicherheit für Ihre APIs. Dieser Leitfaden behandelte die wesentlichen Komponenten, einschließlich der Einrichtung von FastAPI, der Implementierung von Passwort-Hashing, der Erstellung von JWT-Tokens und der Sicherung von Endpunkten. Durch die Befolgung dieser Schritte können Sie die Sicherheit Ihrer Anwendungen verbessern und gleichzeitig die Effizienz von FastAPI nutzen.
Bereit, Ihre FastAPI-Anwendung auf die nächste Stufe zu heben? Beginnen Sie noch heute mit der Implementierung dieser Sicherheitspraktiken, um Ihre Benutzer und Daten zu schützen.