Skip to content

Commit

Permalink
refactor: make course mode logic dynamic (#287)
Browse files Browse the repository at this point in the history
Description:
Make Fulfillment logic dynamic to support all course modes
  • Loading branch information
ahtesham-quraish authored Nov 14, 2024
1 parent 3f583c0 commit 5899fe9
Show file tree
Hide file tree
Showing 4 changed files with 53 additions and 19 deletions.
20 changes: 20 additions & 0 deletions commerce_coordinator/apps/commercetools/catalog_info/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
from commercetools.platform.models import Attribute as CTAttribute
from commercetools.platform.models import CentPrecisionMoney as CTCentPrecisionMoney
from commercetools.platform.models import HighPrecisionMoney as CTHighPrecisionMoney
from commercetools.platform.models import LineItem as CTLineItem
from commercetools.platform.models import LocalizedString as CTLocalizedString
from commercetools.platform.models import MoneyType as CTMoneyType
from commercetools.platform.models import Price as CTPrice
Expand Down Expand Up @@ -32,6 +33,25 @@ def ls(string_dict: LSLike) -> CTLocalizedString:
return string_dict


def get_line_item_attribute(in_line_item, in_attribute_name): # pragma no cover
"""Utility to get line item's attribute's value."""
attribute_value = None
for attribute in in_line_item.variant.attributes:
if attribute.name == in_attribute_name and hasattr(attribute, 'value'):
if isinstance(attribute.value, dict):
attribute_value = attribute.value.get('label', None)
elif isinstance(attribute.value, str):
attribute_value = attribute.value
break

return attribute_value


def get_course_mode_from_ct_order(line_item: CTLineItem) -> str:
course_mode = get_line_item_attribute(line_item, 'mode')
return course_mode or 'verified'


def ls_eq(a: LSLike, b: LSLike) -> bool:
if a is None or b is None:
return False
Expand Down
25 changes: 8 additions & 17 deletions commerce_coordinator/apps/commercetools/sub_messages/tasks.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,10 @@
get_edx_product_course_run_key,
is_edx_lms_order
)
from commerce_coordinator.apps.commercetools.catalog_info.utils import (
get_course_mode_from_ct_order,
get_line_item_attribute
)
from commerce_coordinator.apps.commercetools.clients import CommercetoolsAPIClient
from commerce_coordinator.apps.commercetools.constants import EMAIL_NOTIFICATION_CACHE_TTL_SECS
from commerce_coordinator.apps.commercetools.filters import OrderRefundRequested
Expand Down Expand Up @@ -83,7 +87,6 @@ def fulfill_order_placed_message_signal_task(
'order_id': order.id,
'provider_id': None,
'edx_lms_user_id': lms_user_id,
'course_mode': 'verified',
'date_placed': order.last_modified_at.strftime(ISO_8601_FORMAT),
'source_system': source_system,
}
Expand Down Expand Up @@ -112,6 +115,7 @@ def fulfill_order_placed_message_signal_task(
**default_params,
'course_id': get_edx_product_course_run_key(item), # likely not correct
'line_item_id': item.id,
'course_mode': get_course_mode_from_ct_order(item),
'item_quantity': item.quantity,
'line_item_state_id': line_item_state_id,
'message_id': message_id
Expand Down Expand Up @@ -202,19 +206,6 @@ def fulfill_order_returned_signal_task(
):
"""Celery task for an order return (and refunded) message."""

def _get_line_item_attribute(in_line_item, in_attribute_name): # pragma no cover
"""Utility to get line item's attribute's value."""
attribute_value = None
for attribute in in_line_item.variant.attributes:
if attribute.name == in_attribute_name and hasattr(attribute, 'value'):
if isinstance(attribute.value, dict):
attribute_value = attribute.value.get('label', None)
elif isinstance(attribute.value, str):
attribute_value = attribute.value
break

return attribute_value

def _cents_to_dollars(in_amount):
return in_amount.cent_amount / pow(
10, in_amount.fraction_digits
Expand Down Expand Up @@ -299,10 +290,10 @@ def _prepare_segment_event_properties(in_order, return_line_item_return_id):
'name': line_item.name['en-US'],
'price': _cents_to_dollars(line_item.price.value),
'quantity': line_item.quantity,
'category': _get_line_item_attribute(line_item, 'primary-subject-area'),
'category': get_line_item_attribute(line_item, 'primary-subject-area'),
'image_url': line_item.variant.images[0].url if line_item.variant.images else None,
'brand': _get_line_item_attribute(line_item, 'brand-text'),
'url': _get_line_item_attribute(line_item, 'url-course'),
'brand': get_line_item_attribute(line_item, 'brand-text'),
'url': get_line_item_attribute(line_item, 'url-course'),
'lob': 'edX', # TODO: Decision was made to hardcode this value for phase 1.
'product_type': line_item.product_type.obj.name
if hasattr(line_item.product_type.obj, 'name') else None
Expand Down
Original file line number Diff line number Diff line change
@@ -1,22 +1,28 @@
""" Commcercetools API Utilities """
from typing import Union
from unittest import TestCase

import ddt
import pytest
from commercetools.platform.models import CentPrecisionMoney, HighPrecisionMoney, Price
from commercetools.platform.models import CentPrecisionMoney, HighPrecisionMoney
from commercetools.platform.models import Order as CTOrder
from commercetools.platform.models import Price
from currencies import Currency

from commerce_coordinator.apps.commercetools.catalog_info.constants import Languages
from commerce_coordinator.apps.commercetools.catalog_info.edx_utils import get_edx_items
from commerce_coordinator.apps.commercetools.catalog_info.utils import (
attribute_dict,
get_course_mode_from_ct_order,
ls,
ls_eq,
price_to_string,
typed_money_add,
typed_money_to_string,
un_ls
)
from commerce_coordinator.apps.core.tests.utils import name_test
from commerce_coordinator.apps.commercetools.tests.conftest import gen_order
from commerce_coordinator.apps.core.tests.utils import name_test, uuid4_str

# <Country>_<Currency>
JAPAN_YEN = "JPY" # 0 fractional digits
Expand All @@ -29,12 +35,25 @@
class LocalizedStringsTests(TestCase):
""" Localized String Utility Tests"""

order: Union[CTOrder, None]

def setUp(self):
self.order = gen_order(uuid4_str())
super().setUp()

def tearDown(self):
self.order = None
super().tearDown()

# ls()
def test_single_unknown_key_ls_creation(self):
string = "test"
result = ls({'ZZ': string})
self.assertEqual(result, {'ZZ': string, Languages.ENGLISH: string, Languages.US_ENGLISH: string})

def test_get_course_mode_from_ct_order(self):
self.assertEqual(get_course_mode_from_ct_order(get_edx_items(self.order)[0]), 'professional')

def test_single_key_ls_creation(self):
string = "test-2"
result = ls({Languages.ENGLISH: string})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,10 @@
"name": "brand-text",
"value": "MichiganX"
},
{
"name": "mode",
"value": "professional"
},
{
"name": "date-created",
"value": "2019-08-21T00:02:00.000Z"
Expand Down

0 comments on commit 5899fe9

Please sign in to comment.