From 674af156969819879b114779fec28eb51b68f50e Mon Sep 17 00:00:00 2001 From: Gursheen Kaur Anand <40693548+GursheenK@users.noreply.github.com> Date: Sun, 9 Jul 2023 20:41:12 +0530 Subject: [PATCH] fix: deferred accounting entries on accounts frozen (#35978) * fix: accounts frozen entries in deferred accounting * test: accounts frozen date in deferred accounting * fix: reset account settings after running test * fix: resolve conflicts * fix: modify expected gle when deferred accounting is disabled through JE * fix: change posting date when accounts not frozen --- erpnext/accounts/deferred_revenue.py | 88 +++++++++++-------- .../test_process_deferred_accounting.py | 36 +++++--- 2 files changed, 77 insertions(+), 47 deletions(-) diff --git a/erpnext/accounts/deferred_revenue.py b/erpnext/accounts/deferred_revenue.py index 45e04ee6b0..fb49ef3a42 100644 --- a/erpnext/accounts/deferred_revenue.py +++ b/erpnext/accounts/deferred_revenue.py @@ -136,7 +136,7 @@ def convert_deferred_revenue_to_income( send_mail(deferred_process) -def get_booking_dates(doc, item, posting_date=None): +def get_booking_dates(doc, item, posting_date=None, prev_posting_date=None): if not posting_date: posting_date = add_days(today(), -1) @@ -146,39 +146,42 @@ def get_booking_dates(doc, item, posting_date=None): "deferred_revenue_account" if doc.doctype == "Sales Invoice" else "deferred_expense_account" ) - prev_gl_entry = frappe.db.sql( - """ - select name, posting_date from `tabGL Entry` where company=%s and account=%s and - voucher_type=%s and voucher_no=%s and voucher_detail_no=%s - and is_cancelled = 0 - order by posting_date desc limit 1 - """, - (doc.company, item.get(deferred_account), doc.doctype, doc.name, item.name), - as_dict=True, - ) + if not prev_posting_date: + prev_gl_entry = frappe.db.sql( + """ + select name, posting_date from `tabGL Entry` where company=%s and account=%s and + voucher_type=%s and voucher_no=%s and voucher_detail_no=%s + and is_cancelled = 0 + order by posting_date desc limit 1 + """, + (doc.company, item.get(deferred_account), doc.doctype, doc.name, item.name), + as_dict=True, + ) - prev_gl_via_je = frappe.db.sql( - """ - SELECT p.name, p.posting_date FROM `tabJournal Entry` p, `tabJournal Entry Account` c - WHERE p.name = c.parent and p.company=%s and c.account=%s - and c.reference_type=%s and c.reference_name=%s - and c.reference_detail_no=%s and c.docstatus < 2 order by posting_date desc limit 1 - """, - (doc.company, item.get(deferred_account), doc.doctype, doc.name, item.name), - as_dict=True, - ) + prev_gl_via_je = frappe.db.sql( + """ + SELECT p.name, p.posting_date FROM `tabJournal Entry` p, `tabJournal Entry Account` c + WHERE p.name = c.parent and p.company=%s and c.account=%s + and c.reference_type=%s and c.reference_name=%s + and c.reference_detail_no=%s and c.docstatus < 2 order by posting_date desc limit 1 + """, + (doc.company, item.get(deferred_account), doc.doctype, doc.name, item.name), + as_dict=True, + ) - if prev_gl_via_je: - if (not prev_gl_entry) or ( - prev_gl_entry and prev_gl_entry[0].posting_date < prev_gl_via_je[0].posting_date - ): - prev_gl_entry = prev_gl_via_je + if prev_gl_via_je: + if (not prev_gl_entry) or ( + prev_gl_entry and prev_gl_entry[0].posting_date < prev_gl_via_je[0].posting_date + ): + prev_gl_entry = prev_gl_via_je + + if prev_gl_entry: + start_date = getdate(add_days(prev_gl_entry[0].posting_date, 1)) + else: + start_date = item.service_start_date - if prev_gl_entry: - start_date = getdate(add_days(prev_gl_entry[0].posting_date, 1)) else: - start_date = item.service_start_date - + start_date = getdate(add_days(prev_posting_date, 1)) end_date = get_last_day(start_date) if end_date >= item.service_end_date: end_date = item.service_end_date @@ -341,9 +344,15 @@ def book_deferred_income_or_expense(doc, deferred_process, posting_date=None): accounts_frozen_upto = frappe.get_cached_value("Accounts Settings", "None", "acc_frozen_upto") def _book_deferred_revenue_or_expense( - item, via_journal_entry, submit_journal_entry, book_deferred_entries_based_on + item, + via_journal_entry, + submit_journal_entry, + book_deferred_entries_based_on, + prev_posting_date=None, ): - start_date, end_date, last_gl_entry = get_booking_dates(doc, item, posting_date=posting_date) + start_date, end_date, last_gl_entry = get_booking_dates( + doc, item, posting_date=posting_date, prev_posting_date=prev_posting_date + ) if not (start_date and end_date): return @@ -377,9 +386,12 @@ def book_deferred_income_or_expense(doc, deferred_process, posting_date=None): if not amount: return + gl_posting_date = end_date + prev_posting_date = None # check if books nor frozen till endate: if accounts_frozen_upto and getdate(end_date) <= getdate(accounts_frozen_upto): - end_date = get_last_day(add_days(accounts_frozen_upto, 1)) + gl_posting_date = get_last_day(add_days(accounts_frozen_upto, 1)) + prev_posting_date = end_date if via_journal_entry: book_revenue_via_journal_entry( @@ -388,7 +400,7 @@ def book_deferred_income_or_expense(doc, deferred_process, posting_date=None): debit_account, amount, base_amount, - end_date, + gl_posting_date, project, account_currency, item.cost_center, @@ -404,7 +416,7 @@ def book_deferred_income_or_expense(doc, deferred_process, posting_date=None): against, amount, base_amount, - end_date, + gl_posting_date, project, account_currency, item.cost_center, @@ -418,7 +430,11 @@ def book_deferred_income_or_expense(doc, deferred_process, posting_date=None): if getdate(end_date) < getdate(posting_date) and not last_gl_entry: _book_deferred_revenue_or_expense( - item, via_journal_entry, submit_journal_entry, book_deferred_entries_based_on + item, + via_journal_entry, + submit_journal_entry, + book_deferred_entries_based_on, + prev_posting_date, ) via_journal_entry = cint( diff --git a/erpnext/accounts/doctype/process_deferred_accounting/test_process_deferred_accounting.py b/erpnext/accounts/doctype/process_deferred_accounting/test_process_deferred_accounting.py index 83646c90ba..263621dcf4 100644 --- a/erpnext/accounts/doctype/process_deferred_accounting/test_process_deferred_accounting.py +++ b/erpnext/accounts/doctype/process_deferred_accounting/test_process_deferred_accounting.py @@ -16,8 +16,10 @@ from erpnext.stock.doctype.item.test_item import create_item class TestProcessDeferredAccounting(unittest.TestCase): def test_creation_of_ledger_entry_on_submit(self): """test creation of gl entries on submission of document""" + change_acc_settings(acc_frozen_upto="2023-05-31", book_deferred_entries_based_on="Months") + deferred_account = create_account( - account_name="Deferred Revenue", + account_name="Deferred Revenue for Accounts Frozen", parent_account="Current Liabilities - _TC", company="_Test Company", ) @@ -29,21 +31,21 @@ class TestProcessDeferredAccounting(unittest.TestCase): item.save() si = create_sales_invoice( - item=item.name, update_stock=0, posting_date="2019-01-10", do_not_submit=True + item=item.name, rate=3000, update_stock=0, posting_date="2023-07-01", do_not_submit=True ) si.items[0].enable_deferred_revenue = 1 - si.items[0].service_start_date = "2019-01-10" - si.items[0].service_end_date = "2019-03-15" + si.items[0].service_start_date = "2023-05-01" + si.items[0].service_end_date = "2023-07-31" si.items[0].deferred_revenue_account = deferred_account si.save() si.submit() - process_deferred_accounting = frappe.get_doc( + process_deferred_accounting = doc = frappe.get_doc( dict( doctype="Process Deferred Accounting", - posting_date="2019-01-01", - start_date="2019-01-01", - end_date="2019-01-31", + posting_date="2023-07-01", + start_date="2023-05-01", + end_date="2023-06-30", type="Income", ) ) @@ -52,11 +54,16 @@ class TestProcessDeferredAccounting(unittest.TestCase): process_deferred_accounting.submit() expected_gle = [ - [deferred_account, 33.85, 0.0, "2019-01-31"], - ["Sales - _TC", 0.0, 33.85, "2019-01-31"], + ["Debtors - _TC", 3000, 0.0, "2023-07-01"], + [deferred_account, 0.0, 3000, "2023-07-01"], + ["Sales - _TC", 0.0, 1000, "2023-06-30"], + [deferred_account, 1000, 0.0, "2023-06-30"], + ["Sales - _TC", 0.0, 1000, "2023-06-30"], + [deferred_account, 1000, 0.0, "2023-06-30"], ] - check_gl_entries(self, si.name, expected_gle, "2019-01-31") + check_gl_entries(self, si.name, expected_gle, "2023-07-01") + change_acc_settings() def test_pda_submission_and_cancellation(self): pda = frappe.get_doc( @@ -70,3 +77,10 @@ class TestProcessDeferredAccounting(unittest.TestCase): ) pda.submit() pda.cancel() + + +def change_acc_settings(acc_frozen_upto="", book_deferred_entries_based_on="Days"): + acc_settings = frappe.get_doc("Accounts Settings", "Accounts Settings") + acc_settings.acc_frozen_upto = acc_frozen_upto + acc_settings.book_deferred_entries_based_on = book_deferred_entries_based_on + acc_settings.save()