"""Code generated by Speakeasy (https://speakeasyapi.dev). DO NOT EDIT."""

from __future__ import annotations
import dataclasses
from ..shared import customerminified as shared_customerminified
from ..shared import discounttype as shared_discounttype
from ..shared import lineitem as shared_lineitem
from ..shared import subscriptionminified as shared_subscriptionminified
from dataclasses_json import Undefined, dataclass_json
from datetime import date
from orb import utils
from typing import Optional


@dataclass_json(undefined=Undefined.EXCLUDE)

@dataclasses.dataclass
class UpcomingInvoiceDiscount:
    discount_type: shared_discounttype.DiscountType = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('discount_type') }})
    amount_discount: Optional[str] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('amount_discount'), 'exclude': lambda f: f is None }})
    r"""Only available if discount_type is `amount`."""
    applies_to_price_ids: Optional[list[str]] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('applies_to_price_ids'), 'exclude': lambda f: f is None }})
    r"""List of price_ids that this discount applies to. For plan/plan phase discounts, this can be a subset of prices."""
    percentage_discount: Optional[float] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('percentage_discount'), 'exclude': lambda f: f is None }})
    r"""Only available if discount_type is `percentage`.This is a number between 0 and 1."""
    trial_amount_discount: Optional[str] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('trial_amount_discount'), 'exclude': lambda f: f is None }})
    r"""Only available if discount_type is `trial`"""
    usage_discount: Optional[float] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('usage_discount'), 'exclude': lambda f: f is None }})
    r"""Only available if discount_type is `usage`. Number of usage units that this discount is for"""
    



@dataclass_json(undefined=Undefined.EXCLUDE)

@dataclasses.dataclass
class UpcomingInvoiceMaximumAmount:
    applies_to_price_ids: list[str] = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('applies_to_price_ids') }})
    r"""List of price_ids that this maximum amount applies to. For plan/plan phase maximums, this can be a subset of prices."""
    maximum_amount: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('maximum_amount') }})
    r"""Maximum amount applied"""
    



@dataclass_json(undefined=Undefined.EXCLUDE)

@dataclasses.dataclass
class UpcomingInvoiceMinimumAmount:
    applies_to_price_ids: list[str] = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('applies_to_price_ids') }})
    r"""List of price_ids that this minimum amount applies to. For plan/plan phase minimums, this can be a subset of prices."""
    minimum_amount: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('minimum_amount') }})
    r"""Minimum amount applied"""
    



@dataclass_json(undefined=Undefined.EXCLUDE)

@dataclasses.dataclass
class UpcomingInvoice:
    r"""Upcoming invoices contain a line-by-line breakdown of an upcoming amount due for a subscription, including incurred usage in the billing period as well as any recurring fees.

    Although each line item will be invoiced on the `target_date`, each invoice line item may have distinct date ranges (e.g. for usage billed in arrears, the range may specify the current month whereas an in-advance recurring fees will be for the following month).

    Since an invoice resource has not been created for this upcoming invoice, this endpoint intentionally does not return an `id` field.
    """
    amount_due: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('amount_due') }})
    r"""The final amount to be charged to the customer after all minimums and discounts have been applied. Only populated for non-pre-paid plans."""
    currency: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('currency') }})
    r"""An ISO 4217 currency string or `credits`"""
    customer: shared_customerminified.CustomerMinified = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('customer') }})
    r"""The customer receiving this invoice."""
    discount: UpcomingInvoiceDiscount = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('discount') }})
    hosted_invoice_url: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('hosted_invoice_url') }})
    r"""A URL for the invoice portal."""
    line_items: list[shared_lineitem.LineItem] = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('line_items') }})
    r"""The breakdown of prices in this invoice."""
    minimum: UpcomingInvoiceMinimumAmount = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('minimum') }})
    subscription: shared_subscriptionminified.SubscriptionMinified = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('subscription') }})
    r"""The associated subscription for this invoice."""
    subtotal: str = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('subtotal') }})
    r"""The total before any discounts and minimums are applied."""
    target_date: date = dataclasses.field(metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('target_date'), 'encoder': utils.dateisoformat(False), 'decoder': utils.datefromisoformat }})
    r"""The expected issue date of the invoice."""
    maximum: Optional[UpcomingInvoiceMaximumAmount] = dataclasses.field(default=None, metadata={'dataclasses_json': { 'letter_case': utils.get_field_name('maximum'), 'exclude': lambda f: f is None }})
    

