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
100 changes: 100 additions & 0 deletions mpt_api_client/resources/commerce/assets.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
from mpt_api_client.http import AsyncService, Service
from mpt_api_client.http.mixins import (
AsyncCollectionMixin,
AsyncCreateMixin,
AsyncGetMixin,
AsyncUpdateMixin,
CollectionMixin,
CreateMixin,
GetMixin,
UpdateMixin,
)
from mpt_api_client.models import Model
from mpt_api_client.models.model import ResourceData


class Asset(Model):
"""Asset resource."""


class AssetTemplate(Model):
"""Asset template resource."""


class AssetsServiceConfig:
"""Assets service config."""

_endpoint = "/public/v1/commerce/assets"
_model_class = Asset
_collection_key = "data"


class AssetsService(
CreateMixin[Asset],
UpdateMixin[Asset],
GetMixin[Asset],
CollectionMixin[Asset],
Service[Asset],
AssetsServiceConfig,
):
"""Assets service."""

def terminate(self, asset_id: str, resource_data: ResourceData | None = None) -> Asset:
"""Terminate the given Asset id.

Args:
asset_id: Asset ID.
resource_data: Resource data will be updated
"""
response = self._resource_do_request(asset_id, "POST", "terminate", json=resource_data)
return self._model_class.from_response(response)

def render(self, asset_id: str) -> AssetTemplate:
"""Renders the template for the given Asset id.

Args:
asset_id: Asset ID.

Returns:
Render asset template json.
"""
response = self._resource_do_request(asset_id, action="render")

return AssetTemplate.from_response(response)


class AsyncAssetsService(
AsyncCreateMixin[Asset],
AsyncUpdateMixin[Asset],
AsyncGetMixin[Asset],
AsyncCollectionMixin[Asset],
AsyncService[Asset],
AssetsServiceConfig,
):
"""Asynchronous Assets service."""

async def terminate(self, asset_id: str, resource_data: ResourceData | None = None) -> Asset:
"""Terminate the given Asset id.

Args:
asset_id: Asset ID.
resource_data: Resource data will be updated
"""
response = await self._resource_do_request(
asset_id, "POST", "terminate", json=resource_data
)

return self._model_class.from_response(response)

async def render(self, asset_id: str) -> AssetTemplate:
"""Renders the template for the given Asset id.

Args:
asset_id: Asset ID.

Returns:
Render asset template json.
"""
response = await self._resource_do_request(asset_id, action="render")

return AssetTemplate.from_response(response)
11 changes: 11 additions & 0 deletions mpt_api_client/resources/commerce/commerce.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
from mpt_api_client.http import AsyncHTTPClient, HTTPClient
from mpt_api_client.resources.commerce.agreements import AgreementsService, AsyncAgreementsService
from mpt_api_client.resources.commerce.assets import AssetsService, AsyncAssetsService
from mpt_api_client.resources.commerce.orders import AsyncOrdersService, OrdersService
from mpt_api_client.resources.commerce.subscriptions import (
AsyncSubscriptionsService,
Expand Down Expand Up @@ -28,6 +29,11 @@ def subscriptions(self) -> SubscriptionsService:
"""Subscription service."""
return SubscriptionsService(http_client=self.http_client)

@property
def assets(self) -> AssetsService:
"""Asset service."""
return AssetsService(http_client=self.http_client)


class AsyncCommerce:
"""Commerce MPT API Module."""
Expand All @@ -49,3 +55,8 @@ def orders(self) -> AsyncOrdersService:
def subscriptions(self) -> AsyncSubscriptionsService:
"""Subscription service."""
return AsyncSubscriptionsService(http_client=self.http_client)

@property
def assets(self) -> AsyncAssetsService:
"""Asset service."""
return AsyncAssetsService(http_client=self.http_client)
106 changes: 106 additions & 0 deletions tests/unit/resources/commerce/test_assets.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
import httpx
import pytest
import respx

from mpt_api_client.constants import APPLICATION_JSON
from mpt_api_client.resources.commerce.assets import AssetsService, AsyncAssetsService


@pytest.fixture
def assets_service(http_client):
return AssetsService(http_client=http_client)


@pytest.fixture
def async_assets_service(async_http_client):
return AsyncAssetsService(http_client=async_http_client)


async def test_async_render(async_assets_service):
render_response = {"id": "ASSET-123", "title": "Sample Asset"}
with respx.mock:
respx.get("https://api.example.com/public/v1/commerce/assets/ASSET-123/render").mock(
return_value=httpx.Response(
status_code=200,
headers={"content-type": APPLICATION_JSON},
json=render_response,
)
)

result = await async_assets_service.render("ASSET-123")

assert result is not None


def test_render(assets_service):
render_response = {"id": "ASSET-123", "title": "Sample Asset"}
with respx.mock:
mock_route = respx.get(
"https://api.example.com/public/v1/commerce/assets/ASSET-123/render"
).mock(
return_value=httpx.Response(
status_code=200,
headers={"content-type": APPLICATION_JSON},
json=render_response,
)
)

result = assets_service.render("ASSET-123")

assert mock_route.called
assert mock_route.call_count == 1
assert result is not None


def test_terminate(assets_service):
response_data = {"id": "ASSET-123", "status": "terminated"}
with respx.mock:
mock_route = respx.post(
"https://api.example.com/public/v1/commerce/assets/ASSET-123/terminate"
).mock(
return_value=httpx.Response(
status_code=200,
headers={"content-type": APPLICATION_JSON},
json=response_data,
)
)

result = assets_service.terminate("ASSET-123")

assert mock_route.called
assert mock_route.call_count == 1
assert result is not None


async def test_async_terminate(async_assets_service):
response_data = {"id": "ASSET-123", "status": "terminated"}
with respx.mock:
mock_route = respx.post(
"https://api.example.com/public/v1/commerce/assets/ASSET-123/terminate"
).mock(
return_value=httpx.Response(
status_code=200,
headers={"content-type": APPLICATION_JSON},
json=response_data,
)
)

result = await async_assets_service.terminate("ASSET-123")

assert mock_route.called
assert mock_route.call_count == 1
assert result is not None


@pytest.mark.parametrize("method", ["create", "update", "get", "render", "terminate"])
def test_assets_service_methods(assets_service, method):
result = hasattr(assets_service, method)

assert result is True


@pytest.mark.parametrize("method", ["create", "update", "get", "render", "terminate"])
def test_async_assets_service_methods(async_assets_service, method):
result = hasattr(async_assets_service, method)

assert result is True
3 changes: 3 additions & 0 deletions tests/unit/resources/commerce/test_commerce.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
from mpt_api_client.http import AsyncHTTPClient
from mpt_api_client.resources.commerce import AsyncCommerce, Commerce
from mpt_api_client.resources.commerce.agreements import AgreementsService, AsyncAgreementsService
from mpt_api_client.resources.commerce.assets import AssetsService, AsyncAssetsService
from mpt_api_client.resources.commerce.orders import AsyncOrdersService, OrdersService
from mpt_api_client.resources.commerce.subscriptions import (
AsyncSubscriptionsService,
Expand Down Expand Up @@ -40,6 +41,7 @@ def test_async_commerce_init(async_http_client: AsyncHTTPClient):
("agreements", AgreementsService),
("orders", OrdersService),
("subscriptions", SubscriptionsService),
("assets", AssetsService),
],
)
def test_commerce_properties(http_client, attr_name, expected):
Expand All @@ -56,6 +58,7 @@ def test_commerce_properties(http_client, attr_name, expected):
("agreements", AsyncAgreementsService),
("orders", AsyncOrdersService),
("subscriptions", AsyncSubscriptionsService),
("assets", AsyncAssetsService),
],
)
def test_async_commerce_properties(http_client, attr_name, expected):
Expand Down