liveBook · Manning

Pydantic

As explained in Build Financial Software with Generative AI (From Scratch)

Pydantic is a Python library for declaring data models and validating and serializing data using Python type annotations.

Pydantic turns Python type-annotated classes into explicit data contracts. A model can replace an ad hoc JSON dictionary with a named object, making an API easier to extend while supplying validation and schema documentation. In an ACH application, this means modeling a returned file or a file-summary response rather than passing loosely defined values between routes, database code, and clients. section 4.9.2 section 7.3

Start with a response model

A minimal model declares the shape of a file returned by an endpoint: from pydantic import BaseModel class AchFile(BaseModel): file_id: str The route can declare AchFile as its return type and return AchFile(file_id=file_id). This replaces a hardcoded dictionary with a reusable contract that can later grow into a fuller ACH-file representation. section 4.9.2

Fields can carry both constraints and descriptions. Field metadata gives API consumers meaningful titles, descriptions, and examples in generated schema documentation. A richer file-list response uses types such as UUID4, datetime, Decimal, and str, then constrains values such as filename length and nonnegative credit and debit totals. Keeping API schemas separate from database schemas preserves separation of concerns, flexibility, security, and data integrity. section 4.9.2 section 7.3

Listing 7.6 The AchFilesResponse class
from decimal import Decimal
from datetime import datetime
from pydantic import BaseModel, UUID4, Field


class AchFilesResponse(BaseModel):
    id: UUID4 = Field(...,  #1
        description="Unique identifier for the ACH file", #2
        title="ID")  #3
    date: datetime = Field(...,
        description="The date and time the ACH file was uploaded.", 
        title="Date")
    filename: str = Field(...,
        title="Filename",
        description="The name of the file the ACH file was loaded from.",
        max_length=255, #4
    )
    credit_total: Decimal = Field(
        ...,
        description="The total amount of credit
➥ transactions in the ACH file.",
        ge=0, #5
        title="Credit Total",
    )
    debit_total: Decimal = Field(
        ...,
        description="The total amount of debit 
➥transactions in the ACH file.",
        ge=0,
        title="Debit Total",
    )

    class Config:                              
        json_schema_extra = {                  
            "example": {                       
                "id": "123e4567-e89b-12d3-a456-426614174000", 
                "date": "2024-01-01T12:00:00",  
                "filename": "ACH_20240101_123.ach", 
                "creditTotal": "1000.00",
                "debitTotal": "5000.23",
            }
        }

The response model shows typed identifiers, dates, monetary totals, field descriptions, and numeric constraints together in one API contract. section 7.3

Validation belongs at the boundary of a production system rather than being trusted to a UI or another service. A pattern can restrict a file ID to lowercase letters, digits, and underscores. FastAPI can then handle a validation error with a 400 response and tests can confirm both accepted and rejected input. Detailed errors are useful, but production responses should avoid exposing sensitive information. section 4.9.3

Validate known and changing business values

Some rules are structural: a file ID modifier must be one uppercase letter or digit. Others depend on current business data: an ACH immediate destination must match an allowed bank routing number. A field_validator can call database-backed logic for that second rule, avoiding hardcoded routing numbers that may change after a merger or acquisition. Consider the cost of database validation when many records require checks. section 8.5.3

Use Pydantic models to make an API progressively more dependable:

  • Declare a BaseModel for each response shape instead of returning an unstructured dictionary. section 4.9.2
  • Add Field titles, descriptions, examples, and constraints so generated API documentation serves developers, QA, technical writers, and consumers. section 4.9.2 section 7.3
  • Test valid and invalid inputs, then translate validation failures into responses appropriate for the environment. section 4.9.3
  • Separate API and database schemas when their responsibilities and exposed data differ. section 7.3

Pydantic also supports database-oriented modeling, documentation, and validation while SQL handles storage and queries. When validation or parsing routines become overly complex, split responsibilities into focused record-type classes rather than allowing a parser to absorb every rule. section 5.12 section 8.5.3

How Build Financial Software with Generative AI (From Scratch) covers it

How deep it goes
Builds models, field metadata, pattern constraints, exception handling, tests, and database-backed field validation.
Examples
Uses AchFile and AchFilesResponse models, file-ID patterns, validation-error tests, and bank-routing-number checks.
What it assumes
Introduces model and validation usage through Python API examples without assuming advanced framework knowledge.
What you can do after
Apply it via Pydantic to define documented response models and enforce structural or database-backed validation rules.
How it connects
Connects FastAPI, OpenAPI, BaseModel, Field, field_validator, SQL, unit tests, and Docker deployment.

Also explained in

Compare how 4 books explain Pydantic →

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Build Financial Software with Generative AI (From Scratch). The section links point to the parts of the book it draws on.