typing_validation.nodes

The node model: one interned node per distinct type, holding the type it was built from, its form, its interned children, and its memoised properties.

Everything except validate is built on this one class. It is simultaneously the unit of interning, the thing inspect_type reports, and the thing that explains a failure. It can be all of those at once precisely because none of them is on a hot path — which is also why this module may share freely with them, and why it shares nothing with the interpreter.

TypeForm

final class TypeForm(*values)[source]

Bases: Enum

What kind of type a node is, mirroring the catalogue in TYPES.md.

ALIAS = 'alias'

A PEP 695 type alias, and the point at which a recursive type closes.

ANNOTATED = 'Annotated'

Annotated, validated as the type it wraps.

ANY = 'Any'

Any: every value is valid.

ANY_NAMED_TUPLE = 'any NamedTuple'

Bare typing.NamedTuple: any named tuple instance.

CLASS = 'class'

A plain class or abstract base class, checked with isinstance.

COLLECTION = 'collection'

A collection whose every item is checked against one type argument.

GENERIC_CLASS = 'generic class'

A parametrised class whose arguments cannot be checked, by design.

ITERATOR = 'iterator'

An iterator, whose items cannot be checked without consuming it.

LITERAL = 'literal'

A Literal, whose children are values rather than types.

MAPPING = 'mapping'

A mapping whose keys and values are each checked against an argument.

MAYBE_ITEMS = 'iterable or container'

An iterable or container, whose items are checked only when the value is also a Collection.

NAMED_TUPLE = 'NamedTuple'

A concrete named tuple class, whose children are its field types.

NEW_TYPE = 'NewType'

A NewType, validated as its supertype.

NONE = 'None'

None and types.NoneType.

PLUGIN = 'plugin'

A parametrised class whose arguments a plugin knows how to check.

PROTOCOL = 'protocol'

A runtime-checkable protocol.

TUPLE = 'tuple'

A fixed-length, variadic or empty tuple.

TYPED_DICT = 'TypedDict'

A TypedDict, whose children are its field types.

TYPE_OF = 'type of'

Type[T] and type[T].

TYPE_VAR = 'type variable'

A type variable, checked against its bound or its constraints.

UNION = 'union'

A union: valid if at least one member is.

UNSUPPORTED = 'unsupported'

A type we cannot validate against. Poisons whatever contains it.

TypeNode

final class TypeNode(t, /)[source]

Bases: object

One distinct type, analysed.

Nodes are interned on the type itself, so list[int] is analysed once and shared everywhere it occurs. Interning is never semantically observable: a cold, cleared or bypassed cache changes cost and nothing else. That is what lets an unhashable type simply skip the cache, and what makes eviction safe to expose at all.

property children

The nodes for this type’s component types.

Return type:

tuple[TypeNode, …]

property form

What kind of type this is.

Return type:

TypeForm

property labels

Names for the children, where they have them.

Return type:

tuple[str, …] | None

property reason

Why this node itself is unsupported, if it is.

Return type:

str | None

property supported

Whether this type, and every component of it, can be validated against.

Support is all-or-nothing: one unsupported component poisons the whole type, transitively.

Return type:

bool

property t

The type this node describes.

Return type:

Any

unsupported_components()[source]

The nodes that make this type unsupported, in the order met.

Totality means the answer to “can this be validated” is always “no” once anything in here is non-empty. It should never be an opaque “no”, so this names the culprits rather than the victim.

Return type:

tuple[TypeNode, …]

walk()[source]

Every distinct node reachable from this one, including itself.

Terminates on recursive types: the graph is not a tree, and not even a DAG, so nodes already met are not revisited.

Return type:

Iterator[TypeNode]

node_for

node_for(t, /)[source]

The interned node for a type, building it if it is not already cached.

Parameters:

t (Any)

Return type:

TypeNode