From 5d9be7366b72064f758e4dc79f0eda3a1a36f404 Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Wed, 21 May 2025 23:12:40 +0530 Subject: [PATCH 01/12] fix: remove public access to list items (backport #45838) * fix: remove public access to list items (cherry picked from commit 2bd596ee3d98d418ea74105eb49604df64877b8f) # Conflicts: # erpnext/stock/doctype/item/item.json * fix: resolve conflict --------- Co-authored-by: CaseSolved Co-authored-by: Sagar Vora <16315650+sagarvora@users.noreply.github.com> --- erpnext/stock/doctype/item/item.json | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/erpnext/stock/doctype/item/item.json b/erpnext/stock/doctype/item/item.json index b9256c8ee56..29d59b4ce70 100644 --- a/erpnext/stock/doctype/item/item.json +++ b/erpnext/stock/doctype/item/item.json @@ -1,6 +1,5 @@ { "actions": [], - "allow_guest_to_view": 1, "allow_import": 1, "allow_rename": 1, "autoname": "field:item_code", @@ -897,10 +896,9 @@ "icon": "fa fa-tag", "idx": 2, "image_field": "image", - "index_web_pages_for_search": 1, "links": [], "make_attachments_public": 1, - "modified": "2024-01-08 18:09:30.225085", + "modified": "2025-02-03 23:43:57.253667", "modified_by": "Administrator", "module": "Stock", "name": "Item", From d5d4b3a7f3ed89301755d9438c11afc75241ca15 Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Thu, 22 May 2025 16:17:42 +0530 Subject: [PATCH 02/12] fix: incorrect valuation rate due to positive qty (backport #47686) (#47687) fix: incorrect valuation rate due to positive qty (#47686) (cherry picked from commit 6ed97b5fdada89a1971d7e7eb69e6834f0b3b3bc) Co-authored-by: Khushi Rawat <142375893+khushi8112@users.noreply.github.com> --- .../assets/doctype/asset_capitalization/asset_capitalization.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/erpnext/assets/doctype/asset_capitalization/asset_capitalization.js b/erpnext/assets/doctype/asset_capitalization/asset_capitalization.js index 6f73dfc6736..7491c4a72aa 100644 --- a/erpnext/assets/doctype/asset_capitalization/asset_capitalization.js +++ b/erpnext/assets/doctype/asset_capitalization/asset_capitalization.js @@ -380,7 +380,7 @@ erpnext.assets.AssetCapitalization = class AssetCapitalization extends erpnext.s args: { item_code: item.item_code, warehouse: cstr(item.warehouse), - qty: flt(item.stock_qty), + qty: -1 * flt(item.stock_qty), serial_no: item.serial_no, posting_date: me.frm.doc.posting_date, posting_time: me.frm.doc.posting_time, From 1f1cb338feea1061a41bc226f5aa57cb3428d9ab Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Sat, 24 May 2025 17:17:09 +0530 Subject: [PATCH 03/12] fix: skip last purchase rate for free item (backport #47693) (#47695) fix: skip last purchase rate for free item (#47693) (cherry picked from commit c3b17024bd8c024c91dbde578b979dc00de83b33) Co-authored-by: rohitwaghchaure --- erpnext/buying/utils.py | 3 +++ 1 file changed, 3 insertions(+) diff --git a/erpnext/buying/utils.py b/erpnext/buying/utils.py index 8223917792c..9ee8868e2c7 100644 --- a/erpnext/buying/utils.py +++ b/erpnext/buying/utils.py @@ -20,6 +20,9 @@ def update_last_purchase_rate(doc, is_submit) -> None: this_purchase_date = getdate(doc.get("posting_date") or doc.get("transaction_date")) for d in doc.get("items"): + if d.get("is_free_item"): + continue + # get last purchase details last_purchase_details = get_last_purchase_details(d.item_code, doc.name) From 70bcfb47486829d7b7f86025dd1277c6455f47f6 Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Mon, 26 May 2025 13:29:28 +0530 Subject: [PATCH 04/12] fix: patch to rename group_by filter in custom reports (backport #47709) (#47729) * fix: patch to rename group_by filter in custom reports (cherry picked from commit 0d19c18c0628fc7f4a2727c8e5c9d0fe0f93d66d) # Conflicts: # erpnext/patches.txt # erpnext/patches/v14_0/rename_group_by_to_categorize_by_in_custom_reports.py * fix: using python instead of sql query (cherry picked from commit 48eccb1f734a1e0e158e28892759bc77c6e4904e) * chore: resolve conflict --------- Co-authored-by: diptanilsaha --- erpnext/patches.txt | 1 + ...p_by_to_categorize_by_in_custom_reports.py | 24 +++++++++++++++++++ 2 files changed, 25 insertions(+) create mode 100644 erpnext/patches/v14_0/rename_group_by_to_categorize_by_in_custom_reports.py diff --git a/erpnext/patches.txt b/erpnext/patches.txt index be4b89bfc6d..83e4c7bb569 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -375,3 +375,4 @@ erpnext.stock.doctype.stock_ledger_entry.patches.ensure_sle_indexes erpnext.patches.v14_0.rename_group_by_to_categorize_by execute:frappe.db.set_single_value("Accounts Settings", "receivable_payable_fetch_method", "Buffered Cursor") erpnext.patches.v14_0.set_update_price_list_based_on +erpnext.patches.v14_0.rename_group_by_to_categorize_by_in_custom_reports diff --git a/erpnext/patches/v14_0/rename_group_by_to_categorize_by_in_custom_reports.py b/erpnext/patches/v14_0/rename_group_by_to_categorize_by_in_custom_reports.py new file mode 100644 index 00000000000..bc671a4a6ac --- /dev/null +++ b/erpnext/patches/v14_0/rename_group_by_to_categorize_by_in_custom_reports.py @@ -0,0 +1,24 @@ +import json + +import frappe + + +def execute(): + custom_reports = frappe.get_all( + "Report", + filters={ + "report_type": "Custom Report", + "reference_report": ["in", ["General Ledger", "Supplier Quotation Comparison"]], + }, + fields=["name", "json"], + ) + + for report in custom_reports: + report_json = json.loads(report.json) + + if "filters" in report_json and "group_by" in report_json["filters"]: + report_json["filters"]["categorize_by"] = ( + report_json["filters"].pop("group_by").replace("Group", "Categorize") + ) + + frappe.db.set_value("Report", report.name, "json", json.dumps(report_json)) From 70e6ea6b3fbc62e6275e221cb9e341a3a01732c2 Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Mon, 26 May 2025 16:02:06 +0530 Subject: [PATCH 05/12] fix: rate changing while making PR (negative discount) (backport #40539) (#47735) fix: rate changing while making PR (negative discount) (#40539) (cherry picked from commit 81369544840c4eded80bf40fd3e45ed0eb6f52b1) Co-authored-by: rohitwaghchaure --- erpnext/public/js/controllers/taxes_and_totals.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/erpnext/public/js/controllers/taxes_and_totals.js b/erpnext/public/js/controllers/taxes_and_totals.js index bab4b715902..dca9f353457 100644 --- a/erpnext/public/js/controllers/taxes_and_totals.js +++ b/erpnext/public/js/controllers/taxes_and_totals.js @@ -26,7 +26,7 @@ erpnext.taxes_and_totals = class TaxesAndTotals extends erpnext.payments { item.discount_amount = flt(item.rate_with_margin) * flt(item.discount_percentage) / 100; } - if (item.discount_amount) { + if (item.discount_amount > 0) { item_rate = flt((item.rate_with_margin) - (item.discount_amount), precision('rate', item)); item.discount_percentage = 100 * flt(item.discount_amount) / flt(item.rate_with_margin); } From de937a6badca9f7af0ed8530b2d164dd4a1e2c9b Mon Sep 17 00:00:00 2001 From: ruthra kumar Date: Fri, 23 May 2025 13:50:46 +0530 Subject: [PATCH 06/12] refactor: full name field in contract (cherry picked from commit 016924361a781c94c821c18c438bb93df1aa9efd) # Conflicts: # erpnext/crm/doctype/contract/contract.json # erpnext/crm/doctype/contract/contract.py --- erpnext/crm/doctype/contract/contract.json | 15 +++++++- erpnext/crm/doctype/contract/contract.py | 40 ++++++++++++++++++++++ 2 files changed, 54 insertions(+), 1 deletion(-) diff --git a/erpnext/crm/doctype/contract/contract.json b/erpnext/crm/doctype/contract/contract.json index de3230f0e67..4c76adeb248 100755 --- a/erpnext/crm/doctype/contract/contract.json +++ b/erpnext/crm/doctype/contract/contract.json @@ -14,6 +14,7 @@ "party_user", "status", "fulfilment_status", + "party_full_name", "sb_terms", "start_date", "cb_date", @@ -244,11 +245,22 @@ "fieldname": "authorised_by_section", "fieldtype": "Section Break", "label": "Authorised By" + }, + { + "fieldname": "party_full_name", + "fieldtype": "Data", + "label": "Party Full Name", + "read_only": 1 } ], + "grid_page_length": 50, "is_submittable": 1, "links": [], +<<<<<<< HEAD "modified": "2020-12-07 11:15:58.385521", +======= + "modified": "2025-05-23 13:54:03.346537", +>>>>>>> 016924361a (refactor: full name field in contract) "modified_by": "Administrator", "module": "CRM", "name": "Contract", @@ -315,9 +327,10 @@ "write": 1 } ], + "row_format": "Dynamic", "show_name_in_global_search": 1, "sort_field": "modified", "sort_order": "DESC", "track_changes": 1, "track_seen": 1 -} \ No newline at end of file +} diff --git a/erpnext/crm/doctype/contract/contract.py b/erpnext/crm/doctype/contract/contract.py index db23d570644..849fce7ba1a 100644 --- a/erpnext/crm/doctype/contract/contract.py +++ b/erpnext/crm/doctype/contract/contract.py @@ -9,6 +9,46 @@ from frappe.utils import getdate, nowdate class Contract(Document): +<<<<<<< HEAD +======= + # begin: auto-generated types + # This code is auto-generated. Do not modify anything in this block. + + from typing import TYPE_CHECKING + + if TYPE_CHECKING: + from frappe.types import DF + + from erpnext.crm.doctype.contract_fulfilment_checklist.contract_fulfilment_checklist import ( + ContractFulfilmentChecklist, + ) + + amended_from: DF.Link | None + contract_template: DF.Link | None + contract_terms: DF.TextEditor + document_name: DF.DynamicLink | None + document_type: DF.Literal[ + "", "Quotation", "Project", "Sales Order", "Purchase Order", "Sales Invoice", "Purchase Invoice" + ] + end_date: DF.Date | None + fulfilment_deadline: DF.Date | None + fulfilment_status: DF.Literal["N/A", "Unfulfilled", "Partially Fulfilled", "Fulfilled", "Lapsed"] + fulfilment_terms: DF.Table[ContractFulfilmentChecklist] + ip_address: DF.Data | None + is_signed: DF.Check + party_full_name: DF.Data | None + party_name: DF.DynamicLink + party_type: DF.Literal["Customer", "Supplier", "Employee"] + party_user: DF.Link | None + requires_fulfilment: DF.Check + signed_by_company: DF.Link | None + signed_on: DF.Datetime | None + signee: DF.Data | None + start_date: DF.Date | None + status: DF.Literal["Unsigned", "Active", "Inactive"] + # end: auto-generated types + +>>>>>>> 016924361a (refactor: full name field in contract) def autoname(self): name = self.party_name From 05911ad563604a62f5c51f27432b542d3c41b6b6 Mon Sep 17 00:00:00 2001 From: ruthra kumar Date: Fri, 23 May 2025 14:04:07 +0530 Subject: [PATCH 07/12] refactor: fetch party name on selection (cherry picked from commit 752024e222b9d74b4193f410bf4a3ec840810b28) --- erpnext/crm/doctype/contract/contract.js | 6 ++++++ erpnext/crm/doctype/contract/contract.py | 7 +++++++ 2 files changed, 13 insertions(+) diff --git a/erpnext/crm/doctype/contract/contract.js b/erpnext/crm/doctype/contract/contract.js index 8d44c22db28..42bd7f9b769 100644 --- a/erpnext/crm/doctype/contract/contract.js +++ b/erpnext/crm/doctype/contract/contract.js @@ -29,4 +29,10 @@ frappe.ui.form.on("Contract", { }); } }, + party_name: function (frm) { + let field = frm.doc.party_type.toLowerCase() + "_name"; + frappe.db.get_value(frm.doc.party_type, frm.doc.party_name, field, (r) => { + frm.set_value("party_full_name", r[field]); + }); + }, }); diff --git a/erpnext/crm/doctype/contract/contract.py b/erpnext/crm/doctype/contract/contract.py index 849fce7ba1a..eb1dcbfa957 100644 --- a/erpnext/crm/doctype/contract/contract.py +++ b/erpnext/crm/doctype/contract/contract.py @@ -63,10 +63,17 @@ class Contract(Document): self.name = _(name) def validate(self): + self.set_missing_values() self.validate_dates() self.update_contract_status() self.update_fulfilment_status() + def set_missing_values(self): + if not self.party_full_name: + field = self.party_type.lower() + "_name" + if res := frappe.db.get_value(self.party_type, self.party_name, field): + self.party_full_name = res + def before_submit(self): self.signed_by_company = frappe.session.user From caf145e3ca5fa696e5cb6c96d1a574fd9f54f99a Mon Sep 17 00:00:00 2001 From: ruthra kumar Date: Fri, 23 May 2025 14:24:50 +0530 Subject: [PATCH 08/12] refactor: patch old contract with full party name (cherry picked from commit 8e2221178b00f8f148ad38bb90a6928ade9bdc23) # Conflicts: # erpnext/patches.txt --- erpnext/patches.txt | 9 +++++++++ .../patches/v14_0/update_full_name_in_contract.py | 15 +++++++++++++++ 2 files changed, 24 insertions(+) create mode 100644 erpnext/patches/v14_0/update_full_name_in_contract.py diff --git a/erpnext/patches.txt b/erpnext/patches.txt index 83e4c7bb569..f6ee99c86c3 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -375,4 +375,13 @@ erpnext.stock.doctype.stock_ledger_entry.patches.ensure_sle_indexes erpnext.patches.v14_0.rename_group_by_to_categorize_by execute:frappe.db.set_single_value("Accounts Settings", "receivable_payable_fetch_method", "Buffered Cursor") erpnext.patches.v14_0.set_update_price_list_based_on +<<<<<<< HEAD erpnext.patches.v14_0.rename_group_by_to_categorize_by_in_custom_reports +======= +erpnext.patches.v15_0.update_journal_entry_type +erpnext.patches.v15_0.set_grand_total_to_default_mop +execute:frappe.db.set_single_value("Accounts Settings", "use_new_budget_controller", True) +erpnext.patches.v15_0.rename_group_by_to_categorize_by_in_custom_reports +erpnext.patches.v15_0.remove_agriculture_roles +erpnext.patches.v14_0.update_full_name_in_contract +>>>>>>> 8e2221178b (refactor: patch old contract with full party name) diff --git a/erpnext/patches/v14_0/update_full_name_in_contract.py b/erpnext/patches/v14_0/update_full_name_in_contract.py new file mode 100644 index 00000000000..19ee055ad12 --- /dev/null +++ b/erpnext/patches/v14_0/update_full_name_in_contract.py @@ -0,0 +1,15 @@ +import frappe +from frappe import qb + + +def execute(): + con = qb.DocType("Contract") + for c in ( + qb.from_(con) + .select(con.name, con.party_type, con.party_name) + .where(con.party_full_name.isnull()) + .run(as_dict=True) + ): + field = c.party_type.lower() + "_name" + if res := frappe.db.get_value(c.party_type, c.party_name, field): + frappe.db.set_value("Contract", c.name, "party_full_name", res) From 274ce1032913dc56b4844f0f1eb8443664a4db3c Mon Sep 17 00:00:00 2001 From: ruthra kumar Date: Mon, 26 May 2025 17:46:10 +0530 Subject: [PATCH 09/12] chore: resolve conflicts --- erpnext/crm/doctype/contract/contract.json | 4 --- erpnext/crm/doctype/contract/contract.py | 40 ---------------------- erpnext/patches.txt | 8 ----- 3 files changed, 52 deletions(-) diff --git a/erpnext/crm/doctype/contract/contract.json b/erpnext/crm/doctype/contract/contract.json index 4c76adeb248..948243402fe 100755 --- a/erpnext/crm/doctype/contract/contract.json +++ b/erpnext/crm/doctype/contract/contract.json @@ -256,11 +256,7 @@ "grid_page_length": 50, "is_submittable": 1, "links": [], -<<<<<<< HEAD - "modified": "2020-12-07 11:15:58.385521", -======= "modified": "2025-05-23 13:54:03.346537", ->>>>>>> 016924361a (refactor: full name field in contract) "modified_by": "Administrator", "module": "CRM", "name": "Contract", diff --git a/erpnext/crm/doctype/contract/contract.py b/erpnext/crm/doctype/contract/contract.py index eb1dcbfa957..f30d576213f 100644 --- a/erpnext/crm/doctype/contract/contract.py +++ b/erpnext/crm/doctype/contract/contract.py @@ -9,46 +9,6 @@ from frappe.utils import getdate, nowdate class Contract(Document): -<<<<<<< HEAD -======= - # begin: auto-generated types - # This code is auto-generated. Do not modify anything in this block. - - from typing import TYPE_CHECKING - - if TYPE_CHECKING: - from frappe.types import DF - - from erpnext.crm.doctype.contract_fulfilment_checklist.contract_fulfilment_checklist import ( - ContractFulfilmentChecklist, - ) - - amended_from: DF.Link | None - contract_template: DF.Link | None - contract_terms: DF.TextEditor - document_name: DF.DynamicLink | None - document_type: DF.Literal[ - "", "Quotation", "Project", "Sales Order", "Purchase Order", "Sales Invoice", "Purchase Invoice" - ] - end_date: DF.Date | None - fulfilment_deadline: DF.Date | None - fulfilment_status: DF.Literal["N/A", "Unfulfilled", "Partially Fulfilled", "Fulfilled", "Lapsed"] - fulfilment_terms: DF.Table[ContractFulfilmentChecklist] - ip_address: DF.Data | None - is_signed: DF.Check - party_full_name: DF.Data | None - party_name: DF.DynamicLink - party_type: DF.Literal["Customer", "Supplier", "Employee"] - party_user: DF.Link | None - requires_fulfilment: DF.Check - signed_by_company: DF.Link | None - signed_on: DF.Datetime | None - signee: DF.Data | None - start_date: DF.Date | None - status: DF.Literal["Unsigned", "Active", "Inactive"] - # end: auto-generated types - ->>>>>>> 016924361a (refactor: full name field in contract) def autoname(self): name = self.party_name diff --git a/erpnext/patches.txt b/erpnext/patches.txt index f6ee99c86c3..1d051fd2489 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -375,13 +375,5 @@ erpnext.stock.doctype.stock_ledger_entry.patches.ensure_sle_indexes erpnext.patches.v14_0.rename_group_by_to_categorize_by execute:frappe.db.set_single_value("Accounts Settings", "receivable_payable_fetch_method", "Buffered Cursor") erpnext.patches.v14_0.set_update_price_list_based_on -<<<<<<< HEAD erpnext.patches.v14_0.rename_group_by_to_categorize_by_in_custom_reports -======= -erpnext.patches.v15_0.update_journal_entry_type -erpnext.patches.v15_0.set_grand_total_to_default_mop -execute:frappe.db.set_single_value("Accounts Settings", "use_new_budget_controller", True) -erpnext.patches.v15_0.rename_group_by_to_categorize_by_in_custom_reports -erpnext.patches.v15_0.remove_agriculture_roles erpnext.patches.v14_0.update_full_name_in_contract ->>>>>>> 8e2221178b (refactor: patch old contract with full party name) From 792f3afa1b73b74f21787553816d7908fba914f2 Mon Sep 17 00:00:00 2001 From: "mergify[bot]" <37929162+mergify[bot]@users.noreply.github.com> Date: Thu, 15 May 2025 10:31:28 +0530 Subject: [PATCH 10/12] fix: validation message format (backport #47542) (#47549) fix: validation message format (#47542) (cherry picked from commit a18e1cffa7ce0eff12ba7d91b40fc8a4f85cf584) Co-authored-by: rohitwaghchaure (cherry picked from commit f225e1986ee3109d77bb09187868204eeb7cefac) --- erpnext/stock/doctype/stock_entry/stock_entry.py | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/erpnext/stock/doctype/stock_entry/stock_entry.py b/erpnext/stock/doctype/stock_entry/stock_entry.py index ca15db485fd..eb020f55155 100644 --- a/erpnext/stock/doctype/stock_entry/stock_entry.py +++ b/erpnext/stock/doctype/stock_entry/stock_entry.py @@ -458,17 +458,19 @@ class StockEntry(StockController): if acc_details.account_type == "Stock": frappe.throw( _( - "At row {0}: the Difference Account must not be a Stock type account, please change the Account Type for the account {1} or select a different account" + "At row #{0}: the Difference Account must not be a Stock type account, please change the Account Type for the account {1} or select a different account" ).format(d.idx, get_link_to_form("Account", d.expense_account)), - OpeningEntryAccountError, + title=_("Difference Account in Items Table"), ) if self.purpose != "Material Issue" and acc_details.account_type == "Cost of Goods Sold": frappe.msgprint( _( - "At row {0}: You have selected the Difference Account {1}, which is a Cost of Goods Sold type account. Please select a different account" + "At row #{0}: you have selected the Difference Account {1}, which is a Cost of Goods Sold type account. Please select a different account" ).format(d.idx, bold(get_link_to_form("Account", d.expense_account))), - title=_("Warning : Cost of Goods Sold Account"), + title=_("Cost of Goods Sold Account in Items Table"), + indicator="orange", + alert=1, ) def validate_warehouse(self): From 43aeff38aa29ce95d069b8e041fc9f8d439d565d Mon Sep 17 00:00:00 2001 From: ljain112 Date: Mon, 26 May 2025 15:36:12 +0530 Subject: [PATCH 11/12] fix: only include advances within the tcs period (cherry picked from commit 477ec9fdccb8eeea3f431a6dc02242a11bb2c628) --- .../tax_withholding_category.py | 1 + .../test_tax_withholding_category.py | 22 ++++++++++++++----- 2 files changed, 18 insertions(+), 5 deletions(-) diff --git a/erpnext/accounts/doctype/tax_withholding_category/tax_withholding_category.py b/erpnext/accounts/doctype/tax_withholding_category/tax_withholding_category.py index da329324e95..b4640b1ef3c 100644 --- a/erpnext/accounts/doctype/tax_withholding_category/tax_withholding_category.py +++ b/erpnext/accounts/doctype/tax_withholding_category/tax_withholding_category.py @@ -622,6 +622,7 @@ def get_tcs_amount(parties, inv, tax_details, vouchers, adv_vouchers): conditions.append(ple.party.isin(parties)) conditions.append(ple.voucher_no == ple.against_voucher_no) conditions.append(ple.company == inv.company) + conditions.append(ple.posting_date[tax_details.from_date : tax_details.to_date]) advance_amt = ( qb.from_(ple).select(Abs(Sum(ple.amount))).where(Criterion.all(conditions)).run()[0][0] or 0.0 diff --git a/erpnext/accounts/doctype/tax_withholding_category/test_tax_withholding_category.py b/erpnext/accounts/doctype/tax_withholding_category/test_tax_withholding_category.py index 6a7fc3c43d2..2d8837cd9db 100644 --- a/erpnext/accounts/doctype/tax_withholding_category/test_tax_withholding_category.py +++ b/erpnext/accounts/doctype/tax_withholding_category/test_tax_withholding_category.py @@ -243,17 +243,18 @@ class TestTaxWithholdingCategory(FrappeTestCase): frappe.db.set_value( "Customer", "Test TCS Customer", "tax_withholding_category", "Cumulative Threshold TCS" ) + fiscal_year = get_fiscal_year(today(), company="_Test Company") vouchers = [] # create advance payment - pe = create_payment_entry( + pe1 = create_payment_entry( payment_type="Receive", party_type="Customer", party="Test TCS Customer", paid_amount=20000 ) - pe.paid_from = "Debtors - _TC" - pe.paid_to = "Cash - _TC" - pe.submit() - vouchers.append(pe) + pe1.paid_from = "Debtors - _TC" + pe1.paid_to = "Cash - _TC" + pe1.submit() + vouchers.append(pe1) # create invoice si1 = create_sales_invoice(customer="Test TCS Customer", rate=5000) @@ -275,6 +276,17 @@ class TestTaxWithholdingCategory(FrappeTestCase): # make another invoice # sum of unallocated amount from payment entry and this sales invoice will breach cumulative threashold # TDS should be calculated + + # this payment should not be considered for TCS calculation as it is outside of fiscal year + pe2 = create_payment_entry( + payment_type="Receive", party_type="Customer", party="Test TCS Customer", paid_amount=10000 + ) + pe2.paid_from = "Debtors - _TC" + pe2.paid_to = "Cash - _TC" + pe2.posting_date = add_days(fiscal_year[1], -10) + pe2.submit() + vouchers.append(pe2) + si2 = create_sales_invoice(customer="Test TCS Customer", rate=15000) si2.submit() vouchers.append(si2) From d37b12f38586b030db4eb86c29a4c86dbd06bdb4 Mon Sep 17 00:00:00 2001 From: rohitwaghchaure Date: Tue, 27 May 2025 13:23:40 +0530 Subject: [PATCH 12/12] fix: incorrect status in the serial no (#47740) --- erpnext/stock/doctype/serial_no/serial_no.py | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/erpnext/stock/doctype/serial_no/serial_no.py b/erpnext/stock/doctype/serial_no/serial_no.py index 654f28e661c..bc4d4998d0b 100644 --- a/erpnext/stock/doctype/serial_no/serial_no.py +++ b/erpnext/stock/doctype/serial_no/serial_no.py @@ -178,13 +178,13 @@ class SerialNo(StockController): entries = {} sle_dict = self.get_stock_ledger_entries(serial_no) if sle_dict: + last_sle = sle_dict.get("last_sle") or {} + entries["last_sle"] = last_sle + if sle_dict.get("incoming", []): entries["purchase_sle"] = sle_dict["incoming"][-1] - if len(sle_dict.get("incoming", [])) - len(sle_dict.get("outgoing", [])) > 0: - entries["last_sle"] = sle_dict["incoming"][0] - else: - entries["last_sle"] = sle_dict["outgoing"][0] + if last_sle.get("actual_qty") < 0 and sle_dict.get("outgoing", []): entries["delivery_sle"] = sle_dict["outgoing"][0] return entries @@ -221,6 +221,9 @@ class SerialNo(StockController): as_dict=1, ): if serial_no.upper() in get_serial_nos(sle.serial_no): + if "last_sle" not in sle_dict: + sle_dict["last_sle"] = sle + if cint(sle.actual_qty) > 0: sle_dict.setdefault("incoming", []).append(sle) else: