Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions lago_python_client/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
from .invoiced_usages.clients import InvoicedUsageClient
from .invoices.clients import InvoiceClient
from .mrrs.clients import MrrClient
from .order_forms.clients import OrderFormClient
from .orders.clients import OrderClient
from .organizations.clients import OrganizationClient
from .overdue_balances.clients import OverdueBalanceClient
from .payment_receipts.clients import PaymentReceiptClient
Expand All @@ -33,6 +35,8 @@
from .plans.charges_client import PlanChargesClient
from .plans.clients import PlanClient
from .plans.fixed_charges_client import PlanFixedChargesClient
from .quote_versions.clients import QuoteVersionClient
from .quotes.clients import QuoteClient
from .services.rate_limit import RateLimitCallback, RateLimitRetryConfig
from .subscriptions.charges_client import SubscriptionChargesClient
from .subscriptions.clients import SubscriptionClient
Expand Down Expand Up @@ -180,6 +184,14 @@ def invoiced_usages(self) -> InvoicedUsageClient:
def mrrs(self) -> MrrClient:
return self._create_client(MrrClient, self.base_api_url, self.api_key)

@callable_cached_property
def order_forms(self) -> OrderFormClient:
return self._create_client(OrderFormClient, self.base_api_url, self.api_key)

@callable_cached_property
def orders(self) -> OrderClient:
return self._create_client(OrderClient, self.base_api_url, self.api_key)

@callable_cached_property
def organizations(self) -> OrganizationClient:
return self._create_client(OrganizationClient, self.base_api_url, self.api_key)
Expand Down Expand Up @@ -216,6 +228,14 @@ def plan_charges(self) -> PlanChargesClient:
def plan_fixed_charges(self) -> PlanFixedChargesClient:
return self._create_client(PlanFixedChargesClient, self.base_api_url, self.api_key)

@callable_cached_property
def quotes(self) -> QuoteClient:
return self._create_client(QuoteClient, self.base_api_url, self.api_key)

@callable_cached_property
def quote_versions(self) -> QuoteVersionClient:
return self._create_client(QuoteVersionClient, self.base_api_url, self.api_key)

@callable_cached_property
def subscriptions(self) -> SubscriptionClient:
return self._create_client(SubscriptionClient, self.base_api_url, self.api_key)
Expand Down
42 changes: 42 additions & 0 deletions lago_python_client/models/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,21 @@
from .minimum_commitment import (
MinimumCommitmentResponse as MinimumCommitmentResponse,
)
from .order import (
OrderExecute as OrderExecute,
)
from .order import (
OrderExecutionRecordResponse as OrderExecutionRecordResponse,
)
from .order import (
OrderResponse as OrderResponse,
)
from .order_form import (
OrderFormMarkAsSigned as OrderFormMarkAsSigned,
)
from .order_form import (
OrderFormResponse as OrderFormResponse,
)
from .organization import (
Organization as Organization,
)
Expand All @@ -234,6 +249,33 @@
from .payment_request import PaymentRequest as PaymentRequest
from .payment_method import PaymentMethod as PaymentMethod, PaymentMethodResponse as PaymentMethodResponse
from .plan import Plan as Plan
from .quote import (
QuoteBillingItemAddOnResponse as QuoteBillingItemAddOnResponse,
)
from .quote import (
QuoteBillingItemCouponResponse as QuoteBillingItemCouponResponse,
)
from .quote import (
QuoteBillingItemPlanResponse as QuoteBillingItemPlanResponse,
)
from .quote import (
QuoteBillingItemsResponse as QuoteBillingItemsResponse,
)
from .quote import (
QuoteBillingItemWalletCreditResponse as QuoteBillingItemWalletCreditResponse,
)
from .quote import (
QuoteOwnerResponse as QuoteOwnerResponse,
)
from .quote import (
QuoteResponse as QuoteResponse,
)
from .quote import (
QuoteVersionApprove as QuoteVersionApprove,
)
from .quote import (
QuoteVersionResponse as QuoteVersionResponse,
)
from .subscription import ActivationRuleInput as ActivationRuleInput, Subscription as Subscription
from .tax import (
Tax as Tax,
Expand Down
39 changes: 39 additions & 0 deletions lago_python_client/models/order.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
from typing import List, Optional

from lago_python_client.base_model import BaseModel

from ..base_model import BaseResponseModel
from .quote import QuoteBillingItemsResponse


class OrderExecute(BaseModel):
execution_mode: Optional[str]


class OrderExecutionRecordResponse(BaseResponseModel):
executed_at: Optional[str]
execution_mode: Optional[str]
invoice_id: Optional[str]
subscription_ids: Optional[List[str]]
terminated_subscription_ids: Optional[List[str]]
applied_coupon_ids: Optional[List[str]]
wallet_ids: Optional[List[str]]
errors: Optional[List[str]]


class OrderResponse(BaseResponseModel):
lago_id: str
number: str
status: str
order_type: str
execution_mode: Optional[str]
currency: Optional[str]
executed_at: Optional[str]
execution_record: Optional[OrderExecutionRecordResponse]
lago_organization_id: str
lago_customer_id: str
lago_order_form_id: str
created_at: str
updated_at: str
# Omitted from the webhook payloads, being a heavy blob.
billing_snapshot: Optional[QuoteBillingItemsResponse]
28 changes: 28 additions & 0 deletions lago_python_client/models/order_form.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
from typing import Optional

from lago_python_client.base_model import BaseModel

from ..base_model import BaseResponseModel


class OrderFormMarkAsSigned(BaseModel):
signed_document: Optional[str]
execution_mode: Optional[str]
execute_at: Optional[str]


class OrderFormResponse(BaseResponseModel):
lago_id: str
number: str
status: str
void_reason: Optional[str]
expires_at: Optional[str]
signed_at: Optional[str]
voided_at: Optional[str]
signed_document_url: Optional[str]
lago_organization_id: str
lago_customer_id: str
lago_quote_id: str
lago_quote_version_id: str
created_at: str
updated_at: str
83 changes: 83 additions & 0 deletions lago_python_client/models/quote.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
from typing import Any, Dict, List, Optional

from lago_python_client.base_model import BaseModel

from ..base_model import BaseResponseModel


class QuoteVersionApprove(BaseModel):
expires_at: Optional[str]


class QuoteBillingItemAddOnResponse(BaseResponseModel):
id: Optional[str]
localId: Optional[str]
type: Optional[str]
payload: Optional[Dict[str, Any]]
overrides: Optional[Dict[str, Any]]


class QuoteBillingItemPlanResponse(BaseResponseModel):
id: Optional[str]
localId: Optional[str]
type: Optional[str]
payload: Optional[Dict[str, Any]]
overrides: Optional[Dict[str, Any]]


class QuoteBillingItemCouponResponse(BaseResponseModel):
id: Optional[str]
localId: Optional[str]
type: Optional[str]
payload: Optional[Dict[str, Any]]
overrides: Optional[Dict[str, Any]]


class QuoteBillingItemWalletCreditResponse(BaseResponseModel):
localId: Optional[str]
type: Optional[str]
payload: Optional[Dict[str, Any]]


class QuoteBillingItemsResponse(BaseResponseModel):
addOns: Optional[List[QuoteBillingItemAddOnResponse]]
plans: Optional[List[QuoteBillingItemPlanResponse]]
coupons: Optional[List[QuoteBillingItemCouponResponse]]
walletCredits: Optional[List[QuoteBillingItemWalletCreditResponse]]


class QuoteVersionResponse(BaseResponseModel):
lago_id: str
lago_quote_id: str
lago_organization_id: str
version: int
status: str
currency: Optional[str]
billing_entity_code: Optional[str]
void_reason: Optional[str]
approved_at: Optional[str]
voided_at: Optional[str]
created_at: str
updated_at: str
# Only returned when a single version is retrieved.
content: Optional[str]
billing_items: Optional[QuoteBillingItemsResponse]


class QuoteOwnerResponse(BaseResponseModel):
lago_id: str
email: Optional[str]


class QuoteResponse(BaseResponseModel):
lago_id: str
number: str
order_type: str
lago_customer_id: str
lago_subscription_id: Optional[str]
lago_organization_id: str
created_at: str
updated_at: str
current_version: Optional[QuoteVersionResponse]
# Only returned when a single quote is retrieved.
owners: Optional[List[QuoteOwnerResponse]]
Empty file.
74 changes: 74 additions & 0 deletions lago_python_client/order_forms/clients.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
from typing import ClassVar, Optional, Type

import httpx

from ..base_client import BaseClient
from ..mixins import (
DEFAULT_TIMEOUT,
FindAllCommandMixin,
FindCommandMixin,
)
from ..models.order_form import OrderFormMarkAsSigned, OrderFormResponse
from ..services.json import to_json
from ..services.request import (
make_headers,
make_url,
send_post_request,
)
from ..services.response import Response, get_response_data, prepare_object_response


class OrderFormClient(
FindCommandMixin[OrderFormResponse],
FindAllCommandMixin[OrderFormResponse],
BaseClient,
):
API_RESOURCE: ClassVar[str] = "order_forms"
RESPONSE_MODEL: ClassVar[Type[OrderFormResponse]] = OrderFormResponse
ROOT_NAME: ClassVar[str] = "order_form"

def mark_as_signed(
self,
resource_id: str,
input_object: Optional[OrderFormMarkAsSigned] = None,
timeout: Optional[httpx.Timeout] = DEFAULT_TIMEOUT,
) -> OrderFormResponse:
"""Record the customer's signature and create the order carrying the deal out."""
payload = input_object.dict(exclude_none=True) if input_object else {}

api_response: Response = send_post_request(
url=make_url(
origin=self.base_url,
path_parts=(self.API_RESOURCE, resource_id, "mark_as_signed"),
),
content=to_json({self.ROOT_NAME: payload}) if payload else None,
headers=make_headers(api_key=self.api_key),
timeout=timeout,
rate_limit_retry_config=self.rate_limit_retry_config,
)

return prepare_object_response(
response_model=self.RESPONSE_MODEL,
data=get_response_data(response=api_response, key=self.ROOT_NAME),
)

def void(
self,
resource_id: str,
timeout: Optional[httpx.Timeout] = DEFAULT_TIMEOUT,
) -> OrderFormResponse:
"""Void a generated order form, cascading to the quote version it came from."""
api_response: Response = send_post_request(
url=make_url(
origin=self.base_url,
path_parts=(self.API_RESOURCE, resource_id, "void"),
),
headers=make_headers(api_key=self.api_key),
timeout=timeout,
rate_limit_retry_config=self.rate_limit_retry_config,
)

return prepare_object_response(
response_model=self.RESPONSE_MODEL,
data=get_response_data(response=api_response, key=self.ROOT_NAME),
)
Empty file.
53 changes: 53 additions & 0 deletions lago_python_client/orders/clients.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
from typing import ClassVar, Optional, Type

import httpx

from ..base_client import BaseClient
from ..mixins import (
DEFAULT_TIMEOUT,
FindAllCommandMixin,
FindCommandMixin,
)
from ..models.order import OrderExecute, OrderResponse
from ..services.json import to_json
from ..services.request import (
make_headers,
make_url,
send_post_request,
)
from ..services.response import Response, get_response_data, prepare_object_response


class OrderClient(
FindCommandMixin[OrderResponse],
FindAllCommandMixin[OrderResponse],
BaseClient,
):
API_RESOURCE: ClassVar[str] = "orders"
RESPONSE_MODEL: ClassVar[Type[OrderResponse]] = OrderResponse
ROOT_NAME: ClassVar[str] = "order"

def execute(
self,
resource_id: str,
input_object: Optional[OrderExecute] = None,
timeout: Optional[httpx.Timeout] = DEFAULT_TIMEOUT,
) -> OrderResponse:
"""Carry out an order on demand, without waiting for its schedule."""
payload = input_object.dict(exclude_none=True) if input_object else {}

api_response: Response = send_post_request(
url=make_url(
origin=self.base_url,
path_parts=(self.API_RESOURCE, resource_id, "execute"),
),
content=to_json({self.ROOT_NAME: payload}) if payload else None,
headers=make_headers(api_key=self.api_key),
timeout=timeout,
rate_limit_retry_config=self.rate_limit_retry_config,
)

return prepare_object_response(
response_model=self.RESPONSE_MODEL,
data=get_response_data(response=api_response, key=self.ROOT_NAME),
)
Empty file.
Loading
Loading