"""Code generated by Speakeasy (https://speakeasy.com). DO NOT EDIT."""

from __future__ import annotations
from .pricefeature import PriceFeature, PriceFeatureTypedDict
from .priceproperties_union import PricePropertiesUnion, PricePropertiesUnionTypedDict
from datetime import datetime
from paygentic_sdk.types import (
    BaseModel,
    Nullable,
    OptionalNullable,
    UNSET,
    UNSET_SENTINEL,
    UnrecognizedStr,
)
import pydantic
from pydantic import model_serializer
from typing import List, Literal, Optional, Union
from typing_extensions import Annotated, NotRequired, TypedDict


SchemasPriceObject = Literal["price",]


SchemasPriceModel = Union[
    Literal[
        "standard",
        "dynamic",
        "volume",
        "percentage",
    ],
    UnrecognizedStr,
]


SchemasPricePaymentTerm = Union[
    Literal[
        "instant",
        "in_arrears",
        "in_advance",
    ],
    UnrecognizedStr,
]


class SchemasPriceTypedDict(TypedDict):
    id: str
    r"""Unique identifier for a price"""
    created_at: datetime
    invoice_display_name: str
    payment_term: SchemasPricePaymentTerm
    properties: PricePropertiesUnionTypedDict
    updated_at: datetime
    object: NotRequired[SchemasPriceObject]
    billable_metric_id: NotRequired[str]
    r"""Unique identifier for a billable metric"""
    fee_id: NotRequired[str]
    r"""The unique identifier for the fee referred to by this price. Present when price is linked to a fee."""
    billing_cadence: NotRequired[Nullable[str]]
    r"""ISO 8601 duration. 'P0D' for one-time, 'P1M' for monthly, 'P1Y' for yearly. Required for fees, optional for billable metrics. Defaults to plan's billingCadence if not specified."""
    model: NotRequired[SchemasPriceModel]
    features: NotRequired[List[PriceFeatureTypedDict]]
    r"""Features associated with this price"""


class SchemasPrice(BaseModel):
    id: str
    r"""Unique identifier for a price"""

    created_at: Annotated[datetime, pydantic.Field(alias="createdAt")]

    invoice_display_name: Annotated[str, pydantic.Field(alias="invoiceDisplayName")]

    payment_term: Annotated[
        SchemasPricePaymentTerm, pydantic.Field(alias="paymentTerm")
    ]

    properties: PricePropertiesUnion

    updated_at: Annotated[datetime, pydantic.Field(alias="updatedAt")]

    object: Optional[SchemasPriceObject] = "price"

    billable_metric_id: Annotated[
        Optional[str], pydantic.Field(alias="billableMetricId")
    ] = None
    r"""Unique identifier for a billable metric"""

    fee_id: Annotated[Optional[str], pydantic.Field(alias="feeId")] = None
    r"""The unique identifier for the fee referred to by this price. Present when price is linked to a fee."""

    billing_cadence: Annotated[
        OptionalNullable[str], pydantic.Field(alias="billingCadence")
    ] = UNSET
    r"""ISO 8601 duration. 'P0D' for one-time, 'P1M' for monthly, 'P1Y' for yearly. Required for fees, optional for billable metrics. Defaults to plan's billingCadence if not specified."""

    model: Optional[SchemasPriceModel] = None

    features: Optional[List[PriceFeature]] = None
    r"""Features associated with this price"""

    @model_serializer(mode="wrap")
    def _serialize_model(self, handler):
        optional_fields = set(
            [
                "object",
                "billableMetricId",
                "feeId",
                "billingCadence",
                "model",
                "features",
            ]
        )
        nullable_fields = set(["billingCadence"])
        serialized = handler(self)
        m = {}

        for n, f in type(self).model_fields.items():
            k = f.alias or n
            val = serialized.get(k, serialized.get(n))
            is_nullable_and_explicitly_set = (
                k in nullable_fields
                and (self.__pydantic_fields_set__.intersection({n}))  # pylint: disable=no-member
            )

            if val != UNSET_SENTINEL:
                if (
                    val is not None
                    or k not in optional_fields
                    or is_nullable_and_explicitly_set
                ):
                    m[k] = val

        return m


try:
    SchemasPrice.model_rebuild()
except NameError:
    pass
