# Python Pydantic for Data Validation

Pydantic is the most widely used data validation library for Python. It uses Python type hints to validate data. It is fast, extensible, and plays nicely with IDEs and linters.

## Installation

```bash
pip install pydantic
```

## Basic Usage

Define a model by inheriting from `BaseModel` and using standard Python type hints.

```python
from pydantic import BaseModel
from typing import List, Optional

class User(BaseModel):
    id: int
    name: str = 'John Doe'
    signup_ts: Optional[str] = None
    friends: List[int] = []

external_data = {
    'id': '123',
    'signup_ts': '2019-06-01 12:22',
    'friends': [1, 2, '3'],
}

user = User(**external_data)
print(user.id)
# Output: 123 (converted to int)
print(user.friends)
# Output: [1, 2, 3] (converted elements to int)
```

## Error Handling

If validation fails, Pydantic raises a `ValidationError`.

```python
from pydantic import ValidationError

try:
    User(id='not an int', signup_ts='2019-06-01 12:22')
except ValidationError as e:
    print(e)
```

## Field Validation

You can use `Field` to add extra validation constraints (like `gt` for greater than).

```python
from pydantic import BaseModel, Field

class Item(BaseModel):
    name: str
    price: float = Field(gt=0, description="The price must be greater than zero")
    quantity: int = Field(default=1, ge=1)
```

## Custom Validators

You can define custom validation logic using the `@field_validator` decorator.

```python
from pydantic import BaseModel, field_validator

class User(BaseModel):
    name: str
    
    @field_validator('name')
    @classmethod
    def name_must_contain_space(cls, v: str) -> str:
        if ' ' not in v:
            raise ValueError('must contain a space')
        return v.title()
```

## Serialization

Pydantic models provide methods to export data.

```python
# Convert to dictionary
print(user.model_dump())

# Convert to JSON string
print(user.model_dump_json())
```

[[programming/python/python]]