Skip to main content

No project description provided

Project description

netaddr-pydantic

PyPI version Supported Python Version License PyPI - Downloads

Pylint Static Quality Github Action Mypy Static Quality Github Action Pylint Static Quality Github Action

Use Netaddr objects in Pydantic Models

Rational

Origin of the issue.

The ipaddress module supports Iternet Protocol addresses and networks but lacks support for funny objects such as ranges, IP sets, globbing and so on.

The Pydantic framework provides out-of-the-box support for IPv4/IPv6 addresses and networks through the ipaddress module and this allows you to easily validate or serialize data from/to interfaces.

import pydantic

class Model(pydantic.BaseModel):
    address: pydantic.IPvAnyAddress


m = Model(address="1.2.3.4")
print(type(m.address))
print(m.model_dump_json())

This produces:

<class 'ipaddress.IPv4Address'>
{"address":"1.2.3.4"}

Unfortunately, once the data is parsed, ipaddress objects cannot be inserted as-is to a netaddr.IPSet for example.

Alternatively, you would want to switch to netaddr-typed fields with like this:

import pydantic
import netaddr

class Model(pydantic.BaseModel):
    address: netaddr.IPAddress

Unfortunately, pydantic cannot compile such thing:

pydantic.errors.PydanticSchemaGenerationError: Unable to generate pydantic-core schema for <class 'netaddr.ip.IPAddress'>. Set `arbitrary_types_allowed=True` in the model_config to ignore this error or implement `__get_pydantic_core_schema__` on your type to fully support it.

If you got this error by calling handler(<some type>) within `__get_pydantic_core_schema__` then you likely need to call `handler.generate_schema(<some type>)` since we do not call `__get_pydantic_core_schema__` on `<some type>` otherwise to avoid infinite recursion.

For further information visit https://errors.pydantic.dev/2.11/u/schema-for-unknown-type

This is due to the lack of pydantic metadata in netaddr classes. Mainly, pydantic needs to know how to validate (from basic types, such as strings and integers) and how to to serialize the objects (return the basic types).

Should you use netaddr-pydantic?

A way to fix this issue is to write your own validators and serializers and if you're lazy enough (no judgement here :]), this is just what netaddr-pydantic is bringing on the table.

This code:

import pydantic
import netaddr_pydantic

class Model(pydantic.BaseModel):
    address: netaddr_pydantic.IPAddress

m = Model(address="1.2.3.4")
print(type(m.address))
print(m.model_dump_json())

Naturally produces the following:

<class 'netaddr.ip.IPAddress'>
{"address":"1.2.3.4"}

Basically, netaddr-pydantic just defines Annotated types with pydantic functional validators and serializers. For instance, IPAddress and IPNetwork are just defined this way:

from typing import Annotated
from pydantic import PlainValidator, PlainSerializer
import netaddr

IPAddress = Annotated[
    netaddr.IPAddress, PlainValidator(netaddr.IPAddress), PlainSerializer(str)
]

IPNetwork = Annotated[
    netaddr.IPNetwork, PlainValidator(netaddr.IPNetwork), PlainSerializer(str)
]

And by all means, if this is all you need, do not bother with netaddr-pydantic. But if you need to use IPRanges and/or IPSets as well then maybe you should use netaddr-pydantic, because, while IPrange and IPSet validators and serializers are just a very little bit more complex, I dont feel they are worth repeating.

Plus this is what I need in my own production environment, these days, so it will be maintained for a while.

Still there? OK, then let's see.

The netaddr-pydantic annotations are only really useful in a pydantic context. You can use plain netaddr in other places.

Supported objects and conversions

Object Types Can be obtained from Serialized as Comment
IPAddress str, int str
IPNetwork str, 2-items tuple or list a CIDR str
IPRange "<start-ip>-<end-ip>" str or 2-items list or tuple a "<start-ip>-<end-ip>" str
IPSet list, tuple or set of strs or ints list of strs. The IPSet.iter_cidrs is used to compute the items of the list. If you do not want to work with IPSet, use list[IPAddress | IPNetwork], or similar.
IPGlob str str netaddr implementation seems to be limited to IPv4

The validation relies mostly on netaddr objects constructors. There's currently no bijection possible from the validated format to the serialized format. I do not intend to implement it at this time.

Additionnal features

That may not be much, but an IPAny type is available. pydantic should produce the most acccurate object depending of the source object. An IPAny field will produce

  • an IPSet if provided type is list, tuple or set
  • an IPNetwork if value is a CIDR str
  • an IPRange if value is an str containing a - character
  • an IPGlob if value is an str containing a * char.
  • an IPAddress in other cases.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

netaddr_pydantic-0.1.2.tar.gz (13.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

netaddr_pydantic-0.1.2-py3-none-any.whl (14.2 kB view details)

Uploaded Python 3

File details

Details for the file netaddr_pydantic-0.1.2.tar.gz.

File metadata

  • Download URL: netaddr_pydantic-0.1.2.tar.gz
  • Upload date:
  • Size: 13.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.3 CPython/3.13.5 Linux/6.15.5-200.fc42.x86_64

File hashes

Hashes for netaddr_pydantic-0.1.2.tar.gz
Algorithm Hash digest
SHA256 d5146dea2aa56fb594a1b593bdad1ea7ca8ece5926ebaa520d0187af8ea579b8
MD5 3649dec5e4b586a4471eb43e668c04bd
BLAKE2b-256 8f38ddbd790951b8579b3d70ff002290917406461f477a3e847488ce794b281d

See more details on using hashes here.

File details

Details for the file netaddr_pydantic-0.1.2-py3-none-any.whl.

File metadata

  • Download URL: netaddr_pydantic-0.1.2-py3-none-any.whl
  • Upload date:
  • Size: 14.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: poetry/2.1.3 CPython/3.13.5 Linux/6.15.5-200.fc42.x86_64

File hashes

Hashes for netaddr_pydantic-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 9441f9705995312a570c052a711f3eefc51651b56ee22f0bbf4c7b1e8e4fefcb
MD5 c4e1ddf6507cbb59c6613542fef9b0ec
BLAKE2b-256 7efc567866fd4c05e01dd37143ac4622663973bbb6cbf3a5887bc79c08e2e176

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page