Browse Source

Bug fix

pull/81/head
cybroodoo 9 years ago
parent
commit
ebd7fb7670
  1. 55
      sale_discount_total/models/sale.py
  2. 145
      sale_discount_total/models/sale.py~

55
sale_discount_total/models/sale.py

@ -68,12 +68,30 @@ class SaleOrder(models.Model):
self.supply_rate()
return True
class AccountTax(models.Model):
_inherit = 'account.tax'
@api.multi
@api.v8
def compute_all(self, price_unit, currency=None, quantity=1.0, product=None, partner=None):
print "hello"
""" Returns all information required to apply taxes (in self + their children in case of a tax goup).
We consider the sequence of the parent for group of taxes.
Eg. considering letters as taxes and alphabetic order as sequence :
[G, B([A, D, F]), E, C] will be computed as [A, D, F, C, E, G]
RETURN: {
'total_excluded': 0.0, # Total without taxes
'total_included': 0.0, # Total with taxes
'taxes': [{ # One dict for each tax in self and their children
'id': int,
'name': str,
'amount': float,
'sequence': int,
'account_id': int,
'refund_account_id': int,
'analytic': boolean,
}]
} """
if len(self) == 0:
company_id = self.env.user.company_id
else:
@ -81,18 +99,25 @@ class AccountTax(models.Model):
if not currency:
currency = company_id.currency_id
taxes = []
# By default, for each tax, tax amount will first be computed
# and rounded at the 'Account' decimal precision for each
# PO/SO/invoice line and then these rounded amounts will be
# summed, leading to the total amount for that tax. But, if the
# company has tax_calculation_rounding_method = round_globally,
# we still follow the same method, but we use a much larger
# precision when we round the tax amount for each line (we use
# the 'Account' decimal precision + 5), and that way it's like
# rounding after the sum of the tax amounts of each line
prec = currency.decimal_places
round_tax = False if company_id.tax_calculation_rounding_method == 'round_globally' else True
round_total = True
if 'round' in self.env.context:
round_tax = bool(self.env.context['round'])
round_total = bool(self.env.context['round'])
if not round_tax:
if company_id.tax_calculation_rounding_method == 'round_globally' or not bool(self.env.context.get("round", True)):
prec += 5
# total_excluded = total_included = base = round(price_unit * quantity, prec)
total_excluded = total_included = base = (price_unit * quantity)
#total_excluded = total_included = base = round(price_unit * quantity, prec)
total_excluded = total_included = base = round(price_unit * quantity)
# Sorting key is mandatory in this case. When no key is provided, sorted() will perform a
# search. However, the search method is overridden in account.tax in order to add a domain
# depending on the context. This domain might filter out some taxes from self, e.g. in the
# case of group taxes.
for tax in self.sorted(key=lambda r: r.sequence):
if tax.amount_type == 'group':
ret = tax.children_tax_ids.compute_all(price_unit, currency, quantity, product, partner)
@ -104,7 +129,7 @@ class AccountTax(models.Model):
continue
tax_amount = tax._compute_amount(base, price_unit, quantity, product, partner)
if not round_tax:
if company_id.tax_calculation_rounding_method == 'round_globally' or not bool(self.env.context.get("round", True)):
tax_amount = round(tax_amount, prec)
else:
tax_amount = currency.round(tax_amount)
@ -127,12 +152,10 @@ class AccountTax(models.Model):
'refund_account_id': tax.refund_account_id.id,
'analytic': tax.analytic,
})
print "total_excluded:",total_excluded
print "total_included:",total_included
return {
'taxes': sorted(taxes, key=lambda k: k['sequence']),
'total_excluded': total_excluded,
'total_included': total_included,
'total_excluded': currency.round(total_excluded) if bool(self.env.context.get("round", True)) else total_excluded,
'total_included': currency.round(total_included) if bool(self.env.context.get("round", True)) else total_included,
'base': base,
}

145
sale_discount_total/models/sale.py~

@ -0,0 +1,145 @@
from openerp import api, fields, models
import openerp.addons.decimal_precision as dp
class SaleOrder(models.Model):
_inherit = "sale.order"
@api.depends('order_line.price_total')
def _amount_all(self):
"""
Compute the total amounts of the SO.
"""
for order in self:
amount_untaxed = amount_tax = amount_discount = 0.0
for line in order.order_line:
amount_untaxed += line.price_subtotal
amount_tax += line.price_tax
amount_discount += (line.product_uom_qty * line.price_unit * line.discount)/100
order.update({
'amount_untaxed': order.pricelist_id.currency_id.round(amount_untaxed),
'amount_tax': order.pricelist_id.currency_id.round(amount_tax),
'amount_discount': order.pricelist_id.currency_id.round(amount_discount),
'amount_total': amount_untaxed + amount_tax,
})
discount_type = fields.Selection([('percent', 'Percentage'), ('amount', 'Amount')], string='Discount type',
readonly=True,states={'draft': [('readonly', False)], 'sent': [('readonly', False)]},
default='percent')
discount_rate = fields.Float('Discount Rate', digits_compute=dp.get_precision('Account'),
readonly=True, states={'draft': [('readonly', False)], 'sent': [('readonly', False)]})
amount_untaxed = fields.Monetary(string='Untaxed Amount', store=True, readonly=True, compute='_amount_all',
track_visibility='always')
amount_tax = fields.Monetary(string='Taxes', store=True, readonly=True, compute='_amount_all',
track_visibility='always')
amount_total = fields.Monetary(string='Total', store=True, readonly=True, compute='_amount_all',
track_visibility='always')
amount_discount = fields.Monetary(string='Discount', store=True, readonly=True, compute='_amount_all',
digits_compute=dp.get_precision('Account'), track_visibility='always')
@api.onchange('discount_type', 'discount_rate', 'order_line')
def supply_rate(self):
for order in self:
if order.discount_type == 'percent':
for line in order.order_line:
line.discount = order.discount_rate
else:
total = discount = 0.0
for line in order.order_line:
total += round((line.product_uom_qty * line.price_unit))
if order.discount_rate != 0:
discount = (order.discount_rate / total) * 100
else:
discount = order.discount_rate
for line in order.order_line:
line.discount = discount
@api.multi
def _prepare_invoice(self,):
invoice_vals = super(SaleOrder, self)._prepare_invoice()
invoice_vals.update({
'discount_type': self.discount_type,
'discount_rate': self.discount_rate
})
return invoice_vals
@api.multi
def button_dummy(self):
self.supply_rate()
return True
class AccountTax(models.Model):
_inherit = 'account.tax'
@api.multi
def compute_all(self, price_unit, currency=None, quantity=1.0, product=None, partner=None):
print "hello"
if len(self) == 0:
company_id = self.env.user.company_id
else:
company_id = self[0].company_id
if not currency:
currency = company_id.currency_id
taxes = []
prec = currency.decimal_places
round_tax = False if company_id.tax_calculation_rounding_method == 'round_globally' else True
round_total = True
if 'round' in self.env.context:
round_tax = bool(self.env.context['round'])
round_total = bool(self.env.context['round'])
if not round_tax:
prec += 5
# total_excluded = total_included = base = round(price_unit * quantity, prec)
total_excluded = total_included = base = (price_unit * quantity)
for tax in self.sorted(key=lambda r: r.sequence):
if tax.amount_type == 'group':
ret = tax.children_tax_ids.compute_all(price_unit, currency, quantity, product, partner)
total_excluded = ret['total_excluded']
base = ret['base']
total_included = ret['total_included']
tax_amount = total_included - total_excluded
taxes += ret['taxes']
continue
tax_amount = tax._compute_amount(base, price_unit, quantity, product, partner)
if not round_tax:
tax_amount = round(tax_amount, prec)
else:
tax_amount = currency.round(tax_amount)
if tax.price_include:
total_excluded -= tax_amount
base -= tax_amount
else:
total_included += tax_amount
if tax.include_base_amount:
base += tax_amount
taxes.append({
'id': tax.id,
'name': tax.with_context(**{'lang': partner.lang} if partner else {}).name,
'amount': tax_amount,
'sequence': tax.sequence,
'account_id': tax.account_id.id,
'refund_account_id': tax.refund_account_id.id,
'analytic': tax.analytic,
})
print "total_excluded:",total_excluded
print "total_included:",total_included
return {
'taxes': sorted(taxes, key=lambda k: k['sequence']),
'total_excluded': total_excluded,
'total_included': total_included,
'base': base,
}
class SaleOrderLine(models.Model):
_inherit = "sale.order.line"
discount = fields.Float(string='Discount (%)', digits=(16, 20), default=0.0)
Loading…
Cancel
Save