def test_category_links_plugin_with_customer(rf, show_all_categories): """ Test plugin for categories that is visible for certain group """ shop = get_default_shop() group = get_default_customer_group() customer = create_random_person() customer.groups.add(group) customer.save() request = rf.get("/") request.shop = get_default_shop() apply_request_middleware(request) request.customer = customer category = get_default_category() category.status = CategoryStatus.VISIBLE category.visibility = CategoryVisibility.VISIBLE_TO_GROUPS category.visibility_groups.add(group) category.shops.add(shop) category.save() vars = {"request": request} context = get_jinja_context(**vars) plugin = CategoryLinksPlugin({"categories": [category.pk], "show_all_categories": show_all_categories}) assert category.is_visible(customer) assert category in plugin.get_context_data(context)["categories"] customer_without_groups = create_random_person() customer_without_groups.groups.clear() assert not category.is_visible(customer_without_groups) request.customer = customer_without_groups context = get_jinja_context(**vars) assert category not in plugin.get_context_data(context)["categories"]
def test_get_pagination_variables(): populate_if_required() # Makes sure there is at least 30 products in db products = Product.objects.all()[:19] assert len(products) == 19 vars = {"products": products} context = get_jinja_context(**vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert variables["page"].number == 1 assert len(variables["objects"]) == 4 context = get_jinja_context(path="/?page=5", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert variables["page"].number == 5 assert len(variables["objects"]) == 3 variables = general.get_pagination_variables(context, context["products"], limit=20) assert not variables["is_paginated"] assert variables["page"].number == 1 context = get_jinja_context(path="/?page=42", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert variables["page"].number == 5 assert len(variables["objects"]) == 3 vars = {"products": []} context = get_jinja_context(path="/", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert not variables["is_paginated"]
def test_get_pagination_variables(reindex_catalog): from shuup.front.template_helpers import general populate_if_required() # Makes sure there is at least 30 products in db products = Product.objects.all()[:19] assert len(products) == 19 vars = {"products": products} reindex_catalog() context = get_jinja_context(**vars) variables = general.get_pagination_variables(context, context["products"], limit=2) assert variables["page"].number == 1 assert len(variables["objects"]) == 2 assert variables["page_range"][0] == 1 assert variables["page_range"][-1] == 5 context = get_jinja_context(path="/?page=5", **vars) variables = general.get_pagination_variables(context, context["products"], limit=2) assert variables["page"].number == 5 assert len(variables["objects"]) == 2 assert variables["page_range"][0] == 3 assert variables["page_range"][-1] == 7 variables = general.get_pagination_variables(context, context["products"], limit=20) assert not variables["is_paginated"] assert variables["page"].number == 1 assert variables["page_range"][0] == variables["page_range"][-1] == 1 context = get_jinja_context(path="/?page=42", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert variables["page"].number == 5 assert len(variables["objects"]) == 3 assert variables["page_range"][0] == 1 assert variables["page_range"][-1] == 5 vars = {"products": []} context = get_jinja_context(path="/", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert not variables["is_paginated"] assert variables["page_range"][0] == variables["page_range"][-1] == 1
def test_get_best_selling_products(): context = get_jinja_context() cache.clear() # No products sold assert len(list(general.get_best_selling_products(context, n_products=2))) == 0 supplier = get_default_supplier() shop = get_default_shop() product = get_default_product() create_order_with_product(product, supplier, quantity=1, taxless_base_unit_price=10, shop=shop) cache.clear() # One product sold assert len(list(general.get_best_selling_products(context, n_products=2))) == 1 # Make order unorderable shop_product = product.get_shop_instance(shop) shop_product.visibility = ShopProductVisibility.NOT_VISIBLE shop_product.save() assert len(list(general.get_best_selling_products(context, n_products=2))) == 0
def test_get_listed_products_orderable_only(): if "shuup.simple_supplier" not in settings.INSTALLED_APPS: pytest.skip("Need shuup.simple_supplier in INSTALLED_APPS") from shuup_tests.simple_supplier.utils import get_simple_supplier context = get_jinja_context() shop = get_default_shop() simple_supplier = get_simple_supplier() n_products = 2 # Create product without stock product = create_product( "test-sku", supplier=simple_supplier, shop=shop, stock_behavior=StockBehavior.STOCKED ) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 0 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1 # Increase stock on product quantity = product.get_shop_instance(shop).minimum_purchase_quantity simple_supplier.adjust_stock(product.id, quantity) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 1 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1 # Decrease stock on product simple_supplier.adjust_stock(product.id, -quantity) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 0 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1
def test_banner_box_plugin(): context = get_jinja_context() test_carousel = Carousel.objects.create(name="test") plugin = BannerBoxPlugin(config={"carousel": test_carousel.pk, "title": "Test"}) data = plugin.get_context_data(context) assert data.get("carousel") == test_carousel assert data.get("title") == "Test"
def get_context(rf, customer=None): request = rf.get("/") request.shop = factories.get_default_shop() apply_request_middleware(request) if customer: request.customer = customer return get_jinja_context(**{"request": request})
def test_best_selling_products_with_multiple_orders(): context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() n_products = 2 price = 10 product_1 = create_product("test-sku-1", supplier=supplier, shop=shop) product_2 = create_product("test-sku-2", supplier=supplier, shop=shop) create_order_with_product(product_1, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) cache.clear() # Two initial products sold assert product_1 in general.get_best_selling_products(context, n_products=n_products) assert product_2 in general.get_best_selling_products(context, n_products=n_products) product_3 = create_product("test-sku-3", supplier=supplier, shop=shop) create_order_with_product(product_3, supplier, quantity=2, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product sold in greater quantity assert product_3 in general.get_best_selling_products(context, n_products=n_products) create_order_with_product(product_1, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product outsold by first two products assert product_3 not in general.get_best_selling_products(context, n_products=n_products)
def test_products_for_category(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() category = get_default_category() products = [ create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2) ] children = [ create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2) ] category.shops.add(shop) for child in children: child.link_to_parent(products[0]) context = get_jinja_context() for product in products: product.get_shop_instance(shop).categories.add(category) category_products = list( general.get_products_for_categories(context, [category])) assert len(category_products) == 2 assert products[0] in category_products assert products[1] in category_products
def test_cross_sell_plugin_cache_bump(): shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier) context = get_jinja_context(product=product) total_count = 5 trim_count = 3 type = ProductCrossSellType.RELATED _create_cross_sell_products(product, shop, supplier, type, total_count) assert ProductCrossSell.objects.filter(product1=product, type=type).count() == total_count set_cached_value_mock = mock.Mock(wraps=context_cache.set_cached_value) def set_cache_value(key, value, timeout=None): if "product_cross_sells" in key: return set_cached_value_mock(key, value, timeout) with mock.patch.object(context_cache, "set_cached_value", new=set_cache_value): assert set_cached_value_mock.call_count == 0 assert product_helpers.get_product_cross_sells(context, product, type, trim_count) assert set_cached_value_mock.call_count == 1 # call again, the cache should be returned instead and the set_cached_value shouldn't be called again assert product_helpers.get_product_cross_sells(context, product, type, trim_count) assert set_cached_value_mock.call_count == 1 # bump caches ProductCrossSell.objects.filter(product1=product, type=type).first().save() assert product_helpers.get_product_cross_sells(context, product, type, trim_count) assert set_cached_value_mock.call_count == 2
def test_get_random_products(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() products = [ create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2) ] children = [ create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2) ] for child in children: child.link_to_parent(products[0]) context = get_jinja_context() random_products = list(general.get_random_products(context, n_products=10)) assert len(random_products) == 2 # only 2 parent products exist assert products[0] in random_products assert products[1] in random_products
def test_get_listed_products_cache_bump(): supplier = get_default_supplier() shop = get_default_shop() product_1 = create_product("test-sku-1", supplier=supplier, shop=shop,) from shuup.front.template_helpers import general filter_dict = {"id": product_1.pk} cache.clear() context = get_jinja_context() set_cached_value_mock = mock.Mock(wraps=context_cache.set_cached_value) def set_cache_value(key, value, timeout=None): if "listed_products" in key: return set_cached_value_mock(key, value, timeout) with mock.patch.object(context_cache, "set_cached_value", new=set_cache_value): assert set_cached_value_mock.call_count == 0 for cache_test in range(2): assert general.get_listed_products(context, n_products=2, filter_dict=filter_dict, orderable_only=False) assert set_cached_value_mock.call_count == 1 # bump cache product_1.save() for cache_test in range(2): assert general.get_listed_products(context, n_products=2, filter_dict=filter_dict, orderable_only=False) assert set_cached_value_mock.call_count == 2 # use other filters from django.db.models import Q for cache_test in range(2): assert general.get_listed_products(context, n_products=2, extra_filters=Q(translations__name__isnull=False)) assert set_cached_value_mock.call_count == 3
def test_get_random_products_cache_bump(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() products = [create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2)] children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2)] for child in children: child.link_to_parent(products[0]) context = get_jinja_context() cache.clear() set_cached_value_mock = mock.Mock(wraps=context_cache.set_cached_value) def set_cache_value(key, value, timeout=None): if "random_products" in key: return set_cached_value_mock(key, value, timeout) with mock.patch.object(context_cache, "set_cached_value", new=set_cache_value): assert set_cached_value_mock.call_count == 0 assert general.get_random_products(context, n_products=10) assert set_cached_value_mock.call_count == 1 # call again, the cache should be returned instead and the set_cached_value shouldn't be called again assert general.get_random_products(context, n_products=10) assert set_cached_value_mock.call_count == 1 # change a shop product, the cache should be bumped ShopProduct.objects.filter(shop=shop).first().save() assert general.get_random_products(context, n_products=10) assert set_cached_value_mock.call_count == 2
def test_get_root_categories(): populate_if_required() context = get_jinja_context() from shuup.front.template_helpers import general for root in general.get_root_categories(context=context): assert not root.parent_id
def test_get_newest_products(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() products = [create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2)] children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2)] for child in children: child.link_to_parent(products[0]) context = get_jinja_context() for cache_test in range(2): newest_products = list(general.get_newest_products(context, n_products=10)) # only 2 products exist assert len(newest_products) == 2 assert products[0] in newest_products assert products[1] in newest_products # Delete one product products[0].soft_delete() for cache_test in range(2): newest_products = list(general.get_newest_products(context, n_products=10)) # only 2 products exist assert len(newest_products) == 1 assert products[0] not in newest_products assert products[1] in newest_products
def test_best_selling_products_with_multiple_orders(): context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() n_products = 2 price = 10 product_1 = create_product("test-sku-1", supplier=supplier, shop=shop) product_2 = create_product("test-sku-2", supplier=supplier, shop=shop) create_order_with_product(product_1, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) cache.clear() # Two initial products sold assert product_1 in general.get_best_selling_products(context, n_products=n_products) assert product_2 in general.get_best_selling_products(context, n_products=n_products) product_3 = create_product("test-sku-3", supplier=supplier, shop=shop) create_order_with_product(product_3, supplier, quantity=2, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product sold in greater quantity assert product_3 in general.get_best_selling_products(context, n_products=n_products) create_order_with_product(product_1, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product outsold by first two products assert product_3 not in general.get_best_selling_products(context, n_products=n_products) children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(5)] for child in children: child.link_to_parent(product_3) create_order_with_product(child, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product now sold in greatest quantity assert product_3 == general.get_best_selling_products(context, n_products=n_products)[0]
def test_get_listed_products_filter(): context = get_jinja_context() shop = get_default_shop() supplier = get_default_supplier() product_1 = create_product( "test-sku-1", supplier=supplier, shop=shop, ) product_2 = create_product( "test-sku-2", supplier=supplier, shop=shop, ) cache.clear() from shuup.front.template_helpers import general filter_dict = {"id": product_1.id} for cache_test in range(2): product_list = general.get_listed_products(context, n_products=2, filter_dict=filter_dict) assert product_1 in product_list assert product_2 not in product_list for cache_test in range(2): product_list = general.get_listed_products(context, n_products=2, filter_dict=filter_dict, orderable_only=False) assert product_1 in product_list assert product_2 not in product_list
def test_get_all_manufacturers(reindex_catalog): from shuup.front.template_helpers import general context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() manuf1 = Manufacturer.objects.create(name="M1") manuf2 = Manufacturer.objects.create(name="M2") manuf3 = Manufacturer.objects.create(name="M2") manuf1.shops.add(shop) manuf2.shops.add(shop) products = [ create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(3) ] products[0].manufacturer = manuf1 products[0].save() products[1].manufacturer = manuf2 products[1].save() products[2].manufacturer = manuf3 products[2].save() reindex_catalog() assert len(general.get_all_manufacturers(context)) == 3
def test_cross_sell_plugin_renders(): """ Test that the plugin renders a product """ shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier, stock_behavior=StockBehavior.UNSTOCKED) computed = create_product("test-computed-sku", shop=shop, supplier=supplier, stock_behavior=StockBehavior.UNSTOCKED) type = ProductCrossSellType.COMPUTED ProductCrossSell.objects.create(product1=product, product2=computed, type=type) assert ProductCrossSell.objects.filter(product1=product, type=type).count() == 1 context = get_jinja_context(product=product) rendered = ProductCrossSellsPlugin({"type": type}).render(context) assert computed.sku in rendered
def test_page_links_plugin_show_all(): """ Test that show_all_pages forces plugin to return all visible pages """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) page_two = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) page_three = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) plugin = PageLinksPlugin({"show_all_pages": False}) assert not plugin.get_context_data(context)["pages"] plugin = PageLinksPlugin({"show_all_pages": True}) assert page in plugin.get_context_data(context)["pages"] page_ordered_list = [page_three.pk, page.pk, page_two.pk] plugin = PageLinksPlugin({ "show_all_pages": False, "pages": page_ordered_list }) assert page_ordered_list == [ x.pk for x in plugin.get_context_data(context)["pages"] ]
def test_get_listed_products_filter(): context = get_jinja_context() shop = get_default_shop() supplier = get_default_supplier() product_1 = create_product( "test-sku-1", supplier=supplier, shop=shop, ) product_2 = create_product( "test-sku-2", supplier=supplier, shop=shop, ) filter_dict = {"id": product_1.id} product_list = general.get_listed_products(context, n_products=2, filter_dict=filter_dict) assert product_1 in product_list assert product_2 not in product_list product_list = general.get_listed_products(context, n_products=2, filter_dict=filter_dict, orderable_only=False) assert product_1 in product_list assert product_2 not in product_list
def test_page_links_plugin_hide_expired(show_all_pages): """ Make sure plugin correctly filters out expired pages based on plugin configuration """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) another_page = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) plugin = PageLinksPlugin({ "pages": [page.pk, another_page.pk], "show_all_pages": show_all_pages }) assert page in plugin.get_context_data(context)["pages"] page.available_from = None page.available_to = None page.save() assert page in plugin.get_context_data(context)["pages"] plugin.config["hide_expired"] = True pages_in_context = plugin.get_context_data(context)["pages"] assert page not in pages_in_context assert another_page in pages_in_context
def test_social_media_plugin_ordering(): """ Test that social media plugin ordering works as expected """ context = get_jinja_context() icon_classes = SocialMediaLinksPlugin.icon_classes link_1_type = "Facebook" link_1 = { "url": "http://www.facebook.com", "ordering": 2, } link_2_type = "Twitter" link_2 = { "url": "http://www.twitter.com", "ordering": 1, } links = { link_1_type: link_1, link_2_type: link_2, } plugin = SocialMediaLinksPlugin({"links": links}) assert len(plugin.get_links()) == 2 # Make sure link 2 comes first assert plugin.get_links()[0][2] == link_2["url"]
def test_get_random_products_sale_only(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() product = create_product("sku-1", supplier=supplier, shop=shop, default_price=10) context = get_jinja_context() cache.clear() for cache_test in range(2): assert len(general.get_random_products(context, n_products=10)) == 1 assert len(general.get_random_products(context, n_products=10, sale_items_only=True)) == 0 # add a catalog campaign discount for the product from shuup.campaigns.models import CatalogCampaign from shuup.campaigns.models.catalog_filters import ProductFilter from shuup.campaigns.models.product_effects import ProductDiscountAmount campaign = CatalogCampaign.objects.create(shop=shop, public_name="test", name="test", active=True) product_filter = ProductFilter.objects.create() product_filter.products.add(product) campaign.filters.add(product_filter) ProductDiscountAmount.objects.create(campaign=campaign, discount_amount=0.1) cache.clear() for cache_test in range(2): assert len(general.get_random_products(context, n_products=10, sale_items_only=True)) == 1 assert product in general.get_random_products(context, n_products=10, sale_items_only=True)
def test_cross_sell_plugin_type(): """ Test that template helper returns correct number of cross sells when shop contains multiple relation types """ shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier) context = get_jinja_context(product=product) type_counts = ((ProductCrossSellType.RELATED, 1), (ProductCrossSellType.RECOMMENDED, 2), (ProductCrossSellType.BOUGHT_WITH, 3)) # Create cross sell products and relations in different quantities for type, count in type_counts: _create_cross_sell_products(product, shop, supplier, type, count) assert ProductCrossSell.objects.filter(product1=product, type=type).count() == count # Make sure quantities returned by plugin match for type, count in type_counts: cache.clear() assert len( list( product_helpers.get_product_cross_sells( context, product, type, count))) == count
def test_get_listed_products_orderable_only(): context = get_jinja_context() shop = get_default_shop() simple_supplier = get_simple_supplier() n_products = 2 # Create product without stock product = create_product( "test-sku", supplier=simple_supplier, shop=shop, stock_behavior=StockBehavior.STOCKED ) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 0 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1 # Increase stock on product quantity = product.get_shop_instance(shop).minimum_purchase_quantity simple_supplier.adjust_stock(product.id, quantity) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 1 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1 # Decrease stock on product simple_supplier.adjust_stock(product.id, -quantity) assert len(general.get_listed_products(context, n_products, orderable_only=True)) == 0 assert len(general.get_listed_products(context, n_products, orderable_only=False)) == 1
def test_bought_with_template_helper(): shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier) context = get_jinja_context(product=product) type = ProductCrossSellType.COMPUTED visible_count = 10 hidden_count = 4 _create_cross_sell_products(product, shop, supplier, type, visible_count) _create_cross_sell_products(product, shop, supplier, type, hidden_count, hidden=True) assert ProductCrossSell.objects.filter( product1=product, type=type).count() == (visible_count + hidden_count) # Make sure quantities returned by plugin match cache.clear() assert len( list( product_helpers.get_products_bought_with( context, product, visible_count))) == visible_count
def test_plugin_renders_absolute_links(): """ Test that the plugin renders only absolute links. """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True, shop=get_default_shop()) absolute_link = "/%s" % page.url plugin = PageLinksPlugin({"show_all_pages": True}) assert absolute_link in plugin.render(context)
def test_carousel_plugin_form_get_context(): shop = get_default_shop() context = get_jinja_context() test_carousel = Carousel.objects.create(name="test") plugin = CarouselPlugin(config={"carousel": test_carousel.pk}) assert plugin.get_context_data(context).get("carousel") is None test_carousel.shops.add(shop) plugin = CarouselPlugin(config={"carousel": test_carousel.pk}) assert plugin.get_context_data(context).get("carousel") == test_carousel
def test_plugin_renders_absolute_links(): """ Test that the plugin renders only absolute links. """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True) absolute_link = "/%s" % page.url plugin = PageLinksPlugin({"show_all_pages": True}) assert absolute_link in plugin.render(context)
def test_get_best_selling_products(): from shuup.front.template_helpers import general context = get_jinja_context() # No products sold assert len(list(general.get_best_selling_products(context, n_products=3))) == 0 shop = get_default_shop() supplier = get_default_supplier() supplier2 = Supplier.objects.create(name="supplier2", enabled=True, is_approved=True) supplier3 = Supplier.objects.create(name="supplier3", enabled=True, is_approved=True) supplier2.shops.add(shop) supplier3.shops.add(shop) product1 = create_product("product1", shop, supplier, 10) product2 = create_product("product2", shop, supplier, 20) create_order_with_product(product1, supplier, quantity=1, taxless_base_unit_price=10, shop=shop) create_order_with_product(product2, supplier, quantity=2, taxless_base_unit_price=20, shop=shop) cache.clear() # Two products sold for cache_test in range(2): best_selling_products = list(general.get_best_selling_products(context, n_products=3)) assert len(best_selling_products) == 2 assert product1 in best_selling_products assert product2 in best_selling_products # Make order unorderable shop_product = product1.get_shop_instance(shop) shop_product.visibility = ShopProductVisibility.NOT_VISIBLE shop_product.save() cache.clear() for cache_test in range(2): best_selling_products = list(general.get_best_selling_products(context, n_products=3)) assert len(best_selling_products) == 1 assert product1 not in best_selling_products assert product2 in best_selling_products # add a new product with discounted amount product3 = create_product("product3", supplier=supplier, shop=shop, default_price=30) create_order_with_product(product3, supplier, quantity=1, taxless_base_unit_price=30, shop=shop) from shuup.customer_group_pricing.models import CgpDiscount CgpDiscount.objects.create( shop=shop, product=product3, group=AnonymousContact.get_default_group(), discount_amount_value=5 ) cache.clear() for cache_test in range(2): best_selling_products = list(general.get_best_selling_products(context, n_products=3, orderable_only=True)) assert len(best_selling_products) == 2 assert product1 not in best_selling_products assert product2 in best_selling_products assert product3 in best_selling_products
def test_get_random_products(): supplier = get_default_supplier() shop = get_default_shop() products = [create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2)] children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2)] for child in children: child.link_to_parent(products[0]) context = get_jinja_context() # only 2 parent products exist assert len(list(general.get_random_products(context, n_products=10))) == 2
def test_carousel_plugin_form_get_context(): shop = get_default_shop() context = get_jinja_context() test_carousel = Carousel.objects.create(name="test") plugin = CarouselPlugin(config={"carousel": test_carousel.pk}) assert plugin.get_context_data(context).get("carousel") == None test_carousel.shops = [shop] plugin = CarouselPlugin(config={"carousel": test_carousel.pk}) assert plugin.get_context_data(context).get("carousel") == test_carousel
def test_get_listed_products_orderable_only(): context = get_jinja_context() shop = get_default_shop() simple_supplier = get_simple_supplier() n_products = 2 # Create product without stock product = create_product("test-sku", supplier=simple_supplier, shop=shop) create_product("test-sku-2", supplier=simple_supplier, shop=shop) create_product("test-sku-3", supplier=simple_supplier, shop=shop) create_product("test-sku-4", supplier=simple_supplier, shop=shop) from shuup.front.template_helpers import general for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=True)) == 0 for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=False)) == 2 # Increase stock on product quantity = product.get_shop_instance(shop).minimum_purchase_quantity simple_supplier.adjust_stock(product.id, quantity) for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=True)) == 0 for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=False)) == 2 # Decrease stock on product simple_supplier.adjust_stock(product.id, -quantity) for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=True)) == 0 for cache_test in range(2): assert len( general.get_listed_products(context, n_products, orderable_only=False)) == 2
def test_best_selling_products_with_multiple_orders(): from shuup.front.template_helpers import general context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() n_products = 2 price = 10 product_1 = create_product("test-sku-1", supplier=supplier, shop=shop, default_price=price) product_2 = create_product("test-sku-2", supplier=supplier, shop=shop, default_price=price) create_order_with_product(product_1, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) # Two initial products sold for cache_test in range(2): assert product_1 in general.get_best_selling_products(context, n_products=n_products) assert product_2 in general.get_best_selling_products(context, n_products=n_products) product_3 = create_product("test-sku-3", supplier=supplier, shop=shop, default_price=price) create_order_with_product(product_3, supplier, quantity=2, taxless_base_unit_price=price, shop=shop) # Third product sold in greater quantity cache.clear() assert product_3 in general.get_best_selling_products(context, n_products=n_products) create_order_with_product(product_1, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) create_order_with_product(product_2, supplier, quantity=4, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product outsold by first two products for cache_test in range(2): assert product_3 not in general.get_best_selling_products(context, n_products=n_products) children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(5)] for child in children: child.link_to_parent(product_3) create_order_with_product(child, supplier, quantity=1, taxless_base_unit_price=price, shop=shop) cache.clear() # Third product now sold in greatest quantity for cache_test in range(2): assert product_3 == general.get_best_selling_products(context, n_products=n_products)[0] # add a new product with discounted amount product_4 = create_product("test-sku-4", supplier=supplier, shop=shop, default_price=price) create_order_with_product(product_4, supplier, quantity=2, taxless_base_unit_price=price, shop=shop) from shuup.customer_group_pricing.models import CgpDiscount CgpDiscount.objects.create( shop=shop, product=product_4, group=AnonymousContact.get_default_group(), discount_amount_value=(price * 0.1) )
def test_page_links_plugin_show_all(): """ Test that show_all_pages forces plugin to return all visible pages """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True) plugin = PageLinksPlugin({"show_all_pages": False}) assert not plugin.get_context_data(context)["pages"] plugin = PageLinksPlugin({"show_all_pages": True}) assert page in plugin.get_context_data(context)["pages"]
def test_get_pagination_variables(): from shuup.front.template_helpers import general populate_if_required() # Makes sure there is at least 30 products in db products = Product.objects.all()[:19] assert len(products) == 19 vars = {"products": products} context = get_jinja_context(**vars) variables = general.get_pagination_variables(context, context["products"], limit=2) assert variables["page"].number == 1 assert len(variables["objects"]) == 2 assert variables["page_range"][0] == 1 assert variables["page_range"][-1] == 5 context = get_jinja_context(path="/?page=5", **vars) variables = general.get_pagination_variables(context, context["products"], limit=2) assert variables["page"].number == 5 assert len(variables["objects"]) == 2 assert variables["page_range"][0] == 3 assert variables["page_range"][-1] == 7 variables = general.get_pagination_variables(context, context["products"], limit=20) assert not variables["is_paginated"] assert variables["page"].number == 1 assert variables["page_range"][0] == variables["page_range"][-1] == 1 context = get_jinja_context(path="/?page=42", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert variables["page"].number == 5 assert len(variables["objects"]) == 3 assert variables["page_range"][0] == 1 assert variables["page_range"][-1] == 5 vars = {"products": []} context = get_jinja_context(path="/", **vars) variables = general.get_pagination_variables(context, context["products"], limit=4) assert not variables["is_paginated"] assert variables["page_range"][0] == variables["page_range"][-1] == 1
def test_get_best_selling_products(): context = get_jinja_context() cache.clear() # No products sold assert len(list(general.get_best_selling_products(context, n_products=2))) == 0 supplier = get_default_supplier() shop = get_default_shop() product = get_default_product() create_order_with_product(product, supplier, quantity=1, taxless_base_unit_price=10, shop=shop) cache.clear() # One product sold assert len(list(general.get_best_selling_products(context, n_products=2))) == 1
def test_cross_sell_plugin_count(): shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier, stock_behavior=StockBehavior.UNSTOCKED) context = get_jinja_context(product=product) total_count = 5 trim_count = 3 type = ProductCrossSellType.RELATED _create_cross_sell_products(product, shop, supplier, type, total_count) assert ProductCrossSell.objects.filter(product1=product, type=type).count() == total_count assert len(list(product_helpers.get_product_cross_sells(context, product, type, trim_count))) == trim_count
def test_page_links_plugin_visible_in_menu(): """ Make sure plugin correctly filters out pages that are not set to be visible in menus """ context = get_jinja_context() page = create_page(eternal=True, visible_in_menu=True) plugin = PageLinksPlugin({"pages": [page.pk]}) assert page in plugin.get_context_data(context)["pages"] page.visible_in_menu = False page.save() assert page not in plugin.get_context_data(context)["pages"]
def test_bought_with_template_helper(): shop = get_default_shop() supplier = get_default_supplier() product = create_product("test-sku", shop=shop, supplier=supplier) context = get_jinja_context(product=product) type = ProductCrossSellType.COMPUTED visible_count = 10 hidden_count = 4 _create_cross_sell_products(product, shop, supplier, type, visible_count) _create_cross_sell_products(product, shop, supplier, type, hidden_count, hidden=True) assert ProductCrossSell.objects.filter(product1=product, type=type).count() == (visible_count + hidden_count) # Make sure quantities returned by plugin match cache.clear() assert len(list(product_helpers.get_products_bought_with(context, product, visible_count))) == visible_count
def test_products_from_category_plugin(): shop = get_default_shop() supplier = get_default_supplier() cat = Category.objects.create(identifier="cat-1") for name, sku, price in CATEGORY_PRODUCT_DATA: product = _create_orderable_product(name, sku, price=price) shop_product = product.get_shop_instance(shop) cat = Category.objects.first() shop_product.primary_category = cat shop_product.save() shop_product.categories.add(cat) context = get_jinja_context() rendered = ProductsFromCategoryPlugin({"title": "Products", "count": 4, "category": cat.id}).render(context) soup = BeautifulSoup(rendered) assert "Products" in soup.find("h2").contents[0] assert len(soup.findAll("div", {"class": "product-card"})) == 4
def test_get_sorts_and_filters(rf): context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() product1 = create_product("product1", shop, supplier, 10) product2 = create_product("product2", shop, supplier, 20) request = apply_request_middleware(rf.get("/")) queryset = Product.objects.all() cache.clear() for time in range(2): products = list(get_product_queryset(queryset, request, None, {})) assert len(products) == 2 assert product1 in products assert product2 in products
def test_get_best_selling_products_cache_bump(): supplier = get_default_supplier() shop = get_default_shop() shop2 = get_shop(identifier="shop2") product1 = create_product("product1", shop, supplier, 10) product2 = create_product("product2", shop, supplier, 20) product3 = create_product("product3", shop2, supplier, 20) shop1_product1 = product1.get_shop_instance(shop) shop2_product3 = product3.get_shop_instance(shop2) create_order_with_product(product1, supplier, quantity=1, taxless_base_unit_price=10, shop=shop) create_order_with_product(product2, supplier, quantity=2, taxless_base_unit_price=20, shop=shop) create_order_with_product(product3, supplier, quantity=2, taxless_base_unit_price=30, shop=shop2) cache.clear() from shuup.front.template_helpers import general context = get_jinja_context() set_cached_value_mock = mock.Mock(wraps=context_cache.set_cached_value) def set_cache_value(key, value, timeout=None): if "best_selling_products" in key: return set_cached_value_mock(key, value, timeout) with mock.patch.object(context_cache, "set_cached_value", new=set_cache_value): assert set_cached_value_mock.call_count == 0 assert general.get_best_selling_products(context, 2, orderable_only=False) assert set_cached_value_mock.call_count == 1 # call again, the cache should be returned instead and the set_cached_value shouldn't be called again assert general.get_best_selling_products(context, 2, orderable_only=False) assert set_cached_value_mock.call_count == 1 # save the shop2 product and see whether the cache is bumped shop2_product3.save() # neve SHOULD be changed and things should be cached assert general.get_best_selling_products(context, 2, orderable_only=False) assert set_cached_value_mock.call_count == 1 # now change shop1 product, it should bump the cache shop1_product1.save() assert general.get_best_selling_products(context, 2, orderable_only=False) assert set_cached_value_mock.call_count == 2
def test_get_all_manufacturers(): from shuup.front.template_helpers import general context = get_jinja_context() supplier = get_default_supplier() shop = get_default_shop() manuf1 = Manufacturer.objects.create(name="M1") manuf2 = Manufacturer.objects.create(name="M2") manuf3 = Manufacturer.objects.create(name="M2") manuf1.shops.add(shop) manuf2.shops.add(shop) products = [ create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(3) ] products[0].manufacturer = manuf1; products[0].save() products[1].manufacturer = manuf2; products[1].save() products[2].manufacturer = manuf3; products[2].save() set_cached_value_mock = mock.Mock(wraps=context_cache.set_cached_value) def set_cache_value(key, value, timeout=None): if "all_manufacturers" in key: return set_cached_value_mock(key, value, timeout) with mock.patch.object(context_cache, "set_cached_value", new=set_cache_value): assert set_cached_value_mock.call_count == 0 # manufacturers are cached assert len(general.get_all_manufacturers(context)) == 3 assert set_cached_value_mock.call_count == 1 # call again, cache is used assert len(general.get_all_manufacturers(context)) == 3 assert set_cached_value_mock.call_count == 1 # change manufacturer, the cache is bumped manuf1.save() assert len(general.get_all_manufacturers(context)) == 3 assert set_cached_value_mock.call_count == 2 # change a manufacturer with no shop, cache bumped manuf3.save() assert len(general.get_all_manufacturers(context)) == 3 assert set_cached_value_mock.call_count == 3
def test_get_random_products(): from shuup.front.template_helpers import general supplier = get_default_supplier() shop = get_default_shop() products = [create_product("sku-%d" % x, supplier=supplier, shop=shop) for x in range(2)] children = [create_product("SimpleVarChild-%d" % x, supplier=supplier, shop=shop) for x in range(2)] for child in children: child.link_to_parent(products[0]) context = get_jinja_context() random_products = list(general.get_random_products(context, n_products=10)) assert len(random_products) == 2 # only 2 parent products exist assert products[0] in random_products assert products[1] in random_products