diff --git a/l10n_it_withholding_tax/__init__.py b/l10n_it_withholding_tax/__init__.py index 83e553ac462c..0aa9b03c5794 100644 --- a/l10n_it_withholding_tax/__init__.py +++ b/l10n_it_withholding_tax/__init__.py @@ -1,3 +1,4 @@ # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). from . import models +from . import wizards diff --git a/l10n_it_withholding_tax/models/account.py b/l10n_it_withholding_tax/models/account.py index 44da0e5be2fc..5234de7fdc20 100644 --- a/l10n_it_withholding_tax/models/account.py +++ b/l10n_it_withholding_tax/models/account.py @@ -3,7 +3,7 @@ # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). from odoo import _, api, fields, models -from odoo.exceptions import UserError, ValidationError +from odoo.exceptions import ValidationError from odoo.tools.float_utils import float_compare, float_round @@ -565,25 +565,6 @@ def _compute_payments_widget_reconciled_info(self): payment_val["wt_move_line"] = False return - def action_register_payment(self): - """ - Set net to pay how default amount to pay - """ - res = super().action_register_payment() - amount_net_pay_residual = 0 - currency_id = self.currency_id - if len(currency_id) > 1: - raise UserError(_("Invoices must have the same currency")) - for am in self: - if am.withholding_tax_amount: - amount_net_pay_residual += am.amount_net_pay_residual - if not currency_id.is_zero(amount_net_pay_residual): - ctx = res.get("context", {}) - if ctx: - ctx.update({"default_amount": amount_net_pay_residual}) - res.update({"context": ctx}) - return res - class AccountMoveLine(models.Model): _inherit = "account.move.line" diff --git a/l10n_it_withholding_tax/readme/ROADMAP.rst b/l10n_it_withholding_tax/readme/ROADMAP.rst new file mode 100644 index 000000000000..1fae45cb26f1 --- /dev/null +++ b/l10n_it_withholding_tax/readme/ROADMAP.rst @@ -0,0 +1 @@ +The Residual Net To Pay set in the Payment wizard should be converted in the wizard's currency when it changes diff --git a/l10n_it_withholding_tax/tests/test_withholding_tax.py b/l10n_it_withholding_tax/tests/test_withholding_tax.py index 20b03c053326..dc142d3e0117 100644 --- a/l10n_it_withholding_tax/tests/test_withholding_tax.py +++ b/l10n_it_withholding_tax/tests/test_withholding_tax.py @@ -320,3 +320,44 @@ def test_wt_after_repost(self): self.assertEqual(self.invoice.amount_net_pay_residual, 200) self.assertEqual(self.invoice.amount_residual, 250) self.assertEqual(self.invoice.state, "posted") + + def _get_payment_wizard(self, invoice): + wizard_action = invoice.action_register_payment() + wizard_model = wizard_action["res_model"] + wizard_context = wizard_action["context"] + wizard = self.env[wizard_model].with_context(**wizard_context).create({}) + return wizard + + def test_payment_reset_net_pay_residual(self): + """The amount to pay is reset to the Residual Net To Pay + when amount and Journal are changed.""" + # Arrange: Pay an invoice + invoice = self.invoice + wizard = self._get_payment_wizard(invoice) + user_set_amount = 20 + # pre-condition + self.assertEqual( + wizard.amount, + invoice.amount_net_pay_residual, + ) + self.assertTrue( + invoice.withholding_tax_amount, + ) + + # Act: Change amount + wizard.amount = user_set_amount + + # Assert: User's change is kept + self.assertEqual( + wizard.amount, + user_set_amount, + ) + + # Act: Change Journal + wizard.journal_id = self.journal_bank + + # Assert: Amount is reset to the Residual Net To Pay + self.assertEqual( + wizard.amount, + invoice.amount_net_pay_residual, + ) diff --git a/l10n_it_withholding_tax/wizards/__init__.py b/l10n_it_withholding_tax/wizards/__init__.py new file mode 100644 index 000000000000..704c7ed05751 --- /dev/null +++ b/l10n_it_withholding_tax/wizards/__init__.py @@ -0,0 +1,3 @@ +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from . import account_payment_register diff --git a/l10n_it_withholding_tax/wizards/account_payment_register.py b/l10n_it_withholding_tax/wizards/account_payment_register.py new file mode 100644 index 000000000000..19bc8916c1a8 --- /dev/null +++ b/l10n_it_withholding_tax/wizards/account_payment_register.py @@ -0,0 +1,57 @@ +# Copyright 2023 Simone Rubino - TAKOBI +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import _, api, models +from odoo.exceptions import UserError + + +class AccountPaymentRegister(models.TransientModel): + _inherit = "account.payment.register" + + @api.model + def _get_wizard_values_from_batch(self, batch_result): + wizard_values_from_batch = super()._get_wizard_values_from_batch(batch_result) + self._inject_withholding_net_pay_residual(wizard_values_from_batch) + return wizard_values_from_batch + + def _inject_withholding_net_pay_residual(self, wizard_values_from_batch): + """If the payment is for Invoices having Withholding Taxes, + set the Residual Net To Pay as the amount to be paid. + """ + if self.env.context.get("active_model") == "account.move": + moves_ids = self.env.context.get("active_ids", []) + moves = self.env["account.move"].browse(moves_ids) + withholding_moves = moves.filtered("withholding_tax") + if withholding_moves: + currency = withholding_moves.currency_id + if len(currency) > 1: + raise UserError(_("Invoices must have the same currency")) + net_pay_residual_amount = sum( + withholding_moves.mapped("amount_net_pay_residual") + ) + if not currency.is_zero( + net_pay_residual_amount, + ): + wizard_values_from_batch["source_amount"] = net_pay_residual_amount + # Withholding tax amount is a simple float + # and does not change for different currencies + wizard_values_from_batch[ + "source_amount_currency" + ] = net_pay_residual_amount + return wizard_values_from_batch + + def _get_total_amount_in_wizard_currency_to_full_reconcile( + self, batch_result, early_payment_discount=True + ): + amount, mode = super()._get_total_amount_in_wizard_currency_to_full_reconcile( + batch_result, early_payment_discount=early_payment_discount + ) + withholding_net_pay_residual_values = self._inject_withholding_net_pay_residual( + dict() + ) + withholding_net_pay_residual = withholding_net_pay_residual_values.get( + "source_amount" + ) + if withholding_net_pay_residual is not None: + amount = withholding_net_pay_residual + return amount, mode