From c2bdd30e6de215c79f40bf20d95a797a711f7080 Mon Sep 17 00:00:00 2001 From: ljain112 Date: Fri, 28 Mar 2025 13:26:28 +0530 Subject: [PATCH 1/2] fix: correct outstanding amount for invoice in dunning --- erpnext/accounts/doctype/sales_invoice/sales_invoice.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py index 1afd67c7822..49e93f76f22 100644 --- a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py +++ b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py @@ -2717,9 +2717,11 @@ def create_dunning(source_name, target_doc=None, ignore_permissions=False): target.closing_text = letter_text.get("closing_text") target.language = letter_text.get("language") - # update outstanding + # update outstanding from doc if source.payment_schedule and len(source.payment_schedule) == 1: - target.overdue_payments[0].outstanding = source.get("outstanding_amount") + for row in target.overdue_payments: + if row.payment_schedule == source.payment_schedule[0].name: + row.outstanding = source.get("outstanding_amount") target.validate() From 3b613c44a60320e3f57fb1efad7f0dafe6fe4a86 Mon Sep 17 00:00:00 2001 From: ljain112 Date: Tue, 15 Apr 2025 11:36:19 +0530 Subject: [PATCH 2/2] chore: added test for `Fetch Overdue Payments` in dunning --- .../accounts/doctype/dunning/test_dunning.py | 33 +++++++++++++++++++ 1 file changed, 33 insertions(+) diff --git a/erpnext/accounts/doctype/dunning/test_dunning.py b/erpnext/accounts/doctype/dunning/test_dunning.py index 3ed931f3c8f..2340d66f499 100644 --- a/erpnext/accounts/doctype/dunning/test_dunning.py +++ b/erpnext/accounts/doctype/dunning/test_dunning.py @@ -1,6 +1,9 @@ # Copyright (c) 2023, Frappe Technologies Pvt. Ltd. and Contributors # See license.txt +import json + import frappe +from frappe.model import mapper from frappe.tests import IntegrationTestCase, UnitTestCase from frappe.utils import add_days, nowdate, today @@ -77,6 +80,36 @@ class TestDunning(IntegrationTestCase): dunning.reload() self.assertEqual(dunning.status, "Resolved") + def test_fetch_overdue_payments(self): + """ + Create SI with overdue payment. Check if overdue payment is fetched in Dunning. + """ + si1 = create_sales_invoice_against_cost_center( + posting_date=add_days(today(), -1 * 6), + qty=1, + rate=100, + ) + + si2 = create_sales_invoice_against_cost_center( + posting_date=add_days(today(), -1 * 6), + qty=1, + rate=300, + ) + + dunning = create_dunning_from_sales_invoice(si1.name) + dunning.overdue_payments = [] + + method = "erpnext.accounts.doctype.sales_invoice.sales_invoice.create_dunning" + updated_dunning = mapper.map_docs(method, json.dumps([si1.name, si2.name]), dunning) + + self.assertEqual(len(updated_dunning.overdue_payments), 2) + + self.assertEqual(updated_dunning.overdue_payments[0].sales_invoice, si1.name) + self.assertEqual(updated_dunning.overdue_payments[0].outstanding, si1.outstanding_amount) + + self.assertEqual(updated_dunning.overdue_payments[1].sales_invoice, si2.name) + self.assertEqual(updated_dunning.overdue_payments[1].outstanding, si2.outstanding_amount) + def test_dunning_and_payment_against_partially_due_invoice(self): """ Create SI with first installment overdue. Check impact of Dunning and Payment Entry.