Files
cfw-autumn/others/python-sdk/src/autumn_sdk/models/checkop.py
amianthus 2c7f7973f0 feat: 🎸 202
2026-04-29 16:53:58 +01:00

2023 lines
67 KiB
Python

"""Code generated by Speakeasy (https://speakeasy.com). DO NOT EDIT."""
from __future__ import annotations
from .balance import Balance, BalanceTypedDict
from autumn_sdk.types import (
BaseModel,
Nullable,
OptionalNullable,
UNSET,
UNSET_SENTINEL,
UnrecognizedStr,
)
from autumn_sdk.utils import FieldMetadata, HeaderMetadata, validate_const
import pydantic
from pydantic import model_serializer
from pydantic.functional_validators import AfterValidator
from typing import Any, Dict, List, Literal, Optional, Union
from typing_extensions import Annotated, NotRequired, TypeAliasType, TypedDict
class CheckGlobalsTypedDict(TypedDict):
x_api_version: NotRequired[str]
class CheckGlobals(BaseModel):
x_api_version: Annotated[
Optional[str],
pydantic.Field(alias="x-api-version"),
FieldMetadata(header=HeaderMetadata(style="simple", explode=False)),
] = "2.2.0"
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["x-api-version"])
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))
if val != UNSET_SENTINEL:
if val is not None or k not in optional_fields:
m[k] = val
return m
class CheckLockTypedDict(TypedDict):
r"""Reserve units of a feature upfront by passing a lock_id, then call balances.finalize to confirm or release the hold."""
lock_id: str
r"""A unique identifier for this lock. Used to finalize the lock later via balances.finalize."""
enabled: Literal[True]
r"""Must be true to enable locking."""
expires_at: NotRequired[float]
r"""Unix timestamp (ms) when the lock automatically expires and releases the held balance."""
class CheckLock(BaseModel):
r"""Reserve units of a feature upfront by passing a lock_id, then call balances.finalize to confirm or release the hold."""
lock_id: str
r"""A unique identifier for this lock. Used to finalize the lock later via balances.finalize."""
enabled: Annotated[
Annotated[Literal[True], AfterValidator(validate_const(True))],
pydantic.Field(alias="enabled"),
] = True
r"""Must be true to enable locking."""
expires_at: Optional[float] = None
r"""Unix timestamp (ms) when the lock automatically expires and releases the held balance."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["expires_at"])
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))
if val != UNSET_SENTINEL:
if val is not None or k not in optional_fields:
m[k] = val
return m
class CheckParamsTypedDict(TypedDict):
customer_id: str
r"""The ID of the customer."""
feature_id: str
r"""The ID of the feature."""
entity_id: NotRequired[str]
r"""The ID of the entity for entity-scoped balances (e.g., per-seat limits)."""
required_balance: NotRequired[float]
r"""Minimum balance required for access. Returns allowed: false if the customer's balance is below this value. Defaults to 1."""
properties: NotRequired[Dict[str, Any]]
r"""Additional properties to attach to the usage event if send_event is true."""
send_event: NotRequired[bool]
r"""If true, atomically records a usage event while checking access. The required_balance value is used as the usage amount. Combines check + track in one call."""
lock: NotRequired[CheckLockTypedDict]
r"""Reserve units of a feature upfront by passing a lock_id, then call balances.finalize to confirm or release the hold."""
with_preview: NotRequired[bool]
r"""If true, includes upgrade/upsell information in the response when access is denied. Useful for displaying paywalls."""
class CheckParams(BaseModel):
customer_id: str
r"""The ID of the customer."""
feature_id: str
r"""The ID of the feature."""
entity_id: Optional[str] = None
r"""The ID of the entity for entity-scoped balances (e.g., per-seat limits)."""
required_balance: Optional[float] = None
r"""Minimum balance required for access. Returns allowed: false if the customer's balance is below this value. Defaults to 1."""
properties: Optional[Dict[str, Any]] = None
r"""Additional properties to attach to the usage event if send_event is true."""
send_event: Optional[bool] = None
r"""If true, atomically records a usage event while checking access. The required_balance value is used as the usage amount. Combines check + track in one call."""
lock: Optional[CheckLock] = None
r"""Reserve units of a feature upfront by passing a lock_id, then call balances.finalize to confirm or release the hold."""
with_preview: Optional[bool] = None
r"""If true, includes upgrade/upsell information in the response when access is denied. Useful for displaying paywalls."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(
[
"entity_id",
"required_balance",
"properties",
"send_event",
"lock",
"with_preview",
]
)
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))
if val != UNSET_SENTINEL:
if val is not None or k not in optional_fields:
m[k] = val
return m
FlagType2 = Union[
Literal[
"boolean",
"metered",
"credit_system",
],
UnrecognizedStr,
]
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
class CheckCreditSchema2TypedDict(TypedDict):
metered_feature_id: str
r"""ID of the metered feature that draws from this credit system."""
credit_cost: float
r"""Credits consumed per unit of the metered feature."""
class CheckCreditSchema2(BaseModel):
metered_feature_id: str
r"""ID of the metered feature that draws from this credit system."""
credit_cost: float
r"""Credits consumed per unit of the metered feature."""
class FlagDisplay2TypedDict(TypedDict):
r"""Display names for the feature in billing UI and customer-facing components."""
singular: NotRequired[Nullable[str]]
r"""Singular form for UI display (e.g., 'API call', 'seat')."""
plural: NotRequired[Nullable[str]]
r"""Plural form for UI display (e.g., 'API calls', 'seats')."""
class FlagDisplay2(BaseModel):
r"""Display names for the feature in billing UI and customer-facing components."""
singular: OptionalNullable[str] = UNSET
r"""Singular form for UI display (e.g., 'API call', 'seat')."""
plural: OptionalNullable[str] = UNSET
r"""Plural form for UI display (e.g., 'API calls', 'seats')."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["singular", "plural"])
nullable_fields = set(["singular", "plural"])
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
class CheckFeature2TypedDict(TypedDict):
r"""The full feature object if expanded."""
id: str
r"""The unique identifier for this feature, used in /check and /track calls."""
name: str
r"""Human-readable name displayed in the dashboard and billing UI."""
type: FlagType2
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
consumable: bool
r"""For metered features: true if usage resets periodically (API calls, credits), false if allocated persistently (seats, storage)."""
archived: bool
r"""Whether the feature is archived and hidden from the dashboard."""
event_names: NotRequired[List[str]]
r"""Event names that trigger this feature's balance. Allows multiple features to respond to a single event."""
credit_schema: NotRequired[List[CheckCreditSchema2TypedDict]]
r"""For credit_system features: maps metered features to their credit costs."""
display: NotRequired[FlagDisplay2TypedDict]
r"""Display names for the feature in billing UI and customer-facing components."""
class CheckFeature2(BaseModel):
r"""The full feature object if expanded."""
id: str
r"""The unique identifier for this feature, used in /check and /track calls."""
name: str
r"""Human-readable name displayed in the dashboard and billing UI."""
type: FlagType2
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
consumable: bool
r"""For metered features: true if usage resets periodically (API calls, credits), false if allocated persistently (seats, storage)."""
archived: bool
r"""Whether the feature is archived and hidden from the dashboard."""
event_names: Optional[List[str]] = None
r"""Event names that trigger this feature's balance. Allows multiple features to respond to a single event."""
credit_schema: Optional[List[CheckCreditSchema2]] = None
r"""For credit_system features: maps metered features to their credit costs."""
display: Optional[FlagDisplay2] = None
r"""Display names for the feature in billing UI and customer-facing components."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["event_names", "credit_schema", "display"])
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))
if val != UNSET_SENTINEL:
if val is not None or k not in optional_fields:
m[k] = val
return m
class Flag2TypedDict(TypedDict):
id: str
r"""The unique identifier for this flag."""
plan_id: Nullable[str]
r"""The plan ID this flag originates from, or null for standalone flags."""
expires_at: Nullable[float]
r"""Timestamp when this flag expires, or null for no expiration."""
feature_id: str
r"""The feature ID this flag is for."""
feature: NotRequired[CheckFeature2TypedDict]
r"""The full feature object if expanded."""
class Flag2(BaseModel):
id: str
r"""The unique identifier for this flag."""
plan_id: Nullable[str]
r"""The plan ID this flag originates from, or null for standalone flags."""
expires_at: Nullable[float]
r"""Timestamp when this flag expires, or null for no expiration."""
feature_id: str
r"""The feature ID this flag is for."""
feature: Optional[CheckFeature2] = None
r"""The full feature object if expanded."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["feature"])
nullable_fields = set(["plan_id", "expires_at"])
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
Scenario2 = Union[
Literal[
"usage_limit",
"feature_flag",
],
UnrecognizedStr,
]
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
CheckEnv2 = Union[
Literal[
"sandbox",
"live",
],
UnrecognizedStr,
]
r"""The environment of the product"""
ProductType2 = Union[
Literal[
"feature",
"priced_feature",
"price",
],
UnrecognizedStr,
]
FeatureType2 = Union[
Literal[
"single_use",
"continuous_use",
"boolean",
"static",
],
UnrecognizedStr,
]
IncludedUsage2TypedDict = TypeAliasType("IncludedUsage2TypedDict", Union[float, str])
IncludedUsage2 = TypeAliasType("IncludedUsage2", Union[float, str])
CheckInterval2 = Union[
Literal[
"minute",
"hour",
"day",
"week",
"month",
"quarter",
"semi_annual",
"year",
],
UnrecognizedStr,
]
CheckTierBehavior2 = Union[
Literal[
"graduated",
"volume",
],
UnrecognizedStr,
]
UsageModel2 = Union[
Literal[
"prepaid",
"pay_per_use",
],
UnrecognizedStr,
]
class ProductDisplay2TypedDict(TypedDict):
primary_text: str
secondary_text: NotRequired[Nullable[str]]
class ProductDisplay2(BaseModel):
primary_text: str
secondary_text: OptionalNullable[str] = UNSET
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["secondary_text"])
nullable_fields = set(["secondary_text"])
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
ConfigDuration2 = Union[
Literal[
"month",
"forever",
],
UnrecognizedStr,
]
class CheckRollover2TypedDict(TypedDict):
length: float
max: NotRequired[Nullable[float]]
max_percentage: NotRequired[Nullable[float]]
duration: NotRequired[ConfigDuration2]
class CheckRollover2(BaseModel):
length: float
max: OptionalNullable[float] = UNSET
max_percentage: OptionalNullable[float] = UNSET
duration: Optional[ConfigDuration2] = "month"
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["max", "max_percentage", "duration"])
nullable_fields = set(["max", "max_percentage"])
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
CheckOnIncrease2 = Union[
Literal[
"bill_immediately",
"prorate_immediately",
"prorate_next_cycle",
"bill_next_cycle",
],
UnrecognizedStr,
]
CheckOnDecrease2 = Union[
Literal[
"prorate",
"prorate_immediately",
"prorate_next_cycle",
"none",
"no_prorations",
],
UnrecognizedStr,
]
class CheckConfig2TypedDict(TypedDict):
rollover: NotRequired[Nullable[CheckRollover2TypedDict]]
on_increase: NotRequired[Nullable[CheckOnIncrease2]]
on_decrease: NotRequired[Nullable[CheckOnDecrease2]]
class CheckConfig2(BaseModel):
rollover: OptionalNullable[CheckRollover2] = UNSET
on_increase: OptionalNullable[CheckOnIncrease2] = UNSET
on_decrease: OptionalNullable[CheckOnDecrease2] = UNSET
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["rollover", "on_increase", "on_decrease"])
nullable_fields = set(["rollover", "on_increase", "on_decrease"])
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
class CheckItem2TypedDict(TypedDict):
r"""Product item defining features and pricing within a product"""
type: NotRequired[Nullable[ProductType2]]
r"""The type of the product item"""
feature_id: NotRequired[Nullable[str]]
r"""The feature ID of the product item. If the item is a fixed price, should be `null`"""
feature_type: NotRequired[Nullable[FeatureType2]]
r"""Single use features are used once and then depleted, like API calls or credits. Continuous use features are those being used on an ongoing-basis, like storage or seats."""
included_usage: NotRequired[Nullable[IncludedUsage2TypedDict]]
r"""The amount of usage included for this feature."""
interval: NotRequired[Nullable[CheckInterval2]]
r"""The reset or billing interval of the product item. If null, feature will have no reset date, and if there's a price, it will be billed one-off."""
interval_count: NotRequired[Nullable[float]]
r"""The interval count of the product item."""
price: NotRequired[Nullable[float]]
r"""The price of the product item. Should be `null` if tiered pricing is set."""
tiers: NotRequired[Nullable[List[Nullable[Any]]]]
r"""Tiered pricing for the product item. Not applicable for fixed price items."""
tier_behavior: NotRequired[Nullable[CheckTierBehavior2]]
r"""How tiers are applied: graduated (split across bands) or volume (flat rate for the matched tier). Defaults to graduated."""
usage_model: NotRequired[Nullable[UsageModel2]]
r"""Whether the feature should be prepaid upfront or billed for how much they use end of billing period."""
billing_units: NotRequired[Nullable[float]]
r"""The amount per billing unit (eg. $9 / 250 units)"""
reset_usage_when_enabled: NotRequired[Nullable[bool]]
r"""Whether the usage should be reset when the product is enabled."""
entity_feature_id: NotRequired[Nullable[str]]
r"""The entity feature ID of the product item if applicable."""
display: NotRequired[Nullable[ProductDisplay2TypedDict]]
r"""The display of the product item."""
quantity: NotRequired[Nullable[float]]
r"""Used in customer context. Quantity of the feature the customer has prepaid for."""
next_cycle_quantity: NotRequired[Nullable[float]]
r"""Used in customer context. Quantity of the feature the customer will prepay for in the next cycle."""
config: NotRequired[Nullable[CheckConfig2TypedDict]]
r"""Configuration for rollover and proration behavior of the feature."""
class CheckItem2(BaseModel):
r"""Product item defining features and pricing within a product"""
type: OptionalNullable[ProductType2] = UNSET
r"""The type of the product item"""
feature_id: OptionalNullable[str] = UNSET
r"""The feature ID of the product item. If the item is a fixed price, should be `null`"""
feature_type: OptionalNullable[FeatureType2] = UNSET
r"""Single use features are used once and then depleted, like API calls or credits. Continuous use features are those being used on an ongoing-basis, like storage or seats."""
included_usage: OptionalNullable[IncludedUsage2] = UNSET
r"""The amount of usage included for this feature."""
interval: OptionalNullable[CheckInterval2] = UNSET
r"""The reset or billing interval of the product item. If null, feature will have no reset date, and if there's a price, it will be billed one-off."""
interval_count: OptionalNullable[float] = UNSET
r"""The interval count of the product item."""
price: OptionalNullable[float] = UNSET
r"""The price of the product item. Should be `null` if tiered pricing is set."""
tiers: OptionalNullable[List[Nullable[Any]]] = UNSET
r"""Tiered pricing for the product item. Not applicable for fixed price items."""
tier_behavior: OptionalNullable[CheckTierBehavior2] = UNSET
r"""How tiers are applied: graduated (split across bands) or volume (flat rate for the matched tier). Defaults to graduated."""
usage_model: OptionalNullable[UsageModel2] = UNSET
r"""Whether the feature should be prepaid upfront or billed for how much they use end of billing period."""
billing_units: OptionalNullable[float] = UNSET
r"""The amount per billing unit (eg. $9 / 250 units)"""
reset_usage_when_enabled: OptionalNullable[bool] = UNSET
r"""Whether the usage should be reset when the product is enabled."""
entity_feature_id: OptionalNullable[str] = UNSET
r"""The entity feature ID of the product item if applicable."""
display: OptionalNullable[ProductDisplay2] = UNSET
r"""The display of the product item."""
quantity: OptionalNullable[float] = UNSET
r"""Used in customer context. Quantity of the feature the customer has prepaid for."""
next_cycle_quantity: OptionalNullable[float] = UNSET
r"""Used in customer context. Quantity of the feature the customer will prepay for in the next cycle."""
config: OptionalNullable[CheckConfig2] = UNSET
r"""Configuration for rollover and proration behavior of the feature."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(
[
"type",
"feature_id",
"feature_type",
"included_usage",
"interval",
"interval_count",
"price",
"tiers",
"tier_behavior",
"usage_model",
"billing_units",
"reset_usage_when_enabled",
"entity_feature_id",
"display",
"quantity",
"next_cycle_quantity",
"config",
]
)
nullable_fields = set(
[
"type",
"feature_id",
"feature_type",
"included_usage",
"interval",
"interval_count",
"price",
"tiers",
"tier_behavior",
"usage_model",
"billing_units",
"reset_usage_when_enabled",
"entity_feature_id",
"display",
"quantity",
"next_cycle_quantity",
"config",
]
)
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
FreeTrialDuration2 = Union[
Literal[
"day",
"month",
"year",
],
UnrecognizedStr,
]
r"""The duration type of the free trial"""
class CheckFreeTrial2TypedDict(TypedDict):
duration: FreeTrialDuration2
r"""The duration type of the free trial"""
length: float
r"""The length of the duration type specified"""
unique_fingerprint: bool
r"""Whether the free trial is limited to one per customer fingerprint"""
card_required: bool
r"""Whether the free trial requires a card. If false, the customer can attach the product without going through a checkout flow or having a card on file."""
trial_available: NotRequired[Nullable[bool]]
r"""Used in customer context. Whether the free trial is available for the customer if they were to attach the product."""
class CheckFreeTrial2(BaseModel):
duration: FreeTrialDuration2
r"""The duration type of the free trial"""
length: float
r"""The length of the duration type specified"""
unique_fingerprint: bool
r"""Whether the free trial is limited to one per customer fingerprint"""
card_required: bool
r"""Whether the free trial requires a card. If false, the customer can attach the product without going through a checkout flow or having a card on file."""
trial_available: OptionalNullable[bool] = True
r"""Used in customer context. Whether the free trial is available for the customer if they were to attach the product."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["trial_available"])
nullable_fields = set(["trial_available"])
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
ProductScenario2 = Union[
Literal[
"scheduled",
"active",
"new",
"renew",
"upgrade",
"update_prepaid_quantity",
"downgrade",
"cancel",
"expired",
"past_due",
],
UnrecognizedStr,
]
r"""Scenario for when this product is used in attach flows"""
class Properties2TypedDict(TypedDict):
is_free: bool
r"""True if the product has no base price or usage prices"""
is_one_off: bool
r"""True if the product only contains a one-time price"""
interval_group: NotRequired[Nullable[str]]
r"""The billing interval group for recurring products (e.g., 'monthly', 'yearly')"""
has_trial: NotRequired[Nullable[bool]]
r"""True if the product includes a free trial"""
updateable: NotRequired[Nullable[bool]]
r"""True if the product can be updated after creation (only applicable if there are prepaid recurring prices)"""
class Properties2(BaseModel):
is_free: bool
r"""True if the product has no base price or usage prices"""
is_one_off: bool
r"""True if the product only contains a one-time price"""
interval_group: OptionalNullable[str] = UNSET
r"""The billing interval group for recurring products (e.g., 'monthly', 'yearly')"""
has_trial: OptionalNullable[bool] = UNSET
r"""True if the product includes a free trial"""
updateable: OptionalNullable[bool] = UNSET
r"""True if the product can be updated after creation (only applicable if there are prepaid recurring prices)"""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["interval_group", "has_trial", "updateable"])
nullable_fields = set(["interval_group", "has_trial", "updateable"])
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
class Product2TypedDict(TypedDict):
id: str
r"""The ID of the product you set when creating the product"""
name: str
r"""The name of the product"""
group: Nullable[str]
r"""Product group which this product belongs to"""
env: CheckEnv2
r"""The environment of the product"""
is_add_on: bool
r"""Whether the product is an add-on and can be purchased alongside other products"""
is_default: bool
r"""Whether the product is the default product"""
archived: bool
r"""Whether this product has been archived and is no longer available"""
version: float
r"""The current version of the product"""
created_at: float
r"""The timestamp of when the product was created in milliseconds since epoch"""
items: List[CheckItem2TypedDict]
r"""Array of product items that define the product's features and pricing"""
free_trial: Nullable[CheckFreeTrial2TypedDict]
r"""Free trial configuration for this product, if available"""
base_variant_id: Nullable[str]
r"""ID of the base variant this product is derived from"""
scenario: NotRequired[ProductScenario2]
r"""Scenario for when this product is used in attach flows"""
properties: NotRequired[Properties2TypedDict]
class Product2(BaseModel):
id: str
r"""The ID of the product you set when creating the product"""
name: str
r"""The name of the product"""
group: Nullable[str]
r"""Product group which this product belongs to"""
env: CheckEnv2
r"""The environment of the product"""
is_add_on: bool
r"""Whether the product is an add-on and can be purchased alongside other products"""
is_default: bool
r"""Whether the product is the default product"""
archived: bool
r"""Whether this product has been archived and is no longer available"""
version: float
r"""The current version of the product"""
created_at: float
r"""The timestamp of when the product was created in milliseconds since epoch"""
items: List[CheckItem2]
r"""Array of product items that define the product's features and pricing"""
free_trial: Nullable[CheckFreeTrial2]
r"""Free trial configuration for this product, if available"""
base_variant_id: Nullable[str]
r"""ID of the base variant this product is derived from"""
scenario: Optional[ProductScenario2] = None
r"""Scenario for when this product is used in attach flows"""
properties: Optional[Properties2] = None
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["scenario", "properties"])
nullable_fields = set(["group", "free_trial", "base_variant_id"])
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
class Preview2TypedDict(TypedDict):
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
scenario: Scenario2
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
title: str
r"""A title suitable for displaying in a paywall or upgrade modal."""
message: str
r"""A message explaining why access was denied."""
feature_id: str
r"""The ID of the feature that was checked."""
feature_name: str
r"""The display name of the feature."""
products: List[Product2TypedDict]
r"""Products that would grant access to this feature. Use to display upgrade options."""
class Preview2(BaseModel):
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
scenario: Scenario2
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
title: str
r"""A title suitable for displaying in a paywall or upgrade modal."""
message: str
r"""A message explaining why access was denied."""
feature_id: str
r"""The ID of the feature that was checked."""
feature_name: str
r"""The display name of the feature."""
products: List[Product2]
r"""Products that would grant access to this feature. Use to display upgrade options."""
class CheckResponseBody2TypedDict(TypedDict):
r"""Accepted. Autumn is experiencing degraded service from a downstream provider, so access was allowed fail-open."""
allowed: bool
r"""Whether the customer is allowed to use the feature. True if they have sufficient balance or the feature is unlimited/boolean."""
customer_id: str
r"""The ID of the customer that was checked."""
balance: Nullable[BalanceTypedDict]
r"""The customer's balance for this feature. Null if the customer has no balance for this feature."""
flag: Nullable[Flag2TypedDict]
r"""The flag associated with this check, if any."""
entity_id: NotRequired[Nullable[str]]
r"""The ID of the entity, if an entity-scoped check was performed."""
required_balance: NotRequired[float]
r"""The required balance that was checked against."""
preview: NotRequired[Preview2TypedDict]
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
class CheckResponseBody2(BaseModel):
r"""Accepted. Autumn is experiencing degraded service from a downstream provider, so access was allowed fail-open."""
allowed: bool
r"""Whether the customer is allowed to use the feature. True if they have sufficient balance or the feature is unlimited/boolean."""
customer_id: str
r"""The ID of the customer that was checked."""
balance: Nullable[Balance]
r"""The customer's balance for this feature. Null if the customer has no balance for this feature."""
flag: Nullable[Flag2]
r"""The flag associated with this check, if any."""
entity_id: OptionalNullable[str] = UNSET
r"""The ID of the entity, if an entity-scoped check was performed."""
required_balance: Optional[float] = None
r"""The required balance that was checked against."""
preview: Optional[Preview2] = None
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["entity_id", "required_balance", "preview"])
nullable_fields = set(["entity_id", "balance", "flag"])
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
FlagType1 = Union[
Literal[
"boolean",
"metered",
"credit_system",
],
UnrecognizedStr,
]
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
class CheckCreditSchema1TypedDict(TypedDict):
metered_feature_id: str
r"""ID of the metered feature that draws from this credit system."""
credit_cost: float
r"""Credits consumed per unit of the metered feature."""
class CheckCreditSchema1(BaseModel):
metered_feature_id: str
r"""ID of the metered feature that draws from this credit system."""
credit_cost: float
r"""Credits consumed per unit of the metered feature."""
class FlagDisplay1TypedDict(TypedDict):
r"""Display names for the feature in billing UI and customer-facing components."""
singular: NotRequired[Nullable[str]]
r"""Singular form for UI display (e.g., 'API call', 'seat')."""
plural: NotRequired[Nullable[str]]
r"""Plural form for UI display (e.g., 'API calls', 'seats')."""
class FlagDisplay1(BaseModel):
r"""Display names for the feature in billing UI and customer-facing components."""
singular: OptionalNullable[str] = UNSET
r"""Singular form for UI display (e.g., 'API call', 'seat')."""
plural: OptionalNullable[str] = UNSET
r"""Plural form for UI display (e.g., 'API calls', 'seats')."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["singular", "plural"])
nullable_fields = set(["singular", "plural"])
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
class CheckFeature1TypedDict(TypedDict):
r"""The full feature object if expanded."""
id: str
r"""The unique identifier for this feature, used in /check and /track calls."""
name: str
r"""Human-readable name displayed in the dashboard and billing UI."""
type: FlagType1
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
consumable: bool
r"""For metered features: true if usage resets periodically (API calls, credits), false if allocated persistently (seats, storage)."""
archived: bool
r"""Whether the feature is archived and hidden from the dashboard."""
event_names: NotRequired[List[str]]
r"""Event names that trigger this feature's balance. Allows multiple features to respond to a single event."""
credit_schema: NotRequired[List[CheckCreditSchema1TypedDict]]
r"""For credit_system features: maps metered features to their credit costs."""
display: NotRequired[FlagDisplay1TypedDict]
r"""Display names for the feature in billing UI and customer-facing components."""
class CheckFeature1(BaseModel):
r"""The full feature object if expanded."""
id: str
r"""The unique identifier for this feature, used in /check and /track calls."""
name: str
r"""Human-readable name displayed in the dashboard and billing UI."""
type: FlagType1
r"""Feature type: 'boolean' for on/off access, 'metered' for usage-tracked features, 'credit_system' for unified credit pools."""
consumable: bool
r"""For metered features: true if usage resets periodically (API calls, credits), false if allocated persistently (seats, storage)."""
archived: bool
r"""Whether the feature is archived and hidden from the dashboard."""
event_names: Optional[List[str]] = None
r"""Event names that trigger this feature's balance. Allows multiple features to respond to a single event."""
credit_schema: Optional[List[CheckCreditSchema1]] = None
r"""For credit_system features: maps metered features to their credit costs."""
display: Optional[FlagDisplay1] = None
r"""Display names for the feature in billing UI and customer-facing components."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["event_names", "credit_schema", "display"])
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))
if val != UNSET_SENTINEL:
if val is not None or k not in optional_fields:
m[k] = val
return m
class Flag1TypedDict(TypedDict):
id: str
r"""The unique identifier for this flag."""
plan_id: Nullable[str]
r"""The plan ID this flag originates from, or null for standalone flags."""
expires_at: Nullable[float]
r"""Timestamp when this flag expires, or null for no expiration."""
feature_id: str
r"""The feature ID this flag is for."""
feature: NotRequired[CheckFeature1TypedDict]
r"""The full feature object if expanded."""
class Flag1(BaseModel):
id: str
r"""The unique identifier for this flag."""
plan_id: Nullable[str]
r"""The plan ID this flag originates from, or null for standalone flags."""
expires_at: Nullable[float]
r"""Timestamp when this flag expires, or null for no expiration."""
feature_id: str
r"""The feature ID this flag is for."""
feature: Optional[CheckFeature1] = None
r"""The full feature object if expanded."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["feature"])
nullable_fields = set(["plan_id", "expires_at"])
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
Scenario1 = Union[
Literal[
"usage_limit",
"feature_flag",
],
UnrecognizedStr,
]
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
CheckEnv1 = Union[
Literal[
"sandbox",
"live",
],
UnrecognizedStr,
]
r"""The environment of the product"""
ProductType1 = Union[
Literal[
"feature",
"priced_feature",
"price",
],
UnrecognizedStr,
]
FeatureType1 = Union[
Literal[
"single_use",
"continuous_use",
"boolean",
"static",
],
UnrecognizedStr,
]
IncludedUsage1TypedDict = TypeAliasType("IncludedUsage1TypedDict", Union[float, str])
IncludedUsage1 = TypeAliasType("IncludedUsage1", Union[float, str])
CheckInterval1 = Union[
Literal[
"minute",
"hour",
"day",
"week",
"month",
"quarter",
"semi_annual",
"year",
],
UnrecognizedStr,
]
CheckTierBehavior1 = Union[
Literal[
"graduated",
"volume",
],
UnrecognizedStr,
]
UsageModel1 = Union[
Literal[
"prepaid",
"pay_per_use",
],
UnrecognizedStr,
]
class ProductDisplay1TypedDict(TypedDict):
primary_text: str
secondary_text: NotRequired[Nullable[str]]
class ProductDisplay1(BaseModel):
primary_text: str
secondary_text: OptionalNullable[str] = UNSET
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["secondary_text"])
nullable_fields = set(["secondary_text"])
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
ConfigDuration1 = Union[
Literal[
"month",
"forever",
],
UnrecognizedStr,
]
class CheckRollover1TypedDict(TypedDict):
length: float
max: NotRequired[Nullable[float]]
max_percentage: NotRequired[Nullable[float]]
duration: NotRequired[ConfigDuration1]
class CheckRollover1(BaseModel):
length: float
max: OptionalNullable[float] = UNSET
max_percentage: OptionalNullable[float] = UNSET
duration: Optional[ConfigDuration1] = "month"
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["max", "max_percentage", "duration"])
nullable_fields = set(["max", "max_percentage"])
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
CheckOnIncrease1 = Union[
Literal[
"bill_immediately",
"prorate_immediately",
"prorate_next_cycle",
"bill_next_cycle",
],
UnrecognizedStr,
]
CheckOnDecrease1 = Union[
Literal[
"prorate",
"prorate_immediately",
"prorate_next_cycle",
"none",
"no_prorations",
],
UnrecognizedStr,
]
class CheckConfig1TypedDict(TypedDict):
rollover: NotRequired[Nullable[CheckRollover1TypedDict]]
on_increase: NotRequired[Nullable[CheckOnIncrease1]]
on_decrease: NotRequired[Nullable[CheckOnDecrease1]]
class CheckConfig1(BaseModel):
rollover: OptionalNullable[CheckRollover1] = UNSET
on_increase: OptionalNullable[CheckOnIncrease1] = UNSET
on_decrease: OptionalNullable[CheckOnDecrease1] = UNSET
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["rollover", "on_increase", "on_decrease"])
nullable_fields = set(["rollover", "on_increase", "on_decrease"])
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
class CheckItem1TypedDict(TypedDict):
r"""Product item defining features and pricing within a product"""
type: NotRequired[Nullable[ProductType1]]
r"""The type of the product item"""
feature_id: NotRequired[Nullable[str]]
r"""The feature ID of the product item. If the item is a fixed price, should be `null`"""
feature_type: NotRequired[Nullable[FeatureType1]]
r"""Single use features are used once and then depleted, like API calls or credits. Continuous use features are those being used on an ongoing-basis, like storage or seats."""
included_usage: NotRequired[Nullable[IncludedUsage1TypedDict]]
r"""The amount of usage included for this feature."""
interval: NotRequired[Nullable[CheckInterval1]]
r"""The reset or billing interval of the product item. If null, feature will have no reset date, and if there's a price, it will be billed one-off."""
interval_count: NotRequired[Nullable[float]]
r"""The interval count of the product item."""
price: NotRequired[Nullable[float]]
r"""The price of the product item. Should be `null` if tiered pricing is set."""
tiers: NotRequired[Nullable[List[Nullable[Any]]]]
r"""Tiered pricing for the product item. Not applicable for fixed price items."""
tier_behavior: NotRequired[Nullable[CheckTierBehavior1]]
r"""How tiers are applied: graduated (split across bands) or volume (flat rate for the matched tier). Defaults to graduated."""
usage_model: NotRequired[Nullable[UsageModel1]]
r"""Whether the feature should be prepaid upfront or billed for how much they use end of billing period."""
billing_units: NotRequired[Nullable[float]]
r"""The amount per billing unit (eg. $9 / 250 units)"""
reset_usage_when_enabled: NotRequired[Nullable[bool]]
r"""Whether the usage should be reset when the product is enabled."""
entity_feature_id: NotRequired[Nullable[str]]
r"""The entity feature ID of the product item if applicable."""
display: NotRequired[Nullable[ProductDisplay1TypedDict]]
r"""The display of the product item."""
quantity: NotRequired[Nullable[float]]
r"""Used in customer context. Quantity of the feature the customer has prepaid for."""
next_cycle_quantity: NotRequired[Nullable[float]]
r"""Used in customer context. Quantity of the feature the customer will prepay for in the next cycle."""
config: NotRequired[Nullable[CheckConfig1TypedDict]]
r"""Configuration for rollover and proration behavior of the feature."""
class CheckItem1(BaseModel):
r"""Product item defining features and pricing within a product"""
type: OptionalNullable[ProductType1] = UNSET
r"""The type of the product item"""
feature_id: OptionalNullable[str] = UNSET
r"""The feature ID of the product item. If the item is a fixed price, should be `null`"""
feature_type: OptionalNullable[FeatureType1] = UNSET
r"""Single use features are used once and then depleted, like API calls or credits. Continuous use features are those being used on an ongoing-basis, like storage or seats."""
included_usage: OptionalNullable[IncludedUsage1] = UNSET
r"""The amount of usage included for this feature."""
interval: OptionalNullable[CheckInterval1] = UNSET
r"""The reset or billing interval of the product item. If null, feature will have no reset date, and if there's a price, it will be billed one-off."""
interval_count: OptionalNullable[float] = UNSET
r"""The interval count of the product item."""
price: OptionalNullable[float] = UNSET
r"""The price of the product item. Should be `null` if tiered pricing is set."""
tiers: OptionalNullable[List[Nullable[Any]]] = UNSET
r"""Tiered pricing for the product item. Not applicable for fixed price items."""
tier_behavior: OptionalNullable[CheckTierBehavior1] = UNSET
r"""How tiers are applied: graduated (split across bands) or volume (flat rate for the matched tier). Defaults to graduated."""
usage_model: OptionalNullable[UsageModel1] = UNSET
r"""Whether the feature should be prepaid upfront or billed for how much they use end of billing period."""
billing_units: OptionalNullable[float] = UNSET
r"""The amount per billing unit (eg. $9 / 250 units)"""
reset_usage_when_enabled: OptionalNullable[bool] = UNSET
r"""Whether the usage should be reset when the product is enabled."""
entity_feature_id: OptionalNullable[str] = UNSET
r"""The entity feature ID of the product item if applicable."""
display: OptionalNullable[ProductDisplay1] = UNSET
r"""The display of the product item."""
quantity: OptionalNullable[float] = UNSET
r"""Used in customer context. Quantity of the feature the customer has prepaid for."""
next_cycle_quantity: OptionalNullable[float] = UNSET
r"""Used in customer context. Quantity of the feature the customer will prepay for in the next cycle."""
config: OptionalNullable[CheckConfig1] = UNSET
r"""Configuration for rollover and proration behavior of the feature."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(
[
"type",
"feature_id",
"feature_type",
"included_usage",
"interval",
"interval_count",
"price",
"tiers",
"tier_behavior",
"usage_model",
"billing_units",
"reset_usage_when_enabled",
"entity_feature_id",
"display",
"quantity",
"next_cycle_quantity",
"config",
]
)
nullable_fields = set(
[
"type",
"feature_id",
"feature_type",
"included_usage",
"interval",
"interval_count",
"price",
"tiers",
"tier_behavior",
"usage_model",
"billing_units",
"reset_usage_when_enabled",
"entity_feature_id",
"display",
"quantity",
"next_cycle_quantity",
"config",
]
)
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
FreeTrialDuration1 = Union[
Literal[
"day",
"month",
"year",
],
UnrecognizedStr,
]
r"""The duration type of the free trial"""
class CheckFreeTrial1TypedDict(TypedDict):
duration: FreeTrialDuration1
r"""The duration type of the free trial"""
length: float
r"""The length of the duration type specified"""
unique_fingerprint: bool
r"""Whether the free trial is limited to one per customer fingerprint"""
card_required: bool
r"""Whether the free trial requires a card. If false, the customer can attach the product without going through a checkout flow or having a card on file."""
trial_available: NotRequired[Nullable[bool]]
r"""Used in customer context. Whether the free trial is available for the customer if they were to attach the product."""
class CheckFreeTrial1(BaseModel):
duration: FreeTrialDuration1
r"""The duration type of the free trial"""
length: float
r"""The length of the duration type specified"""
unique_fingerprint: bool
r"""Whether the free trial is limited to one per customer fingerprint"""
card_required: bool
r"""Whether the free trial requires a card. If false, the customer can attach the product without going through a checkout flow or having a card on file."""
trial_available: OptionalNullable[bool] = True
r"""Used in customer context. Whether the free trial is available for the customer if they were to attach the product."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["trial_available"])
nullable_fields = set(["trial_available"])
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
ProductScenario1 = Union[
Literal[
"scheduled",
"active",
"new",
"renew",
"upgrade",
"update_prepaid_quantity",
"downgrade",
"cancel",
"expired",
"past_due",
],
UnrecognizedStr,
]
r"""Scenario for when this product is used in attach flows"""
class Properties1TypedDict(TypedDict):
is_free: bool
r"""True if the product has no base price or usage prices"""
is_one_off: bool
r"""True if the product only contains a one-time price"""
interval_group: NotRequired[Nullable[str]]
r"""The billing interval group for recurring products (e.g., 'monthly', 'yearly')"""
has_trial: NotRequired[Nullable[bool]]
r"""True if the product includes a free trial"""
updateable: NotRequired[Nullable[bool]]
r"""True if the product can be updated after creation (only applicable if there are prepaid recurring prices)"""
class Properties1(BaseModel):
is_free: bool
r"""True if the product has no base price or usage prices"""
is_one_off: bool
r"""True if the product only contains a one-time price"""
interval_group: OptionalNullable[str] = UNSET
r"""The billing interval group for recurring products (e.g., 'monthly', 'yearly')"""
has_trial: OptionalNullable[bool] = UNSET
r"""True if the product includes a free trial"""
updateable: OptionalNullable[bool] = UNSET
r"""True if the product can be updated after creation (only applicable if there are prepaid recurring prices)"""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["interval_group", "has_trial", "updateable"])
nullable_fields = set(["interval_group", "has_trial", "updateable"])
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
class Product1TypedDict(TypedDict):
id: str
r"""The ID of the product you set when creating the product"""
name: str
r"""The name of the product"""
group: Nullable[str]
r"""Product group which this product belongs to"""
env: CheckEnv1
r"""The environment of the product"""
is_add_on: bool
r"""Whether the product is an add-on and can be purchased alongside other products"""
is_default: bool
r"""Whether the product is the default product"""
archived: bool
r"""Whether this product has been archived and is no longer available"""
version: float
r"""The current version of the product"""
created_at: float
r"""The timestamp of when the product was created in milliseconds since epoch"""
items: List[CheckItem1TypedDict]
r"""Array of product items that define the product's features and pricing"""
free_trial: Nullable[CheckFreeTrial1TypedDict]
r"""Free trial configuration for this product, if available"""
base_variant_id: Nullable[str]
r"""ID of the base variant this product is derived from"""
scenario: NotRequired[ProductScenario1]
r"""Scenario for when this product is used in attach flows"""
properties: NotRequired[Properties1TypedDict]
class Product1(BaseModel):
id: str
r"""The ID of the product you set when creating the product"""
name: str
r"""The name of the product"""
group: Nullable[str]
r"""Product group which this product belongs to"""
env: CheckEnv1
r"""The environment of the product"""
is_add_on: bool
r"""Whether the product is an add-on and can be purchased alongside other products"""
is_default: bool
r"""Whether the product is the default product"""
archived: bool
r"""Whether this product has been archived and is no longer available"""
version: float
r"""The current version of the product"""
created_at: float
r"""The timestamp of when the product was created in milliseconds since epoch"""
items: List[CheckItem1]
r"""Array of product items that define the product's features and pricing"""
free_trial: Nullable[CheckFreeTrial1]
r"""Free trial configuration for this product, if available"""
base_variant_id: Nullable[str]
r"""ID of the base variant this product is derived from"""
scenario: Optional[ProductScenario1] = None
r"""Scenario for when this product is used in attach flows"""
properties: Optional[Properties1] = None
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["scenario", "properties"])
nullable_fields = set(["group", "free_trial", "base_variant_id"])
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
class Preview1TypedDict(TypedDict):
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
scenario: Scenario1
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
title: str
r"""A title suitable for displaying in a paywall or upgrade modal."""
message: str
r"""A message explaining why access was denied."""
feature_id: str
r"""The ID of the feature that was checked."""
feature_name: str
r"""The display name of the feature."""
products: List[Product1TypedDict]
r"""Products that would grant access to this feature. Use to display upgrade options."""
class Preview1(BaseModel):
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
scenario: Scenario1
r"""The reason access was denied. 'usage_limit' means the customer exceeded their balance, 'feature_flag' means the feature is not included in their plan."""
title: str
r"""A title suitable for displaying in a paywall or upgrade modal."""
message: str
r"""A message explaining why access was denied."""
feature_id: str
r"""The ID of the feature that was checked."""
feature_name: str
r"""The display name of the feature."""
products: List[Product1]
r"""Products that would grant access to this feature. Use to display upgrade options."""
class CheckResponseBody1TypedDict(TypedDict):
r"""OK"""
allowed: bool
r"""Whether the customer is allowed to use the feature. True if they have sufficient balance or the feature is unlimited/boolean."""
customer_id: str
r"""The ID of the customer that was checked."""
balance: Nullable[BalanceTypedDict]
r"""The customer's balance for this feature. Null if the customer has no balance for this feature."""
flag: Nullable[Flag1TypedDict]
r"""The flag associated with this check, if any."""
entity_id: NotRequired[Nullable[str]]
r"""The ID of the entity, if an entity-scoped check was performed."""
required_balance: NotRequired[float]
r"""The required balance that was checked against."""
preview: NotRequired[Preview1TypedDict]
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
class CheckResponseBody1(BaseModel):
r"""OK"""
allowed: bool
r"""Whether the customer is allowed to use the feature. True if they have sufficient balance or the feature is unlimited/boolean."""
customer_id: str
r"""The ID of the customer that was checked."""
balance: Nullable[Balance]
r"""The customer's balance for this feature. Null if the customer has no balance for this feature."""
flag: Nullable[Flag1]
r"""The flag associated with this check, if any."""
entity_id: OptionalNullable[str] = UNSET
r"""The ID of the entity, if an entity-scoped check was performed."""
required_balance: Optional[float] = None
r"""The required balance that was checked against."""
preview: Optional[Preview1] = None
r"""Upgrade/upsell information when access is denied. Only present if with_preview was true and allowed is false."""
@model_serializer(mode="wrap")
def serialize_model(self, handler):
optional_fields = set(["entity_id", "required_balance", "preview"])
nullable_fields = set(["entity_id", "balance", "flag"])
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
CheckResponseTypedDict = TypeAliasType(
"CheckResponseTypedDict",
Union[CheckResponseBody1TypedDict, CheckResponseBody2TypedDict],
)
CheckResponse = TypeAliasType(
"CheckResponse", Union[CheckResponseBody1, CheckResponseBody2]
)
try:
CheckLock.model_rebuild()
except NameError:
pass