diff --git a/erpnext/accounts/doctype/accounts_settings/accounts_settings.json b/erpnext/accounts/doctype/accounts_settings/accounts_settings.json index c77750cf9f0..0c7d78b4cfc 100644 --- a/erpnext/accounts/doctype/accounts_settings/accounts_settings.json +++ b/erpnext/accounts/doctype/accounts_settings/accounts_settings.json @@ -640,7 +640,7 @@ } ], "grid_page_length": 50, - "hide_toolbar": 1, + "hide_toolbar": 0, "icon": "icon-cog", "idx": 1, "index_web_pages_for_search": 1, diff --git a/erpnext/accounts/doctype/pricing_rule/pricing_rule.json b/erpnext/accounts/doctype/pricing_rule/pricing_rule.json index bc8c3280412..9a4eba07423 100644 --- a/erpnext/accounts/doctype/pricing_rule/pricing_rule.json +++ b/erpnext/accounts/doctype/pricing_rule/pricing_rule.json @@ -121,7 +121,7 @@ "in_list_view": 1, "in_standard_filter": 1, "label": "Apply On", - "options": "\nItem Code\nItem Group\nBrand\nTransaction", + "options": "Item Code\nItem Group\nBrand\nTransaction", "reqd": 1 }, { @@ -657,7 +657,7 @@ "icon": "fa fa-gift", "idx": 1, "links": [], - "modified": "2025-08-20 11:40:07.096854", + "modified": "2026-02-17 12:24:07.553505", "modified_by": "Administrator", "module": "Accounts", "name": "Pricing Rule", @@ -714,9 +714,10 @@ "write": 1 } ], + "row_format": "Dynamic", "show_name_in_global_search": 1, "sort_field": "creation", "sort_order": "DESC", "states": [], "title_field": "title" -} \ No newline at end of file +} diff --git a/erpnext/accounts/doctype/pricing_rule/pricing_rule.py b/erpnext/accounts/doctype/pricing_rule/pricing_rule.py index 378d349e83d..5a4f3ca3249 100644 --- a/erpnext/accounts/doctype/pricing_rule/pricing_rule.py +++ b/erpnext/accounts/doctype/pricing_rule/pricing_rule.py @@ -45,7 +45,7 @@ class PricingRule(Document): apply_discount_on: DF.Literal["Grand Total", "Net Total"] apply_discount_on_rate: DF.Check apply_multiple_pricing_rules: DF.Check - apply_on: DF.Literal["", "Item Code", "Item Group", "Brand", "Transaction"] + apply_on: DF.Literal["Item Code", "Item Group", "Brand", "Transaction"] apply_recursion_over: DF.Float apply_rule_on_other: DF.Literal["", "Item Code", "Item Group", "Brand"] brands: DF.Table[PricingRuleBrand] diff --git a/erpnext/accounts/doctype/pricing_rule_brand/pricing_rule_brand.json b/erpnext/accounts/doctype/pricing_rule_brand/pricing_rule_brand.json index 67c0525539c..73413a88cf4 100644 --- a/erpnext/accounts/doctype/pricing_rule_brand/pricing_rule_brand.json +++ b/erpnext/accounts/doctype/pricing_rule_brand/pricing_rule_brand.json @@ -10,7 +10,7 @@ ], "fields": [ { - "depends_on": "eval:parent.apply_on == 'Item Code'", + "depends_on": "eval:parent.apply_on == 'Brand'", "fieldname": "brand", "fieldtype": "Link", "in_list_view": 1, @@ -28,14 +28,15 @@ ], "istable": 1, "links": [], - "modified": "2024-03-27 13:10:17.857046", + "modified": "2026-02-17 12:17:13.073587", "modified_by": "Administrator", "module": "Accounts", "name": "Pricing Rule Brand", "owner": "Administrator", "permissions": [], + "row_format": "Dynamic", "sort_field": "creation", "sort_order": "DESC", "states": [], "track_changes": 1 -} \ No newline at end of file +} diff --git a/erpnext/accounts/doctype/pricing_rule_item_group/pricing_rule_item_group.json b/erpnext/accounts/doctype/pricing_rule_item_group/pricing_rule_item_group.json index a3ac16226e0..d1b5443dc0a 100644 --- a/erpnext/accounts/doctype/pricing_rule_item_group/pricing_rule_item_group.json +++ b/erpnext/accounts/doctype/pricing_rule_item_group/pricing_rule_item_group.json @@ -10,7 +10,7 @@ ], "fields": [ { - "depends_on": "eval:parent.apply_on == 'Item Code'", + "depends_on": "eval:parent.apply_on == 'Item Group'", "fieldname": "item_group", "fieldtype": "Link", "in_list_view": 1, @@ -28,14 +28,15 @@ ], "istable": 1, "links": [], - "modified": "2024-03-27 13:10:18.221095", + "modified": "2026-02-17 12:16:57.778471", "modified_by": "Administrator", "module": "Accounts", "name": "Pricing Rule Item Group", "owner": "Administrator", "permissions": [], + "row_format": "Dynamic", "sort_field": "creation", "sort_order": "DESC", "states": [], "track_changes": 1 -} \ No newline at end of file +} diff --git a/erpnext/accounts/doctype/purchase_invoice_item/purchase_invoice_item.json b/erpnext/accounts/doctype/purchase_invoice_item/purchase_invoice_item.json index d007f4bf8cd..00951fdd4cc 100644 --- a/erpnext/accounts/doctype/purchase_invoice_item/purchase_invoice_item.json +++ b/erpnext/accounts/doctype/purchase_invoice_item/purchase_invoice_item.json @@ -52,6 +52,7 @@ "stock_uom_rate", "is_free_item", "apply_tds", + "allow_zero_valuation_rate", "section_break_22", "net_rate", "net_amount", @@ -97,7 +98,6 @@ "service_start_date", "service_end_date", "reference", - "allow_zero_valuation_rate", "item_tax_rate", "bom", "include_exploded_items", @@ -420,6 +420,7 @@ "options": "UOM" }, { + "depends_on": "eval:parent.update_stock", "fieldname": "warehouse_section", "fieldtype": "Section Break", "label": "Warehouse" @@ -447,7 +448,6 @@ "print_hide": 1 }, { - "depends_on": "eval:!doc.is_fixed_asset && doc.use_serial_batch_fields === 1 && parent.update_stock === 1", "fieldname": "batch_no", "fieldtype": "Link", "label": "Batch No", @@ -459,14 +459,12 @@ "fieldtype": "Column Break" }, { - "depends_on": "eval:!doc.is_fixed_asset && doc.use_serial_batch_fields === 1 && parent.update_stock === 1", "fieldname": "serial_no", "fieldtype": "Text", "label": "Serial No", "no_copy": 1 }, { - "depends_on": "eval:!doc.is_fixed_asset && doc.use_serial_batch_fields === 1 && parent.update_stock === 1", "fieldname": "rejected_serial_no", "fieldtype": "Text", "label": "Rejected Serial No", @@ -577,6 +575,7 @@ }, { "default": "0", + "depends_on": "eval:parent.update_stock", "fieldname": "allow_zero_valuation_rate", "fieldtype": "Check", "label": "Allow Zero Valuation Rate", @@ -800,7 +799,7 @@ "read_only": 1 }, { - "depends_on": "eval:parent.is_internal_supplier && parent.update_stock", + "depends_on": "eval:parent.is_internal_supplier", "fieldname": "from_warehouse", "fieldtype": "Link", "ignore_user_permissions": 1, @@ -896,7 +895,7 @@ "label": "Consider for Tax Withholding" }, { - "depends_on": "eval:parent.update_stock == 1 && (doc.use_serial_batch_fields === 0 || doc.docstatus === 1)", + "depends_on": "eval:doc.use_serial_batch_fields === 0 || doc.docstatus === 1", "fieldname": "serial_and_batch_bundle", "fieldtype": "Link", "label": "Serial and Batch Bundle", @@ -906,7 +905,7 @@ "search_index": 1 }, { - "depends_on": "eval:parent.update_stock == 1 && (doc.use_serial_batch_fields === 0 || doc.docstatus === 1)", + "depends_on": "eval:doc.use_serial_batch_fields === 0 || doc.docstatus === 1", "fieldname": "rejected_serial_and_batch_bundle", "fieldtype": "Link", "label": "Rejected Serial and Batch Bundle", @@ -922,7 +921,7 @@ "options": "Asset" }, { - "depends_on": "eval:parent.update_stock === 1 && (doc.use_serial_batch_fields === 0 || doc.docstatus === 1)", + "depends_on": "eval:doc.use_serial_batch_fields === 0 && doc.docstatus === 0", "fieldname": "add_serial_batch_bundle", "fieldtype": "Button", "label": "Add Serial / Batch No" @@ -992,7 +991,7 @@ "idx": 1, "istable": 1, "links": [], - "modified": "2025-12-13 14:10:02.379392", + "modified": "2026-02-15 21:07:49.455930", "modified_by": "Administrator", "module": "Accounts", "name": "Purchase Invoice Item", diff --git a/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json b/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json index 7608ea87de8..28a2256e2ec 100644 --- a/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json +++ b/erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json @@ -52,6 +52,7 @@ "is_free_item", "apply_tds", "grant_commission", + "allow_zero_valuation_rate", "section_break_21", "net_rate", "net_amount", @@ -88,7 +89,6 @@ "serial_and_batch_bundle", "use_serial_batch_fields", "col_break5", - "allow_zero_valuation_rate", "incoming_rate", "item_tax_rate", "actual_batch_qty", @@ -580,6 +580,7 @@ { "collapsible": 1, "collapsible_depends_on": "eval:doc.serial_no || doc.batch_no", + "depends_on": "eval:parent.update_stock", "fieldname": "warehouse_and_reference", "fieldtype": "Section Break", "label": "Stock Details" @@ -595,7 +596,7 @@ "print_hide": 1 }, { - "depends_on": "eval: parent.is_internal_customer && parent.update_stock", + "depends_on": "eval: parent.is_internal_customer", "fieldname": "target_warehouse", "fieldtype": "Link", "hidden": 1, @@ -613,7 +614,6 @@ "options": "Quality Inspection" }, { - "depends_on": "eval: doc.use_serial_batch_fields === 1 && parent.update_stock === 1", "fieldname": "batch_no", "fieldtype": "Link", "label": "Batch No", @@ -626,6 +626,7 @@ }, { "default": "0", + "depends_on": "eval:parent.update_stock", "fieldname": "allow_zero_valuation_rate", "fieldtype": "Check", "label": "Allow Zero Valuation Rate", @@ -633,7 +634,6 @@ "print_hide": 1 }, { - "depends_on": "eval: doc.use_serial_batch_fields === 1 && parent.update_stock === 1", "fieldname": "serial_no", "fieldtype": "Text", "label": "Serial No", @@ -906,7 +906,7 @@ "read_only": 1 }, { - "depends_on": "eval:parent.update_stock == 1 && (doc.use_serial_batch_fields === 0 || doc.docstatus === 1)", + "depends_on": "eval:doc.use_serial_batch_fields === 0 || doc.docstatus === 1", "fieldname": "serial_and_batch_bundle", "fieldtype": "Link", "label": "Serial and Batch Bundle", @@ -916,7 +916,7 @@ "search_index": 1 }, { - "depends_on": "eval:parent.update_stock === 1", + "depends_on": "eval:doc.use_serial_batch_fields === 0 && doc.docstatus === 0", "fieldname": "pick_serial_and_batch", "fieldtype": "Button", "label": "Pick Serial / Batch No" @@ -1009,7 +1009,7 @@ "idx": 1, "istable": 1, "links": [], - "modified": "2025-09-04 11:08:25.583561", + "modified": "2026-02-15 21:08:57.341638", "modified_by": "Administrator", "module": "Accounts", "name": "Sales Invoice Item", diff --git a/erpnext/accounts/doctype/sales_invoice_payment/sales_invoice_payment.json b/erpnext/accounts/doctype/sales_invoice_payment/sales_invoice_payment.json index 1389e0992d3..dc50e65d258 100644 --- a/erpnext/accounts/doctype/sales_invoice_payment/sales_invoice_payment.json +++ b/erpnext/accounts/doctype/sales_invoice_payment/sales_invoice_payment.json @@ -26,7 +26,7 @@ }, { "default": "0", - "depends_on": "eval:parent.doctype == 'Sales Invoice'", + "depends_on": "eval: [\"POS Invoice\", \"Sales Invoice\"].includes(parent.doctype)", "fieldname": "amount", "fieldtype": "Currency", "in_list_view": 1, @@ -85,14 +85,15 @@ ], "istable": 1, "links": [], - "modified": "2024-03-27 13:10:36.427565", + "modified": "2026-02-16 20:46:34.592604", "modified_by": "Administrator", "module": "Accounts", "name": "Sales Invoice Payment", "owner": "Administrator", "permissions": [], "quick_entry": 1, + "row_format": "Dynamic", "sort_field": "creation", "sort_order": "DESC", "states": [] -} \ No newline at end of file +} diff --git a/erpnext/accounts/report/profitability_analysis/profitability_analysis.py b/erpnext/accounts/report/profitability_analysis/profitability_analysis.py index 5f3215fe7e2..4d057636a69 100644 --- a/erpnext/accounts/report/profitability_analysis/profitability_analysis.py +++ b/erpnext/accounts/report/profitability_analysis/profitability_analysis.py @@ -3,7 +3,8 @@ import frappe -from frappe import _ +from frappe import _, qb +from frappe.query_builder import Criterion from frappe.utils import cstr, flt from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_dimensions @@ -33,11 +34,19 @@ def execute(filters=None): def get_accounts_data(based_on, company): if based_on == "Cost Center": - return frappe.db.sql( - """select name, parent_cost_center as parent_account, cost_center_name as account_name, lft, rgt - from `tabCost Center` where company=%s order by name""", - company, - as_dict=True, + cc = qb.DocType("Cost Center") + return ( + qb.from_(cc) + .select( + cc.name, + cc.parent_cost_center.as_("parent_account"), + cc.cost_center_name.as_("account_name"), + cc.lft, + cc.rgt, + ) + .where(cc.company.eq(company)) + .orderby(cc.name) + .run(as_dict=True) ) elif based_on == "Project": return frappe.get_all("Project", fields=["name"], filters={"company": company}, order_by="name") @@ -206,27 +215,38 @@ def set_gl_entries_by_account( company, from_date, to_date, based_on, gl_entries_by_account, ignore_closing_entries=False ): """Returns a dict like { "account": [gl entries], ... }""" - additional_conditions = [] + gl = qb.DocType("GL Entry") + acc = qb.DocType("Account") + + conditions = [] + conditions.append(gl.company.eq(company)) + conditions.append(gl[based_on].notnull()) + conditions.append(gl.is_cancelled.eq(0)) + + if from_date and to_date: + conditions.append(gl.posting_date.between(from_date, to_date)) + elif from_date and not to_date: + conditions.append(gl.posting_date.gte(from_date)) + elif not from_date and to_date: + conditions.append(gl.posting_date.lte(to_date)) if ignore_closing_entries: - additional_conditions.append("and voucher_type !='Period Closing Voucher'") + conditions.append(gl.voucher_type.ne("Period Closing Voucher")) - if from_date: - additional_conditions.append("and posting_date >= %(from_date)s") - - gl_entries = frappe.db.sql( - """select posting_date, {based_on} as based_on, debit, credit, - is_opening, (select root_type from `tabAccount` where name = account) as type - from `tabGL Entry` where company=%(company)s - {additional_conditions} - and posting_date <= %(to_date)s - and {based_on} is not null - and is_cancelled = 0 - order by {based_on}, posting_date""".format( - additional_conditions="\n".join(additional_conditions), based_on=based_on - ), - {"company": company, "from_date": from_date, "to_date": to_date}, - as_dict=True, + root_subquery = qb.from_(acc).select(acc.root_type).where(acc.name.eq(gl.account)) + gl_entries = ( + qb.from_(gl) + .select( + gl.posting_date, + gl[based_on].as_("based_on"), + gl.debit, + gl.credit, + gl.is_opening, + root_subquery.as_("type"), + ) + .where(Criterion.all(conditions)) + .orderby(gl[based_on], gl.posting_date) + .run(as_dict=True) ) for entry in gl_entries: diff --git a/erpnext/controllers/accounts_controller.py b/erpnext/controllers/accounts_controller.py index a97fb4000fb..25959c651cf 100644 --- a/erpnext/controllers/accounts_controller.py +++ b/erpnext/controllers/accounts_controller.py @@ -4079,6 +4079,12 @@ def update_child_qty_rate(parent_doctype, trans_items, parent_doctype_name, chil flt(d.get("conversion_factor"), conv_fac_precision) or conversion_factor ) + if child_item.get("total_weight") and child_item.get("weight_per_unit"): + child_item.total_weight = flt( + child_item.weight_per_unit * child_item.qty * child_item.conversion_factor, + child_item.precision("total_weight"), + ) + if d.get("delivery_date") and parent_doctype == "Sales Order": child_item.delivery_date = d.get("delivery_date") diff --git a/erpnext/controllers/buying_controller.py b/erpnext/controllers/buying_controller.py index 837bbbc793c..86cfbc01172 100644 --- a/erpnext/controllers/buying_controller.py +++ b/erpnext/controllers/buying_controller.py @@ -783,7 +783,9 @@ class BuyingController(SubcontractingController): or self.is_return or (self.is_internal_transfer() and self.docstatus == 2) else self.get_package_for_target_warehouse( - d, type_of_transaction=type_of_transaction + d, + type_of_transaction=type_of_transaction, + via_landed_cost_voucher=via_landed_cost_voucher, ) ), }, @@ -871,7 +873,22 @@ class BuyingController(SubcontractingController): via_landed_cost_voucher=via_landed_cost_voucher, ) - def get_package_for_target_warehouse(self, item, warehouse=None, type_of_transaction=None) -> str: + def get_package_for_target_warehouse( + self, item, warehouse=None, type_of_transaction=None, via_landed_cost_voucher=None + ) -> str: + if via_landed_cost_voucher and item.get("warehouse"): + if sabb := frappe.db.get_value( + "Serial and Batch Bundle", + { + "voucher_detail_no": item.name, + "warehouse": item.get("warehouse"), + "docstatus": 1, + "is_cancelled": 0, + }, + "name", + ): + return sabb + if not item.serial_and_batch_bundle: return "" diff --git a/erpnext/controllers/stock_controller.py b/erpnext/controllers/stock_controller.py index f2e93a4e933..7ff2c4061f2 100644 --- a/erpnext/controllers/stock_controller.py +++ b/erpnext/controllers/stock_controller.py @@ -2017,7 +2017,7 @@ def get_gl_entries_for_preview(doctype, docname, fields): def get_columns(raw_columns, fields): return [ - {"name": d.get("label"), "editable": False, "width": 110} + {"name": d.get("label"), "editable": False, "width": 110, "fieldtype": d.get("fieldtype")} for d in raw_columns if not d.get("hidden") and d.get("fieldname") in fields ] diff --git a/erpnext/locale/main.pot b/erpnext/locale/main.pot index eab1b559dde..77c3cdac6aa 100644 --- a/erpnext/locale/main.pot +++ b/erpnext/locale/main.pot @@ -7,8 +7,8 @@ msgid "" msgstr "" "Project-Id-Version: ERPNext VERSION\n" "Report-Msgid-Bugs-To: hello@frappe.io\n" -"POT-Creation-Date: 2026-02-08 09:43+0000\n" -"PO-Revision-Date: 2026-02-08 09:43+0000\n" +"POT-Creation-Date: 2026-02-15 09:44+0000\n" +"PO-Revision-Date: 2026-02-15 09:44+0000\n" "Last-Translator: hello@frappe.io\n" "Language-Team: hello@frappe.io\n" "MIME-Version: 1.0\n" @@ -16,7 +16,7 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Generated-By: Babel 2.16.0\n" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1466 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1469 msgid "" "\n" "\t\t\tThe Batch {0} of an item {1} has negative stock in the warehouse {2}. Please add a stock quantity of {3} to proceed with this entry." @@ -3782,7 +3782,7 @@ msgstr "" #: erpnext/accounts/doctype/process_payment_reconciliation_log_allocations/process_payment_reconciliation_log_allocations.json #: erpnext/accounts/doctype/purchase_invoice_advance/purchase_invoice_advance.json #: erpnext/accounts/doctype/unreconcile_payment_entries/unreconcile_payment_entries.json -#: erpnext/accounts/report/gross_profit/gross_profit.py:398 +#: erpnext/accounts/report/gross_profit/gross_profit.py:409 #: erpnext/public/js/utils/unreconcile.js:87 msgid "Allocated Amount" msgstr "" @@ -3952,11 +3952,17 @@ msgstr "" #: erpnext/stock/doctype/item/item.json #: erpnext/stock/doctype/repost_item_valuation/repost_item_valuation.json #: erpnext/stock/doctype/stock_settings/stock_settings.json -#: erpnext/stock/doctype/stock_settings/stock_settings.py:178 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:190 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:179 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:191 msgid "Allow Negative Stock" msgstr "" +#. Label of the allow_negative_stock_for_batch (Check) field in DocType 'Stock +#. Settings' +#: erpnext/stock/doctype/stock_settings/stock_settings.json +msgid "Allow Negative Stock for Batch" +msgstr "" + #. Label of the allow_negative_rates_for_items (Check) field in DocType #. 'Selling Settings' #: erpnext/selling/doctype/selling_settings/selling_settings.json @@ -4472,7 +4478,7 @@ msgstr "" #: erpnext/selling/report/sales_order_analysis/sales_order_analysis.py:290 #: erpnext/selling/report/sales_partner_commission_summary/sales_partner_commission_summary.py:53 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:69 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:67 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:68 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:109 #: erpnext/stock/doctype/delivery_note_item/delivery_note_item.json #: erpnext/stock/doctype/landed_cost_item/landed_cost_item.json @@ -5152,7 +5158,7 @@ msgstr "" msgid "As there are existing submitted transactions against item {0}, you can not change the value of {1}." msgstr "" -#: erpnext/stock/doctype/stock_settings/stock_settings.py:203 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:204 msgid "As there are reserved stock, you cannot disable {0}." msgstr "" @@ -5164,8 +5170,8 @@ msgstr "" msgid "As there are sufficient raw materials, Material Request is not required for Warehouse {0}." msgstr "" -#: erpnext/stock/doctype/stock_settings/stock_settings.py:177 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:189 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:178 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:190 msgid "As {0} is enabled, you can not enable {1}." msgstr "" @@ -5567,7 +5573,7 @@ msgstr "" msgid "Asset deleted" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:168 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:181 msgid "Asset issued to Employee {0}" msgstr "" @@ -5575,7 +5581,7 @@ msgstr "" msgid "Asset out of order due to Asset Repair {0}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:155 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:168 msgid "Asset received at Location {0} and issued to Employee {1}" msgstr "" @@ -5608,7 +5614,7 @@ msgstr "" msgid "Asset submitted" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:163 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:176 msgid "Asset transferred to Location {0}" msgstr "" @@ -5628,15 +5634,15 @@ msgstr "" msgid "Asset {0} does not belong to Item {1}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:44 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:45 msgid "Asset {0} does not belong to company {1}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:92 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:105 msgid "Asset {0} does not belong to the custodian {1}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:64 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:77 msgid "Asset {0} does not belong to the location {1}" msgstr "" @@ -6345,7 +6351,7 @@ msgstr "" msgid "Avg. Selling Price List Rate" msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:336 +#: erpnext/accounts/report/gross_profit/gross_profit.py:347 msgid "Avg. Selling Rate" msgstr "" @@ -7224,10 +7230,6 @@ msgstr "" msgid "Base Taxable Amount" msgstr "" -#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:163 -msgid "Base Total" -msgstr "" - #. Label of the base_total_billable_amount (Currency) field in DocType #. 'Timesheet' #: erpnext/projects/doctype/timesheet/timesheet.json @@ -7419,7 +7421,7 @@ msgstr "" msgid "Batch No is mandatory" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:3256 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:3262 msgid "Batch No {0} does not exists" msgstr "" @@ -7442,7 +7444,7 @@ msgstr "" msgid "Batch Nos" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1850 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1853 msgid "Batch Nos are created successfully" msgstr "" @@ -8356,7 +8358,7 @@ msgstr "" msgid "Buying & Selling Settings" msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:357 +#: erpnext/accounts/report/gross_profit/gross_profit.py:368 msgid "Buying Amount" msgstr "" @@ -8679,6 +8681,10 @@ msgstr "" msgid "Campaign Schedules" msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:113 +msgid "Campaign {0} not found" +msgstr "" + #: erpnext/setup/doctype/authorization_control/authorization_control.py:60 msgid "Can be approved by {0}" msgstr "" @@ -8723,7 +8729,7 @@ msgid "Can refer row only if the charge type is 'On Previous Row Amount' or 'Pre msgstr "" #: erpnext/setup/doctype/company/company.py:207 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:144 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:145 msgid "Can't change the valuation method, as there are transactions against some items which do not have its own valuation method" msgstr "" @@ -8933,7 +8939,7 @@ msgid "Cannot delete an item which has been ordered" msgstr "" #: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:195 -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:778 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:780 msgid "Cannot delete protected core DocType: {0}" msgstr "" @@ -10045,7 +10051,7 @@ msgstr "" #: erpnext/selling/report/sales_partner_commission_summary/sales_partner_commission_summary.py:67 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:78 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:82 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:83 msgid "Commission Rate %" msgstr "" @@ -10617,7 +10623,7 @@ msgstr "" msgid "Company Address Name" msgstr "" -#: erpnext/controllers/accounts_controller.py:4318 +#: erpnext/controllers/accounts_controller.py:4324 msgid "Company Address is missing. You don't have permission to update it. Please contact your System Manager." msgstr "" @@ -11410,7 +11416,7 @@ msgstr "" msgid "Contract Terms and Conditions" msgstr "" -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:76 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:77 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:122 msgid "Contribution %" msgstr "" @@ -11420,7 +11426,7 @@ msgstr "" msgid "Contribution (%)" msgstr "" -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:88 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:89 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:130 msgid "Contribution Amount" msgstr "" @@ -11486,7 +11492,7 @@ msgstr "" #: erpnext/manufacturing/doctype/bom_creator_item/bom_creator_item.json #: erpnext/manufacturing/doctype/bom_item/bom_item.json #: erpnext/manufacturing/doctype/material_request_plan_item/material_request_plan_item.json -#: erpnext/public/js/utils.js:807 +#: erpnext/public/js/utils.js:811 #: erpnext/selling/doctype/delivery_schedule_item/delivery_schedule_item.json #: erpnext/stock/doctype/packed_item/packed_item.json #: erpnext/stock/doctype/purchase_receipt_item/purchase_receipt_item.json @@ -11748,7 +11754,7 @@ msgstr "" #: erpnext/accounts/report/general_ledger/general_ledger.js:153 #: erpnext/accounts/report/general_ledger/general_ledger.py:778 #: erpnext/accounts/report/gross_profit/gross_profit.js:68 -#: erpnext/accounts/report/gross_profit/gross_profit.py:384 +#: erpnext/accounts/report/gross_profit/gross_profit.py:395 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:297 #: erpnext/accounts/report/purchase_register/purchase_register.js:46 #: erpnext/accounts/report/sales_payment_summary/sales_payment_summary.py:29 @@ -13071,7 +13077,7 @@ msgstr "" #: erpnext/accounts/doctype/tax_rule/tax_rule.json #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.js:38 #: erpnext/accounts/report/delivered_items_to_be_billed/delivered_items_to_be_billed.py:29 -#: erpnext/accounts/report/gross_profit/gross_profit.py:405 +#: erpnext/accounts/report/gross_profit/gross_profit.py:416 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py:37 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.js:22 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:213 @@ -13125,7 +13131,7 @@ msgstr "" #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.js:53 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:32 #: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.js:40 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:53 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:54 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.js:53 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:65 #: erpnext/selling/workspace/selling/selling.json @@ -13339,7 +13345,7 @@ msgstr "" #: erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py:185 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.js:56 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.py:165 -#: erpnext/accounts/report/gross_profit/gross_profit.py:412 +#: erpnext/accounts/report/gross_profit/gross_profit.py:423 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:200 #: erpnext/accounts/report/sales_register/sales_register.js:27 #: erpnext/accounts/report/sales_register/sales_register.py:202 @@ -13449,7 +13455,7 @@ msgstr "" #: erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py:156 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.js:92 #: erpnext/accounts/report/delivered_items_to_be_billed/delivered_items_to_be_billed.py:35 -#: erpnext/accounts/report/gross_profit/gross_profit.py:419 +#: erpnext/accounts/report/gross_profit/gross_profit.py:430 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:220 #: erpnext/accounts/report/sales_register/sales_register.py:193 #: erpnext/buying/doctype/purchase_order/purchase_order.json @@ -13515,10 +13521,6 @@ msgstr "" msgid "Customer PO Details" msgstr "" -#: erpnext/public/js/utils/contact_address_quick_entry.js:114 -msgid "Customer POS Id" -msgstr "" - #. Label of the customer_pos_id (Data) field in DocType 'Customer' #: erpnext/selling/doctype/customer/customer.json msgid "Customer POS id" @@ -13728,7 +13730,7 @@ msgstr "" msgid "Daily Project Summary for {0}" msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:181 +#: erpnext/setup/doctype/email_digest/email_digest.py:179 msgid "Daily Reminders" msgstr "" @@ -14805,8 +14807,8 @@ msgstr "" msgid "Deleting {0} and all associated Common Code documents..." msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1095 -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1114 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1097 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1116 msgid "Deletion in Progress!" msgstr "" @@ -14939,7 +14941,7 @@ msgstr "" #: erpnext/manufacturing/doctype/master_production_schedule_item/master_production_schedule_item.json #: erpnext/manufacturing/doctype/sales_forecast_item/sales_forecast_item.json #: erpnext/manufacturing/report/material_requirements_planning_report/material_requirements_planning_report.py:1067 -#: erpnext/public/js/utils.js:800 +#: erpnext/public/js/utils.js:804 #: erpnext/selling/doctype/delivery_schedule_item/delivery_schedule_item.json #: erpnext/selling/doctype/sales_order/sales_order.js:624 #: erpnext/selling/doctype/sales_order/sales_order.js:1486 @@ -16259,7 +16261,7 @@ msgid "Do you want to submit the stock entry?" msgstr "" #: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:180 -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:441 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:443 msgid "DocType {0} does not exist" msgstr "" @@ -16866,11 +16868,21 @@ msgstr "" msgid "Email Campaign" msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:112 +#: erpnext/crm/doctype/email_campaign/email_campaign.py:149 +#: erpnext/crm/doctype/email_campaign/email_campaign.py:157 +msgid "Email Campaign Error" +msgstr "" + #. Label of the email_campaign_for (Select) field in DocType 'Email Campaign' #: erpnext/crm/doctype/email_campaign/email_campaign.json msgid "Email Campaign For " msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:125 +msgid "Email Campaign Send Error" +msgstr "" + #. Label of the supplier_response_section (Section Break) field in DocType #. 'Request for Quotation' #: erpnext/buying/doctype/request_for_quotation/request_for_quotation.json @@ -17097,12 +17109,12 @@ msgstr "" msgid "Employee cannot report to himself." msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:96 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:109 msgid "Employee is required while issuing Asset {0}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:79 -#: erpnext/assets/doctype/asset_movement/asset_movement.py:100 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:92 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:113 msgid "Employee {0} does not belong to the company {1}" msgstr "" @@ -17118,7 +17130,7 @@ msgstr "" msgid "Empty" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:750 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:752 msgid "Empty To Delete List" msgstr "" @@ -18004,7 +18016,7 @@ msgstr "" #: erpnext/accounts/report/account_balance/account_balance.js:28 #: erpnext/accounts/report/deferred_revenue_and_expense/deferred_revenue_and_expense.js:89 #: erpnext/accounts/report/profit_and_loss_statement/profit_and_loss_statement.py:182 -#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:190 +#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:199 msgid "Expense" msgstr "" @@ -18273,6 +18285,10 @@ msgstr "" msgid "Failed to post depreciation entries" msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:126 +msgid "Failed to send email for campaign {0} to {1}" +msgstr "" + #: erpnext/setup/setup_wizard/setup_wizard.py:30 #: erpnext/setup/setup_wizard/setup_wizard.py:31 msgid "Failed to setup company" @@ -18434,15 +18450,15 @@ msgstr "" msgid "Fields will be copied over only at time of creation." msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1062 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1064 msgid "File does not belong to this Transaction Deletion Record" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1056 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1058 msgid "File not found" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1070 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1072 msgid "File not found on server" msgstr "" @@ -18666,7 +18682,7 @@ msgstr "" #. Service Item' #. Label of the fg_item (Link) field in DocType 'Subcontracting Order Service #. Item' -#: erpnext/public/js/utils.js:826 +#: erpnext/public/js/utils.js:830 #: erpnext/subcontracting/doctype/subcontracting_inward_order_service_item/subcontracting_inward_order_service_item.json #: erpnext/subcontracting/doctype/subcontracting_order_service_item/subcontracting_order_service_item.json msgid "Finished Good Item" @@ -18679,7 +18695,7 @@ msgstr "" msgid "Finished Good Item Code" msgstr "" -#: erpnext/public/js/utils.js:844 +#: erpnext/public/js/utils.js:848 msgid "Finished Good Item Qty" msgstr "" @@ -19506,7 +19522,7 @@ msgstr "" msgid "From Employee" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:85 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:98 msgid "From Employee is required while issuing Asset {0}" msgstr "" @@ -20044,7 +20060,7 @@ msgstr "" msgid "Generate To Delete List" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:468 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:470 msgid "Generate To Delete list first" msgstr "" @@ -20499,7 +20515,6 @@ msgstr "" #: erpnext/accounts/report/pos_register/pos_register.py:202 #: erpnext/accounts/report/purchase_register/purchase_register.py:275 #: erpnext/accounts/report/sales_register/sales_register.py:305 -#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:175 #: erpnext/buying/doctype/purchase_order/purchase_order.json #: erpnext/buying/doctype/supplier_quotation/supplier_quotation.json #: erpnext/manufacturing/doctype/production_plan_sales_order/production_plan_sales_order.json @@ -20533,6 +20548,7 @@ msgstr "" #: erpnext/accounts/doctype/pos_invoice/pos_invoice.json #: erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json #: erpnext/accounts/doctype/sales_invoice/sales_invoice.json +#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:169 #: erpnext/buying/doctype/purchase_order/purchase_order.json #: erpnext/buying/doctype/supplier_quotation/supplier_quotation.json #: erpnext/selling/doctype/quotation/quotation.json @@ -20542,6 +20558,10 @@ msgstr "" msgid "Grand Total (Company Currency)" msgstr "" +#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:175 +msgid "Grand Total (Transaction Currency)" +msgstr "" + #. Label of the grant_commission (Check) field in DocType 'POS Invoice Item' #. Label of the grant_commission (Check) field in DocType 'Sales Invoice Item' #. Label of the grant_commission (Check) field in DocType 'Sales Order Item' @@ -20602,18 +20622,18 @@ msgstr "" #. Label of the gross_profit (Currency) field in DocType 'Quotation Item' #. Label of the gross_profit (Currency) field in DocType 'Sales Order Item' #: erpnext/accounts/report/gross_profit/gross_profit.json -#: erpnext/accounts/report/gross_profit/gross_profit.py:364 +#: erpnext/accounts/report/gross_profit/gross_profit.py:375 #: erpnext/accounts/workspace/financial_reports/financial_reports.json #: erpnext/selling/doctype/quotation_item/quotation_item.json #: erpnext/selling/doctype/sales_order_item/sales_order_item.json msgid "Gross Profit" msgstr "" -#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:197 +#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:206 msgid "Gross Profit / Loss" msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:371 +#: erpnext/accounts/report/gross_profit/gross_profit.py:382 msgid "Gross Profit Percent" msgstr "" @@ -20664,7 +20684,7 @@ msgstr "" msgid "Group Same Items" msgstr "" -#: erpnext/stock/doctype/stock_settings/stock_settings.py:119 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:120 msgid "Group Warehouses cannot be used in transactions. Please change the value of {0}" msgstr "" @@ -21468,6 +21488,12 @@ msgstr "" msgid "If enabled, the source and target warehouse in the Material Transfer Stock Entry must be different else an error will be thrown. If inventory dimensions are present, same source and target warehouse can be allowed but atleast any one of the inventory dimension fields must be different." msgstr "" +#. Description of the 'Allow Negative Stock for Batch' (Check) field in DocType +#. 'Stock Settings' +#: erpnext/stock/doctype/stock_settings/stock_settings.json +msgid "If enabled, the system will allow negative stock entries for the batch, but this could calculate the valuation rate incorrectly, so avoid using this option." +msgstr "" + #. Description of the 'Allow UOM with Conversion Rate Defined in Item' (Check) #. field in DocType 'Stock Settings' #: erpnext/stock/doctype/stock_settings/stock_settings.json @@ -21889,7 +21915,7 @@ msgstr "" msgid "Import Successful" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:560 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:562 msgid "Import Summary" msgstr "" @@ -22130,7 +22156,7 @@ msgstr "" #. Label of the incentives (Currency) field in DocType 'Sales Team' #: erpnext/selling/doctype/sales_team/sales_team.json -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:93 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:94 msgid "Incentives" msgstr "" @@ -22344,7 +22370,7 @@ msgstr "" #: erpnext/accounts/report/account_balance/account_balance.js:27 #: erpnext/accounts/report/financial_statements.py:776 #: erpnext/accounts/report/profit_and_loss_statement/profit_and_loss_statement.py:180 -#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:183 +#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:192 msgid "Income" msgstr "" @@ -22473,7 +22499,7 @@ msgid "Incorrect Type of Transaction" msgstr "" #: erpnext/stock/doctype/pick_list/pick_list.py:175 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:122 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:123 msgid "Incorrect Warehouse" msgstr "" @@ -23009,7 +23035,7 @@ msgstr "" msgid "Invalid Blanket Order for the selected Customer and Item" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:494 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:496 msgid "Invalid CSV format. Expected column: doctype_name" msgstr "" @@ -23176,7 +23202,7 @@ msgstr "" msgid "Invalid condition expression" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1051 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1053 msgid "Invalid file URL" msgstr "" @@ -24412,7 +24438,7 @@ msgstr "" #: erpnext/accounts/doctype/sales_invoice/sales_invoice.js:1078 #: erpnext/accounts/report/billed_items_to_be_received/billed_items_to_be_received.py:68 #: erpnext/accounts/report/delivered_items_to_be_billed/delivered_items_to_be_billed.py:37 -#: erpnext/accounts/report/gross_profit/gross_profit.py:301 +#: erpnext/accounts/report/gross_profit/gross_profit.py:312 #: erpnext/accounts/report/item_wise_purchase_register/item_wise_purchase_register.py:142 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:159 #: erpnext/accounts/report/received_items_to_be_billed/received_items_to_be_billed.py:37 @@ -24663,7 +24689,7 @@ msgstr "" #: erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json #: erpnext/accounts/doctype/tax_rule/tax_rule.json #: erpnext/accounts/report/gross_profit/gross_profit.js:44 -#: erpnext/accounts/report/gross_profit/gross_profit.py:314 +#: erpnext/accounts/report/gross_profit/gross_profit.py:325 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.js:21 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py:28 #: erpnext/accounts/report/item_wise_purchase_register/item_wise_purchase_register.js:28 @@ -24890,7 +24916,7 @@ msgstr "" #: erpnext/accounts/doctype/sales_invoice_item/sales_invoice_item.json #: erpnext/accounts/report/billed_items_to_be_received/billed_items_to_be_received.py:74 #: erpnext/accounts/report/delivered_items_to_be_billed/delivered_items_to_be_billed.py:71 -#: erpnext/accounts/report/gross_profit/gross_profit.py:308 +#: erpnext/accounts/report/gross_profit/gross_profit.py:319 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py:33 #: erpnext/accounts/report/item_wise_purchase_register/item_wise_purchase_register.py:148 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:165 @@ -24941,7 +24967,7 @@ msgstr "" #: erpnext/manufacturing/report/quality_inspection_summary/quality_inspection_summary.py:92 #: erpnext/manufacturing/report/work_order_consumed_materials/work_order_consumed_materials.py:138 #: erpnext/public/js/controllers/transaction.js:2801 -#: erpnext/public/js/utils.js:736 +#: erpnext/public/js/utils.js:740 #: erpnext/selling/doctype/quotation_item/quotation_item.json #: erpnext/selling/doctype/sales_order/sales_order.js:1252 #: erpnext/selling/doctype/sales_order_item/sales_order_item.json @@ -25559,11 +25585,11 @@ msgstr "" msgid "Items and Pricing" msgstr "" -#: erpnext/controllers/accounts_controller.py:4176 +#: erpnext/controllers/accounts_controller.py:4182 msgid "Items cannot be updated as Subcontracting Inward Order(s) exist against this Subcontracted Sales Order." msgstr "" -#: erpnext/controllers/accounts_controller.py:4169 +#: erpnext/controllers/accounts_controller.py:4175 msgid "Items cannot be updated as Subcontracting Order is created against the Purchase Order {0}." msgstr "" @@ -27615,7 +27641,7 @@ msgstr "" msgid "Mapping Subcontracting Order ..." msgstr "" -#: erpnext/public/js/utils.js:971 +#: erpnext/public/js/utils.js:975 msgid "Mapping {0} ..." msgstr "" @@ -28265,7 +28291,7 @@ msgstr "" msgid "Merge Similar Account Heads" msgstr "" -#: erpnext/public/js/utils.js:1003 +#: erpnext/public/js/utils.js:1007 msgid "Merge taxes from multiple documents" msgstr "" @@ -29012,7 +29038,7 @@ msgstr "" msgid "Naming Series is mandatory" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:932 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:934 msgid "Naming series '{0}' for DocType '{1}' does not contain standard '.' or '{{' separator. Using fallback extraction." msgstr "" @@ -29055,7 +29081,7 @@ msgstr "" msgid "Negative Quantity is not allowed" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1475 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1478 #: erpnext/stock/serial_batch_bundle.py:1520 msgid "Negative Stock Error" msgstr "" @@ -29619,7 +29645,7 @@ msgstr "" msgid "No Delivery Note selected for Customer {}" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:749 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:751 msgid "No DocTypes in To Delete list. Please generate or import the list before submitting." msgstr "" @@ -29712,7 +29738,7 @@ msgstr "" msgid "No Tax withholding account set for Company {0} in Tax Withholding Category {1}." msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:893 +#: erpnext/accounts/report/gross_profit/gross_profit.py:965 msgid "No Terms" msgstr "" @@ -29770,6 +29796,10 @@ msgstr "" msgid "No difference found for stock account {0}" msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:150 +msgid "No email found for {0} {1}" +msgstr "" + #: erpnext/telephony/doctype/call_log/call_log.py:117 msgid "No employee was scheduled for call popup" msgstr "" @@ -29795,10 +29825,6 @@ msgstr "" msgid "No items in cart" msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:166 -msgid "No items to be received are overdue" -msgstr "" - #: erpnext/accounts/doctype/bank_reconciliation_tool/bank_reconciliation_tool.py:456 msgid "No matches occurred via auto reconciliation" msgstr "" @@ -29925,6 +29951,10 @@ msgstr "" msgid "No recent transactions found" msgstr "" +#: erpnext/crm/doctype/email_campaign/email_campaign.py:158 +msgid "No recipients found for campaign {0}" +msgstr "" + #: erpnext/accounts/report/purchase_register/purchase_register.py:45 #: erpnext/accounts/report/sales_register/sales_register.py:46 #: erpnext/crm/report/lead_conversion_time/lead_conversion_time.py:18 @@ -30551,7 +30581,7 @@ msgstr "" msgid "Only CSV and Excel files can be used to for importing data. Please check the file format you are trying to upload" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1065 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1067 msgid "Only CSV files are allowed" msgstr "" @@ -33412,7 +33442,7 @@ msgstr "" #: erpnext/accounts/doctype/payment_term/payment_term.json #: erpnext/accounts/doctype/payment_terms_template_detail/payment_terms_template_detail.json #: erpnext/accounts/report/accounts_receivable/accounts_receivable.py:1214 -#: erpnext/accounts/report/gross_profit/gross_profit.py:438 +#: erpnext/accounts/report/gross_profit/gross_profit.py:449 #: erpnext/accounts/workspace/invoicing/invoicing.json #: erpnext/selling/report/payment_terms_status_for_sales_order/payment_terms_status_for_sales_order.py:30 msgid "Payment Term" @@ -33678,7 +33708,7 @@ msgstr "" msgid "Pending Work Order" msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:182 +#: erpnext/setup/doctype/email_digest/email_digest.py:180 msgid "Pending activities for today" msgstr "" @@ -35121,7 +35151,7 @@ msgstr "" #: erpnext/selling/report/sales_partner_commission_summary/sales_partner_commission_summary.py:21 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:21 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:42 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:43 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:54 msgid "Please select the document type first" msgstr "" @@ -35375,7 +35405,7 @@ msgstr "" msgid "Please set the cost center field in {0} or setup a default Cost Center for the Company." msgstr "" -#: erpnext/crm/doctype/email_campaign/email_campaign.py:50 +#: erpnext/crm/doctype/email_campaign/email_campaign.py:48 msgid "Please set up the Campaign Schedule in the Campaign {0}" msgstr "" @@ -35622,7 +35652,7 @@ msgstr "" #: erpnext/accounts/report/billed_items_to_be_received/billed_items_to_be_received.py:66 #: erpnext/accounts/report/cheques_and_deposits_incorrectly_cleared/cheques_and_deposits_incorrectly_cleared.py:151 #: erpnext/accounts/report/general_ledger/general_ledger.py:681 -#: erpnext/accounts/report/gross_profit/gross_profit.py:289 +#: erpnext/accounts/report/gross_profit/gross_profit.py:300 #: erpnext/accounts/report/item_wise_purchase_register/item_wise_purchase_register.py:175 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:192 #: erpnext/accounts/report/payment_ledger/payment_ledger.py:143 @@ -35640,7 +35670,7 @@ msgstr "" #: erpnext/selling/report/payment_terms_status_for_sales_order/payment_terms_status_for_sales_order.py:25 #: erpnext/selling/report/sales_partner_commission_summary/sales_partner_commission_summary.py:51 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:45 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:66 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:67 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:85 #: erpnext/stock/doctype/landed_cost_purchase_receipt/landed_cost_purchase_receipt.json #: erpnext/stock/doctype/landed_cost_voucher/landed_cost_voucher.json @@ -35715,7 +35745,7 @@ msgstr "" #: erpnext/accounts/doctype/pos_invoice_merge_log/pos_invoice_merge_log.json #: erpnext/accounts/doctype/purchase_invoice/purchase_invoice.json #: erpnext/accounts/doctype/sales_invoice/sales_invoice.json -#: erpnext/accounts/report/gross_profit/gross_profit.py:295 +#: erpnext/accounts/report/gross_profit/gross_profit.py:306 #: erpnext/assets/doctype/asset_capitalization/asset_capitalization.json #: erpnext/stock/doctype/delivery_note/delivery_note.json #: erpnext/stock/doctype/purchase_receipt/purchase_receipt.json @@ -37248,7 +37278,7 @@ msgid "Prospects Engaged But Not Converted" msgstr "" #: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:196 -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:779 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:781 msgid "Protected DocType" msgstr "" @@ -37950,7 +37980,7 @@ msgstr "" #: erpnext/accounts/doctype/pricing_rule/pricing_rule.json #: erpnext/accounts/doctype/promotional_scheme_product_discount/promotional_scheme_product_discount.json #: erpnext/accounts/print_format/sales_invoice_print/sales_invoice_print.html:91 -#: erpnext/accounts/report/gross_profit/gross_profit.py:334 +#: erpnext/accounts/report/gross_profit/gross_profit.py:345 #: erpnext/assets/doctype/asset_capitalization_service_item/asset_capitalization_service_item.json #: erpnext/buying/report/purchase_order_analysis/purchase_order_analysis.py:240 #: erpnext/buying/report/requested_items_to_order_and_receive/requested_items_to_order_and_receive.py:224 @@ -37973,7 +38003,7 @@ msgstr "" #: erpnext/public/js/bom_configurator/bom_configurator.bundle.js:398 #: erpnext/public/js/bom_configurator/bom_configurator.bundle.js:499 #: erpnext/public/js/stock_reservation.js:134 -#: erpnext/public/js/stock_reservation.js:336 erpnext/public/js/utils.js:774 +#: erpnext/public/js/stock_reservation.js:336 erpnext/public/js/utils.js:778 #: erpnext/selling/doctype/delivery_schedule_item/delivery_schedule_item.json #: erpnext/selling/doctype/product_bundle_item/product_bundle_item.json #: erpnext/selling/doctype/sales_order/sales_order.js:390 @@ -38982,7 +39012,7 @@ msgstr "" #: erpnext/manufacturing/doctype/bom_item/bom_item.json #: erpnext/manufacturing/doctype/bom_scrap_item/bom_scrap_item.json #: erpnext/manufacturing/doctype/work_order_item/work_order_item.json -#: erpnext/public/js/utils.js:784 +#: erpnext/public/js/utils.js:788 #: erpnext/selling/doctype/product_bundle_item/product_bundle_item.json #: erpnext/selling/doctype/quotation_item/quotation_item.json #: erpnext/selling/doctype/sales_order_item/sales_order_item.json @@ -40660,7 +40690,7 @@ msgstr "" msgid "Reqd Qty (BOM)" msgstr "" -#: erpnext/public/js/utils.js:800 +#: erpnext/public/js/utils.js:804 msgid "Reqd by date" msgstr "" @@ -42737,7 +42767,7 @@ msgstr "" msgid "Row {0}: As {1} is enabled, raw materials cannot be added to {2} entry. Use {3} entry to consume raw materials." msgstr "" -#: erpnext/stock/doctype/material_request/material_request.py:882 +#: erpnext/stock/doctype/material_request/material_request.py:885 msgid "Row {0}: Bill of Materials not found for the Item {1}" msgstr "" @@ -43139,7 +43169,7 @@ msgstr "" msgid "SLA Paused On" msgstr "" -#: erpnext/public/js/utils.js:1160 +#: erpnext/public/js/utils.js:1164 msgid "SLA is on hold since {0}" msgstr "" @@ -43330,8 +43360,8 @@ msgstr "" #: erpnext/accounts/doctype/sales_invoice_reference/sales_invoice_reference.json #: erpnext/accounts/print_format/sales_auditing_voucher/sales_auditing_voucher.html:5 #: erpnext/accounts/report/gross_profit/gross_profit.js:30 -#: erpnext/accounts/report/gross_profit/gross_profit.py:276 -#: erpnext/accounts/report/gross_profit/gross_profit.py:283 +#: erpnext/accounts/report/gross_profit/gross_profit.py:287 +#: erpnext/accounts/report/gross_profit/gross_profit.py:294 #: erpnext/crm/doctype/contract/contract.json #: erpnext/projects/doctype/timesheet/timesheet.json #: erpnext/projects/doctype/timesheet_detail/timesheet_detail.json @@ -43783,14 +43813,14 @@ msgstr "" #: erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py:191 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.js:80 #: erpnext/accounts/report/gross_profit/gross_profit.js:50 -#: erpnext/accounts/report/gross_profit/gross_profit.py:391 +#: erpnext/accounts/report/gross_profit/gross_profit.py:402 #: erpnext/crm/workspace/crm/crm.json #: erpnext/maintenance/doctype/maintenance_schedule_detail/maintenance_schedule_detail.json #: erpnext/maintenance/doctype/maintenance_schedule_item/maintenance_schedule_item.json #: erpnext/maintenance/doctype/maintenance_visit_purpose/maintenance_visit_purpose.json #: erpnext/selling/doctype/sales_team/sales_team.json #: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.js:8 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:69 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:70 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.js:8 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:116 #: erpnext/selling/workspace/selling/selling.json @@ -43860,7 +43890,7 @@ msgstr "" msgid "Sales Representative" msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:893 +#: erpnext/accounts/report/gross_profit/gross_profit.py:964 #: erpnext/stock/doctype/delivery_note/delivery_note.js:270 msgid "Sales Return" msgstr "" @@ -44384,7 +44414,7 @@ msgstr "" msgid "Segregate Serial / Batch Bundle" msgstr "" -#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:22 +#: erpnext/accounts/report/profitability_analysis/profitability_analysis.py:23 msgid "Select Accounting Dimension." msgstr "" @@ -44793,7 +44823,7 @@ msgstr "" msgid "Selling" msgstr "" -#: erpnext/accounts/report/gross_profit/gross_profit.py:350 +#: erpnext/accounts/report/gross_profit/gross_profit.py:361 msgid "Selling Amount" msgstr "" @@ -44812,7 +44842,7 @@ msgstr "" #: erpnext/selling/doctype/selling_settings/selling_settings.json #: erpnext/selling/workspace/selling/selling.json #: erpnext/setup/workspace/erpnext_settings/erpnext_settings.json -#: erpnext/stock/doctype/stock_settings/stock_settings.py:221 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:222 msgid "Selling Settings" msgstr "" @@ -45052,7 +45082,7 @@ msgstr "" msgid "Serial No Range" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2513 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2516 msgid "Serial No Reserved" msgstr "" @@ -45132,7 +45162,7 @@ msgstr "" msgid "Serial No {0} does not exist" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:3250 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:3256 msgid "Serial No {0} does not exists" msgstr "" @@ -45186,7 +45216,7 @@ msgstr "" msgid "Serial Nos and Batches" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1799 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:1802 msgid "Serial Nos are created successfully" msgstr "" @@ -45268,11 +45298,11 @@ msgstr "" msgid "Serial and Batch Bundle" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2021 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2024 msgid "Serial and Batch Bundle created" msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2093 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2096 msgid "Serial and Batch Bundle updated" msgstr "" @@ -46686,7 +46716,7 @@ msgstr "" msgid "Skip Material Transfer to WIP Warehouse" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:559 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:561 msgid "Skipped {0} DocType(s):
{1}" msgstr "" @@ -46737,7 +46767,7 @@ msgstr "" msgid "Solvency Ratios" msgstr "" -#: erpnext/controllers/accounts_controller.py:4310 +#: erpnext/controllers/accounts_controller.py:4316 msgid "Some required Company details are missing. You don't have permission to update them. Please contact your System Manager." msgstr "" @@ -46857,7 +46887,7 @@ msgstr "" msgid "Source Warehouse {0} must be same as Customer Warehouse {1} in the Subcontracting Inward Order." msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:72 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:85 msgid "Source and Target Location cannot be same" msgstr "" @@ -47628,9 +47658,9 @@ msgstr "" #: erpnext/stock/doctype/stock_reservation_entry/stock_reservation_entry.py:1699 #: erpnext/stock/doctype/stock_reservation_entry/stock_reservation_entry.py:1716 #: erpnext/stock/doctype/stock_settings/stock_settings.json -#: erpnext/stock/doctype/stock_settings/stock_settings.py:178 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:190 -#: erpnext/stock/doctype/stock_settings/stock_settings.py:204 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:179 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:191 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:205 #: erpnext/subcontracting/doctype/subcontracting_order/subcontracting_order.js:182 #: erpnext/subcontracting/doctype/subcontracting_order/subcontracting_order.js:195 #: erpnext/subcontracting/doctype/subcontracting_order/subcontracting_order.js:207 @@ -48640,11 +48670,11 @@ msgstr "" msgid "Suggestions" msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:188 +#: erpnext/setup/doctype/email_digest/email_digest.py:186 msgid "Summary for this month and pending activities" msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:185 +#: erpnext/setup/doctype/email_digest/email_digest.py:183 msgid "Summary for this week and pending activities" msgstr "" @@ -49445,11 +49475,11 @@ msgstr "" msgid "Target Location" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:70 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:83 msgid "Target Location is required for transferring Asset {0}" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:76 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:89 msgid "Target Location is required while receiving Asset {0}" msgstr "" @@ -49623,7 +49653,7 @@ msgstr "" #. Label of the amount (Currency) field in DocType 'Item Wise Tax Detail' #: erpnext/accounts/doctype/item_wise_tax_detail/item_wise_tax_detail.json -#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:169 +#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:163 #: erpnext/accounts/report/tds_computation_summary/tds_computation_summary.py:115 msgid "Tax Amount" msgstr "" @@ -49983,6 +50013,7 @@ msgstr "" #. Label of the taxable_amount (Currency) field in DocType 'Item Wise Tax #. Detail' #: erpnext/accounts/doctype/item_wise_tax_detail/item_wise_tax_detail.json +#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:157 #: erpnext/controllers/taxes_and_totals.py:1207 msgid "Taxable Amount" msgstr "" @@ -50413,7 +50444,7 @@ msgstr "" #: erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py:182 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.js:68 #: erpnext/accounts/report/customer_ledger_summary/customer_ledger_summary.py:171 -#: erpnext/accounts/report/gross_profit/gross_profit.py:425 +#: erpnext/accounts/report/gross_profit/gross_profit.py:436 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.js:8 #: erpnext/accounts/report/inactive_sales_items/inactive_sales_items.py:21 #: erpnext/accounts/report/item_wise_sales_register/item_wise_sales_register.py:251 @@ -50442,7 +50473,7 @@ msgstr "" #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.js:59 #: erpnext/selling/report/sales_partner_transaction_summary/sales_partner_transaction_summary.py:39 #: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.js:46 -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:60 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:61 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.js:59 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:72 #: erpnext/selling/report/territory_wise_sales/territory_wise_sales.py:22 @@ -50569,7 +50600,7 @@ msgstr "" msgid "The Serial No at Row #{0}: {1} is not available in warehouse {2}." msgstr "" -#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2510 +#: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py:2513 msgid "The Serial No {0} is reserved against the {1} {2} and cannot be used for any other transaction." msgstr "" @@ -50684,7 +50715,7 @@ msgstr "" msgid "The following rows are duplicates:" msgstr "" -#: erpnext/stock/doctype/material_request/material_request.py:892 +#: erpnext/stock/doctype/material_request/material_request.py:895 msgid "The following {0} were created: {1}" msgstr "" @@ -50787,7 +50818,7 @@ msgstr "" msgid "The percentage you are allowed to transfer more against the quantity ordered. For example, if you have ordered 100 units, and your Allowance is 10%, then you are allowed transfer 110 units." msgstr "" -#: erpnext/public/js/utils.js:872 +#: erpnext/public/js/utils.js:876 msgid "The reserved stock will be released when you update items. Are you certain you wish to proceed?" msgstr "" @@ -50926,7 +50957,7 @@ msgstr "" msgid "The {0} prefix '{1}' already exists. Please change the Serial No Series, otherwise you will get a Duplicate Entry error." msgstr "" -#: erpnext/stock/doctype/material_request/material_request.py:898 +#: erpnext/stock/doctype/material_request/material_request.py:901 msgid "The {0} {1} created successfully" msgstr "" @@ -51037,7 +51068,7 @@ msgstr "" msgid "This Item is a Variant of {0} (Template)." msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:187 +#: erpnext/setup/doctype/email_digest/email_digest.py:185 msgid "This Month's Summary" msgstr "" @@ -51049,7 +51080,7 @@ msgstr "" msgid "This Sales Order has been fully subcontracted." msgstr "" -#: erpnext/setup/doctype/email_digest/email_digest.py:184 +#: erpnext/setup/doctype/email_digest/email_digest.py:182 msgid "This Week's Summary" msgstr "" @@ -51786,7 +51817,7 @@ msgstr "" msgid "To use a different finance book, please uncheck 'Include Default FB Assets'" msgstr "" -#: erpnext/accounts/doctype/financial_report_template/financial_report_engine.py:709 +#: erpnext/accounts/doctype/financial_report_template/financial_report_engine.py:705 #: erpnext/accounts/report/financial_statements.py:624 #: erpnext/accounts/report/general_ledger/general_ledger.py:310 #: erpnext/accounts/report/trial_balance/trial_balance.py:310 @@ -51948,8 +51979,6 @@ msgstr "" #. Label of the total_amount (Currency) field in DocType 'Stock Entry' #: erpnext/accounts/doctype/invoice_discounting/invoice_discounting.json #: erpnext/accounts/doctype/journal_entry/journal_entry.json -#: erpnext/accounts/report/tax_withholding_details/tax_withholding_details.py:157 -#: erpnext/accounts/report/tds_computation_summary/tds_computation_summary.py:109 #: erpnext/selling/page/sales_funnel/sales_funnel.py:167 #: erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.json #: erpnext/stock/doctype/stock_entry/stock_entry.json @@ -52471,6 +52500,10 @@ msgstr "" msgid "Total Tax" msgstr "" +#: erpnext/accounts/report/tds_computation_summary/tds_computation_summary.py:109 +msgid "Total Taxable Amount" +msgstr "" + #. Label of the total_taxes_and_charges (Currency) field in DocType 'Payment #. Entry' #. Label of the total_taxes_and_charges (Currency) field in DocType 'POS @@ -52784,11 +52817,11 @@ msgstr "" msgid "Transaction Deletion Record To Delete" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1096 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1098 msgid "Transaction Deletion Record {0} is already running. {1}" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1115 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:1117 msgid "Transaction Deletion Record {0} is currently deleting {1}. Cannot save documents until deletion completes." msgstr "" @@ -52854,6 +52887,10 @@ msgstr "" msgid "Transaction currency: {0} cannot be different from Bank Account({1}) currency: {2}" msgstr "" +#: erpnext/assets/doctype/asset_movement/asset_movement.py:65 +msgid "Transaction date can't be earlier than previous movement date" +msgstr "" + #. Description of the 'Applicable For' (Section Break) field in DocType 'Tax #. Withholding Entry' #: erpnext/accounts/doctype/tax_withholding_entry/tax_withholding_entry.json @@ -53271,7 +53308,7 @@ msgstr "" #: erpnext/manufacturing/doctype/workstation/workstation.js:480 #: erpnext/manufacturing/report/bom_explorer/bom_explorer.py:70 #: erpnext/manufacturing/report/bom_operations_time/bom_operations_time.py:110 -#: erpnext/public/js/stock_analytics.js:94 erpnext/public/js/utils.js:745 +#: erpnext/public/js/stock_analytics.js:94 erpnext/public/js/utils.js:749 #: erpnext/quality_management/doctype/quality_goal_objective/quality_goal_objective.json #: erpnext/quality_management/doctype/quality_review_objective/quality_review_objective.json #: erpnext/selling/doctype/delivery_schedule_item/delivery_schedule_item.json @@ -53407,7 +53444,7 @@ msgstr "" msgid "UnReconcile Allocations" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:462 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:464 msgid "Unable to fetch DocType details. Please contact system administrator." msgstr "" @@ -53496,7 +53533,7 @@ msgstr "" msgid "Under Working Hours table, you can add start and end times for a Workstation. For example, a Workstation may be active from 9 am to 1 pm, then 2 pm to 5 pm. You can also specify the working hours based on shifts. While scheduling a Work Order, the system will check for the availability of the Workstation based on the working hours specified." msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:931 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:933 msgid "Unexpected Naming Series Pattern" msgstr "" @@ -53863,7 +53900,7 @@ msgstr "" #: erpnext/buying/doctype/purchase_order/purchase_order.js:324 #: erpnext/buying/doctype/supplier_quotation/supplier_quotation.js:43 -#: erpnext/public/js/utils.js:851 +#: erpnext/public/js/utils.js:855 #: erpnext/selling/doctype/quotation/quotation.js:135 #: erpnext/selling/doctype/sales_order/sales_order.js:75 #: erpnext/selling/doctype/sales_order/sales_order.js:940 @@ -54490,7 +54527,7 @@ msgstr "" #. Label of the valuation_rate (Currency) field in DocType 'Stock #. Reconciliation Item' #: erpnext/accounts/doctype/purchase_invoice_item/purchase_invoice_item.json -#: erpnext/accounts/report/gross_profit/gross_profit.py:343 +#: erpnext/accounts/report/gross_profit/gross_profit.py:354 #: erpnext/assets/doctype/asset_capitalization_stock_item/asset_capitalization_stock_item.json #: erpnext/assets/doctype/asset_repair_consumed_item/asset_repair_consumed_item.json #: erpnext/manufacturing/doctype/bom/bom.json @@ -55860,7 +55897,7 @@ msgstr "" #: erpnext/selling/doctype/sales_order/sales_order.js:1050 #: erpnext/stock/doctype/material_request/material_request.js:216 #: erpnext/stock/doctype/material_request/material_request.json -#: erpnext/stock/doctype/material_request/material_request.py:899 +#: erpnext/stock/doctype/material_request/material_request.py:902 #: erpnext/stock/doctype/pick_list/pick_list.json #: erpnext/stock/doctype/serial_no/serial_no.json #: erpnext/stock/doctype/stock_entry/stock_entry.json @@ -55920,7 +55957,7 @@ msgstr "" msgid "Work Order Summary" msgstr "" -#: erpnext/stock/doctype/material_request/material_request.py:905 +#: erpnext/stock/doctype/material_request/material_request.py:908 msgid "Work Order cannot be created for following reason:
{0}" msgstr "" @@ -55946,7 +55983,7 @@ msgid "Work Order {0}: Job Card not found for the operation {1}" msgstr "" #: erpnext/manufacturing/report/job_card_summary/job_card_summary.js:56 -#: erpnext/stock/doctype/material_request/material_request.py:893 +#: erpnext/stock/doctype/material_request/material_request.py:896 msgid "Work Orders" msgstr "" @@ -56413,7 +56450,7 @@ msgstr "" msgid "You had {} errors while creating opening invoices. Check {} for more details" msgstr "" -#: erpnext/public/js/utils.js:951 +#: erpnext/public/js/utils.js:955 msgid "You have already selected items from {0} {1}" msgstr "" @@ -56421,7 +56458,7 @@ msgstr "" msgid "You have been invited to collaborate on the project {0}." msgstr "" -#: erpnext/stock/doctype/stock_settings/stock_settings.py:216 +#: erpnext/stock/doctype/stock_settings/stock_settings.py:217 msgid "You have enabled {0} and {1} in {2}. This can lead to prices from the default price list being inserted in the transaction price list." msgstr "" @@ -56575,7 +56612,7 @@ msgstr "" msgid "discount applied" msgstr "" -#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:46 +#: erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py:47 #: erpnext/selling/report/sales_person_wise_transaction_summary/sales_person_wise_transaction_summary.py:58 msgid "doc_type" msgstr "" @@ -56922,7 +56959,7 @@ msgstr "" msgid "{0} and {1} are mandatory" msgstr "" -#: erpnext/assets/doctype/asset_movement/asset_movement.py:41 +#: erpnext/assets/doctype/asset_movement/asset_movement.py:42 msgid "{0} asset cannot be transferred" msgstr "" @@ -57007,7 +57044,7 @@ msgstr "" msgid "{0} in row {1}" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:448 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:450 msgid "{0} is a child table and will be deleted automatically with its parent" msgstr "" @@ -57021,7 +57058,7 @@ msgstr "" msgid "{0} is added multiple times on rows: {1}" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:624 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:626 msgid "{0} is already running for {1}" msgstr "" @@ -57074,7 +57111,7 @@ msgstr "" msgid "{0} is not enabled in {1}" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:632 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:634 msgid "{0} is not running. Cannot trigger events for this Document" msgstr "" @@ -57382,19 +57419,19 @@ msgstr "" msgid "{0}, complete the operation {1} before the operation {2}." msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:519 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:521 msgid "{0}: Child table (auto-deleted with parent)" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:514 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:516 msgid "{0}: Not found" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:510 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:512 msgid "{0}: Protected DocType" msgstr "" -#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:524 +#: erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py:526 msgid "{0}: Virtual DocType (no database table)" msgstr "" diff --git a/erpnext/manufacturing/doctype/bom_operation/bom_operation.json b/erpnext/manufacturing/doctype/bom_operation/bom_operation.json index 27025c12fdb..ad33af6dfff 100644 --- a/erpnext/manufacturing/doctype/bom_operation/bom_operation.json +++ b/erpnext/manufacturing/doctype/bom_operation/bom_operation.json @@ -146,7 +146,7 @@ "label": "Batch Size" }, { - "depends_on": "eval:doc.parenttype == \"Routing\"", + "depends_on": "eval:doc.parenttype == \"Routing\" || !parent.routing", "description": "If you want to run operations in parallel, keep the same sequence ID for them.", "fieldname": "sequence_id", "fieldtype": "Int", @@ -297,7 +297,7 @@ "index_web_pages_for_search": 1, "istable": 1, "links": [], - "modified": "2026-01-01 17:15:59.806874", + "modified": "2026-02-17 15:33:28.495850", "modified_by": "Administrator", "module": "Manufacturing", "name": "BOM Operation", diff --git a/erpnext/manufacturing/doctype/plant_floor/plant_floor.json b/erpnext/manufacturing/doctype/plant_floor/plant_floor.json index f595cfd5fc4..ceadefdf01b 100644 --- a/erpnext/manufacturing/doctype/plant_floor/plant_floor.json +++ b/erpnext/manufacturing/doctype/plant_floor/plant_floor.json @@ -49,7 +49,8 @@ "fieldname": "warehouse", "fieldtype": "Link", "label": "Warehouse", - "options": "Warehouse" + "options": "Warehouse", + "set_only_once": 1 }, { "depends_on": "eval:!doc.__islocal && doc.warehouse", @@ -66,13 +67,14 @@ "fieldname": "company", "fieldtype": "Link", "label": "Company", - "options": "Company" + "options": "Company", + "set_only_once": 1 } ], "hide_toolbar": 1, "index_web_pages_for_search": 1, "links": [], - "modified": "2024-09-25 10:27:41.139634", + "modified": "2026-02-17 11:53:17.940039", "modified_by": "Administrator", "module": "Manufacturing", "name": "Plant Floor", @@ -92,7 +94,8 @@ "write": 1 } ], + "row_format": "Dynamic", "sort_field": "creation", "sort_order": "DESC", "states": [] -} \ No newline at end of file +} diff --git a/erpnext/manufacturing/doctype/production_plan/production_plan.js b/erpnext/manufacturing/doctype/production_plan/production_plan.js index 308eb32ca90..22c87fe5d6a 100644 --- a/erpnext/manufacturing/doctype/production_plan/production_plan.js +++ b/erpnext/manufacturing/doctype/production_plan/production_plan.js @@ -24,8 +24,8 @@ frappe.ui.form.on("Production Plan", { "Material Request": "Material Request", }; - frm.set_df_property("sub_assembly_items", "cannot_delete_rows", true); - frm.set_df_property("mr_items", "cannot_delete_rows", true); + frm.set_df_property("sub_assembly_items", "cannot_add_rows", true); + frm.set_df_property("mr_items", "cannot_add_rows", true); }, setup_queries(frm) { diff --git a/erpnext/manufacturing/doctype/production_plan/production_plan.py b/erpnext/manufacturing/doctype/production_plan/production_plan.py index ab989185b73..947eb45787e 100644 --- a/erpnext/manufacturing/doctype/production_plan/production_plan.py +++ b/erpnext/manufacturing/doctype/production_plan/production_plan.py @@ -694,8 +694,8 @@ class ProductionPlan(Document): self.status = "Completed" if self.status != "Completed": - self.update_ordered_status() self.update_requested_status() + self.update_ordered_status() if close is not None: self.db_set("status", self.status) @@ -704,25 +704,17 @@ class ProductionPlan(Document): self.update_bin_qty() def update_ordered_status(self): - update_status = False - for d in self.po_items: - if d.planned_qty == d.ordered_qty: - update_status = True - - if update_status and self.status != "Completed": - self.status = "In Process" + for child_table in ["po_items", "sub_assembly_items"]: + for item in self.get(child_table): + if item.ordered_qty: + self.status = "In Process" + return def update_requested_status(self): - if not self.mr_items: - return - - update_status = True for d in self.mr_items: - if d.quantity != d.requested_qty: - update_status = False - - if update_status: - self.status = "Material Requested" + if d.requested_qty: + self.status = "Material Requested" + break def get_production_items(self): item_dict = {} @@ -844,6 +836,8 @@ class ProductionPlan(Document): "stock_uom", "bom_level", "schedule_date", + "sales_order", + "sales_order_item", ]: if row.get(field): wo_data[field] = row.get(field) @@ -898,6 +892,8 @@ class ProductionPlan(Document): "qty", "description", "production_plan_item", + "sales_order", + "sales_order_item", ]: po_data[field] = row.get(field) @@ -1122,6 +1118,10 @@ class ProductionPlan(Document): if not is_group_warehouse: data.fg_warehouse = self.sub_assembly_warehouse + if not self.combine_sub_items: + data.sales_order = row.sales_order + data.sales_order_item = row.sales_order_item + def set_default_supplier_for_subcontracting_order(self): items = [ d.production_item for d in self.sub_assembly_items if d.type_of_manufacturing == "Subcontract" diff --git a/erpnext/manufacturing/doctype/production_plan/test_production_plan.py b/erpnext/manufacturing/doctype/production_plan/test_production_plan.py index e960e734bc1..b7787d6489b 100644 --- a/erpnext/manufacturing/doctype/production_plan/test_production_plan.py +++ b/erpnext/manufacturing/doctype/production_plan/test_production_plan.py @@ -626,6 +626,90 @@ class TestProductionPlan(IntegrationTestCase): frappe.db.count("Purchase Order Item", {"production_plan": plan.name, "docstatus": 1}), 2 ) # 2 since we have already created and submitted 2 POs + def test_sales_order_references_for_sub_assembly_items(self): + """ + Test that Sales Order and Sales Order Item references in Work Order and Purchase Order + are correctly propagated from the Production Plan. + """ + + from erpnext.manufacturing.doctype.bom.test_bom import create_nested_bom + + # Setup Test Items & BOM + fg_item = "Test FG Good Item" + sub_assembly_item1 = "Test Sub Assembly Item 1" + sub_assembly_item2 = "Test Sub Assembly Item 2" + + bom_tree = { + fg_item: { + sub_assembly_item1: {"Test Raw Material 1": {}}, + sub_assembly_item2: {"Test Raw Material 2": {}}, + } + } + + create_nested_bom(bom_tree, prefix="") + + # Create Sales Order + so = make_sales_order(item_code=fg_item, qty=10) + so_item_row = so.items[0].name + + # Create Production Plan from Sales Order + production_plan = frappe.new_doc("Production Plan") + production_plan.company = so.company + production_plan.get_items_from = "Sales Order" + production_plan.item_code = fg_item + + production_plan.get_open_sales_orders() + self.assertEqual(production_plan.sales_orders[0].sales_order, so.name) + + production_plan.get_so_items() + + production_plan.skip_available_sub_assembly_item = 0 + production_plan.get_sub_assembly_items() + + self.assertEqual(len(production_plan.sub_assembly_items), 2) + + # Validate Sales Order references in Sub Assembly Items + for row in production_plan.sub_assembly_items: + if row.production_item == sub_assembly_item1: + row.supplier = "_Test Supplier" + row.type_of_manufacturing = "Subcontract" + + self.assertEqual(row.sales_order, so.name) + self.assertEqual(row.sales_order_item, so_item_row) + + # Submit Production Plan + production_plan.save() + production_plan.submit() + production_plan.make_work_order() + + # Validate Purchase Order (Subcontracted Item) + po_items = frappe.get_all( + "Purchase Order Item", + { + "production_plan": production_plan.name, + "fg_item": sub_assembly_item1, + }, + ["sales_order", "sales_order_item"], + ) + + self.assertTrue(po_items) + self.assertEqual(po_items[0].sales_order, so.name) + self.assertEqual(po_items[0].sales_order_item, so_item_row) + + # Validate Work Order (In-house Item) + work_orders = frappe.get_all( + "Work Order", + { + "production_plan": production_plan.name, + "production_item": sub_assembly_item2, + }, + ["sales_order", "sales_order_item"], + ) + + self.assertTrue(work_orders) + self.assertEqual(work_orders[0].sales_order, so.name) + self.assertEqual(work_orders[0].sales_order_item, so_item_row) + def test_production_plan_for_mr_items(self): from erpnext.manufacturing.doctype.bom.test_bom import create_nested_bom diff --git a/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.json b/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.json index 5fbb83ae579..26d65116396 100644 --- a/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.json +++ b/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.json @@ -21,6 +21,9 @@ "subcontracting_section", "supplier", "purchase_order", + "column_break_oqry", + "sales_order", + "sales_order_item", "work_order_details_section", "production_plan_item", "wo_produced_qty", @@ -240,13 +243,32 @@ "label": "Ordered Qty", "no_copy": 1, "read_only": 1 + }, + { + "fieldname": "column_break_oqry", + "fieldtype": "Column Break" + }, + { + "fieldname": "sales_order", + "fieldtype": "Link", + "label": "Sales Order", + "options": "Sales Order", + "read_only": 1 + }, + { + "fieldname": "sales_order_item", + "fieldtype": "Data", + "hidden": 1, + "label": "Sales Order Item", + "no_copy": 1, + "print_hide": 1 } ], "grid_page_length": 50, "index_web_pages_for_search": 1, "istable": 1, "links": [], - "modified": "2025-11-03 14:33:50.677717", + "modified": "2026-02-11 13:00:09.092676", "modified_by": "Administrator", "module": "Manufacturing", "name": "Production Plan Sub Assembly Item", diff --git a/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.py b/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.py index 5cdcc6cf118..72ae9612176 100644 --- a/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.py +++ b/erpnext/manufacturing/doctype/production_plan_sub_assembly_item/production_plan_sub_assembly_item.py @@ -34,6 +34,8 @@ class ProductionPlanSubAssemblyItem(Document): qty: DF.Float received_qty: DF.Float required_qty: DF.Float + sales_order: DF.Link | None + sales_order_item: DF.Data | None schedule_date: DF.Datetime | None stock_reserved_qty: DF.Float stock_uom: DF.Link | None diff --git a/erpnext/patches.txt b/erpnext/patches.txt index 838c837321e..e6d090dac21 100644 --- a/erpnext/patches.txt +++ b/erpnext/patches.txt @@ -464,3 +464,4 @@ erpnext.patches.v16_0.set_ordered_qty_in_quotation_item erpnext.patches.v16_0.migrate_transaction_deletion_task_flags_to_status # 2 erpnext.patches.v16_0.update_company_custom_field_in_bin erpnext.patches.v15_0.replace_http_with_https_in_sales_partner +erpnext.patches.v15_0.delete_quotation_lost_record_detail diff --git a/erpnext/patches/v15_0/delete_quotation_lost_record_detail.py b/erpnext/patches/v15_0/delete_quotation_lost_record_detail.py new file mode 100644 index 00000000000..2dc37486e1c --- /dev/null +++ b/erpnext/patches/v15_0/delete_quotation_lost_record_detail.py @@ -0,0 +1,11 @@ +import frappe +from frappe.query_builder import DocType + + +def execute(): + qlr = DocType("Quotation Lost Reason Detail") + quotation = DocType("Quotation") + + sub_query = frappe.qb.from_(quotation).select(quotation.name) + query = frappe.qb.from_(qlr).delete().where(qlr.parent.notin(sub_query)) + query.run() diff --git a/erpnext/patches/v15_0/migrate_to_utm_analytics.py b/erpnext/patches/v15_0/migrate_to_utm_analytics.py index 4385e1ab453..cd4762cc6e7 100644 --- a/erpnext/patches/v15_0/migrate_to_utm_analytics.py +++ b/erpnext/patches/v15_0/migrate_to_utm_analytics.py @@ -2,7 +2,7 @@ import click import frappe from frappe.query_builder.functions import Coalesce -from erpnext.setup.install import create_marketgin_campagin_custom_fields +from erpnext.setup.install import create_marketing_campaign_custom_fields def execute(): @@ -31,7 +31,7 @@ def execute(): frappe.delete_doc("DocType", "Lead Source", ignore_missing=True) campaign = frappe.qb.DocType("Campaign") - create_marketgin_campagin_custom_fields() + create_marketing_campaign_custom_fields() marketing_campaign = frappe.qb.DocType("UTM Campaign") # Fetch all Campaigns diff --git a/erpnext/public/js/utils.js b/erpnext/public/js/utils.js index 08b745d2c32..578846f0937 100755 --- a/erpnext/public/js/utils.js +++ b/erpnext/public/js/utils.js @@ -646,7 +646,11 @@ erpnext.utils.update_child_items = function (opts) { get_query: function () { let filters; if (frm.doc.doctype == "Sales Order") { - filters = { is_sales_item: 1, is_stock_item: !frm.doc.is_subcontracted }; + if (frm.doc.is_subcontracted) { + filters = { is_sales_item: 1, is_stock_item: 0 }; + } else { + filters = { is_sales_item: 1 }; + } } else if (frm.doc.doctype == "Purchase Order") { if (frm.doc.is_subcontracted) { if (frm.doc.is_old_subcontracting_flow) { diff --git a/erpnext/public/js/utils/ledger_preview.js b/erpnext/public/js/utils/ledger_preview.js index 84d57efb1eb..a86e0076629 100644 --- a/erpnext/public/js/utils/ledger_preview.js +++ b/erpnext/public/js/utils/ledger_preview.js @@ -84,6 +84,14 @@ erpnext.accounts.ledger_preview = { }, get_datatable(columns, data, wrapper) { + columns.forEach((col) => { + if (col.fieldtype === "Currency") { + col.format = (value) => { + return format_currency(value); + }; + } + }); + const datatable_options = { columns: columns, data: data, diff --git a/erpnext/public/js/utils/serial_no_batch_selector.js b/erpnext/public/js/utils/serial_no_batch_selector.js index 5cc7238d6dd..6610078b9b4 100644 --- a/erpnext/public/js/utils/serial_no_batch_selector.js +++ b/erpnext/public/js/utils/serial_no_batch_selector.js @@ -708,7 +708,7 @@ erpnext.SerialBatchPackageSelector = class SerialNoBatchBundleUpdate { } render_data() { - if (this.bundle || this.frm.doc.is_return) { + if (this.bundle || (this.frm.doc.is_return && this.frm.doc.return_against)) { frappe .call({ method: "erpnext.stock.doctype.serial_and_batch_bundle.serial_and_batch_bundle.get_serial_batch_ledgers", diff --git a/erpnext/selling/page/sales_funnel/sales_funnel.css b/erpnext/selling/page/sales_funnel/sales_funnel.css index 60b2392ac43..e7301cb7086 100644 --- a/erpnext/selling/page/sales_funnel/sales_funnel.css +++ b/erpnext/selling/page/sales_funnel/sales_funnel.css @@ -1,4 +1,4 @@ .funnel-wrapper { - margin: 15px; - width: 100%; + width: calc(100% - 30px); + margin-left: 30px; } diff --git a/erpnext/selling/page/sales_funnel/sales_funnel.js b/erpnext/selling/page/sales_funnel/sales_funnel.js index 75bbdf862c0..a819c72dc80 100644 --- a/erpnext/selling/page/sales_funnel/sales_funnel.js +++ b/erpnext/selling/page/sales_funnel/sales_funnel.js @@ -8,6 +8,9 @@ frappe.pages["sales-funnel"].on_page_load = function (wrapper) { single_column: true, }); + $(wrapper).find(".layout-main").addClass("row"); + $(wrapper).find(".layout-main-section-wrapper").addClass("col-md-12"); + wrapper.sales_funnel = new erpnext.SalesFunnel(wrapper); frappe.breadcrumbs.add("Selling"); diff --git a/erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py b/erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py index 16b2d499af2..b0e611589eb 100644 --- a/erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py +++ b/erpnext/selling/report/sales_person_commission_summary/sales_person_commission_summary.py @@ -3,7 +3,8 @@ import frappe -from frappe import _, msgprint +from frappe import _, msgprint, qb +from frappe.query_builder import Criterion def execute(filters=None): @@ -97,45 +98,53 @@ def get_columns(filters): def get_entries(filters): - date_field = filters["doc_type"] == "Sales Order" and "transaction_date" or "posting_date" + dt = qb.DocType(filters["doc_type"]) + st = qb.DocType("Sales Team") + date_field = dt["transaction_date"] if filters["doc_type"] == "Sales Order" else dt["posting_date"] - conditions, values = get_conditions(filters, date_field) - entries = frappe.db.sql( - """ - select - dt.name, dt.customer, dt.territory, dt.{} as posting_date,dt.base_net_total as base_net_amount, - st.commission_rate,st.sales_person, st.allocated_percentage, st.allocated_amount, st.incentives - from - `tab{}` dt, `tabSales Team` st - where - st.parent = dt.name and st.parenttype = {} - and dt.docstatus = 1 {} order by dt.name desc,st.sales_person - """.format(date_field, filters["doc_type"], "%s", conditions), - tuple([filters["doc_type"], *values]), - as_dict=1, + conditions = get_conditions(dt, st, filters, date_field) + entries = ( + qb.from_(dt) + .join(st) + .on(st.parent.eq(dt.name) & st.parenttype.eq(filters["doc_type"])) + .select( + dt.name, + dt.customer, + dt.territory, + date_field.as_("posting_date"), + dt.base_net_total.as_("base_net_amount"), + st.commission_rate, + st.sales_person, + st.allocated_percentage, + st.allocated_amount, + st.incentives, + ) + .where(Criterion.all(conditions)) + .orderby(dt.name, st.sales_person) + .run(as_dict=True) ) return entries -def get_conditions(filters, date_field): - conditions = [""] - values = [] +def get_conditions(dt, st, filters, date_field): + conditions = [] + + conditions.append(dt.docstatus.eq(1)) + from_dt = filters.get("from_date") + to_dt = filters.get("to_date") + if from_dt and to_dt: + conditions.append(date_field.between(from_dt, to_dt)) + elif from_dt and not to_dt: + conditions.append(date_field.gte(from_dt)) + elif not from_dt and to_dt: + conditions.append(date_field.lte(to_dt)) for field in ["company", "customer", "territory"]: if filters.get(field): - conditions.append(f"dt.{field}=%s") - values.append(filters[field]) + conditions.append(dt[field].eq(filters.get(field))) if filters.get("sales_person"): - conditions.append("st.sales_person = '{}'".format(filters.get("sales_person"))) + conditions.append(st["sales_person"].eq(filters.get("sales_person"))) - if filters.get("from_date"): - conditions.append(f"dt.{date_field}>=%s") - values.append(filters["from_date"]) - - if filters.get("to_date"): - conditions.append(f"dt.{date_field}<=%s") - values.append(filters["to_date"]) - - return " and ".join(conditions), values + return conditions diff --git a/erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py b/erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py index b308453c847..245befce842 100644 --- a/erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py +++ b/erpnext/setup/doctype/transaction_deletion_record/transaction_deletion_record.py @@ -317,7 +317,9 @@ class TransactionDeletionRecord(Document): list: List of child table DocType names (Table field options) """ return frappe.get_all( - "DocField", filters={"parent": doctype_name, "fieldtype": "Table"}, pluck="options" + "DocField", + filters={"parent": doctype_name, "fieldtype": ["in", ["Table", "Table MultiSelect"]]}, + pluck="options", ) def _get_to_delete_row_infos(self, doctype_name, company_field=None, company=None): diff --git a/erpnext/setup/install.py b/erpnext/setup/install.py index 5738182529b..94706443d6b 100644 --- a/erpnext/setup/install.py +++ b/erpnext/setup/install.py @@ -23,7 +23,7 @@ def after_install(): set_single_defaults() create_print_setting_custom_fields() - create_marketgin_campagin_custom_fields() + create_marketing_campaign_custom_fields() create_custom_company_links() add_all_roles_to("Administrator") create_default_success_action() @@ -119,16 +119,16 @@ def create_print_setting_custom_fields(): ) -def create_marketgin_campagin_custom_fields(): +def create_marketing_campaign_custom_fields(): create_custom_fields( { "UTM Campaign": [ { - "label": _("Messaging CRM Campagin"), + "label": _("Messaging CRM Campaign"), "fieldname": "crm_campaign", "fieldtype": "Link", "options": "Campaign", - "insert_after": "campaign_decription", + "insert_after": "campaign_description", }, ] } diff --git a/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py b/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py index df0b28f696e..7fb31928ac5 100644 --- a/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py +++ b/erpnext/stock/doctype/purchase_receipt/test_purchase_receipt.py @@ -1017,6 +1017,102 @@ class TestPurchaseReceipt(IntegrationTestCase): pr.cancel() + def test_lcv_for_internal_transfer(self): + from erpnext.stock.doctype.delivery_note.delivery_note import make_inter_company_purchase_receipt + from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note + from erpnext.stock.doctype.landed_cost_voucher.test_landed_cost_voucher import ( + make_landed_cost_voucher, + ) + + prepare_data_for_internal_transfer() + + customer = "_Test Internal Customer 2" + company = "_Test Company with perpetual inventory" + + item_code = make_item( + "Test Item For LCV in Internal Transfer", + {"has_batch_no": 1, "create_new_batch": 1, "batch_naming_series": "TEST-SBATCH.###"}, + ).name + + pr1 = make_purchase_receipt( + item_code=item_code, + qty=10, + rate=100, + warehouse="Stores - TCP1", + company="_Test Company with perpetual inventory", + ) + + dn1 = create_delivery_note( + item_code=pr1.items[0].item_code, + company=company, + customer=customer, + cost_center="Main - TCP1", + expense_account="Cost of Goods Sold - TCP1", + qty=10, + rate=500, + warehouse="Stores - TCP1", + target_warehouse="Work In Progress - TCP1", + ) + + pr = make_inter_company_purchase_receipt(dn1.name) + pr.items[0].from_warehouse = "Work In Progress - TCP1" + pr.items[0].warehouse = "Stores - TCP1" + pr.submit() + + sle_entries = frappe.get_all( + "Stock Ledger Entry", + filters={"voucher_type": "Purchase Receipt", "voucher_no": pr.name}, + fields=["serial_and_batch_bundle", "actual_qty"], + ) + self.assertEqual(len(sle_entries), 2) + + inward_sabb = frappe.get_all( + "Serial and Batch Bundle", + filters={ + "voucher_type": "Purchase Receipt", + "voucher_no": pr.name, + "total_qty": (">", 0), + "docstatus": 1, + }, + pluck="name", + ) + self.assertEqual(len(inward_sabb), 1) + + original_cost = frappe.db.get_value("Serial and Batch Bundle", inward_sabb[0], "total_amount") + + make_landed_cost_voucher( + company=pr.company, + receipt_document_type="Purchase Receipt", + receipt_document=pr.name, + charges=100, + distribute_charges_based_on="Qty", + expense_account="Expenses Included In Valuation - TCP1", + ) + + sle_entries = frappe.get_all( + "Stock Ledger Entry", + filters={"voucher_type": "Purchase Receipt", "voucher_no": pr.name, "is_cancelled": 0}, + fields=["serial_and_batch_bundle", "actual_qty"], + ) + self.assertEqual(len(sle_entries), 2) + + new_inward_sabb = frappe.get_all( + "Serial and Batch Bundle", + filters={ + "voucher_type": "Purchase Receipt", + "voucher_no": pr.name, + "total_qty": (">", 0), + "docstatus": 1, + }, + pluck="name", + ) + self.assertEqual(len(new_inward_sabb), 1) + + new_cost = frappe.db.get_value("Serial and Batch Bundle", new_inward_sabb[0], "total_amount") + self.assertEqual(new_cost, original_cost + 100) + + self.assertTrue(new_inward_sabb[0] == inward_sabb[0]) + def test_stock_transfer_from_purchase_receipt_with_valuation(self): from erpnext.stock.doctype.delivery_note.delivery_note import make_inter_company_purchase_receipt from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note diff --git a/erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py b/erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py index 6376f6b9f4e..f1b16da4b3e 100644 --- a/erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py +++ b/erpnext/stock/doctype/serial_and_batch_bundle/serial_and_batch_bundle.py @@ -17,6 +17,7 @@ from frappe.utils import ( cint, cstr, flt, + format_datetime, get_datetime, get_link_to_form, getdate, @@ -1459,22 +1460,33 @@ class SerialandBatchBundle(Document): if flt(available_qty, precision) < 0: self.throw_negative_batch(d.batch_no, available_qty, precision) - def throw_negative_batch(self, batch_no, available_qty, precision): + def throw_negative_batch(self, batch_no, available_qty, precision, posting_datetime=None): from erpnext.stock.stock_ledger import NegativeStockError if frappe.db.get_single_value("Stock Settings", "allow_negative_stock_for_batch"): return + date_msg = "" + if posting_datetime: + date_msg = " " + _("as of {0}").format(format_datetime(posting_datetime)) + + msg = _( + """ + The Batch {0} of an item {1} has negative stock in the warehouse {2}{3}. + Please add a stock quantity of {4} to proceed with this entry. + If it is not possible to make an adjustment entry, please enable 'Allow Negative Stock for Batch' in Stock Settings to proceed. + However, enabling this setting may lead to negative stock in the system. + So please ensure the stock levels are adjusted as soon as possible to maintain the correct valuation rate.""" + ).format( + bold(batch_no), + bold(self.item_code), + bold(self.warehouse), + date_msg, + bold(abs(flt(available_qty, precision))), + ) + frappe.throw( - _( - """ - The Batch {0} of an item {1} has negative stock in the warehouse {2}. Please add a stock quantity of {3} to proceed with this entry.""" - ).format( - bold(batch_no), - bold(self.item_code), - bold(self.warehouse), - bold(abs(flt(available_qty, precision))), - ), + msg, title=_("Negative Stock Error"), exc=NegativeStockError, ) @@ -1497,7 +1509,9 @@ class SerialandBatchBundle(Document): available_qty[row.batch_no] = flt(row.qty) if flt(available_qty[row.batch_no], precision) < 0: - self.throw_negative_batch(row.batch_no, available_qty[row.batch_no], precision) + self.throw_negative_batch( + row.batch_no, available_qty[row.batch_no], precision, row.posting_datetime + ) return available_qty @@ -1531,10 +1545,13 @@ class SerialandBatchBundle(Document): def get_available_qty_from_sabb(self): batches = [d.batch_no for d in self.entries if d.batch_no] + sle = frappe.qb.DocType("Stock Ledger Entry") child = frappe.qb.DocType("Serial and Batch Entry") query = ( frappe.qb.from_(child) + .inner_join(sle) + .on(child.parent == sle.serial_and_batch_bundle) .select( child.batch_no, child.qty, @@ -1543,6 +1560,7 @@ class SerialandBatchBundle(Document): ) .where( (child.item_code == self.item_code) + & (sle.is_cancelled == 0) & (child.warehouse == self.warehouse) & (child.is_cancelled == 0) & (child.batch_no.isin(batches)) @@ -1556,6 +1574,9 @@ class SerialandBatchBundle(Document): return query.run(as_dict=True) def validate_voucher_no_docstatus(self): + if self.is_cancelled: + return + if self.voucher_type == "POS Invoice": return diff --git a/erpnext/stock/doctype/stock_settings/stock_settings.json b/erpnext/stock/doctype/stock_settings/stock_settings.json index e3851b5b41f..a9f6d1904a3 100644 --- a/erpnext/stock/doctype/stock_settings/stock_settings.json +++ b/erpnext/stock/doctype/stock_settings/stock_settings.json @@ -550,7 +550,7 @@ }, { "default": "0", - "description": "If enabled, the system will allow negative stock entries for the batch, but this could calculate the valuation rate incorrectly, so avoid using this option.", + "description": "If enabled, the system will allow negative stock entries for the batch. But, this may lead to incorrect valuation rates, so it is recommended to avoid using this option. The system will permit negative stock only when it is caused by backdated entries and will validate and block negative stock in all other cases.", "fieldname": "allow_negative_stock_for_batch", "fieldtype": "Check", "label": "Allow Negative Stock for Batch" @@ -562,7 +562,7 @@ "index_web_pages_for_search": 1, "issingle": 1, "links": [], - "modified": "2026-02-09 15:01:12.466175", + "modified": "2026-02-16 10:36:59.921491", "modified_by": "Administrator", "module": "Stock", "name": "Stock Settings", diff --git a/erpnext/stock/report/incorrect_serial_and_batch_bundle/incorrect_serial_and_batch_bundle.json b/erpnext/stock/report/incorrect_serial_and_batch_bundle/incorrect_serial_and_batch_bundle.json index 11e6e4ea3d4..0833ab5eb3a 100644 --- a/erpnext/stock/report/incorrect_serial_and_batch_bundle/incorrect_serial_and_batch_bundle.json +++ b/erpnext/stock/report/incorrect_serial_and_batch_bundle/incorrect_serial_and_batch_bundle.json @@ -9,7 +9,7 @@ "idx": 0, "is_standard": "Yes", "json": "{}", - "letter_head": "Test", + "letter_head": null, "letterhead": null, "modified": "2025-02-03 15:39:47.613040", "modified_by": "Administrator", diff --git a/erpnext/stock/report/negative_batch_report/__init__.py b/erpnext/stock/report/negative_batch_report/__init__.py new file mode 100644 index 00000000000..e69de29bb2d diff --git a/erpnext/stock/report/negative_batch_report/negative_batch_report.js b/erpnext/stock/report/negative_batch_report/negative_batch_report.js new file mode 100644 index 00000000000..3bfe8fe9c85 --- /dev/null +++ b/erpnext/stock/report/negative_batch_report/negative_batch_report.js @@ -0,0 +1,41 @@ +// Copyright (c) 2026, Frappe Technologies Pvt. Ltd. and contributors +// For license information, please see license.txt + +frappe.query_reports["Negative Batch Report"] = { + filters: [ + { + fieldname: "company", + label: __("Company"), + fieldtype: "Link", + options: "Company", + default: frappe.defaults.get_default("company"), + }, + { + fieldname: "item_code", + label: __("Item Code"), + fieldtype: "Link", + options: "Item", + get_query: function () { + return { + filters: { + has_batch_no: 1, + }, + }; + }, + }, + { + fieldname: "warehouse", + label: __("Warehouse"), + fieldtype: "Link", + options: "Warehouse", + get_query: function () { + return { + filters: { + is_group: 0, + company: frappe.query_report.get_filter_value("company"), + }, + }; + }, + }, + ], +}; diff --git a/erpnext/stock/report/negative_batch_report/negative_batch_report.json b/erpnext/stock/report/negative_batch_report/negative_batch_report.json new file mode 100644 index 00000000000..cecc5716055 --- /dev/null +++ b/erpnext/stock/report/negative_batch_report/negative_batch_report.json @@ -0,0 +1,53 @@ +{ + "add_total_row": 0, + "add_translate_data": 0, + "columns": [], + "creation": "2026-02-17 11:34:21.549485", + "disabled": 0, + "docstatus": 0, + "doctype": "Report", + "filters": [], + "idx": 0, + "is_standard": "Yes", + "json": "", + "letter_head": null, + "modified": "2026-02-17 11:34:59.106045", + "modified_by": "Administrator", + "module": "Stock", + "name": "Negative Batch Report", + "owner": "Administrator", + "prepared_report": 0, + "ref_doctype": "Serial and Batch Bundle", + "report_name": "Negative Batch Report", + "report_type": "Script Report", + "roles": [ + { + "role": "System Manager" + }, + { + "role": "Purchase User" + }, + { + "role": "Purchase Manager" + }, + { + "role": "Stock User" + }, + { + "role": "Stock Manager" + }, + { + "role": "Delivery User" + }, + { + "role": "Delivery Manager" + }, + { + "role": "Manufacturing User" + }, + { + "role": "Manufacturing Manager" + } + ], + "timeout": 0 +} diff --git a/erpnext/stock/report/negative_batch_report/negative_batch_report.py b/erpnext/stock/report/negative_batch_report/negative_batch_report.py new file mode 100644 index 00000000000..b12bd87d538 --- /dev/null +++ b/erpnext/stock/report/negative_batch_report/negative_batch_report.py @@ -0,0 +1,145 @@ +# Copyright (c) 2026, Frappe Technologies Pvt. Ltd. and contributors +# For license information, please see license.txt + +import frappe +from frappe import _ +from frappe.utils import add_to_date, flt, today + +from erpnext.stock.report.stock_ledger.stock_ledger import execute as stock_ledger_execute + + +def execute(filters: dict | None = None): + """Return columns and data for the report. + + This is the main entry point for the report. It accepts the filters as a + dictionary and should return columns and data. It is called by the framework + every time the report is refreshed or a filter is updated. + """ + columns = get_columns() + data = get_data(filters) + + return columns, data + + +def get_columns() -> list[dict]: + return [ + { + "label": _("Posting Datetime"), + "fieldname": "posting_date", + "fieldtype": "Datetime", + "width": 160, + }, + { + "label": _("Batch No"), + "fieldname": "batch_no", + "fieldtype": "Link", + "options": "Batch", + "width": 120, + }, + { + "label": _("Item Code"), + "fieldname": "item_code", + "fieldtype": "Link", + "options": "Item", + "width": 150, + }, + { + "label": _("Warehouse"), + "fieldname": "warehouse", + "fieldtype": "Link", + "options": "Warehouse", + "width": 160, + }, + { + "label": _("Previous Qty"), + "fieldname": "previous_qty", + "fieldtype": "Float", + "width": 130, + }, + { + "label": _("Transaction Qty"), + "fieldname": "actual_qty", + "fieldtype": "Float", + "width": 130, + }, + { + "label": _("Qty After Transaction"), + "fieldname": "qty_after_transaction", + "fieldtype": "Float", + "width": 180, + }, + { + "label": _("Document Type"), + "fieldname": "voucher_type", + "fieldtype": "Data", + "width": 130, + }, + { + "label": _("Document No"), + "fieldname": "voucher_no", + "fieldtype": "Dynamic Link", + "options": "voucher_type", + "width": 130, + }, + ] + + +def get_data(filters) -> list[dict]: + batches = get_batches(filters) + companies = get_companies(filters) + batch_negative_data = [] + + flt_precision = frappe.db.get_default("float_precision") or 2 + for company in companies: + for batch in batches: + _c, data = stock_ledger_execute( + frappe._dict( + { + "company": company, + "batch_no": batch, + "from_date": add_to_date(today(), years=-12), + "to_date": today(), + "segregate_serial_batch_bundle": 1, + "warehouse": filters.get("warehouse"), + "valuation_field_type": "Currency", + } + ) + ) + + previous_qty = 0 + for row in data: + if flt(row.get("qty_after_transaction"), flt_precision) < 0: + batch_negative_data.append( + { + "posting_date": row.get("date"), + "batch_no": row.get("batch_no"), + "item_code": row.get("item_code"), + "item_name": row.get("item_name"), + "warehouse": row.get("warehouse"), + "actual_qty": row.get("actual_qty"), + "qty_after_transaction": row.get("qty_after_transaction"), + "previous_qty": previous_qty, + "voucher_type": row.get("voucher_type"), + "voucher_no": row.get("voucher_no"), + } + ) + + previous_qty = row.get("qty_after_transaction") + + return batch_negative_data + + +def get_batches(filters): + batch_filters = {} + if filters.get("item_code"): + batch_filters["item"] = filters["item_code"] + + return frappe.get_all("Batch", pluck="name", filters=batch_filters) + + +def get_companies(filters): + company_filters = {} + if filters.get("company"): + company_filters["name"] = filters["company"] + + return frappe.get_all("Company", pluck="name", filters=company_filters) diff --git a/erpnext/workspace_sidebar/invoicing.json b/erpnext/workspace_sidebar/invoicing.json index 9a80f8237a6..99a6b367953 100644 --- a/erpnext/workspace_sidebar/invoicing.json +++ b/erpnext/workspace_sidebar/invoicing.json @@ -314,7 +314,7 @@ "type": "Link" } ], - "modified": "2026-01-27 21:23:15.665712", + "modified": "2026-01-26 21:23:15.665712", "modified_by": "Administrator", "module": "Accounts", "name": "Invoicing", diff --git a/erpnext/workspace_sidebar/selling.json b/erpnext/workspace_sidebar/selling.json index 3ac2dc8665c..6b5b9707fe7 100644 --- a/erpnext/workspace_sidebar/selling.json +++ b/erpnext/workspace_sidebar/selling.json @@ -89,6 +89,17 @@ "show_arrow": 0, "type": "Link" }, + { + "child": 1, + "collapsible": 1, + "indent": 0, + "keep_closed": 0, + "label": "POS Profile", + "link_to": "POS Profile", + "link_type": "DocType", + "show_arrow": 0, + "type": "Link" + }, { "child": 1, "collapsible": 1, @@ -122,17 +133,6 @@ "show_arrow": 0, "type": "Link" }, - { - "child": 1, - "collapsible": 1, - "indent": 0, - "keep_closed": 0, - "label": "POS Profile", - "link_to": "POS Profile", - "link_type": "DocType", - "show_arrow": 0, - "type": "Link" - }, { "child": 1, "collapsible": 1, @@ -687,7 +687,7 @@ "type": "Link" } ], - "modified": "2026-01-10 00:06:13.103140", + "modified": "2026-02-16 23:48:24.611112", "modified_by": "Administrator", "module": "Selling", "name": "Selling",