Skip to content
tezvyn:

Pydantic: Reusable Validation with Annotated Types

Source: pydantic.devMediumHow cards are made

Pydantic: Reusable Validation with Annotated Types

Pydantic's Annotated attaches validation logic directly to a type, making it reusable. Define a custom type like SquareNumber once and apply it to any model field, ensuring consistent validation without repeating code.

Why it exists

When the same validation logic applies to many fields across different models, repeating that logic is inefficient and error-prone. Pydantic's Annotated validators solve this by letting you attach validation directly to a type, creating a single source of truth for that logic.

The mental model

Think of Annotated as creating a "validated type alias". Instead of just declaring a field as an int, you can declare it as a PositiveInt or EvenInteger. The validation rules become an intrinsic part of the type's definition, making your models more declarative and your validation logic reusable.

How it works

You use typing.Annotated to wrap a base type (like int) and add one or more Pydantic validators. Pydantic offers four main kinds. First, AfterValidator runs after Pydantic's standard parsing and type coercion, making it the safest choice. Second, BeforeValidator runs on the raw input before any Pydantic processing, offering flexibility at the cost of safety. Third, PlainValidator is a 'before' validator that bypasses all other Pydantic validation. Fourth, WrapValidator is the most powerful, letting you execute code both before and after other validators.

When to use it

Use Annotated validators when validation logic is intrinsic to a data type, not just a specific field in a model. This is ideal for building a library of custom, reusable types for your project, such as NonEmptyString, EmailStr, or domain-specific types like SKU. This improves code clarity and centralizes validation logic.

When not to use it

Avoid Annotated for logic that depends on multiple fields within the same model. For cross-field validation, such as checking if password_confirmation matches password, a model validator (@model_validator) is the appropriate tool. Annotated is designed for validating a single value in isolation.

One canonical example

Let's create a PerfectSquare type that only accepts integers that are perfect squares. First, define the validation function: def check_is_square(v: int): if v**0.5 % 1 != 0: raise ValueError(f'{v} is not a perfect square'); return v. Then, create the type alias: PerfectSquare = Annotated[int, AfterValidator(check_is_square)]. Now you can use it in a model: class Item(BaseModel): quantity: PerfectSquare. An instance like Item(quantity=25) will pass, but Item(quantity=26) will raise a ValidationError.

Interview question

Which scenario best illustrates the intended use of Pydantic's Annotated types for validation?

  • a.Defining a field that requires a specific validation function to run before any Pydantic type coercion occurs.
  • b.Overriding Pydantic's default type parsing and validation entirely for a specific field.
  • c.Implementing validation logic that depends on the values of multiple fields within the same model.
  • d.Creating a custom type alias with intrinsic validation rules that can be reused across different models.Correct
Why?

The card states that Annotated types are for "reusable validation logic" and creating a "validated type alias" where "validation rules become an intrinsic part of the type's definition." Option C describes a cross-field validation, which the card explicitly advises against using Annotated for, recommending a model validator instead.

Just read this? Test yourself on what you have been reading.

Read the original → pydantic.dev

You just looked this up. Could you explain it out loud?

That is the part interviews actually test. Tezvyn takes questions like this one and gives you what the interviewer is really checking, the answer that lands, and the mistake that ends the conversation, in the four minutes before your next meeting.

The iPhone app is on the way

We are building it. Until it lands, nothing here is held back from you: every interview card, your saved cards, streaks and the job board all work in Safari, plus hundreds of free practice quizzes of thirty questions each. Sign in and it all carries over to the app the day it arrives.

Want it as an icon? Tap Share at the bottom of Safari, then Add to Home Screen. It opens full screen and the cards you have read stay available offline.

Get it on Google PlayiPhone app coming soon

We are hiring for this. Open roles that interview on pydantic — each one lists the topics its interview covers.

See open roles