From 4809b572835a94543cd1f37e621a98fabec053fd Mon Sep 17 00:00:00 2001 From: Nicolas Martinelli Date: Fri, 4 Nov 2016 16:08:39 +0100 Subject: [PATCH] [FIX] account: tax line amount The company currency is USD, the invoice currency is EUR. - Create an invoice in EUR, set an invoice date - Compute the taxes (click on "update" button) - Change the exchange rate between EUR and USD - Validate the invoice At validation, the tax lines are not recomputed. Therefore, the tax amounts, are still converted in the company currency using the old rates. On the other hands, the other account move lines will have the appropriate new rate. Closes #14024 opw-692430 --- addons/account/account_invoice.py | 20 +++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/addons/account/account_invoice.py b/addons/account/account_invoice.py index fcf37c7ca74..9f4ee6c7811 100644 --- a/addons/account/account_invoice.py +++ b/addons/account/account_invoice.py @@ -20,6 +20,7 @@ ############################################################################## import itertools +import math from lxml import etree from openerp import models, fields, api, _ @@ -741,8 +742,6 @@ class account_invoice(models.Model): line['currency_id'] = currency.id line['amount_currency'] = currency.round(line['price']) line['price'] = currency.compute(line['price'], company_currency) - if line.get('tax_amount'): - line['tax_amount'] = currency.compute(line['tax_amount'], company_currency) else: line['currency_id'] = False line['amount_currency'] = False @@ -845,6 +844,9 @@ class account_invoice(models.Model): if (total_fixed + total_percent) > 100: raise except_orm(_('Error!'), _("Cannot create the invoice.\nThe related payment term is probably misconfigured as it gives a computed amount greater than the total invoiced amount. In order to avoid rounding issues, the latest line of your payment term must be of type 'balance'.")) + # Force recomputation of tax_amount, since the rate potentially changed between creation + # and validation of the invoice + inv._recompute_tax_amount() # one move line per tax line iml += account_invoice_tax.move_line_get(inv.id) @@ -1227,6 +1229,18 @@ class account_invoice(models.Model): return account_invoice.pay_and_reconcile(recs, pay_amount, pay_account_id, period_id, pay_journal_id, writeoff_acc_id, writeoff_period_id, writeoff_journal_id, name=name) + @api.multi + def _recompute_tax_amount(self): + for invoice in self: + if invoice.currency_id != invoice.company_id.currency_id: + for line in invoice.tax_line: + tax_amount = line.amount_change( + line.amount, currency_id=invoice.currency_id.id, company_id=invoice.company_id.id, + date_invoice=invoice.date_invoice + )['value']['tax_amount'] + line.write({'tax_amount': tax_amount}) + + class account_invoice_line(models.Model): _name = "account.invoice.line" _description = "Invoice Line" @@ -1553,7 +1567,7 @@ class account_invoice_tax(models.Model): currency = self.env['res.currency'].browse(currency_id) currency = currency.with_context(date=date_invoice or fields.Date.context_today(self)) amount = currency.compute(amount, company.currency_id, round=False) - tax_sign = (self.tax_amount / self.amount) if self.amount else 1 + tax_sign = math.copysign(1, (self.tax_amount * self.amount)) return {'value': {'tax_amount': amount * tax_sign}} @api.v8