Pydantic
LLMs speak JSON. JSON lies sometimes. Pydantic is the lie detector every GenAI app runs on.
▶ Watch this reelWhat you'll learn
- BaseModel
- Field validators
- pydantic-settings
- JSON Schema export
Remember this
- BaseModel validates at the boundary — parse LLM JSON instead of hoping
- field_validator/model_validator enforce value rules, not just types
- model_json_schema() feeds structured output — one model, end to end
BaseModel
class ChatRequest(BaseModel):
model: str
prompt: str
temperature: float = 0.7
req = ChatRequest(**json_from_llm) # validates + coerces
- Bad data →
ValidationErrorwith every problem listed.
Validators
Field(ge=, le=, min_length=, ...)for simple rules.@field_validator("model")— per-field; raise ValueError to reject.@model_validator— cross-field rules.
pydantic-settings
class Settings(BaseSettings):
model_config = SettingsConfigDict(env_prefix="APP_")
openai_api_key: str
- Env vars → typed, validated config; crashes at boot when required keys are missing.
JSON Schema export
schema = ChatRequest.model_json_schema()
reply = ChatRequest.model_validate_json(raw)
- The structured-output loop: define once → constrain the LLM → validate the reply. Backbone of Stage 2+.
Code: Pydantic — the GenAI backbone pattern
from pydantic import BaseModel, Field, field_validator
from pydantic_settings import BaseSettings, SettingsConfigDict
# --- 1. BaseModel: parse, don't pray ---------------------------
class ChatRequest(BaseModel):
model: str
prompt: str
temperature: float = 0.7
max_tokens: int = Field(default=1000, ge=1, le=128_000)
req = ChatRequest(**{"model": "gpt-4o", "prompt": "hi", "temperature": "0.2"})
# --- 2. Validators: value rules --------------------------------
ALLOWED = {"gpt-4o", "claude-sonnet", "llama-3"}
@field_validator("model")
@classmethod
def model_must_be_supported(cls, v: str) -> str:
if v not in ALLOWED:
raise ValueError(f"unsupported model: {v}")
return v
# --- 3. Settings: validated env config -------------------------
class Settings(BaseSettings):
model_config = SettingsConfigDict(env_prefix="APP_")
openai_api_key: str
model: str = "gpt-4o"
max_retries: int = 3
# export APP_OPENAI_API_KEY=sk-...
# settings = Settings() # crashes loudly if the key is missing
# --- 4. JSON Schema: structured output --------------------------
print(ChatRequest.model_json_schema())
# → the schema you pass as response_format / tool parameters
# reply = client.chat(..., response_format=ChatRequestSchema)
# parsed = ChatRequest.model_validate_json(reply)