summaryrefslogtreecommitdiff
path: root/addons
diff options
context:
space:
mode:
authorRaf Geens <raf@odoo.com>2021-04-15 11:26:25 +0000
committerRaf Geens <raf@odoo.com>2021-04-15 12:20:36 +0000
commite9538d9cee092e034b85187a2eae857349f42ce7 (patch)
treeedace66466e7106e0657a45b0a18335b189c9a2b /addons
parente179011b3118fe355ea33be194585f674d40df3f (diff)
[FIX] account: Traceback on multiple auto-validation candidates
When an auto-validating reconciliation model is defined for matching bank statement lines to invoices, it was possible to get a traceback when the bank statement lines were in a certain order and matched in a certain way. In particular, if the first bank statement line is priority 3 (communication_flag True) and the amount is an exact match with the invoice, it will be instantly reconciled. If there's a second line that's a priority 5 match, it crashed because _filter_candidates didn't take into account that candidates_by_priority could be empty if the candidates were already reconciled. Instead we just return an empty list of candidates and priorities when this happens. closes odoo/odoo#69309 Ticket: 2507189 Signed-off-by: William André (wan) <wan@odoo.com>
Diffstat (limited to 'addons')
-rw-r--r--addons/account/models/account_reconcile_model.py5
-rw-r--r--addons/account/tests/test_reconciliation_matching_rules.py43
2 files changed, 48 insertions, 0 deletions
diff --git a/addons/account/models/account_reconcile_model.py b/addons/account/models/account_reconcile_model.py
index 50b7ea8d219..2da8dd89fb2 100644
--- a/addons/account/models/account_reconcile_model.py
+++ b/addons/account/models/account_reconcile_model.py
@@ -890,6 +890,11 @@ class AccountReconcileModel(models.Model):
the most prioritary are kept.
"""
candidates_by_priority = self._sort_reconciliation_candidates_by_priority(candidates, aml_ids_to_exclude, reconciled_amls_ids)
+
+ # This can happen if the candidates were already reconciled at this point
+ if not candidates_by_priority:
+ return [], set()
+
max_priority = min(candidates_by_priority.keys())
filtered_candidates = candidates_by_priority[max_priority]
diff --git a/addons/account/tests/test_reconciliation_matching_rules.py b/addons/account/tests/test_reconciliation_matching_rules.py
index 5515f74c9f6..b7718ff0f7b 100644
--- a/addons/account/tests/test_reconciliation_matching_rules.py
+++ b/addons/account/tests/test_reconciliation_matching_rules.py
@@ -477,6 +477,49 @@ class TestReconciliationMatchingRules(AccountTestInvoicingCommon):
self.assertEqual(self.invoice_line_1.amount_residual, 60.0, "The invoice should have been partially reconciled")
+ def test_auto_reconcile_with_duplicate_match(self):
+ """ If multiple bank statement lines match with the same invoice, ensure the
+ correct line is auto-validated and no crashing happens.
+ """
+
+ # Only the invoice defined in this test should have this partner
+ partner = self.env['res.partner'].create({'name': "The Only One"})
+ invoice_line = self._create_invoice_line(
+ 2000, partner, 'out_invoice', ref="REF 7788")
+
+ # Enable auto-validation and don't restrict the partners that can be matched on
+ # so our newly created partner can be matched.
+ self.rule_1.write({
+ 'auto_reconcile': True,
+ 'match_partner_ids': [(5, 0, 0)],
+ })
+ self.rule_1.match_partner_ids = []
+
+ # This line has a matching payment reference and the exact amount of the
+ # invoice. As a result it should auto-validate.
+ self.bank_line_1.amount = 2000
+ self.bank_line_1.partner_id = partner
+ self.bank_line_1.payment_ref = "REF 7788"
+
+ # This line doesn't have a matching amount or reference, but it does have a
+ # matching partner.
+ self.bank_line_2.amount = 1800
+ self.bank_line_2.partner_id = partner
+ self.bank_line_2.payment_ref = "something"
+
+ # Verify the auto-validation happens with the first line, and no exceptions.
+ self._check_statement_matching(self.rule_1, {
+ self.bank_line_1.id: {
+ 'aml_ids': [invoice_line.id],
+ 'model': self.rule_1,
+ 'status': 'reconciled',
+ 'partner': self.bank_line_1.partner_id
+ },
+ self.bank_line_2.id: {
+ 'aml_ids': []
+ },
+ }, statements=self.bank_st)
+
def test_auto_reconcile_with_tax(self):
''' Test auto reconciliation with a tax amount included in the bank statement line'''
self.rule_1.write({