[IMP] sale: Convert _onchange_discount into compute method

This commit is contained in:
Yannick Tivisse
2021-12-02 12:12:02 +01:00
parent 916e92aa30
commit 1003ef0e70
8 changed files with 47 additions and 61 deletions
-2
View File
@@ -118,8 +118,6 @@ class AccountMoveLine(models.Model):
# create the sale lines in batch
new_sale_lines = self.env['sale.order.line'].create(sale_line_values_to_create)
for sol in new_sale_lines:
sol._onchange_discount()
# build result map by replacing index with newly created record of sale.order.line
result = {}
+42 -30
View File
@@ -238,7 +238,9 @@ class SaleOrderLine(models.Model):
price_reduce_taxinc = fields.Monetary(compute='_compute_price_reduce_taxinc', string='Price Reduce Tax inc', store=True)
price_reduce_taxexcl = fields.Monetary(compute='_compute_price_reduce_taxexcl', string='Price Reduce Tax excl', store=True)
discount = fields.Float(string='Discount (%)', digits='Discount', default=0.0)
discount = fields.Float(
string='Discount (%)', digits='Discount',
compute='_compute_discount', store=True, readonly=False)
product_id = fields.Many2one(
'product.product', string='Product', domain="[('sale_ok', '=', True), '|', ('company_id', '=', False), ('company_id', '=', company_id)]",
@@ -781,39 +783,49 @@ class SaleOrderLine(models.Model):
'tax_id', 'analytic_tag_ids'
]
@api.onchange('product_id', 'price_unit', 'product_uom', 'product_uom_qty', 'tax_id')
def _onchange_discount(self):
if not (self.product_id and self.product_uom and
self.order_id.partner_id and self.order_id.pricelist_id and
self.order_id.pricelist_id.discount_policy == 'without_discount' and
self.env.user.has_group('product.group_discount_per_so_line')):
return
@api.depends('product_id', 'price_unit', 'product_uom', 'product_uom_qty', 'tax_id')
def _compute_discount(self):
for line in self:
if not (line.product_id and line.product_uom and
line.order_id.partner_id and line.order_id.pricelist_id and
line.order_id.pricelist_id.discount_policy == 'without_discount' and
self.env.user.has_group('product.group_discount_per_so_line')):
continue
self.discount = 0.0
product = self.product_id.with_context(
lang=self.order_id.partner_id.lang,
partner=self.order_id.partner_id,
quantity=self.product_uom_qty,
date=self.order_id.date_order,
pricelist=self.order_id.pricelist_id.id,
uom=self.product_uom.id,
fiscal_position=self.env.context.get('fiscal_position')
)
line.discount = 0.0
product = line.product_id.with_context(
lang=line.order_id.partner_id.lang,
partner=line.order_id.partner_id,
quantity=line.product_uom_qty,
date=line.order_id.date_order,
pricelist=line.order_id.pricelist_id.id,
uom=line.product_uom.id,
fiscal_position=self.env.context.get('fiscal_position'))
product_context = dict(self.env.context, partner_id=self.order_id.partner_id.id, date=self.order_id.date_order, uom=self.product_uom.id)
product_context = dict(
self.env.context,
partner_id=line.order_id.partner_id.id,
date=line.order_id.date_order,
uom=line.product_uom.id)
price, rule_id = self.order_id.pricelist_id.with_context(product_context).get_product_price_rule(self.product_id, self.product_uom_qty or 1.0, self.order_id.partner_id)
new_list_price, currency = self.with_context(product_context)._get_real_price_currency(product, rule_id, self.product_uom_qty, self.product_uom, self.order_id.pricelist_id.id)
price, rule_id = line.order_id.pricelist_id.with_context(product_context).get_product_price_rule(
line.product_id,
line.product_uom_qty or 1.0,
line.order_id.partner_id)
new_list_price, currency = line.with_context(product_context)._get_real_price_currency(
product, rule_id, line.product_uom_qty,
line.product_uom, line.order_id.pricelist_id.id)
if new_list_price != 0:
if self.order_id.pricelist_id.currency_id != currency:
# we need new_list_price in the same currency as price, which is in the SO's pricelist's currency
new_list_price = currency._convert(
new_list_price, self.order_id.pricelist_id.currency_id,
self.order_id.company_id or self.env.company, self.order_id.date_order or fields.Date.today())
discount = (new_list_price - price) / new_list_price * 100
if (discount > 0 and new_list_price > 0) or (discount < 0 and new_list_price < 0):
self.discount = discount
if new_list_price != 0:
if line.order_id.pricelist_id.currency_id != currency:
# we need new_list_price in the same currency as price, which is in the SO's pricelist's currency
new_list_price = currency._convert(
new_list_price, line.order_id.pricelist_id.currency_id,
line.order_id.company_id or self.env.company,
line.order_id.date_order or fields.Date.today())
discount = (new_list_price - price) / new_list_price * 100
if (discount > 0 and new_list_price > 0) or (discount < 0 and new_list_price < 0):
line.discount = discount
def _is_delivery(self):
self.ensure_one()
-4
View File
@@ -156,12 +156,9 @@ class TestOnchangeProductId(TransactionCase):
'product_id': computer_case.id,
})
# force compute uom and prices
order_line._onchange_discount()
self.assertEqual(order_line.price_subtotal, 90, "Christmas discount pricelist rule not applied")
self.assertEqual(order_line.discount, 10, "Christmas discount not equalt to 10%")
order_line.product_uom = new_uom
order_line._onchange_discount()
self.assertEqual(order_line.price_subtotal, 900, "Christmas discount pricelist rule not applied")
self.assertEqual(order_line.discount, 10, "Christmas discount not equalt to 10%")
@@ -211,7 +208,6 @@ class TestOnchangeProductId(TransactionCase):
'product_id': computer_case.id,
})
order_line._onchange_discount()
self.assertEqual(order_line.price_subtotal, 81, "Second pricelist rule not applied")
self.assertEqual(order_line.discount, 19, "Second discount not applied")
-9
View File
@@ -281,10 +281,6 @@ class TestSaleOrder(TestSaleCommon):
self.sol_serv_order.write({'tax_id': [(4, tax_exclude.id)]})
self.sol_product_deliver.write({'tax_id': [(4, tax_exclude.id)]})
# Trigger onchange to reset discount, unit price, subtotal, ...
for line in self.sale_order.order_line:
line._onchange_discount()
for line in self.sale_order.order_line:
if line.tax_id.price_include:
price = line.price_unit * line.product_uom_qty - line.price_tax
@@ -461,9 +457,6 @@ class TestSaleOrder(TestSaleCommon):
})
]
})
for line in sales_order.order_line:
# Create values autofill does not compute discount.
line._onchange_discount()
so_line_1 = sales_order.order_line[0]
so_line_2 = sales_order.order_line[1]
@@ -492,8 +485,6 @@ class TestSaleOrder(TestSaleCommon):
})
]
})
for line in sales_order.order_line:
line._onchange_discount()
so_line_1 = sales_order.order_line[0]
so_line_2 = sales_order.order_line[1]
-6
View File
@@ -119,9 +119,6 @@ class TestSaleOrder(TestSaleCommon):
""" Test SO with the pricelist and check unit price appeared on its lines """
# Change the pricelist
self.sale_order.write({'pricelist_id': self.pricelist_discount_incl.id})
# Trigger onchange to reset discount, unit price, subtotal, ...
for line in self.sale_order.order_line:
line._onchange_discount()
# Check that pricelist of the SO has been applied on the sale order lines or not
for line in self.sale_order.order_line:
if line.product_id == self.company_data['product_order_no']:
@@ -142,9 +139,6 @@ class TestSaleOrder(TestSaleCommon):
# Change the pricelist
self.sale_order.write({'pricelist_id': self.pricelist_discount_excl.id})
# Trigger onchange to reset discount, unit price, subtotal, ...
for line in self.sale_order.order_line:
line._onchange_discount()
# Check pricelist of the SO apply or not on order lines where pricelist contains formula that add 15% on the cost price
for line in self.sale_order.order_line:
+1 -1
View File
@@ -239,7 +239,7 @@ class SaleOrderOption(models.Model):
# To compute the discount a so line is created in cache
values = self._get_values_to_add_to_order()
new_sol = self.env['sale.order.line'].new(values)
new_sol._onchange_discount()
new_sol._compute_discount()
self.discount = new_sol.discount
if self.order_id.pricelist_id and self.order_id.partner_id:
self.price_unit = new_sol._get_display_price(product)
@@ -115,14 +115,9 @@ class SaleOrder(models.Model):
product_uom_qty=qty,
product_no_variant_attribute_value_ids=no_variant_attribute_values.ids)
))
if product_ids:
if new_lines:
# Add new SO lines
self.update(dict(order_line=new_lines))
# Recompute prices for new/modified lines
for line in self.order_line.filtered(lambda line: line.product_id.id in product_ids):
line._onchange_discount()
if product_ids and new_lines:
# Add new SO lines
self.update(dict(order_line=new_lines))
def _get_matrix(self, product_template):
"""Return the matrix of the given product, updated with current SOLines quantities.
+1 -1
View File
@@ -116,7 +116,7 @@ class SaleOrder(models.Model):
discount = 0
if order.pricelist_id.discount_policy == 'without_discount':
# This part is pretty much a copy-paste of the method '_onchange_discount' of
# This part is pretty much a copy-paste of the method '_compute_discount' of
# 'sale.order.line'.
price, rule_id = order.pricelist_id.with_context(product_context).get_product_price_rule(product, qty or 1.0, order.partner_id)
pu, currency = request.env['sale.order.line'].with_context(product_context)._get_real_price_currency(product, rule_id, qty, product.uom_id, order.pricelist_id.id)