diff --git a/docker/Makefile b/docker/Makefile index 3ce708a5..d726617c 100644 --- a/docker/Makefile +++ b/docker/Makefile @@ -13,6 +13,12 @@ generate-production-static-data deploy # ---------------------- Dev section ---------------------- +repl: + $(dc) exec app python manage.py shell + +bash: + $(dc) exec app bash + migrate: $(dc) run --rm app python manage.py migrate diff --git a/requirements.txt b/requirements.txt index e4f40fbf..d273a63b 100644 --- a/requirements.txt +++ b/requirements.txt @@ -25,4 +25,4 @@ sorl-thumbnail==12.5.0 python-telegram-bot==11.1.0 sentry-sdk==0.7.2 https://github.com/selwin/django-user_agents/archive/master.zip -https://github.com/fidals/refarm-site/archive/0.5.11.zip +https://github.com/fidals/refarm-site/archive/0.5.12.zip diff --git a/shopelectro/admin.py b/shopelectro/admin.py index bdae28c1..301ffbe5 100644 --- a/shopelectro/admin.py +++ b/shopelectro/admin.py @@ -12,7 +12,7 @@ from ecommerce import mailer from ecommerce.models import Position from pages.models import CustomPage, FlatPage, PageTemplate -from generic_admin import inlines, mixins, models, sites +from generic_admin import inlines, mixins, models, sites, filters from shopelectro import models as se_models from shopelectro.views.admin import TableEditor @@ -34,6 +34,11 @@ def prepare_has_filter_queryset(value, db_table, queryset): return queryset.filter(**{query: value != 'yes'}) +class ProductPriceFilter(filters.PriceRange): + + price_lookup = 'shopelectro_product__price' + + class HasTagsFilter(admin.SimpleListFilter): product_model = se_models.Product @@ -155,7 +160,13 @@ class ProductPageAdmin(models.ProductPageAdmin): add = False delete = False category_page_model = se_models.CategoryPage - list_filter = [*models.ProductPageAdmin.list_filter, HasTagsFilter, HasCategoryFilter] + list_filter = [ + *models.ProductPageAdmin.list_filter, + ProductPriceFilter, + HasTagsFilter, + HasCategoryFilter, + ] + list_display = ['model_id', 'name', 'custom_parent', 'price', 'links', 'is_active'] inlines = [ProductInline, inlines.ImageInline] search_fields = [ 'shopelectro_product__vendor_code', 'name', 'slug', @@ -167,10 +178,16 @@ def model_id(self, obj): model_id.short_description = _('Vendor code') model_id.admin_order_field = 'shopelectro_product__vendor_code' + def price(self, obj): + return obj.model.price + + price.short_description = _('Price') + price.admin_order_field = '_product_price' + def get_queryset(self, request): + qs = super().get_queryset(request) return ( - super(ProductPageAdmin, self) - .get_queryset(request) + self.add_reference_to_field_on_related_model(qs, _product_price='price') .select_related('shopelectro_product') ) diff --git a/shopelectro/tests/tests_selenium_admin.py b/shopelectro/tests/tests_selenium_admin.py index 0463b19e..0e7b07b6 100644 --- a/shopelectro/tests/tests_selenium_admin.py +++ b/shopelectro/tests/tests_selenium_admin.py @@ -59,6 +59,10 @@ def setUp(self): class AdminPage(AdminSeleniumTestCase): """Selenium-based tests for Admin page UI.""" + # @todo #835:60m Fix admin filter tests + # Tests rely upon order of html markup. + # It is fragile and always breaks after admin filter modifications. + @classmethod def setUpClass(cls): super().setUpClass() @@ -67,11 +71,11 @@ def setUpClass(cls): cls.title_text = 'Shopelectro administration' cls.active_products = '//*[@id="changelist-filter"]/ul[1]/li[2]/a' cls.inactive_products = '//*[@id="changelist-filter"]/ul[1]/li[3]/a' - cls.price_filter = '//*[@id="changelist-filter"]/ul[2]/li[3]/a' - cls.filter_by_has_content = '//*[@id="changelist-filter"]/ul[3]/li[2]/a' - cls.filter_by_has_not_content = '//*[@id="changelist-filter"]/ul[3]/li[3]/a' - cls.filter_by_has_image = '//*[@id="changelist-filter"]/ul[4]/li[2]/a' - cls.filter_by_has_not_image = '//*[@id="changelist-filter"]/ul[4]/li[3]/a' + cls.price_filter = '//*[@id="changelist-filter"]/ul[4]/li[3]/a' + cls.filter_by_has_content = '//*[@id="changelist-filter"]/ul[2]/li[2]/a' + cls.filter_by_has_not_content = '//*[@id="changelist-filter"]/ul[2]/li[3]/a' + cls.filter_by_has_image = '//*[@id="changelist-filter"]/ul[3]/li[2]/a' + cls.filter_by_has_not_image = '//*[@id="changelist-filter"]/ul[3]/li[3]/a' cls.is_active_img = 'field-is_active' cls.autocomplete_text = 'Prod' cls.jstree_children = 'jstree-children' @@ -143,11 +147,6 @@ def test_login(self): admin_title = self.browser.find_element_by_id('site-name') self.assertIn(self.title_text, admin_title.text) - # @todo #822:30m Resurrect admin price filter. - # It's failing after fix changing `PriceRange.price_lookup` value. - # Fix was here: https://github.com/fidals/refarm-site/pull/325 - # Just disable this filter for STB. It's not relevant there - @unittest.expectedFailure def test_product_price_filter(self): """ Price filter is able to filter products by set range. @@ -164,7 +163,7 @@ def test_product_price_filter(self): )) product_price = int(float(product.text.replace(',', '.'))) - self.assertTrue(product_price >= 1000) + self.assertTrue(product_price >= 1000 and product_price < 2000) def test_image_filter(self): """Image filter is able to filter pages by the presence of the image."""