0
0
FastapiHow-ToBeginner · 3 min read

How to Use Startup and Shutdown Events in FastAPI

In FastAPI, use the @app.on_event("startup") decorator to run code when the app starts, and @app.on_event("shutdown") to run code when the app stops. These events help initialize resources like database connections and clean them up properly.
📐

Syntax

FastAPI provides two decorators to handle lifecycle events: @app.on_event("startup") and @app.on_event("shutdown"). You define functions decorated with these to run code when the app starts or stops.

  • @app.on_event("startup"): Runs once when the app starts.
  • @app.on_event("shutdown"): Runs once when the app is shutting down.

These functions can be async or regular functions.

python
from fastapi import FastAPI

app = FastAPI()

@app.on_event("startup")
async def startup_event():
    # Code to run on startup
    pass

@app.on_event("shutdown")
async def shutdown_event():
    # Code to run on shutdown
    pass
💻

Example

This example shows how to open a database connection on startup and close it on shutdown. It prints messages to the console to demonstrate when each event runs.

python
from fastapi import FastAPI

app = FastAPI()

@app.on_event("startup")
async def startup_event():
    print("Starting up: connecting to database...")
    # Simulate database connection setup
    app.state.db = "Database connection established"

@app.on_event("shutdown")
async def shutdown_event():
    print("Shutting down: closing database connection...")
    # Simulate closing database connection
    app.state.db = None

@app.get("/")
async def read_root():
    return {"message": "Hello World", "db_status": app.state.db}
Output
Starting up: connecting to database... Shutting down: closing database connection...
⚠️

Common Pitfalls

Common mistakes when using startup and shutdown events include:

  • Not using async functions when performing asynchronous operations, which can cause blocking.
  • Forgetting to properly close resources like database connections, leading to resource leaks.
  • Trying to access app state before it is initialized in startup.
  • Placing startup/shutdown code inside route handlers instead of event functions.

Always keep startup and shutdown logic separate and ensure cleanup is done to avoid issues.

python
from fastapi import FastAPI

app = FastAPI()

# Wrong: startup code inside route (runs on every request, not once)
@app.get("/wrong")
async def wrong_startup():
    print("Connecting to DB on every request - inefficient!")
    return {"message": "This is wrong"}

# Right: use startup event
@app.on_event("startup")
async def startup_event():
    print("Connecting to DB once on startup")
📊

Quick Reference

Use these tips to remember how to use startup and shutdown events:

  • Startup: Initialize resources like DB connections, caches, or background tasks.
  • Shutdown: Clean up resources to avoid leaks or dangling connections.
  • Use app.state to store shared objects accessible in routes.
  • Functions can be async or regular functions.
  • Events run once per app lifecycle, not per request.

Key Takeaways

Use @app.on_event("startup") to run code once when FastAPI starts.
Use @app.on_event("shutdown") to run cleanup code when FastAPI stops.
Keep resource setup and teardown in these event functions, not in routes.
You can store shared resources in app.state for access during requests.
Startup and shutdown functions can be async for non-blocking operations.