[IMP] partner_statement: Show only overdue lines

This commit is contained in:
Simone Rubino
2025-06-10 15:30:20 +02:00
committed by Miquel Raïch
parent 795f9c60fe
commit 9703003eca
9 changed files with 84 additions and 4 deletions

View File

@@ -6,7 +6,7 @@
Partner Statement Partner Statement
================= =================
.. ..
!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!! This file is generated by oca-gen-addon-readme !! !! This file is generated by oca-gen-addon-readme !!
!! changes will be overwritten. !! !! changes will be overwritten. !!
@@ -148,6 +148,7 @@ Contributors
- Lois Rilo <lois.rilo@forgeflow.com> - Lois Rilo <lois.rilo@forgeflow.com>
- Dhara Solanki <dhara.solanki@initos.com> - Dhara Solanki <dhara.solanki@initos.com>
- Danny Adair <danny@o4sb.com> - Danny Adair <danny@o4sb.com>
- Simone Rubino <simone.rubino@pytech.it>
Maintainers Maintainers
----------- -----------
@@ -168,7 +169,7 @@ promote its widespread use.
Current `maintainer <https://odoo-community.org/page/maintainer-role>`__: Current `maintainer <https://odoo-community.org/page/maintainer-role>`__:
|maintainer-MiquelRForgeFlow| |maintainer-MiquelRForgeFlow|
This module is part of the `OCA/account-financial-reporting <https://github.com/OCA/account-financial-reporting/tree/17.0/partner_statement>`_ project on GitHub. This module is part of the `OCA/account-financial-reporting <https://github.com/OCA/account-financial-reporting/tree/17.0/partner_statement>`_ project on GitHub.

View File

@@ -3,3 +3,4 @@
- Lois Rilo \<<lois.rilo@forgeflow.com>\> - Lois Rilo \<<lois.rilo@forgeflow.com>\>
- Dhara Solanki \<<dhara.solanki@initos.com>\> - Dhara Solanki \<<dhara.solanki@initos.com>\>
- Danny Adair \<<danny@o4sb.com>\> - Danny Adair \<<danny@o4sb.com>\>
- Simone Rubino \<<simone.rubino@pytech.it>\>

View File

@@ -163,6 +163,7 @@ class ActivityStatement(models.AbstractModel):
excluded_accounts_ids = tuple( excluded_accounts_ids = tuple(
self.env.context.get("excluded_accounts_ids", []) self.env.context.get("excluded_accounts_ids", [])
) or (-1,) ) or (-1,)
show_only_overdue = self.env.context.get("show_only_overdue", False)
payment_ref = _("Payment") payment_ref = _("Payment")
return str( return str(
self._cr.mogrify( self._cr.mogrify(
@@ -203,6 +204,11 @@ class ActivityStatement(models.AbstractModel):
AND l.date <= %(date_end)s AND l.date <= %(date_end)s
AND m.state IN ('posted') AND m.state IN ('posted')
AND aa.account_type = %(account_type)s AND aa.account_type = %(account_type)s
AND CASE
WHEN %(show_only_overdue)s
THEN COALESCE(l.date_maturity, l.date) <= %(date_end)s
ELSE TRUE
END
GROUP BY l.partner_id, m.name, l.date, l.date_maturity, GROUP BY l.partner_id, m.name, l.date, l.date_maturity,
CASE WHEN (aj.type IN ('sale', 'purchase')) CASE WHEN (aj.type IN ('sale', 'purchase'))
THEN l.name THEN l.name

View File

@@ -29,6 +29,7 @@ class OutstandingStatement(models.AbstractModel):
excluded_accounts_ids = tuple( excluded_accounts_ids = tuple(
self.env.context.get("excluded_accounts_ids", []) self.env.context.get("excluded_accounts_ids", [])
) or (-1,) ) or (-1,)
show_only_overdue = self.env.context.get("show_only_overdue", False)
return str( return str(
self._cr.mogrify( self._cr.mogrify(
""" """
@@ -83,6 +84,11 @@ class OutstandingStatement(models.AbstractModel):
(pd.id IS NULL AND pc.id IS NULL) (pd.id IS NULL AND pc.id IS NULL)
) AND l.date <= %(date_end)s AND m.state IN ('posted') ) AND l.date <= %(date_end)s AND m.state IN ('posted')
AND aa.account_type = %(account_type)s AND aa.account_type = %(account_type)s
AND CASE
WHEN %(show_only_overdue)s
THEN COALESCE(l.date_maturity, l.date) <= %(date_end)s
ELSE TRUE
END
GROUP BY l.id, l.partner_id, m.name, l.date, l.date_maturity, l.name, GROUP BY l.id, l.partner_id, m.name, l.date, l.date_maturity, l.name,
CASE WHEN l.ref IS NOT NULL CASE WHEN l.ref IS NOT NULL
THEN l.ref THEN l.ref

View File

@@ -62,6 +62,7 @@ class ReportStatementCommon(models.AbstractModel):
excluded_accounts_ids = tuple( excluded_accounts_ids = tuple(
self.env.context.get("excluded_accounts_ids", []) self.env.context.get("excluded_accounts_ids", [])
) or (-1,) ) or (-1,)
show_only_overdue = self.env.context.get("show_only_overdue", False)
return str( return str(
self._cr.mogrify( self._cr.mogrify(
""" """
@@ -104,6 +105,11 @@ class ReportStatementCommon(models.AbstractModel):
) AND l.date <= %(date_end)s AND not l.blocked ) AND l.date <= %(date_end)s AND not l.blocked
AND m.state IN ('posted') AND m.state IN ('posted')
AND aa.account_type = %(account_type)s AND aa.account_type = %(account_type)s
AND CASE
WHEN %(show_only_overdue)s
THEN COALESCE(l.date_maturity, l.date) <= %(date_end)s
ELSE TRUE
END
GROUP BY l.partner_id, l.currency_id, l.date, l.date_maturity, GROUP BY l.partner_id, l.currency_id, l.date, l.date_maturity,
l.amount_currency, l.balance, l.move_id, l.company_id, l.id l.amount_currency, l.balance, l.move_id, l.company_id, l.id
""", """,
@@ -366,6 +372,11 @@ class ReportStatementCommon(models.AbstractModel):
self = self.with_context( self = self.with_context(
excluded_accounts_ids=excluded_accounts_ids, excluded_accounts_ids=excluded_accounts_ids,
) )
show_only_overdue = data["show_only_overdue"]
if show_only_overdue:
self = self.with_context(
show_only_overdue=show_only_overdue,
)
aging_type = data["aging_type"] aging_type = data["aging_type"]
is_activity = data.get("is_activity") is_activity = data.get("is_activity")
is_detailed = data.get("is_detailed") is_detailed = data.get("is_detailed")
@@ -592,6 +603,7 @@ class ReportStatementCommon(models.AbstractModel):
"Currencies": currencies, "Currencies": currencies,
"account_type": account_type, "account_type": account_type,
"excluded_accounts_ids": excluded_accounts_ids, "excluded_accounts_ids": excluded_accounts_ids,
"show_only_overdue": show_only_overdue,
"is_detailed": is_detailed, "is_detailed": is_detailed,
"bucket_labels": bucket_labels, "bucket_labels": bucket_labels,
"get_inv_addr": self._get_invoice_address, "get_inv_addr": self._get_invoice_address,

View File

@@ -503,6 +503,7 @@ If you spotted it first, help us to smash it by providing a detailed and welcome
<li>Lois Rilo &lt;<a class="reference external" href="mailto:lois.rilo&#64;forgeflow.com">lois.rilo&#64;forgeflow.com</a>&gt;</li> <li>Lois Rilo &lt;<a class="reference external" href="mailto:lois.rilo&#64;forgeflow.com">lois.rilo&#64;forgeflow.com</a>&gt;</li>
<li>Dhara Solanki &lt;<a class="reference external" href="mailto:dhara.solanki&#64;initos.com">dhara.solanki&#64;initos.com</a>&gt;</li> <li>Dhara Solanki &lt;<a class="reference external" href="mailto:dhara.solanki&#64;initos.com">dhara.solanki&#64;initos.com</a>&gt;</li>
<li>Danny Adair &lt;<a class="reference external" href="mailto:danny&#64;o4sb.com">danny&#64;o4sb.com</a>&gt;</li> <li>Danny Adair &lt;<a class="reference external" href="mailto:danny&#64;o4sb.com">danny&#64;o4sb.com</a>&gt;</li>
<li>Simone Rubino &lt;<a class="reference external" href="mailto:simone.rubino&#64;pytech.it">simone.rubino&#64;pytech.it</a>&gt;</li>
</ul> </ul>
</div> </div>
<div class="section" id="maintainers"> <div class="section" id="maintainers">

View File

@@ -1,8 +1,9 @@
# Copyright 2018 ForgeFlow, S.L. (https://www.forgeflow.com) # Copyright 2018 ForgeFlow, S.L. (https://www.forgeflow.com)
# Copyright 2025 Simone Rubino - PyTech
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl.html). # License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl.html).
from odoo.tests import new_test_user from odoo import fields
from odoo.tests.common import TransactionCase from odoo.tests.common import TransactionCase, new_test_user
class TestOutstandingStatement(TransactionCase): class TestOutstandingStatement(TransactionCase):
@@ -148,3 +149,50 @@ class TestOutstandingStatement(TransactionCase):
other_partner = partners - invoice_partner other_partner = partners - invoice_partner
other_partner_data = report["data"].get(other_partner.id) other_partner_data = report["data"].get(other_partner.id)
self.assertFalse(other_partner_data) self.assertFalse(other_partner_data)
def test_show_only_overdue(self):
"""If "Show Only Overdue" is enabled,
only overdue lines are shown.
"""
# Arrange
partner = self.partner1
today = fields.Date.today()
overdue_invoice = self.env["account.move"].search(
[
("partner_id", "=", partner.id),
("state", "=", "posted"),
("invoice_date_due", "<", today),
],
limit=1,
)
due_invoice = self.env["account.move"].search(
[
("partner_id", "=", partner.id),
("state", "=", "posted"),
("invoice_date_due", ">=", today),
],
limit=1,
)
wizard = self.wiz.with_context(
active_ids=partner.ids,
).create(
{
"date_end": today,
"show_only_overdue": True,
}
)
# pre-condition
self.assertTrue(due_invoice)
self.assertTrue(overdue_invoice)
# Act
data = wizard._prepare_statement()
report = self.statement_model._get_report_values(partner.ids, data)
# Assert
# Only the overdue invoice is shown
partner_data = report["data"][partner.id]["currencies"]
partner_move_lines = partner_data[overdue_invoice.currency_id.id]["lines"]
moves_names = [line["name"] for line in partner_move_lines]
self.assertNotIn(due_invoice.name, moves_names)
self.assertIn(overdue_invoice.name, moves_names)

View File

@@ -20,6 +20,9 @@ class StatementCommon(models.AbstractModel):
) )
date_end = fields.Date(required=True, default=fields.Date.context_today) date_end = fields.Date(required=True, default=fields.Date.context_today)
show_aging_buckets = fields.Boolean(default=True) show_aging_buckets = fields.Boolean(default=True)
show_only_overdue = fields.Boolean(
help="Show only lines due before the selected date",
)
number_partner_ids = fields.Integer( number_partner_ids = fields.Integer(
default=lambda self: len(self._context["active_ids"]) default=lambda self: len(self._context["active_ids"])
) )
@@ -94,6 +97,7 @@ class StatementCommon(models.AbstractModel):
"company_id": self.company_id.id, "company_id": self.company_id.id,
"partner_ids": self._context["active_ids"], "partner_ids": self._context["active_ids"],
"show_aging_buckets": self.show_aging_buckets, "show_aging_buckets": self.show_aging_buckets,
"show_only_overdue": self.show_only_overdue,
"filter_non_due_partners": self.filter_partners_non_due, "filter_non_due_partners": self.filter_partners_non_due,
"account_type": self.account_type, "account_type": self.account_type,
"aging_type": self.aging_type, "aging_type": self.aging_type,

View File

@@ -66,6 +66,7 @@
<field name="excluded_accounts_selector" /> <field name="excluded_accounts_selector" />
</group> </group>
<group name="aging_report"> <group name="aging_report">
<field name="show_only_overdue" />
<field name="show_aging_buckets" /> <field name="show_aging_buckets" />
<field name="aging_type" /> <field name="aging_type" />
</group> </group>