Skip to content

Commit 34cc4b8

Browse files
committed
[ADD] dynamic_ribbons: add test cases for the better console in future
1 parent 8fb7fd7 commit 34cc4b8

File tree

6 files changed

+97
-9
lines changed

6 files changed

+97
-9
lines changed

dynamic_ribbons/__manifest__.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,13 @@
44
'summary': '',
55
'author': 'PBCH',
66
'category': 'Website',
7-
'depends': [ 'website_sale', 'stock' ],
7+
'depends': ['website_sale', 'stock'],
88
'data': [
99
'views/product_ribbon_view.xml',
1010
'views/snippet.xml',
1111
],
1212
'assets': {
13-
'website.assets_wysiwyg':[
13+
'website.assets_wysiwyg': [
1414
'dynamic_ribbons/static/src/js/website_sale_editor.js',
1515
],
1616
'website.backend_assets_all_wysiwyg': [

dynamic_ribbons/controllers/shop_product.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
from odoo.addons.website_sale.controllers.main import WebsiteSale
22
from odoo import http
33

4+
45
class WebsiteSaleExtended(WebsiteSale):
56

67
@http.route([
@@ -18,4 +19,3 @@ def shop(self, page=0, category=None, search='', min_price=0.0, max_price=0.0, p
1819
product._get_ribbon(products_prices)
1920

2021
return response
21-

dynamic_ribbons/models/product_ribbon.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
from odoo import fields, models, api
22
from odoo.exceptions import ValidationError
33

4+
45
class ProductRibbon(models.Model):
56
_inherit = "product.ribbon"
67

@@ -38,12 +39,11 @@ def create(self, vals_list):
3839
if existing_ribbon:
3940
raise ValidationError(f"A ribbon with assign type '{assign_type}' already exists. You cannot create another one.")
4041
return super().create(vals_list)
41-
42+
4243
def write(self, vals):
4344
assign_type = vals.get('assign')
4445
if assign_type != 'manual':
4546
existing_ribbon = self.search([('assign', '=', assign_type), ('id', '!=', self.id)])
4647
if existing_ribbon:
4748
raise ValidationError(f"A ribbon with assign type '{assign_type}' already exists. You cannot assign another one.")
4849
return super().write(vals)
49-

dynamic_ribbons/models/product_template.py

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
from odoo import models, fields
22

3+
34
class ProductTemplate(models.Model):
45
_inherit = 'product.template'
56

@@ -21,12 +22,12 @@ def _get_ribbon(self, products_prices):
2122
if out_of_stock_ribbon and self.qty_available <= 0.0 and not self.allow_out_of_stock_order:
2223
self.website_ribbon_id = out_of_stock_ribbon.id
2324
self.website_ribbon_auto = True
24-
return
25+
return
2526

2627
# Sale Ribbon
2728
pricelist_price = products_prices[self.id].get('price_reduce')
2829
sale_ribbon = product_ribbon_sudo.search([('assign', '=', 'sale')])
29-
if sale_ribbon and (pricelist_price < self.list_price or self.list_price < self.compare_list_price):
30+
if sale_ribbon and (pricelist_price < self.list_price or self.list_price < self.compare_list_price):
3031
self.website_ribbon_id = sale_ribbon.id
3132
self.website_ribbon_auto = True
3233
return
@@ -38,12 +39,11 @@ def _get_ribbon(self, products_prices):
3839
if days_since_publish <= new_ribbon.show_period:
3940
self.website_ribbon_id = new_ribbon.id
4041
self.website_ribbon_auto = True
41-
return
42+
return
4243

4344
# If no ribbon was assigned automatically then clearing any existing automatic ribbon
4445
self.website_ribbon_id = None
4546

46-
4747
def write(self, vals):
4848
if 'website_ribbon_id' in vals and vals['website_ribbon_id'] != self.website_ribbon_id.id:
4949
vals['website_ribbon_auto'] = False

dynamic_ribbons/tests/__init__.py

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
from . import product_ribbons_test_case
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,87 @@
1+
from odoo.tests.common import TransactionCase, tagged
2+
from odoo.exceptions import ValidationError
3+
4+
5+
@tagged("post_install", "-at_install")
6+
class TestProductribbon(TransactionCase):
7+
8+
def setUp(self):
9+
super().setUp()
10+
self.website = self.env["website"].search([], limit=1)
11+
self.product = self.env["product.template"].search([], limit=1)
12+
self.christmas_pricelist = self.env["product.pricelist"].search(
13+
[("name", "=", "Christmas")], limit=1
14+
)
15+
self.christmas_pricelist.write({"selectable": True})
16+
self.prices = self.product._get_sales_prices(self.website)
17+
18+
def _create_ribbon(self, name, assign):
19+
return self.env["product.ribbon"].create({
20+
"name": name,
21+
"assign": assign,
22+
})
23+
24+
def test_sale_ribbon_is_assigned_when_discount_applies(self):
25+
ribbon = self._create_ribbon("Sale", "sale")
26+
self.product._get_ribbon(self.prices)
27+
28+
self.assertEqual(
29+
self.product.website_ribbon_id.id,
30+
ribbon.id,
31+
"Expected Sale ribbon to be assigned when pricelist discount is active."
32+
)
33+
34+
def test_out_of_stock_ribbon_priority_over_sale(self):
35+
self.product.write({
36+
"qty_available": 0,
37+
"allow_out_of_stock_order": False
38+
})
39+
40+
out_ribbon = self._create_ribbon("Out of Stock", "out_of_stock")
41+
self._create_ribbon("Sale", "sale")
42+
self.product._get_ribbon(self.prices)
43+
44+
self.assertEqual(
45+
self.product.website_ribbon_id.id,
46+
out_ribbon.id,
47+
"Out of Stock ribbon should take priority over Sale ribbon."
48+
)
49+
50+
def test_validation_error_on_duplicate_ribbon_assign(self):
51+
self._create_ribbon("Sale Discount", "sale")
52+
with self.assertRaises(ValidationError, msg="Duplicate 'sale' ribbon should raise ValidationError"):
53+
self._create_ribbon("Sale Offer", "sale")
54+
55+
def test_manual_ribbon_should_override_automatic(self):
56+
manual = self._create_ribbon("Sold Out", "manual")
57+
self.product.write({"website_ribbon_id": manual.id})
58+
self._create_ribbon("New", "new")
59+
60+
self.product._get_ribbon(self.prices)
61+
62+
self.assertEqual(
63+
self.product.website_ribbon_id.id,
64+
manual.id,
65+
"Manual ribbon must not be replaced by any automatic ribbon."
66+
)
67+
68+
def test_out_of_stock_respects_allow_out_of_stock_flag(self):
69+
ribbon = self._create_ribbon("Out of Stock", "out_of_stock")
70+
71+
# Case 1: Should apply
72+
self.product.write({"qty_available": 0, "allow_out_of_stock_order": False})
73+
self.product._get_ribbon(self.prices)
74+
self.assertEqual(
75+
self.product.website_ribbon_id.id,
76+
ribbon.id,
77+
"Expected Out of Stock ribbon when allow_out_of_stock_order is False."
78+
)
79+
80+
# Case 2: Should NOT apply
81+
self.product.write({"allow_out_of_stock_order": True})
82+
self.product._get_ribbon(self.prices)
83+
self.assertNotEqual(
84+
self.product.website_ribbon_id.id,
85+
ribbon.id,
86+
"Out of Stock ribbon should not be shown when allow_out_of_stock_order is True."
87+
)

0 commit comments

Comments
 (0)