Dependency Injection
FastAPI's superpower for sharing logic, database connections, and authentication.
🧑🏫 Sabse pehle — simple mein samjho#
Express (Node.js) mein hum Middleware use karte the har route pe check lagane ke liye (jaise token verify karna ya DB connect karna). FastAPI mein is cheez ka ek bohot advanced aur clean tareeqa hai jise Dependency Injection (Depends) kehte hain. Tum ek alag function banate ho (jaise verify_token), aur usko seedha apne route ke parameters mein inject kar dete ho. FastAPI route chalane se pehle us function ko chalayega, uska result route ko dega, aur agar wo fail hua to wahi se error fek dega. Isse code bohot reusable ban jata hai.
What is Dependency Injection?#
Dependency Injection means that your code (the route) does not have to create or initialize the things it needs to run (like a database connection or user authentication). Instead, it simply declares what it needs in its parameters, and the framework (FastAPI) automatically "injects" it at runtime.
1. A Simple Dependency#
Let's say multiple routes need to extract pagination parameters (skip and limit) from the URL. Instead of writing skip: int = 0, limit: int = 10 in every single route, we extract it into a dependency.
from fastapi import FastAPI, Depends
app = FastAPI()
# 1. Define the Dependency Function
async def common_parameters(q: str | None = None, skip: int = 0, limit: int = 100):
return {"q": q, "skip": skip, "limit": limit}
# 2. Inject it into the Route using Depends()
@app.get("/items/")
async def read_items(commons: dict = Depends(common_parameters)):
# FastAPI automatically ran common_parameters() and gave us the result in `commons`!
return {"message": "Here are the items", "params": commons}
@app.get("/users/")
async def read_users(commons: dict = Depends(common_parameters)):
return {"message": "Here are the users", "params": commons}
2. Dependencies for Database Connections#
This is the most common use case for Dependency Injection in real-world apps. You need a database session to read/write data, but you must make sure to close the session when the request is done to prevent memory leaks.
# A generator dependency using `yield`
def get_db():
db = SessionLocal() # Open connection
try:
yield db # Give the connection to the route
finally:
db.close() # Close it after the route finishes responding
@app.get("/users/")
def get_users(db: Session = Depends(get_db)):
# Safely use the db session
users = db.query(User).all()
return users
3. Dependencies for Authentication (Middleware Alternative)#
Instead of applying a global middleware, you can inject an authentication dependency directly into the routes that need protection.
from fastapi import HTTPException, status
# A dependency that acts like an Auth Guard
async def verify_token(token: str):
if token != "supersecret":
# If the dependency raises an exception, the route is NEVER executed.
raise HTTPException(status_code=401, detail="Invalid token")
return {"user_id": 123}
@app.get("/dashboard")
async def dashboard(user_data: dict = Depends(verify_token)):
# This code only runs if the token was perfectly valid
return {"message": f"Welcome User {user_data['user_id']}"}