Skip to content

pointer_from_model

pydantic_jsonpointer._model_path

pointer_from_model

pointer_from_model(
    model: type[_T],
    *,
    resolver: FieldResolver | None = None,
) -> _ModelPath[_T, Any]
pointer_from_model(
    model: _T, *, resolver: FieldResolver | None = None
) -> _ModelPath[_T, Any]
pointer_from_model(
    model: type[BaseModel] | BaseModel,
    *,
    resolver: FieldResolver | None = None,
) -> _ModelPath[Any, Any]

Start building a JsonPointer from a pydantic model's attribute chain.

Accepts either a model class or an instance. Instance entry uses only type(model) — no runtime instance peeking. For Union-typed fields, narrow with isinstance and pass the narrowed value.

Usage::

ptr = pointer_from_model(User).name
ptr = pointer_from_model(User).address.city
ptr = pointer_from_model(Order).items[0].name
if isinstance(event.payload, JsonBody):
    ptr = pointer_from_model(event.payload).body
Source code in src/pydantic_jsonpointer/_model_path.py
def pointer_from_model(
    model: type[BaseModel] | BaseModel,
    *,
    resolver: FieldResolver | None = None,
) -> _ModelPath[Any, Any]:
    """Start building a ``JsonPointer`` from a pydantic model's attribute chain.

    Accepts either a model *class* or an *instance*. Instance entry uses
    only ``type(model)`` — no runtime instance peeking. For Union-typed
    fields, narrow with ``isinstance`` and pass the narrowed value.

    Usage::

        ptr = pointer_from_model(User).name
        ptr = pointer_from_model(User).address.city
        ptr = pointer_from_model(Order).items[0].name
        if isinstance(event.payload, JsonBody):
            ptr = pointer_from_model(event.payload).body
    """
    if resolver is None:
        resolver = BySerializationAlias()

    if isinstance(model, BaseModel):
        model_cls = type(model)
    elif isinstance(model, type) and issubclass(model, BaseModel):
        model_cls = model
    else:
        msg = (
            f"pointer_from_model expects a BaseModel class or instance, "
            f"got {type(model).__name__}"
        )
        raise TypeError(msg)

    pending: Any = None
    effective_model_cls = model_cls
    if issubclass(model_cls, RootModel):
        root_field = model_cls.model_fields.get("root")
        if root_field is not None and root_field.annotation is not None:
            pending = root_field.annotation
            inner_cls = _advance_attr(pending)
            if inner_cls is not None:
                effective_model_cls = inner_cls

    return _ModelPath(
        _model_cls=effective_model_cls,
        _resolver=resolver,
        _pending_annotation=pending,
    )