diff --git a/erpnext/accounts/doctype/budget/budget.js b/erpnext/accounts/doctype/budget/budget.js index d3931dec3db..1186b60ab11 100644 --- a/erpnext/accounts/doctype/budget/budget.js +++ b/erpnext/accounts/doctype/budget/budget.js @@ -32,6 +32,16 @@ frappe.ui.form.on("Budget", { refresh: function (frm) { frm.trigger("toggle_reqd_fields"); + + if (!frm.doc.__islocal && frm.doc.docstatus == 1) { + frm.add_custom_button( + __("Revise Budget"), + function () { + frm.events.revise_budget_action(frm); + }, + __("Actions") + ); + } }, budget_against: function (frm) { @@ -51,4 +61,27 @@ frappe.ui.form.on("Budget", { frm.toggle_reqd("cost_center", frm.doc.budget_against == "Cost Center"); frm.toggle_reqd("project", frm.doc.budget_against == "Project"); }, + + revise_budget_action: function (frm) { + frappe.confirm( + __( + "Are you sure you want to revise this budget? The current budget will be cancelled and a new draft will be created." + ), + function () { + frappe.call({ + method: "erpnext.accounts.doctype.budget.budget.revise_budget", + args: { budget_name: frm.doc.name }, + callback: function (r) { + if (r.message) { + frappe.msgprint(__("New revised budget created successfully")); + frappe.set_route("Form", "Budget", r.message); + } + }, + }); + }, + function () { + frappe.msgprint(__("Revision cancelled")); + } + ); + }, }); diff --git a/erpnext/accounts/doctype/budget/budget.json b/erpnext/accounts/doctype/budget/budget.json index 01953359c37..fdf5b74c477 100644 --- a/erpnext/accounts/doctype/budget/budget.json +++ b/erpnext/accounts/doctype/budget/budget.json @@ -45,7 +45,9 @@ "column_break_ybiq", "total_budget_amount", "section_break_fpdt", - "budget_distribution" + "budget_distribution", + "section_break_kkan", + "revision_of" ], "fields": [ { @@ -313,13 +315,23 @@ "fieldname": "budget_amount", "fieldtype": "Currency", "label": "Budget Amount" + }, + { + "fieldname": "section_break_kkan", + "fieldtype": "Section Break" + }, + { + "fieldname": "revision_of", + "fieldtype": "Data", + "label": "Revision Of", + "read_only": 1 } ], "grid_page_length": 50, "index_web_pages_for_search": 1, "is_submittable": 1, "links": [], - "modified": "2025-10-15 02:29:23.201493", + "modified": "2025-10-15 16:55:25.157976", "modified_by": "Administrator", "module": "Accounts", "name": "Budget", diff --git a/erpnext/accounts/doctype/budget/budget.py b/erpnext/accounts/doctype/budget/budget.py index df9ec661423..ed0348c7480 100644 --- a/erpnext/accounts/doctype/budget/budget.py +++ b/erpnext/accounts/doctype/budget/budget.py @@ -64,6 +64,7 @@ class Budget(Document): monthly_distribution: DF.Link | None naming_series: DF.Literal["BUDGET-.YYYY.-"] project: DF.Link | None + revision_of: DF.Data | None total_budget_amount: DF.Currency # end: auto-generated types @@ -159,6 +160,9 @@ class Budget(Document): self.allocate_budget() def allocate_budget(self): + if self.revision_of: + return + self.set("budget_distribution", []) if not (self.budget_start_date and self.budget_end_date and self.allocation_frequency): return @@ -167,7 +171,7 @@ class Budget(Document): end = getdate(self.budget_end_date) freq = self.allocation_frequency - months = month_diff(end, start) + 1 + months = month_diff(end, start) if freq == "Monthly": total_periods = months elif freq == "Quarterly": @@ -652,3 +656,20 @@ def get_expense_cost_center(doctype, args): return frappe.db.get_value( doctype, args.get(frappe.scrub(doctype)), ["cost_center", "default_expense_account"] ) + + +@frappe.whitelist() +def revise_budget(budget_name): + old_budget = frappe.get_doc("Budget", budget_name) + + if old_budget.docstatus == 1: + old_budget.cancel() + frappe.db.commit() + + new_budget = frappe.copy_doc(old_budget) + new_budget.docstatus = 0 + new_budget.revision_of = old_budget.name + new_budget.posting_date = frappe.utils.nowdate() + new_budget.insert() + + return new_budget.name diff --git a/erpnext/accounts/doctype/budget_distribution/budget_distribution.json b/erpnext/accounts/doctype/budget_distribution/budget_distribution.json index 5c633fa392b..7602956e0c6 100644 --- a/erpnext/accounts/doctype/budget_distribution/budget_distribution.json +++ b/erpnext/accounts/doctype/budget_distribution/budget_distribution.json @@ -29,20 +29,22 @@ "fieldname": "amount", "fieldtype": "Currency", "in_list_view": 1, - "label": "Amount" + "label": "Amount", + "read_only_depends_on": "eval:doc.end_date < frappe.datetime.get_today()" }, { "fieldname": "percent", "fieldtype": "Percent", "in_list_view": 1, - "label": "Percent" + "label": "Percent", + "read_only_depends_on": "eval:doc.end_date < frappe.datetime.get_today()" } ], "grid_page_length": 50, "index_web_pages_for_search": 1, "istable": 1, "links": [], - "modified": "2025-10-12 23:47:30.393908", + "modified": "2025-10-15 16:53:23.462653", "modified_by": "Administrator", "module": "Accounts", "name": "Budget Distribution",