# DO NOT EDIT! This file is automatically generated
import datetime
import enum
import typing

from commercetools.types._abstract import _BaseType

if typing.TYPE_CHECKING:
    from ._channel import ChannelReference, ChannelResourceIdentifier
    from ._customer import CustomerReference
    from ._customer_group import CustomerGroupReference, CustomerGroupResourceIdentifier
    from ._product import FacetResults
    from ._product_discount import ProductDiscountReference
    from ._type import CustomFields, CustomFieldsDraft
__all__ = [
    "Address",
    "Asset",
    "AssetDimensions",
    "AssetDraft",
    "AssetSource",
    "BaseResource",
    "CentPrecisionMoney",
    "CentPrecisionMoneyDraft",
    "ClientLogging",
    "CreatedBy",
    "DiscountedPrice",
    "GeoJson",
    "GeoJsonPoint",
    "HighPrecisionMoney",
    "HighPrecisionMoneyDraft",
    "Image",
    "ImageDimensions",
    "KeyReference",
    "LastModifiedBy",
    "LocalizedString",
    "Money",
    "MoneyType",
    "PagedQueryResponse",
    "Price",
    "PriceDraft",
    "PriceTier",
    "PriceTierDraft",
    "QueryPrice",
    "Reference",
    "ReferenceTypeId",
    "ResourceIdentifier",
    "ScopedPrice",
    "TypedMoney",
    "TypedMoneyDraft",
    "Update",
    "UpdateAction",
]


class Address(_BaseType):
    #: Optional :class:`str`
    id: typing.Optional[str]
    #: Optional :class:`str`
    key: typing.Optional[str]
    #: Optional :class:`str`
    title: typing.Optional[str]
    #: Optional :class:`str`
    salutation: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``firstName`` `in Commercetools)`
    first_name: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``lastName`` `in Commercetools)`
    last_name: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``streetName`` `in Commercetools)`
    street_name: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``streetNumber`` `in Commercetools)`
    street_number: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``additionalStreetInfo`` `in Commercetools)`
    additional_street_info: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``postalCode`` `in Commercetools)`
    postal_code: typing.Optional[str]
    #: Optional :class:`str`
    city: typing.Optional[str]
    #: Optional :class:`str`
    region: typing.Optional[str]
    #: Optional :class:`str`
    state: typing.Optional[str]
    #: :class:`str`
    country: "str"
    #: Optional :class:`str`
    company: typing.Optional[str]
    #: Optional :class:`str`
    department: typing.Optional[str]
    #: Optional :class:`str`
    building: typing.Optional[str]
    #: Optional :class:`str`
    apartment: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``pOBox`` `in Commercetools)`
    p_o_box: typing.Optional[str]
    #: Optional :class:`str`
    phone: typing.Optional[str]
    #: Optional :class:`str`
    mobile: typing.Optional[str]
    #: Optional :class:`str`
    email: typing.Optional[str]
    #: Optional :class:`str`
    fax: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``additionalAddressInfo`` `in Commercetools)`
    additional_address_info: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``externalId`` `in Commercetools)`
    external_id: typing.Optional[str]

    def __init__(
        self,
        *,
        country: "str",
        id: typing.Optional[str] = None,
        key: typing.Optional[str] = None,
        title: typing.Optional[str] = None,
        salutation: typing.Optional[str] = None,
        first_name: typing.Optional[str] = None,
        last_name: typing.Optional[str] = None,
        street_name: typing.Optional[str] = None,
        street_number: typing.Optional[str] = None,
        additional_street_info: typing.Optional[str] = None,
        postal_code: typing.Optional[str] = None,
        city: typing.Optional[str] = None,
        region: typing.Optional[str] = None,
        state: typing.Optional[str] = None,
        company: typing.Optional[str] = None,
        department: typing.Optional[str] = None,
        building: typing.Optional[str] = None,
        apartment: typing.Optional[str] = None,
        p_o_box: typing.Optional[str] = None,
        phone: typing.Optional[str] = None,
        mobile: typing.Optional[str] = None,
        email: typing.Optional[str] = None,
        fax: typing.Optional[str] = None,
        additional_address_info: typing.Optional[str] = None,
        external_id: typing.Optional[str] = None,
    ) -> None:
        self.id = id
        self.key = key
        self.title = title
        self.salutation = salutation
        self.first_name = first_name
        self.last_name = last_name
        self.street_name = street_name
        self.street_number = street_number
        self.additional_street_info = additional_street_info
        self.postal_code = postal_code
        self.city = city
        self.region = region
        self.state = state
        self.country = country
        self.company = company
        self.department = department
        self.building = building
        self.apartment = apartment
        self.p_o_box = p_o_box
        self.phone = phone
        self.mobile = mobile
        self.email = email
        self.fax = fax
        self.additional_address_info = additional_address_info
        self.external_id = external_id
        super().__init__()

    def __repr__(self) -> str:
        return (
            "Address(id=%r, key=%r, title=%r, salutation=%r, first_name=%r, last_name=%r, street_name=%r, street_number=%r, additional_street_info=%r, postal_code=%r, city=%r, region=%r, state=%r, country=%r, company=%r, department=%r, building=%r, apartment=%r, p_o_box=%r, phone=%r, mobile=%r, email=%r, fax=%r, additional_address_info=%r, external_id=%r)"
            % (
                self.id,
                self.key,
                self.title,
                self.salutation,
                self.first_name,
                self.last_name,
                self.street_name,
                self.street_number,
                self.additional_street_info,
                self.postal_code,
                self.city,
                self.region,
                self.state,
                self.country,
                self.company,
                self.department,
                self.building,
                self.apartment,
                self.p_o_box,
                self.phone,
                self.mobile,
                self.email,
                self.fax,
                self.additional_address_info,
                self.external_id,
            )
        )


class Asset(_BaseType):
    #: :class:`str`
    id: str
    #: List of :class:`commercetools.types.AssetSource`
    sources: typing.List["AssetSource"]
    #: :class:`commercetools.types.LocalizedString`
    name: "LocalizedString"
    #: Optional :class:`commercetools.types.LocalizedString`
    description: typing.Optional["LocalizedString"]
    #: Optional list of :class:`str`
    tags: typing.Optional[typing.List[str]]
    #: Optional :class:`commercetools.types.CustomFields`
    custom: typing.Optional["CustomFields"]
    #: Optional :class:`str`
    key: typing.Optional[str]

    def __init__(
        self,
        *,
        id: str,
        sources: typing.List["AssetSource"],
        name: "LocalizedString",
        description: typing.Optional["LocalizedString"] = None,
        tags: typing.Optional[typing.List[str]] = None,
        custom: typing.Optional["CustomFields"] = None,
        key: typing.Optional[str] = None,
    ) -> None:
        self.id = id
        self.sources = sources
        self.name = name
        self.description = description
        self.tags = tags
        self.custom = custom
        self.key = key
        super().__init__()

    def __repr__(self) -> str:
        return (
            "Asset(id=%r, sources=%r, name=%r, description=%r, tags=%r, custom=%r, key=%r)"
            % (
                self.id,
                self.sources,
                self.name,
                self.description,
                self.tags,
                self.custom,
                self.key,
            )
        )


class AssetDimensions(_BaseType):
    #: :class:`int`
    w: int
    #: :class:`int`
    h: int

    def __init__(self, *, w: int, h: int) -> None:
        self.w = w
        self.h = h
        super().__init__()

    def __repr__(self) -> str:
        return "AssetDimensions(w=%r, h=%r)" % (self.w, self.h)


class AssetDraft(_BaseType):
    #: List of :class:`commercetools.types.AssetSource`
    sources: typing.List["AssetSource"]
    #: :class:`commercetools.types.LocalizedString`
    name: "LocalizedString"
    #: Optional :class:`commercetools.types.LocalizedString`
    description: typing.Optional["LocalizedString"]
    #: Optional list of :class:`str`
    tags: typing.Optional[typing.List[str]]
    #: Optional :class:`commercetools.types.CustomFieldsDraft`
    custom: typing.Optional["CustomFieldsDraft"]
    #: Optional :class:`str`
    key: typing.Optional[str]

    def __init__(
        self,
        *,
        sources: typing.List["AssetSource"],
        name: "LocalizedString",
        description: typing.Optional["LocalizedString"] = None,
        tags: typing.Optional[typing.List[str]] = None,
        custom: typing.Optional["CustomFieldsDraft"] = None,
        key: typing.Optional[str] = None,
    ) -> None:
        self.sources = sources
        self.name = name
        self.description = description
        self.tags = tags
        self.custom = custom
        self.key = key
        super().__init__()

    def __repr__(self) -> str:
        return (
            "AssetDraft(sources=%r, name=%r, description=%r, tags=%r, custom=%r, key=%r)"
            % (
                self.sources,
                self.name,
                self.description,
                self.tags,
                self.custom,
                self.key,
            )
        )


class AssetSource(_BaseType):
    #: :class:`str`
    uri: str
    #: Optional :class:`str`
    key: typing.Optional[str]
    #: Optional :class:`commercetools.types.AssetDimensions`
    dimensions: typing.Optional["AssetDimensions"]
    #: Optional :class:`str` `(Named` ``contentType`` `in Commercetools)`
    content_type: typing.Optional[str]

    def __init__(
        self,
        *,
        uri: str,
        key: typing.Optional[str] = None,
        dimensions: typing.Optional["AssetDimensions"] = None,
        content_type: typing.Optional[str] = None,
    ) -> None:
        self.uri = uri
        self.key = key
        self.dimensions = dimensions
        self.content_type = content_type
        super().__init__()

    def __repr__(self) -> str:
        return "AssetSource(uri=%r, key=%r, dimensions=%r, content_type=%r)" % (
            self.uri,
            self.key,
            self.dimensions,
            self.content_type,
        )


class BaseResource(_BaseType):
    #: :class:`str`
    id: str
    #: :class:`int`
    version: int
    #: :class:`datetime.datetime` `(Named` ``createdAt`` `in Commercetools)`
    created_at: datetime.datetime
    #: :class:`datetime.datetime` `(Named` ``lastModifiedAt`` `in Commercetools)`
    last_modified_at: datetime.datetime

    def __init__(
        self,
        *,
        id: str,
        version: int,
        created_at: datetime.datetime,
        last_modified_at: datetime.datetime,
    ) -> None:
        self.id = id
        self.version = version
        self.created_at = created_at
        self.last_modified_at = last_modified_at
        super().__init__()

    def __repr__(self) -> str:
        return "BaseResource(id=%r, version=%r, created_at=%r, last_modified_at=%r)" % (
            self.id,
            self.version,
            self.created_at,
            self.last_modified_at,
        )


class ClientLogging(_BaseType):
    #: Optional :class:`str` `(Named` ``clientId`` `in Commercetools)`
    client_id: typing.Optional[str]
    #: Optional :class:`str` `(Named` ``externalUserId`` `in Commercetools)`
    external_user_id: typing.Optional[str]
    #: Optional :class:`commercetools.types.CustomerReference`
    customer: typing.Optional["CustomerReference"]
    #: Optional :class:`str` `(Named` ``anonymousId`` `in Commercetools)`
    anonymous_id: typing.Optional[str]

    def __init__(
        self,
        *,
        client_id: typing.Optional[str] = None,
        external_user_id: typing.Optional[str] = None,
        customer: typing.Optional["CustomerReference"] = None,
        anonymous_id: typing.Optional[str] = None,
    ) -> None:
        self.client_id = client_id
        self.external_user_id = external_user_id
        self.customer = customer
        self.anonymous_id = anonymous_id
        super().__init__()

    def __repr__(self) -> str:
        return (
            "ClientLogging(client_id=%r, external_user_id=%r, customer=%r, anonymous_id=%r)"
            % (self.client_id, self.external_user_id, self.customer, self.anonymous_id)
        )


class DiscountedPrice(_BaseType):
    #: :class:`commercetools.types.Money`
    value: "Money"
    #: :class:`commercetools.types.ProductDiscountReference`
    discount: "ProductDiscountReference"

    def __init__(self, *, value: "Money", discount: "ProductDiscountReference") -> None:
        self.value = value
        self.discount = discount
        super().__init__()

    def __repr__(self) -> str:
        return "DiscountedPrice(value=%r, discount=%r)" % (self.value, self.discount)


class GeoJson(_BaseType):
    #: :class:`str`
    type: str

    def __init__(self, *, type: str) -> None:
        self.type = type
        super().__init__()

    def __repr__(self) -> str:
        return "GeoJson(type=%r)" % (self.type,)


class Image(_BaseType):
    #: :class:`str`
    url: str
    #: :class:`commercetools.types.ImageDimensions`
    dimensions: "ImageDimensions"
    #: Optional :class:`str`
    label: typing.Optional[str]

    def __init__(
        self,
        *,
        url: str,
        dimensions: "ImageDimensions",
        label: typing.Optional[str] = None,
    ) -> None:
        self.url = url
        self.dimensions = dimensions
        self.label = label
        super().__init__()

    def __repr__(self) -> str:
        return "Image(url=%r, dimensions=%r, label=%r)" % (
            self.url,
            self.dimensions,
            self.label,
        )


class ImageDimensions(_BaseType):
    #: :class:`int`
    w: int
    #: :class:`int`
    h: int

    def __init__(self, *, w: int, h: int) -> None:
        self.w = w
        self.h = h
        super().__init__()

    def __repr__(self) -> str:
        return "ImageDimensions(w=%r, h=%r)" % (self.w, self.h)


class KeyReference(_BaseType):
    #: :class:`commercetools.types.ReferenceTypeId` `(Named` ``typeId`` `in Commercetools)`
    type_id: "ReferenceTypeId"
    #: :class:`str`
    key: str

    def __init__(self, *, type_id: "ReferenceTypeId", key: str) -> None:
        self.type_id = type_id
        self.key = key
        super().__init__()

    def __repr__(self) -> str:
        return "KeyReference(type_id=%r, key=%r)" % (self.type_id, self.key)


class LocalizedString(typing.Dict[str, str]):
    def __repr__(self) -> str:
        return "LocalizedString(%s)" % (
            ", ".join(f"{k}={v!r}" for k, v in self.items())
        )


class Money(_BaseType):
    #: :class:`int` `(Named` ``centAmount`` `in Commercetools)`
    cent_amount: int
    #: :class:`str` `(Named` ``currencyCode`` `in Commercetools)`
    currency_code: "str"

    def __init__(self, *, cent_amount: int, currency_code: "str") -> None:
        self.cent_amount = cent_amount
        self.currency_code = currency_code
        super().__init__()

    def __repr__(self) -> str:
        return "Money(cent_amount=%r, currency_code=%r)" % (
            self.cent_amount,
            self.currency_code,
        )


class MoneyType(enum.Enum):
    CENT_PRECISION = "centPrecision"
    HIGH_PRECISION = "highPrecision"


class PagedQueryResponse(_BaseType):
    #: :class:`int`
    limit: int
    #: :class:`int`
    count: int
    #: Optional :class:`int`
    total: typing.Optional[int]
    #: :class:`int`
    offset: int
    #: List of :class:`commercetools.types.BaseResource`
    results: typing.Sequence["BaseResource"]
    #: Optional :class:`commercetools.types.FacetResults`
    facets: typing.Optional["FacetResults"]
    #: Optional :class:`object`
    meta: typing.Optional[object]

    def __init__(
        self,
        *,
        limit: int,
        count: int,
        offset: int,
        results: typing.Sequence["BaseResource"],
        total: typing.Optional[int] = None,
        facets: typing.Optional["FacetResults"] = None,
        meta: typing.Optional[object] = None,
    ) -> None:
        self.limit = limit
        self.count = count
        self.total = total
        self.offset = offset
        self.results = results
        self.facets = facets
        self.meta = meta
        super().__init__()

    def __repr__(self) -> str:
        return (
            "PagedQueryResponse(limit=%r, count=%r, total=%r, offset=%r, results=%r, facets=%r, meta=%r)"
            % (
                self.limit,
                self.count,
                self.total,
                self.offset,
                self.results,
                self.facets,
                self.meta,
            )
        )


class Price(_BaseType):
    #: :class:`str`
    id: str
    #: :class:`commercetools.types.TypedMoney`
    value: "TypedMoney"
    #: Optional :class:`str`
    country: typing.Optional["str"]
    #: Optional :class:`commercetools.types.CustomerGroupReference` `(Named` ``customerGroup`` `in Commercetools)`
    customer_group: typing.Optional["CustomerGroupReference"]
    #: Optional :class:`commercetools.types.ChannelReference`
    channel: typing.Optional["ChannelReference"]
    #: Optional :class:`datetime.datetime` `(Named` ``validFrom`` `in Commercetools)`
    valid_from: typing.Optional[datetime.datetime]
    #: Optional :class:`datetime.datetime` `(Named` ``validUntil`` `in Commercetools)`
    valid_until: typing.Optional[datetime.datetime]
    #: Optional :class:`commercetools.types.DiscountedPrice`
    discounted: typing.Optional["DiscountedPrice"]
    #: Optional :class:`commercetools.types.CustomFields`
    custom: typing.Optional["CustomFields"]
    #: Optional list of :class:`commercetools.types.PriceTier`
    tiers: typing.Optional[typing.List["PriceTier"]]

    def __init__(
        self,
        *,
        id: str,
        value: "TypedMoney",
        country: typing.Optional["str"] = None,
        customer_group: typing.Optional["CustomerGroupReference"] = None,
        channel: typing.Optional["ChannelReference"] = None,
        valid_from: typing.Optional[datetime.datetime] = None,
        valid_until: typing.Optional[datetime.datetime] = None,
        discounted: typing.Optional["DiscountedPrice"] = None,
        custom: typing.Optional["CustomFields"] = None,
        tiers: typing.Optional[typing.List["PriceTier"]] = None,
    ) -> None:
        self.id = id
        self.value = value
        self.country = country
        self.customer_group = customer_group
        self.channel = channel
        self.valid_from = valid_from
        self.valid_until = valid_until
        self.discounted = discounted
        self.custom = custom
        self.tiers = tiers
        super().__init__()

    def __repr__(self) -> str:
        return (
            "Price(id=%r, value=%r, country=%r, customer_group=%r, channel=%r, valid_from=%r, valid_until=%r, discounted=%r, custom=%r, tiers=%r)"
            % (
                self.id,
                self.value,
                self.country,
                self.customer_group,
                self.channel,
                self.valid_from,
                self.valid_until,
                self.discounted,
                self.custom,
                self.tiers,
            )
        )


class PriceDraft(_BaseType):
    #: :class:`commercetools.types.Money`
    value: "Money"
    #: Optional :class:`str`
    country: typing.Optional["str"]
    #: Optional :class:`commercetools.types.CustomerGroupResourceIdentifier` `(Named` ``customerGroup`` `in Commercetools)`
    customer_group: typing.Optional["CustomerGroupResourceIdentifier"]
    #: Optional :class:`commercetools.types.ChannelResourceIdentifier`
    channel: typing.Optional["ChannelResourceIdentifier"]
    #: Optional :class:`datetime.datetime` `(Named` ``validFrom`` `in Commercetools)`
    valid_from: typing.Optional[datetime.datetime]
    #: Optional :class:`datetime.datetime` `(Named` ``validUntil`` `in Commercetools)`
    valid_until: typing.Optional[datetime.datetime]
    #: Optional :class:`commercetools.types.CustomFieldsDraft`
    custom: typing.Optional["CustomFieldsDraft"]
    #: Optional list of :class:`commercetools.types.PriceTierDraft`
    tiers: typing.Optional[typing.List["PriceTierDraft"]]
    #: Optional :class:`commercetools.types.DiscountedPrice`
    discounted: typing.Optional["DiscountedPrice"]

    def __init__(
        self,
        *,
        value: "Money",
        country: typing.Optional["str"] = None,
        customer_group: typing.Optional["CustomerGroupResourceIdentifier"] = None,
        channel: typing.Optional["ChannelResourceIdentifier"] = None,
        valid_from: typing.Optional[datetime.datetime] = None,
        valid_until: typing.Optional[datetime.datetime] = None,
        custom: typing.Optional["CustomFieldsDraft"] = None,
        tiers: typing.Optional[typing.List["PriceTierDraft"]] = None,
        discounted: typing.Optional["DiscountedPrice"] = None,
    ) -> None:
        self.value = value
        self.country = country
        self.customer_group = customer_group
        self.channel = channel
        self.valid_from = valid_from
        self.valid_until = valid_until
        self.custom = custom
        self.tiers = tiers
        self.discounted = discounted
        super().__init__()

    def __repr__(self) -> str:
        return (
            "PriceDraft(value=%r, country=%r, customer_group=%r, channel=%r, valid_from=%r, valid_until=%r, custom=%r, tiers=%r, discounted=%r)"
            % (
                self.value,
                self.country,
                self.customer_group,
                self.channel,
                self.valid_from,
                self.valid_until,
                self.custom,
                self.tiers,
                self.discounted,
            )
        )


class PriceTier(_BaseType):
    #: :class:`int` `(Named` ``minimumQuantity`` `in Commercetools)`
    minimum_quantity: int
    #: :class:`commercetools.types.TypedMoney`
    value: "TypedMoney"

    def __init__(self, *, minimum_quantity: int, value: "TypedMoney") -> None:
        self.minimum_quantity = minimum_quantity
        self.value = value
        super().__init__()

    def __repr__(self) -> str:
        return "PriceTier(minimum_quantity=%r, value=%r)" % (
            self.minimum_quantity,
            self.value,
        )


class PriceTierDraft(_BaseType):
    #: :class:`int` `(Named` ``minimumQuantity`` `in Commercetools)`
    minimum_quantity: int
    #: :class:`commercetools.types.Money`
    value: "Money"

    def __init__(self, *, minimum_quantity: int, value: "Money") -> None:
        self.minimum_quantity = minimum_quantity
        self.value = value
        super().__init__()

    def __repr__(self) -> str:
        return "PriceTierDraft(minimum_quantity=%r, value=%r)" % (
            self.minimum_quantity,
            self.value,
        )


class QueryPrice(_BaseType):
    #: :class:`str`
    id: str
    #: :class:`commercetools.types.Money`
    value: "Money"
    #: Optional :class:`str`
    country: typing.Optional["str"]
    #: Optional :class:`commercetools.types.CustomerGroupReference` `(Named` ``customerGroup`` `in Commercetools)`
    customer_group: typing.Optional["CustomerGroupReference"]
    #: Optional :class:`commercetools.types.ChannelReference`
    channel: typing.Optional["ChannelReference"]
    #: Optional :class:`datetime.datetime` `(Named` ``validFrom`` `in Commercetools)`
    valid_from: typing.Optional[datetime.datetime]
    #: Optional :class:`datetime.datetime` `(Named` ``validUntil`` `in Commercetools)`
    valid_until: typing.Optional[datetime.datetime]
    #: Optional :class:`commercetools.types.DiscountedPrice`
    discounted: typing.Optional["DiscountedPrice"]
    #: Optional :class:`commercetools.types.CustomFields`
    custom: typing.Optional["CustomFields"]
    #: Optional list of :class:`commercetools.types.PriceTierDraft`
    tiers: typing.Optional[typing.List["PriceTierDraft"]]

    def __init__(
        self,
        *,
        id: str,
        value: "Money",
        country: typing.Optional["str"] = None,
        customer_group: typing.Optional["CustomerGroupReference"] = None,
        channel: typing.Optional["ChannelReference"] = None,
        valid_from: typing.Optional[datetime.datetime] = None,
        valid_until: typing.Optional[datetime.datetime] = None,
        discounted: typing.Optional["DiscountedPrice"] = None,
        custom: typing.Optional["CustomFields"] = None,
        tiers: typing.Optional[typing.List["PriceTierDraft"]] = None,
    ) -> None:
        self.id = id
        self.value = value
        self.country = country
        self.customer_group = customer_group
        self.channel = channel
        self.valid_from = valid_from
        self.valid_until = valid_until
        self.discounted = discounted
        self.custom = custom
        self.tiers = tiers
        super().__init__()

    def __repr__(self) -> str:
        return (
            "QueryPrice(id=%r, value=%r, country=%r, customer_group=%r, channel=%r, valid_from=%r, valid_until=%r, discounted=%r, custom=%r, tiers=%r)"
            % (
                self.id,
                self.value,
                self.country,
                self.customer_group,
                self.channel,
                self.valid_from,
                self.valid_until,
                self.discounted,
                self.custom,
                self.tiers,
            )
        )


class Reference(_BaseType):
    #: :class:`commercetools.types.ReferenceTypeId` `(Named` ``typeId`` `in Commercetools)`
    type_id: "ReferenceTypeId"
    #: :class:`str`
    id: str

    def __init__(self, *, type_id: "ReferenceTypeId", id: str) -> None:
        self.type_id = type_id
        self.id = id
        super().__init__()

    def __repr__(self) -> str:
        return "Reference(type_id=%r, id=%r)" % (self.type_id, self.id)


class ReferenceTypeId(enum.Enum):
    CART = "cart"
    CART_DISCOUNT = "cart-discount"
    CATEGORY = "category"
    CHANNEL = "channel"
    CUSTOMER = "customer"
    CUSTOMER_GROUP = "customer-group"
    DISCOUNT_CODE = "discount-code"
    KEY_VALUE_DOCUMENT = "key-value-document"
    PAYMENT = "payment"
    PRODUCT = "product"
    PRODUCT_TYPE = "product-type"
    PRODUCT_DISCOUNT = "product-discount"
    ORDER = "order"
    REVIEW = "review"
    SHOPPING_LIST = "shopping-list"
    SHIPPING_METHOD = "shipping-method"
    STATE = "state"
    STORE = "store"
    TAX_CATEGORY = "tax-category"
    TYPE = "type"
    ZONE = "zone"
    INVENTORY_ENTRY = "inventory-entry"
    ORDER_EDIT = "order-edit"


class ResourceIdentifier(_BaseType):
    #: Optional :class:`commercetools.types.ReferenceTypeId` `(Named` ``typeId`` `in Commercetools)`
    type_id: typing.Optional["ReferenceTypeId"]
    #: Optional :class:`str`
    id: typing.Optional[str]
    #: Optional :class:`str`
    key: typing.Optional[str]

    def __init__(
        self,
        *,
        type_id: typing.Optional["ReferenceTypeId"] = None,
        id: typing.Optional[str] = None,
        key: typing.Optional[str] = None,
    ) -> None:
        self.type_id = type_id
        self.id = id
        self.key = key
        super().__init__()

    def __repr__(self) -> str:
        return "ResourceIdentifier(type_id=%r, id=%r, key=%r)" % (
            self.type_id,
            self.id,
            self.key,
        )


class ScopedPrice(_BaseType):
    #: :class:`str`
    id: str
    #: :class:`commercetools.types.TypedMoney`
    value: "TypedMoney"
    #: :class:`commercetools.types.TypedMoney` `(Named` ``currentValue`` `in Commercetools)`
    current_value: "TypedMoney"
    #: Optional :class:`str`
    country: typing.Optional["str"]
    #: Optional :class:`commercetools.types.CustomerGroupReference` `(Named` ``customerGroup`` `in Commercetools)`
    customer_group: typing.Optional["CustomerGroupReference"]
    #: Optional :class:`commercetools.types.ChannelReference`
    channel: typing.Optional["ChannelReference"]
    #: Optional :class:`datetime.datetime` `(Named` ``validFrom`` `in Commercetools)`
    valid_from: typing.Optional[datetime.datetime]
    #: Optional :class:`datetime.datetime` `(Named` ``validUntil`` `in Commercetools)`
    valid_until: typing.Optional[datetime.datetime]
    #: Optional :class:`commercetools.types.DiscountedPrice`
    discounted: typing.Optional["DiscountedPrice"]
    #: Optional :class:`commercetools.types.CustomFields`
    custom: typing.Optional["CustomFields"]

    def __init__(
        self,
        *,
        id: str,
        value: "TypedMoney",
        current_value: "TypedMoney",
        country: typing.Optional["str"] = None,
        customer_group: typing.Optional["CustomerGroupReference"] = None,
        channel: typing.Optional["ChannelReference"] = None,
        valid_from: typing.Optional[datetime.datetime] = None,
        valid_until: typing.Optional[datetime.datetime] = None,
        discounted: typing.Optional["DiscountedPrice"] = None,
        custom: typing.Optional["CustomFields"] = None,
    ) -> None:
        self.id = id
        self.value = value
        self.current_value = current_value
        self.country = country
        self.customer_group = customer_group
        self.channel = channel
        self.valid_from = valid_from
        self.valid_until = valid_until
        self.discounted = discounted
        self.custom = custom
        super().__init__()

    def __repr__(self) -> str:
        return (
            "ScopedPrice(id=%r, value=%r, current_value=%r, country=%r, customer_group=%r, channel=%r, valid_from=%r, valid_until=%r, discounted=%r, custom=%r)"
            % (
                self.id,
                self.value,
                self.current_value,
                self.country,
                self.customer_group,
                self.channel,
                self.valid_from,
                self.valid_until,
                self.discounted,
                self.custom,
            )
        )


class TypedMoney(_BaseType):
    #: :class:`commercetools.types.MoneyType`
    type: "MoneyType"
    #: :class:`int` `(Named` ``fractionDigits`` `in Commercetools)`
    fraction_digits: int
    #: :class:`int` `(Named` ``centAmount`` `in Commercetools)`
    cent_amount: int
    #: :class:`str` `(Named` ``currencyCode`` `in Commercetools)`
    currency_code: "str"

    def __init__(
        self,
        *,
        type: "MoneyType",
        fraction_digits: int,
        cent_amount: int,
        currency_code: "str",
    ) -> None:
        self.type = type
        self.fraction_digits = fraction_digits
        self.cent_amount = cent_amount
        self.currency_code = currency_code
        super().__init__()

    def __repr__(self) -> str:
        return (
            "TypedMoney(type=%r, fraction_digits=%r, cent_amount=%r, currency_code=%r)"
            % (self.type, self.fraction_digits, self.cent_amount, self.currency_code)
        )


class Update(_BaseType):
    #: :class:`int`
    version: int
    #: :class:`list`
    actions: list

    def __init__(self, *, version: int, actions: list) -> None:
        self.version = version
        self.actions = actions
        super().__init__()

    def __repr__(self) -> str:
        return "Update(version=%r, actions=%r)" % (self.version, self.actions)


class UpdateAction(_BaseType):
    #: :class:`str`
    action: str

    def __init__(self, *, action: str) -> None:
        self.action = action
        super().__init__()

    def __repr__(self) -> str:
        return "UpdateAction(action=%r)" % (self.action,)


class CentPrecisionMoney(TypedMoney):
    def __init__(
        self, *, fraction_digits: int, cent_amount: int, currency_code: "str"
    ) -> None:
        super().__init__(
            type=MoneyType.CENT_PRECISION,
            fraction_digits=fraction_digits,
            cent_amount=cent_amount,
            currency_code=currency_code,
        )

    def __repr__(self) -> str:
        return (
            "CentPrecisionMoney(type=%r, fraction_digits=%r, cent_amount=%r, currency_code=%r)"
            % (self.type, self.fraction_digits, self.cent_amount, self.currency_code)
        )


class CreatedBy(ClientLogging):
    def __init__(
        self,
        *,
        client_id: typing.Optional[str] = None,
        external_user_id: typing.Optional[str] = None,
        customer: typing.Optional["CustomerReference"] = None,
        anonymous_id: typing.Optional[str] = None,
    ) -> None:
        super().__init__(
            client_id=client_id,
            external_user_id=external_user_id,
            customer=customer,
            anonymous_id=anonymous_id,
        )

    def __repr__(self) -> str:
        return (
            "CreatedBy(client_id=%r, external_user_id=%r, customer=%r, anonymous_id=%r)"
            % (self.client_id, self.external_user_id, self.customer, self.anonymous_id)
        )


class GeoJsonPoint(GeoJson):
    #: :class:`list`
    coordinates: list

    def __init__(self, *, coordinates: list) -> None:
        self.coordinates = coordinates
        super().__init__(type="Point")

    def __repr__(self) -> str:
        return "GeoJsonPoint(type=%r, coordinates=%r)" % (self.type, self.coordinates)


class HighPrecisionMoney(TypedMoney):
    #: :class:`int` `(Named` ``preciseAmount`` `in Commercetools)`
    precise_amount: int

    def __init__(
        self,
        *,
        fraction_digits: int,
        cent_amount: int,
        currency_code: "str",
        precise_amount: int,
    ) -> None:
        self.precise_amount = precise_amount
        super().__init__(
            type=MoneyType.HIGH_PRECISION,
            fraction_digits=fraction_digits,
            cent_amount=cent_amount,
            currency_code=currency_code,
        )

    def __repr__(self) -> str:
        return (
            "HighPrecisionMoney(type=%r, fraction_digits=%r, cent_amount=%r, currency_code=%r, precise_amount=%r)"
            % (
                self.type,
                self.fraction_digits,
                self.cent_amount,
                self.currency_code,
                self.precise_amount,
            )
        )


class LastModifiedBy(ClientLogging):
    def __init__(
        self,
        *,
        client_id: typing.Optional[str] = None,
        external_user_id: typing.Optional[str] = None,
        customer: typing.Optional["CustomerReference"] = None,
        anonymous_id: typing.Optional[str] = None,
    ) -> None:
        super().__init__(
            client_id=client_id,
            external_user_id=external_user_id,
            customer=customer,
            anonymous_id=anonymous_id,
        )

    def __repr__(self) -> str:
        return (
            "LastModifiedBy(client_id=%r, external_user_id=%r, customer=%r, anonymous_id=%r)"
            % (self.client_id, self.external_user_id, self.customer, self.anonymous_id)
        )


class TypedMoneyDraft(Money):
    #: :class:`commercetools.types.MoneyType`
    type: "MoneyType"

    def __init__(
        self, *, cent_amount: int, currency_code: "str", type: "MoneyType"
    ) -> None:
        self.type = type
        super().__init__(cent_amount=cent_amount, currency_code=currency_code)

    def __repr__(self) -> str:
        return "TypedMoneyDraft(cent_amount=%r, currency_code=%r, type=%r)" % (
            self.cent_amount,
            self.currency_code,
            self.type,
        )


class CentPrecisionMoneyDraft(TypedMoneyDraft):
    def __init__(self, *, cent_amount: int, currency_code: "str") -> None:
        super().__init__(
            cent_amount=cent_amount,
            currency_code=currency_code,
            type=MoneyType.CENT_PRECISION,
        )

    def __repr__(self) -> str:
        return "CentPrecisionMoneyDraft(cent_amount=%r, currency_code=%r, type=%r)" % (
            self.cent_amount,
            self.currency_code,
            self.type,
        )


class HighPrecisionMoneyDraft(TypedMoneyDraft):
    #: :class:`int` `(Named` ``preciseAmount`` `in Commercetools)`
    precise_amount: int

    def __init__(
        self, *, cent_amount: int, currency_code: "str", precise_amount: int
    ) -> None:
        self.precise_amount = precise_amount
        super().__init__(
            cent_amount=cent_amount,
            currency_code=currency_code,
            type=MoneyType.HIGH_PRECISION,
        )

    def __repr__(self) -> str:
        return (
            "HighPrecisionMoneyDraft(cent_amount=%r, currency_code=%r, type=%r, precise_amount=%r)"
            % (self.cent_amount, self.currency_code, self.type, self.precise_amount)
        )
