Skip to content

no-any-mapping-types

String-keyed mapping types must not erase their values with Any.

Why

An Any-valued mapping disables checking transitively and conceals whether the value is a fixed record, an arbitrary JSON tree, or a genuinely opaque Python object.

Fix

Use TypedDict (and Unpack[TypedDict] for closed keyword arguments) for fixed records, a Pydantic model for untrusted runtime input, pydantic.JsonValue for arbitrary JSON, or object plus explicit narrowing for a genuinely opaque Python value.

Examples

Before — flagged An Any-valued mapping erases the record schema
app/offers.py
from typing import Any
def details() -> dict[str, Any]: ...
After — preferred A TypedDict preserves the record schema
app/offers.py
from typing import TypedDict
class OfferDetails(TypedDict):
id: str
def details() -> OfferDetails: ...

Formerly: no-vague-annotations