Merge pull request #37630 from ruthra-kumar/provision_to_set_for_gain_loss_journal
refactor: configurable exchange gain or loss posting date
This commit is contained in:
commit
025acc0e48
@ -229,6 +229,7 @@ erpnext.accounts.PaymentReconciliationController = class PaymentReconciliationCo
|
|||||||
this.data = [];
|
this.data = [];
|
||||||
const dialog = new frappe.ui.Dialog({
|
const dialog = new frappe.ui.Dialog({
|
||||||
title: __("Select Difference Account"),
|
title: __("Select Difference Account"),
|
||||||
|
size: 'extra-large',
|
||||||
fields: [
|
fields: [
|
||||||
{
|
{
|
||||||
fieldname: "allocation",
|
fieldname: "allocation",
|
||||||
@ -252,6 +253,13 @@ erpnext.accounts.PaymentReconciliationController = class PaymentReconciliationCo
|
|||||||
in_list_view: 1,
|
in_list_view: 1,
|
||||||
read_only: 1
|
read_only: 1
|
||||||
}, {
|
}, {
|
||||||
|
fieldtype:'Date',
|
||||||
|
fieldname:"gain_loss_posting_date",
|
||||||
|
label: __("Posting Date"),
|
||||||
|
in_list_view: 1,
|
||||||
|
reqd: 1,
|
||||||
|
}, {
|
||||||
|
|
||||||
fieldtype:'Link',
|
fieldtype:'Link',
|
||||||
options: 'Account',
|
options: 'Account',
|
||||||
in_list_view: 1,
|
in_list_view: 1,
|
||||||
@ -285,6 +293,9 @@ erpnext.accounts.PaymentReconciliationController = class PaymentReconciliationCo
|
|||||||
args.forEach(d => {
|
args.forEach(d => {
|
||||||
frappe.model.set_value("Payment Reconciliation Allocation", d.docname,
|
frappe.model.set_value("Payment Reconciliation Allocation", d.docname,
|
||||||
"difference_account", d.difference_account);
|
"difference_account", d.difference_account);
|
||||||
|
frappe.model.set_value("Payment Reconciliation Allocation", d.docname,
|
||||||
|
"gain_loss_posting_date", d.gain_loss_posting_date);
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
this.reconcile_payment_entries();
|
this.reconcile_payment_entries();
|
||||||
@ -300,6 +311,7 @@ erpnext.accounts.PaymentReconciliationController = class PaymentReconciliationCo
|
|||||||
'reference_name': d.reference_name,
|
'reference_name': d.reference_name,
|
||||||
'difference_amount': d.difference_amount,
|
'difference_amount': d.difference_amount,
|
||||||
'difference_account': d.difference_account,
|
'difference_account': d.difference_account,
|
||||||
|
'gain_loss_posting_date': d.gain_loss_posting_date
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@ -328,6 +328,7 @@ class PaymentReconciliation(Document):
|
|||||||
res.difference_amount = self.get_difference_amount(pay, inv, res["allocated_amount"])
|
res.difference_amount = self.get_difference_amount(pay, inv, res["allocated_amount"])
|
||||||
res.difference_account = default_exchange_gain_loss_account
|
res.difference_account = default_exchange_gain_loss_account
|
||||||
res.exchange_rate = inv.get("exchange_rate")
|
res.exchange_rate = inv.get("exchange_rate")
|
||||||
|
res.update({"gain_loss_posting_date": pay.get("posting_date")})
|
||||||
|
|
||||||
if pay.get("amount") == 0:
|
if pay.get("amount") == 0:
|
||||||
entries.append(res)
|
entries.append(res)
|
||||||
@ -434,6 +435,7 @@ class PaymentReconciliation(Document):
|
|||||||
"allocated_amount": flt(row.get("allocated_amount")),
|
"allocated_amount": flt(row.get("allocated_amount")),
|
||||||
"difference_amount": flt(row.get("difference_amount")),
|
"difference_amount": flt(row.get("difference_amount")),
|
||||||
"difference_account": row.get("difference_account"),
|
"difference_account": row.get("difference_account"),
|
||||||
|
"difference_posting_date": row.get("gain_loss_posting_date"),
|
||||||
"cost_center": row.get("cost_center"),
|
"cost_center": row.get("cost_center"),
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|||||||
@ -19,6 +19,7 @@
|
|||||||
"is_advance",
|
"is_advance",
|
||||||
"section_break_5",
|
"section_break_5",
|
||||||
"difference_amount",
|
"difference_amount",
|
||||||
|
"gain_loss_posting_date",
|
||||||
"column_break_7",
|
"column_break_7",
|
||||||
"difference_account",
|
"difference_account",
|
||||||
"exchange_rate",
|
"exchange_rate",
|
||||||
@ -151,11 +152,16 @@
|
|||||||
"fieldtype": "Link",
|
"fieldtype": "Link",
|
||||||
"label": "Cost Center",
|
"label": "Cost Center",
|
||||||
"options": "Cost Center"
|
"options": "Cost Center"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "gain_loss_posting_date",
|
||||||
|
"fieldtype": "Date",
|
||||||
|
"label": "Difference Posting Date"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"istable": 1,
|
"istable": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2023-09-03 07:52:33.684217",
|
"modified": "2023-10-23 10:44:56.066303",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Payment Reconciliation Allocation",
|
"name": "Payment Reconciliation Allocation",
|
||||||
|
|||||||
@ -679,7 +679,9 @@ def update_reference_in_payment_entry(
|
|||||||
if not skip_ref_details_update_for_pe:
|
if not skip_ref_details_update_for_pe:
|
||||||
payment_entry.set_missing_ref_details()
|
payment_entry.set_missing_ref_details()
|
||||||
payment_entry.set_amounts()
|
payment_entry.set_amounts()
|
||||||
payment_entry.make_exchange_gain_loss_journal()
|
payment_entry.make_exchange_gain_loss_journal(
|
||||||
|
frappe._dict({"difference_posting_date": d.difference_posting_date})
|
||||||
|
)
|
||||||
|
|
||||||
if not do_not_save:
|
if not do_not_save:
|
||||||
payment_entry.save(ignore_permissions=True)
|
payment_entry.save(ignore_permissions=True)
|
||||||
|
|||||||
@ -1178,7 +1178,9 @@ class AccountsController(TransactionBase):
|
|||||||
self.name,
|
self.name,
|
||||||
arg.get("referenced_row"),
|
arg.get("referenced_row"),
|
||||||
):
|
):
|
||||||
posting_date = frappe.db.get_value(arg.voucher_type, arg.voucher_no, "posting_date")
|
posting_date = arg.get("difference_posting_date") or frappe.db.get_value(
|
||||||
|
arg.voucher_type, arg.voucher_no, "posting_date"
|
||||||
|
)
|
||||||
je = create_gain_loss_journal(
|
je = create_gain_loss_journal(
|
||||||
self.company,
|
self.company,
|
||||||
posting_date,
|
posting_date,
|
||||||
@ -1261,7 +1263,7 @@ class AccountsController(TransactionBase):
|
|||||||
|
|
||||||
je = create_gain_loss_journal(
|
je = create_gain_loss_journal(
|
||||||
self.company,
|
self.company,
|
||||||
self.posting_date,
|
args.get("difference_posting_date") if args else self.posting_date,
|
||||||
self.party_type,
|
self.party_type,
|
||||||
self.party,
|
self.party,
|
||||||
party_account,
|
party_account,
|
||||||
|
|||||||
@ -7,7 +7,7 @@ import frappe
|
|||||||
from frappe import qb
|
from frappe import qb
|
||||||
from frappe.query_builder.functions import Sum
|
from frappe.query_builder.functions import Sum
|
||||||
from frappe.tests.utils import FrappeTestCase, change_settings
|
from frappe.tests.utils import FrappeTestCase, change_settings
|
||||||
from frappe.utils import add_days, flt, nowdate
|
from frappe.utils import add_days, flt, getdate, nowdate
|
||||||
|
|
||||||
from erpnext import get_default_cost_center
|
from erpnext import get_default_cost_center
|
||||||
from erpnext.accounts.doctype.payment_entry.payment_entry import get_payment_entry
|
from erpnext.accounts.doctype.payment_entry.payment_entry import get_payment_entry
|
||||||
@ -614,6 +614,73 @@ class TestAccountsController(FrappeTestCase):
|
|||||||
self.assertEqual(exc_je_for_si, [])
|
self.assertEqual(exc_je_for_si, [])
|
||||||
self.assertEqual(exc_je_for_pe, [])
|
self.assertEqual(exc_je_for_pe, [])
|
||||||
|
|
||||||
|
def test_15_gain_loss_on_different_posting_date(self):
|
||||||
|
# Invoice in Foreign Currency
|
||||||
|
si = self.create_sales_invoice(
|
||||||
|
posting_date=add_days(nowdate(), -2), qty=2, conversion_rate=80, rate=1
|
||||||
|
)
|
||||||
|
# Payment
|
||||||
|
pe = (
|
||||||
|
self.create_payment_entry(posting_date=add_days(nowdate(), -1), amount=2, source_exc_rate=75)
|
||||||
|
.save()
|
||||||
|
.submit()
|
||||||
|
)
|
||||||
|
|
||||||
|
# There should be outstanding in both currencies
|
||||||
|
si.reload()
|
||||||
|
self.assertEqual(si.outstanding_amount, 2)
|
||||||
|
self.assert_ledger_outstanding(si.doctype, si.name, 160.0, 2.0)
|
||||||
|
|
||||||
|
# Reconcile the remaining amount
|
||||||
|
pr = frappe.get_doc("Payment Reconciliation")
|
||||||
|
pr.company = self.company
|
||||||
|
pr.party_type = "Customer"
|
||||||
|
pr.party = self.customer
|
||||||
|
pr.receivable_payable_account = self.debit_usd
|
||||||
|
pr.get_unreconciled_entries()
|
||||||
|
self.assertEqual(len(pr.invoices), 1)
|
||||||
|
self.assertEqual(len(pr.payments), 1)
|
||||||
|
invoices = [x.as_dict() for x in pr.invoices]
|
||||||
|
payments = [x.as_dict() for x in pr.payments]
|
||||||
|
pr.allocate_entries(frappe._dict({"invoices": invoices, "payments": payments}))
|
||||||
|
pr.allocation[0].gain_loss_posting_date = add_days(nowdate(), 1)
|
||||||
|
pr.reconcile()
|
||||||
|
|
||||||
|
# Exchange Gain/Loss Journal should've been created.
|
||||||
|
exc_je_for_si = self.get_journals_for(si.doctype, si.name)
|
||||||
|
exc_je_for_pe = self.get_journals_for(pe.doctype, pe.name)
|
||||||
|
self.assertNotEqual(exc_je_for_si, [])
|
||||||
|
self.assertEqual(len(exc_je_for_si), 1)
|
||||||
|
self.assertEqual(len(exc_je_for_pe), 1)
|
||||||
|
self.assertEqual(exc_je_for_si[0], exc_je_for_pe[0])
|
||||||
|
|
||||||
|
self.assertEqual(
|
||||||
|
frappe.db.get_value("Journal Entry", exc_je_for_si[0].parent, "posting_date"),
|
||||||
|
getdate(add_days(nowdate(), 1)),
|
||||||
|
)
|
||||||
|
|
||||||
|
self.assertEqual(len(pr.invoices), 0)
|
||||||
|
self.assertEqual(len(pr.payments), 0)
|
||||||
|
|
||||||
|
# There should be no outstanding
|
||||||
|
si.reload()
|
||||||
|
self.assertEqual(si.outstanding_amount, 0)
|
||||||
|
self.assert_ledger_outstanding(si.doctype, si.name, 0.0, 0.0)
|
||||||
|
|
||||||
|
# Cancel Payment
|
||||||
|
pe.reload()
|
||||||
|
pe.cancel()
|
||||||
|
|
||||||
|
si.reload()
|
||||||
|
self.assertEqual(si.outstanding_amount, 2)
|
||||||
|
self.assert_ledger_outstanding(si.doctype, si.name, 160.0, 2.0)
|
||||||
|
|
||||||
|
# Exchange Gain/Loss Journal should've been cancelled
|
||||||
|
exc_je_for_si = self.get_journals_for(si.doctype, si.name)
|
||||||
|
exc_je_for_pe = self.get_journals_for(pe.doctype, pe.name)
|
||||||
|
self.assertEqual(exc_je_for_si, [])
|
||||||
|
self.assertEqual(exc_je_for_pe, [])
|
||||||
|
|
||||||
def test_20_journal_against_sales_invoice(self):
|
def test_20_journal_against_sales_invoice(self):
|
||||||
# Invoice in Foreign Currency
|
# Invoice in Foreign Currency
|
||||||
si = self.create_sales_invoice(qty=1, conversion_rate=80, rate=1)
|
si = self.create_sales_invoice(qty=1, conversion_rate=80, rate=1)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user