Deploy a FastAPI API
FastAPI relies on ASGI and Uvicorn to serve an asynchronous API, with data validation and generated documentation. On app hosting, deployment comes down to an entry point that reads PORT, listens on 0.0.0.0 and starts Uvicorn without reload mode.
Application
import os
import uvicorn
from fastapi import FastAPI
app = FastAPI(title="Example API")
@app.get("/health")
def health():
return {"status": "ok"}
@app.get("/items/{item_id}")
def read_item(item_id: int, q: str | None = None):
return {"item_id": item_id, "q": q}
if __name__ == "__main__":
uvicorn.run(app, host="0.0.0.0", port=int(os.environ.get("PORT", "8000")))The str | None syntax requires Python 3.10 or newer. On Python 3.9, use Optional[str] imported from typing.
requirements.txt:
fastapi==0.115.0
uvicorn[standard]==0.30.6Run Uvicorn
uvicorn.run(app, ...) works with the application object. On the command line, pass an import string:
uvicorn main:app --host 0.0.0.0 --port $PORTDo not enable --reload in production: it watches files, consumes memory and restarts the process on every change. For multiple workers, use the import-string form with --workers; each worker is a separate process.
Documentation and validation
FastAPI exposes /docs, /redoc and /openapi.json. Useful in development, sometimes unwanted in production: disable them with FastAPI(docs_url=None, redoc_url=None) when the API is not public, or protect them with authentication.
Pydantic models validate input and document the contract. A missing field returns 422 with details, which beats a 500 error. Use response_model to avoid returning internal fields such as a password hash.
Security and robustness
- Limit body size and field count.
- Validate types before reaching the database.
- Configure CORS with explicit origins, not
*with credentials. - Log errors without exposing the stack to the client.
- Close connections (database, HTTP client) on shutdown.
Check
curl -i http://ADRESSE_FOURNIE:PORT/health
curl -i http://ADRESSE_FOURNIE:PORT/items/42
curl -i http://ADRESSE_FOURNIE:PORT/items/abcExpect 200 for /health and /items/42, 422 for /items/abc. The log should show Uvicorn running on http://0.0.0.0:PORT. If the process starts but the request fails, check the interface and port before the routes.
Adapt the start command
In the panel, replace the command with uvicorn main:app --host 0.0.0.0 --port $PORT. If your plan has limited memory, stay with a single worker: each Uvicorn worker loads a full copy of the application. For real traffic, measure available memory and idle usage before increasing --workers. After the restart, check the /health route and look for Uvicorn running in the logs.
Advertisement