feat: Backdated leave application  (#20201)

* fix: only HR Managers can make backdated leave applications

* fix (leave application): error message changed and user check modified

* fix: Move hardcoded logic to HR Settings

* fix: added role as mandetory field on check restict field

* fix: minor changes
diff --git a/erpnext/hr/doctype/hr_settings/hr_settings.js b/erpnext/hr/doctype/hr_settings/hr_settings.js
index 4004c1c..2e8c99f 100644
--- a/erpnext/hr/doctype/hr_settings/hr_settings.js
+++ b/erpnext/hr/doctype/hr_settings/hr_settings.js
@@ -19,5 +19,6 @@
 			}
 			frm.set_value('password_policy', policy.split(new RegExp(" |-", 'g')).filter((token) => token).join('-'));
 		}
+		frm.toggle_reqd("role_allowed_to_create_backdated_leave_application", frm.doc.restrict_backdated_leave_application);
 	}
-});
+});
\ No newline at end of file
diff --git a/erpnext/hr/doctype/hr_settings/hr_settings.json b/erpnext/hr/doctype/hr_settings/hr_settings.json
index 6cb0e21..90f4988 100644
--- a/erpnext/hr/doctype/hr_settings/hr_settings.json
+++ b/erpnext/hr/doctype/hr_settings/hr_settings.json
@@ -23,10 +23,12 @@
   "leave_settings",
   "leave_approval_notification_template",
   "leave_status_notification_template",
+  "role_allowed_to_create_backdated_leave_application",
   "column_break_18",
   "leave_approver_mandatory_in_leave_application",
   "show_leaves_of_all_department_members_in_calendar",
   "auto_leave_encashment",
+  "restrict_backdated_leave_application",
   "hiring_settings",
   "check_vacancies"
  ],
@@ -169,13 +171,26 @@
    "fieldname": "disable_rounded_total",
    "fieldtype": "Check",
    "label": "Disable Rounded Total"
+  },
+  {
+   "default": "0",
+   "fieldname": "restrict_backdated_leave_application",
+   "fieldtype": "Check",
+   "label": "Restrict Backdated Leave Application"
+  },
+  {
+   "depends_on": "eval:doc.restrict_backdated_leave_application == 1",
+   "fieldname": "role_allowed_to_create_backdated_leave_application",
+   "fieldtype": "Link",
+   "label": "Role Allowed to Create Backdated Leave Application",
+   "options": "Role"
   }
  ],
  "icon": "fa fa-cog",
  "idx": 1,
  "issingle": 1,
  "links": [],
- "modified": "2019-12-31 14:28:32.004121",
+ "modified": "2020-01-06 18:46:30.189815",
  "modified_by": "Administrator",
  "module": "HR",
  "name": "HR Settings",
diff --git a/erpnext/hr/doctype/leave_application/leave_application.py b/erpnext/hr/doctype/leave_application/leave_application.py
index 5222712..7594cb7 100755
--- a/erpnext/hr/doctype/leave_application/leave_application.py
+++ b/erpnext/hr/doctype/leave_application/leave_application.py
@@ -79,6 +79,12 @@
 						frappe.throw(_("{0} applicable after {1} working days").format(self.leave_type, leave_type.applicable_after))
 
 	def validate_dates(self):
+		if frappe.db.get_single_value("HR Settings", "restrict_backdated_leave_application"):
+			if self.from_date and self.from_date < frappe.utils.today():
+				allowed_role = frappe.db.get_single_value("HR Settings", "role_allowed_to_create_backdated_leave_application")
+				if allowed_role not in frappe.get_roles():
+					frappe.throw(_("Only users with the {0} role can create backdated leave applications").format(allowed_role))
+
 		if self.from_date and self.to_date and (getdate(self.to_date) < getdate(self.from_date)):
 			frappe.throw(_("To date cannot be before from date"))