feat: consider carry forwarded leaves on creation of encashment
diff --git a/erpnext/hr/doctype/leave_allocation/leave_allocation.js b/erpnext/hr/doctype/leave_allocation/leave_allocation.js
index 8c910a2..210a73c 100755
--- a/erpnext/hr/doctype/leave_allocation/leave_allocation.js
+++ b/erpnext/hr/doctype/leave_allocation/leave_allocation.js
@@ -63,14 +63,14 @@
 		frm.trigger("calculate_total_leaves_allocated");
 	},
 
-	carry_forwarded_leaves: function(frm) {
+	unused_leaves: function(frm) {
 		frm.set_value("total_leaves_allocated",
-			flt(frm.doc.carry_forwarded_leaves) + flt(frm.doc.new_leaves_allocated));
+			flt(frm.doc.unused_leaves) + flt(frm.doc.new_leaves_allocated));
 	},
 
 	new_leaves_allocated: function(frm) {
 		frm.set_value("total_leaves_allocated",
-			flt(frm.doc.carry_forwarded_leaves) + flt(frm.doc.new_leaves_allocated));
+			flt(frm.doc.unused_leaves) + flt(frm.doc.new_leaves_allocated));
 	},
 
 	leave_policy: function(frm) {
@@ -93,7 +93,7 @@
 				}
 			})
 		} else if (cint(frm.doc.carry_forward) == 0) {
-			frm.set_value("carry_forwarded_leaves", 0);
+			frm.set_value("unused_leaves", 0);
 			frm.set_value("total_leaves_allocated", flt(frm.doc.new_leaves_allocated));
 		}
 	}
diff --git a/erpnext/hr/doctype/leave_allocation/leave_allocation.json b/erpnext/hr/doctype/leave_allocation/leave_allocation.json
index 1618c67..007497e 100644
--- a/erpnext/hr/doctype/leave_allocation/leave_allocation.json
+++ b/erpnext/hr/doctype/leave_allocation/leave_allocation.json
@@ -17,13 +17,14 @@
   "section_break_6",
   "new_leaves_allocated",
   "carry_forward",
-  "carry_forwarded_leaves",
+  "unused_leaves",
   "total_leaves_allocated",
   "total_leaves_encashed",
   "column_break_10",
   "compensatory_request",
   "leave_period",
   "leave_policy",
+  "carry_forwarded_leaves_count",
   "expired",
   "amended_from",
   "notes",
@@ -119,7 +120,7 @@
   },
   {
    "depends_on": "carry_forward",
-   "fieldname": "carry_forwarded_leaves",
+   "fieldname": "unused_leaves",
    "fieldtype": "Float",
    "label": "Unused leaves",
    "read_only": 1
@@ -168,6 +169,15 @@
    "read_only": 1
   },
   {
+   "default": "0",
+   "fieldname": "expired",
+   "fieldtype": "Check",
+   "hidden": 1,
+   "in_standard_filter": 1,
+   "label": "Expired",
+   "read_only": 1
+  },
+  {
    "fieldname": "amended_from",
    "fieldtype": "Link",
    "ignore_user_permissions": 1,
@@ -194,19 +204,17 @@
    "width": "300px"
   },
   {
-   "default": "0",
-   "fieldname": "expired",
-   "fieldtype": "Check",
-   "hidden": 1,
-   "in_standard_filter": 1,
-   "label": "Expired",
+   "depends_on": "carry_forwarded_leaves_count",
+   "fieldname": "carry_forwarded_leaves_count",
+   "fieldtype": "Float",
+   "label": "Carry Forwarded Leaves",
    "read_only": 1
   }
  ],
  "icon": "fa fa-ok",
  "idx": 1,
  "is_submittable": 1,
- "modified": "2019-07-22 17:50:39.591195",
+ "modified": "2019-08-08 15:08:42.440909",
  "modified_by": "Administrator",
  "module": "HR",
  "name": "Leave Allocation",
diff --git a/erpnext/hr/doctype/leave_allocation/leave_allocation.py b/erpnext/hr/doctype/leave_allocation/leave_allocation.py
index 2374e46..5e81999 100755
--- a/erpnext/hr/doctype/leave_allocation/leave_allocation.py
+++ b/erpnext/hr/doctype/leave_allocation/leave_allocation.py
@@ -50,6 +50,8 @@
 
 	def on_cancel(self):
 		self.create_leave_ledger_entry(submit=False)
+		if self.carry_forward:
+			self.set_carry_forwarded_leaves_in_previous_allocation(on_cancel=True)
 
 	def validate_period(self):
 		if date_diff(self.to_date, self.from_date) <= 0:
@@ -89,24 +91,33 @@
 					BackDatedAllocationError)
 
 	def set_total_leaves_allocated(self):
-		self.carry_forwarded_leaves = get_carry_forwarded_leaves(self.employee,
+		self.unused_leaves = get_carry_forwarded_leaves(self.employee,
 			self.leave_type, self.from_date, self.carry_forward)
 
-		self.total_leaves_allocated = flt(self.carry_forwarded_leaves) + flt(self.new_leaves_allocated)
-		self.maintain_carry_forwarded_leaves()
+		self.total_leaves_allocated = flt(self.unused_leaves) + flt(self.new_leaves_allocated)
+
+		if self.carry_forward:
+			self.maintain_carry_forwarded_leaves()
+			self.set_carry_forwarded_leaves_in_previous_allocation()
 
 		if not self.total_leaves_allocated and not frappe.db.get_value("Leave Type", self.leave_type, "is_earned_leave") and not frappe.db.get_value("Leave Type", self.leave_type, "is_compensatory"):
-			frappe.throw(_("Total leaves allocated is mandatory for Leave Type {0}".format(self.leave_type)))
+			frappe.throw(_("Total leaves allocated is mandatory for Leave Type {0}").format(self.leave_type))
 
 	def maintain_carry_forwarded_leaves(self):
-		''' reduce the carry forwarded leaves to be within the maximum allowed leaves '''
-		if not self.carry_forward:
-			return
+		''' Reduce the carry forwarded leaves to be within the maximum allowed leaves '''
+		
 		max_leaves_allowed = frappe.db.get_value("Leave Type", self.leave_type, "max_leaves_allowed")
 		if self.new_leaves_allocated <= max_leaves_allowed <= self.total_leaves_allocated:
-			self.carry_forwarded_leaves = max_leaves_allowed - flt(self.new_leaves_allocated)
+			self.unused_leaves = max_leaves_allowed - flt(self.new_leaves_allocated)
 			self.total_leaves_allocated = flt(max_leaves_allowed)
 
+	def set_carry_forwarded_leaves_in_previous_allocation(self, on_cancel=False):
+		''' Set carry forwarded leaves in previous allocation '''
+		previous_allocation = get_previous_allocation(self.from_date, self.leave_type, self.employee)
+		if on_cancel:
+			self.unused_leaves = 0.0
+		frappe.db.set_value("Leave Allocation", previous_allocation.name, 'carry_forwarded_leaves_count', self.unused_leaves)
+
 	def validate_total_leaves_allocated(self):
 		# Adding a day to include To Date in the difference
 		date_difference = date_diff(self.to_date, self.from_date) + 1
@@ -114,10 +125,10 @@
 			frappe.throw(_("Total allocated leaves are more than days in the period"), OverAllocationError)
 
 	def create_leave_ledger_entry(self, submit=True):
-		if self.carry_forwarded_leaves:
+		if self.unused_leaves:
 			expiry_days = frappe.db.get_value("Leave Type", self.leave_type, "expire_carried_forward_leaves")
 			args = dict(
-				leaves=self.carry_forwarded_leaves,
+				leaves=self.unused_leaves,
 				from_date=self.from_date,
 				to_date=add_days(self.from_date, expiry_days - 1) if expiry_days else self.to_date,
 				is_carry_forward=1
@@ -142,7 +153,7 @@
 			'docstatus': 1
 		},
 		order_by='to_date DESC',
-		fieldname=['name', 'from_date', 'to_date'], as_dict=1)
+		fieldname=['name', 'from_date', 'to_date', 'employee', 'leave_type'], as_dict=1)
 
 def get_leave_allocation_for_period(employee, leave_type, from_date, to_date):
 	leave_allocated = 0
@@ -170,13 +181,13 @@
 @frappe.whitelist()
 def get_carry_forwarded_leaves(employee, leave_type, date, carry_forward=None):
 	''' Returns carry forwarded leaves for the given employee '''
-	carry_forwarded_leaves = 0.0
+	unused_leaves = 0.0
 	previous_allocation = get_previous_allocation(date, leave_type, employee)
 	if carry_forward and previous_allocation:
 		validate_carry_forward(leave_type)
-		carry_forwarded_leaves = get_unused_leaves(employee, leave_type, previous_allocation.from_date, previous_allocation.to_date)
+		unused_leaves = get_unused_leaves(employee, leave_type, previous_allocation.from_date, previous_allocation.to_date)
 
-	return carry_forwarded_leaves
+	return unused_leaves
 
 def get_unused_leaves(employee, leave_type, from_date, to_date):
 	''' Returns unused leaves between the given period while skipping leave allocation expiry '''
diff --git a/erpnext/hr/doctype/leave_encashment/leave_encashment.py b/erpnext/hr/doctype/leave_encashment/leave_encashment.py
index 30529b6..42f0179 100644
--- a/erpnext/hr/doctype/leave_encashment/leave_encashment.py
+++ b/erpnext/hr/doctype/leave_encashment/leave_encashment.py
@@ -64,7 +64,8 @@
 
 		allocation = self.get_leave_allocation()
 
-		self.leave_balance = allocation.total_leaves_allocated - get_unused_leaves(self.employee, self.leave_type, allocation.from_date, self.encashment_date)
+		self.leave_balance = allocation.total_leaves_allocated - allocation.carry_forwarded_leaves_count\
+			- get_unused_leaves(self.employee, self.leave_type, allocation.from_date, self.encashment_date)
 
 		encashable_days = self.leave_balance - frappe.db.get_value('Leave Type', self.leave_type, 'encashment_threshold_days')
 		self.encashable_days = encashable_days if encashable_days > 0 else 0
@@ -76,9 +77,9 @@
 		return True
 
 	def get_leave_allocation(self):
-		leave_allocation = frappe.db.sql("""select name, to_date, total_leaves_allocated from `tabLeave Allocation` where '{0}'
+		leave_allocation = frappe.db.sql("""select name, to_date, total_leaves_allocated, carry_forwarded_leaves_count from `tabLeave Allocation` where '{0}'
 		between from_date and to_date and docstatus=1 and leave_type='{1}'
-		and employee= '{2}'""".format(self.encashment_date or getdate(nowdate()), self.leave_type, self.employee), as_dict=1)
+		and employee= '{2}'""".format(self.encashment_date or getdate(nowdate()), self.leave_type, self.employee), as_dict=1) #nosec
 
 		return leave_allocation[0] if leave_allocation else None
 
diff --git a/erpnext/hr/doctype/leave_ledger_entry/leave_ledger_entry.py b/erpnext/hr/doctype/leave_ledger_entry/leave_ledger_entry.py
index 8fca241..33e4ea0 100644
--- a/erpnext/hr/doctype/leave_ledger_entry/leave_ledger_entry.py
+++ b/erpnext/hr/doctype/leave_ledger_entry/leave_ledger_entry.py
@@ -104,7 +104,7 @@
 				`transaction_type`='Leave Allocation'
 				AND `is_expired`=1""")
 
-		expire_allocation = frappe.get_all("Leave Ledger Entry", 
+		expire_allocation = frappe.get_all("Leave Ledger Entry",
 			fields=['leaves', 'to_date', 'employee', 'leave_type', 'is_carry_forward', 'transaction_name as name', 'transaction_type'],
 			filters={
 				'to_date': ("<", today()),
@@ -119,9 +119,9 @@
 	if expire_allocation:
 		create_expiry_ledger_entry(expire_allocation)
 
-def create_expiry_ledger_entry(expire_allocation):
+def create_expiry_ledger_entry(allocations):
 	''' Create ledger entry for expired allocation '''
-	for allocation in expire_allocation:
+	for allocation in allocations:
 		if allocation.is_carry_forward:
 			expire_carried_forward_allocation(allocation)
 		else:
@@ -138,7 +138,7 @@
 
 @frappe.whitelist()
 def expire_allocation(allocation, expiry_date=None):
-	''' expires allocation '''
+	''' expires non-carry forwarded allocation '''
 	leaves = get_remaining_leaves(allocation)
 	expiry_date = expiry_date if expiry_date else allocation.to_date
 
@@ -146,6 +146,7 @@
 		args = dict(
 			leaves=flt(leaves) * -1,
 			transaction_name=allocation.name,
+			transaction_type='Leave Allocation',
 			from_date=expiry_date,
 			to_date=expiry_date,
 			is_carry_forward=0,
diff --git a/erpnext/hr/doctype/leave_period/leave_period.py b/erpnext/hr/doctype/leave_period/leave_period.py
index 7b0f882..a7de718 100644
--- a/erpnext/hr/doctype/leave_period/leave_period.py
+++ b/erpnext/hr/doctype/leave_period/leave_period.py
@@ -22,7 +22,7 @@
 
 		condition_str = " and " + " and ".join(conditions) if len(conditions) else ""
 
-		employees = frappe._dict(frappe.db.sql("select name, date_of_joining from tabEmployee where status='Active' {condition}"
+		employees = frappe._dict(frappe.db.sql("select name, date_of_joining from tabEmployee where status='Active' {condition}" #nosec
 			.format(condition=condition_str), tuple(values)))
 
 		return employees
diff --git a/erpnext/hr/utils.py b/erpnext/hr/utils.py
index bf09de8..4fe9f6b 100644
--- a/erpnext/hr/utils.py
+++ b/erpnext/hr/utils.py
@@ -318,7 +318,7 @@
 	''' Create leave ledger entry based on the earned leave frequency '''
 	allocation.new_leaves_allocated = earned_leaves
 	allocation.from_date = date
-	allocation.carry_forwarded_leaves = 0
+	allocation.unused_leaves = 0
 	allocation.create_leave_ledger_entry()
 
 def check_frequency_hit(from_date, to_date, frequency):
diff --git a/erpnext/patches/v12_0/generate_leave_ledger_entries.py b/erpnext/patches/v12_0/generate_leave_ledger_entries.py
index 7dfdcc1..c1e1b4f 100644
--- a/erpnext/patches/v12_0/generate_leave_ledger_entries.py
+++ b/erpnext/patches/v12_0/generate_leave_ledger_entries.py
@@ -13,11 +13,22 @@
 	if frappe.db.a_row_exists("Leave Ledger Entry"):
 		return
 
+	if not frappe.get_meta("Leave Allocation").has_field("unused_leaves"):
+		frappe.reload_doc("HR", "doctype", "Leave Allocation")
+		update_leave_allocation_fieldname()
+
 	generate_allocation_ledger_entries()
 	generate_application_leave_ledger_entries()
 	generate_encashment_leave_ledger_entries()
 	generate_expiry_allocation_ledger_entries()
 
+def update_leave_allocation_fieldname():
+	''' maps data from old field to the new field '''
+	frappe.db.sql("""
+		UPDATE `tabLeave Allocation`
+		SET `unused_leaves` = `carry_forwarded_leaves`
+	""")
+
 def generate_allocation_ledger_entries():
 	''' fix ledger entries for missing leave allocation transaction '''
 	allocation_list = get_allocation_records()
@@ -64,7 +75,7 @@
 			employee,
 			leave_type,
 			new_leaves_allocated,
-			carry_forwarded_leaves,
+			unused_leaves,
 			from_date,
 			to_date,
 			carry_forward