Merge pull request #17153 from edx/gbabey/ENT-763
Add util method for localizing catalog pricing
This commit is contained in:
@@ -7,17 +7,24 @@ import mock
|
||||
from django.contrib.auth import get_user_model
|
||||
from django.core.cache import cache
|
||||
from django.test import TestCase, override_settings
|
||||
from django.test.client import RequestFactory
|
||||
from student.tests.factories import UserFactory
|
||||
|
||||
from openedx.core.djangoapps.catalog.cache import PROGRAM_CACHE_KEY_TPL, SITE_PROGRAM_UUIDS_CACHE_KEY_TPL
|
||||
from openedx.core.djangoapps.catalog.models import CatalogIntegration
|
||||
from openedx.core.djangoapps.catalog.tests.factories import CourseFactory, CourseRunFactory, ProgramFactory, ProgramTypeFactory
|
||||
from openedx.core.djangoapps.catalog.tests.factories import (
|
||||
CourseFactory,
|
||||
CourseRunFactory,
|
||||
ProgramFactory,
|
||||
ProgramTypeFactory
|
||||
)
|
||||
from openedx.core.djangoapps.catalog.tests.mixins import CatalogIntegrationMixin
|
||||
from openedx.core.djangoapps.catalog.utils import (
|
||||
get_course_runs,
|
||||
get_course_runs_for_course,
|
||||
get_course_run_details,
|
||||
get_currency_data,
|
||||
get_localized_price_text,
|
||||
get_program_types,
|
||||
get_programs,
|
||||
get_programs_with_type
|
||||
@@ -266,6 +273,27 @@ class TestGetCurrency(CatalogIntegrationMixin, TestCase):
|
||||
self.assertEqual(data, currency_data)
|
||||
|
||||
|
||||
@mock.patch(UTILS_MODULE + '.get_currency_data')
|
||||
class TestGetLocalizedPriceText(TestCase):
|
||||
"""
|
||||
Tests covering converting prices to a localized currency
|
||||
"""
|
||||
def test_localized_string(self, mock_get_currency_data):
|
||||
currency_data = {
|
||||
"BEL": {"rate": 0.835621, "code": "EUR", "symbol": u"\u20ac"},
|
||||
"GBR": {"rate": 0.737822, "code": "GBP", "symbol": u"\u00a3"},
|
||||
"CAN": {"rate": 2, "code": "CAD", "symbol": "$"},
|
||||
}
|
||||
mock_get_currency_data.return_value = currency_data
|
||||
|
||||
request = RequestFactory().get('/dummy-url')
|
||||
request.session = {
|
||||
'country_code': 'CA'
|
||||
}
|
||||
expected_result = '$20 CAD'
|
||||
self.assertEqual(get_localized_price_text(10, request), expected_result)
|
||||
|
||||
|
||||
@skip_unless_lms
|
||||
@mock.patch(UTILS_MODULE + '.get_edx_api_data')
|
||||
class TestGetCourseRuns(CatalogIntegrationMixin, TestCase):
|
||||
@@ -278,7 +306,7 @@ class TestGetCourseRuns(CatalogIntegrationMixin, TestCase):
|
||||
self.catalog_integration = self.create_catalog_integration(cache_ttl=1)
|
||||
self.user = UserFactory(username=self.catalog_integration.service_username)
|
||||
|
||||
def assert_contract(self, call_args): # pylint: disable=redefined-builtin
|
||||
def assert_contract(self, call_args):
|
||||
"""
|
||||
Verify that API data retrieval utility is used correctly.
|
||||
"""
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
import copy
|
||||
import datetime
|
||||
import logging
|
||||
import pycountry
|
||||
|
||||
from dateutil.parser import parse as datetime_parse
|
||||
from django.conf import settings
|
||||
@@ -143,6 +144,49 @@ def get_currency_data():
|
||||
return []
|
||||
|
||||
|
||||
def format_price(price, symbol='$', code='USD'):
|
||||
"""
|
||||
Format the price to have the appropriate currency and digits..
|
||||
|
||||
:param price: The price amount.
|
||||
:param symbol: The symbol for the price (default: $)
|
||||
:param code: The currency code to be appended to the price (default: USD)
|
||||
:return: A formatted price string, i.e. '$10 USD', '$10.52 USD'.
|
||||
"""
|
||||
if int(price) == price:
|
||||
return '{}{} {}'.format(symbol, int(price), code)
|
||||
return '{}{:0.2f} {}'.format(symbol, price, code)
|
||||
|
||||
|
||||
def get_localized_price_text(price, request):
|
||||
"""
|
||||
Returns the localized converted price as string (ex. '$150 USD')
|
||||
|
||||
If the users location has been added to the request, this will return the given price based on conversion rate
|
||||
from the Catalog service and return a localized string otherwise will return the default price in USD
|
||||
"""
|
||||
user_currency = {
|
||||
'symbol': '$',
|
||||
'rate': 1,
|
||||
'code': 'USD'
|
||||
}
|
||||
|
||||
# session.country_code is added via CountryMiddleware in the LMS
|
||||
user_location = getattr(request, 'session', {}).get('country_code')
|
||||
|
||||
# Override default user_currency if location is available
|
||||
if user_location and get_currency_data:
|
||||
currency_data = get_currency_data()
|
||||
user_country = pycountry.countries.get(alpha2=user_location)
|
||||
user_currency = currency_data.get(user_country.alpha3, user_currency)
|
||||
|
||||
return format_price(
|
||||
price=(price * user_currency['rate']),
|
||||
symbol=user_currency['symbol'],
|
||||
code=user_currency['code']
|
||||
)
|
||||
|
||||
|
||||
def get_programs_with_type(site, include_hidden=True):
|
||||
"""
|
||||
Return the list of programs. You can filter the types of programs returned by using the optional
|
||||
|
||||
@@ -54,7 +54,7 @@ git+https://github.com/cpennington/pylint-django@fix-field-inference-during-monk
|
||||
enum34==1.1.6
|
||||
edx-django-oauth2-provider==1.2.5
|
||||
edx-django-sites-extensions==2.3.0
|
||||
edx-enterprise==0.61.3
|
||||
edx-enterprise==0.61.4
|
||||
edx-oauth2-provider==1.2.2
|
||||
edx-organizations==0.4.9
|
||||
edx-rest-api-client==1.7.1
|
||||
@@ -86,6 +86,7 @@ piexif==1.0.2
|
||||
Pillow==3.4
|
||||
polib==1.0.3
|
||||
psutil==1.2.1
|
||||
pycountry==1.20
|
||||
pycryptodomex==3.4.7
|
||||
pygments==2.2.0
|
||||
pygraphviz==1.1
|
||||
|
||||
Reference in New Issue
Block a user