FastAPI: From Basics to Production · FastAPI Basics

Request Bodies, Response Models and Status Codes

Accept JSON bodies with Pydantic and control what you return.

Parameters typed as Pydantic models are read from the JSON body, validated and converted. Declare the return type (or response_model) to filter and document output — FastAPI serializes only the declared fields, so internal data like password hashes never leaks. Set status_code=201 for creation and raise HTTPException for errors.

from fastapi import FastAPI, HTTPException, status
from pydantic import BaseModel, EmailStr, Field

app = FastAPI()


class UserCreate(BaseModel):
    email: EmailStr
    password: str = Field(min_length=12)
    display_name: str = Field(max_length=50)


class UserOut(BaseModel):
    id: int
    email: EmailStr
    display_name: str


@app.post("/users", status_code=status.HTTP_201_CREATED)
async def create_user(body: UserCreate) -> UserOut:
    if await users.exists(body.email):
        raise HTTPException(status_code=409, detail="Email already registered")
    user = await users.create(body)          # returns an object that has password_hash too
    return UserOut.model_validate(user, from_attributes=True)

Common pitfalls

  • Returning ORM objects without a response model and leaking fields.
  • Using the same model for input and output (clients could set id or is_admin).
  • Returning 200 for creations and errors.

Key points

  • Pydantic models validate bodies
  • Response models filter output
  • Separate input and output schemas

Further reading: FastAPI: Response model

Practice questions

Why use separate UserCreate and UserOut models?

Answer

Input and output have different fields: clients send a password but must never receive a hash, and shouldn't be able to set server-controlled fields like id.

What does the return type annotation do in a FastAPI path operation?

Answer

It validates and serializes the returned data according to that type, filters extra fields, and documents the response schema in OpenAPI.

Open in the app to mark lessons complete, take notes and track your progress.