stock recon for serial no, batch no
diff --git a/erpnext/stock/doctype/serial_no/serial_no.py b/erpnext/stock/doctype/serial_no/serial_no.py
index c1aef95..b91fddf 100644
--- a/erpnext/stock/doctype/serial_no/serial_no.py
+++ b/erpnext/stock/doctype/serial_no/serial_no.py
@@ -222,7 +222,7 @@
 						frappe.throw(_("Serial No {0} has already been received").format(serial_no),
 							SerialNoDuplicateError)
 
-					if (sr.delivery_document_no and sle.voucher_type != 'Stock Entry'
+					if (sr.delivery_document_no and sle.voucher_type not in ['Stock Entry', 'Stock Reconciliation']
 						and sle.voucher_type == sr.delivery_document_type):
 						return_against = frappe.db.get_value(sle.voucher_type, sle.voucher_no, 'return_against')
 						if return_against and return_against != sr.delivery_document_no:
diff --git a/erpnext/stock/doctype/stock_ledger_entry/stock_ledger_entry.py b/erpnext/stock/doctype/stock_ledger_entry/stock_ledger_entry.py
index 79da70e..5fe89d6 100644
--- a/erpnext/stock/doctype/stock_ledger_entry/stock_ledger_entry.py
+++ b/erpnext/stock/doctype/stock_ledger_entry/stock_ledger_entry.py
@@ -38,7 +38,7 @@
 		self.check_stock_frozen_date()
 		self.actual_amt_check()
 
-		if not self.get("via_landed_cost_voucher") and self.voucher_type != 'Stock Reconciliation':
+		if not self.get("via_landed_cost_voucher"):
 			from erpnext.stock.doctype.serial_no.serial_no import process_serial_no
 			process_serial_no(self)
 
diff --git a/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.js b/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.js
index ed9d770..818a671 100644
--- a/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.js
+++ b/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.js
@@ -12,8 +12,7 @@
 			return {
 				query: "erpnext.controllers.queries.item_query",
 				filters:{
-					"is_stock_item": 1,
-					"has_serial_no": 0
+					"is_stock_item": 1
 				}
 			}
 		});
@@ -93,7 +92,7 @@
 					frappe.model.set_value(cdt, cdn, "current_valuation_rate", r.message.rate);
 					frappe.model.set_value(cdt, cdn, "current_amount", r.message.rate * r.message.qty);
 					frappe.model.set_value(cdt, cdn, "amount", r.message.rate * r.message.qty);
-
+					frappe.model.set_value(cdt, cdn, "current_serial_no", r.message.serial_nos);
 				}
 			});
 		}
diff --git a/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.py b/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.py
index 205beed..b1abe89 100644
--- a/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.py
+++ b/erpnext/stock/doctype/stock_reconciliation/stock_reconciliation.py
@@ -9,7 +9,8 @@
 from erpnext.stock.stock_ledger import update_entries_after
 from erpnext.controllers.stock_controller import StockController
 from erpnext.accounts.utils import get_company_default
-from erpnext.stock.utils import get_stock_balance
+from erpnext.stock.doctype.serial_no.serial_no import get_serial_nos
+from erpnext.stock.utils import get_stock_balance, get_incoming_rate, get_available_serial_nos
 
 class OpeningEntryAccountError(frappe.ValidationError): pass
 class EmptyStockReconciliationItemsError(frappe.ValidationError): pass
@@ -42,23 +43,28 @@
 		"""Remove items if qty or rate is not changed"""
 		self.difference_amount = 0.0
 		def _changed(item):
-			qty, rate = get_stock_balance(item.item_code, item.warehouse,
-					self.posting_date, self.posting_time, with_valuation_rate=True)
-			if (item.qty==None or item.qty==qty) and (item.valuation_rate==None or item.valuation_rate==rate):
+			item_dict = get_stock_balance_for(item.item_code, item.warehouse,
+				self.posting_date, self.posting_time)
+
+			if ((item.qty==None or item.qty==item_dict.get("qty"))
+				and (item.valuation_rate==None or item.valuation_rate==item_dict.get("rate"))):
 				return False
 			else:
 				# set default as current rates
 				if item.qty==None:
-					item.qty = qty
+					item.qty = item_dict.get("qty")
 
 				if item.valuation_rate==None:
-					item.valuation_rate = rate
+					item.valuation_rate = item_dict.get("rate")
 
-				item.current_qty = qty
-				item.current_valuation_rate = rate
+				if item_dict.get("serial_nos"):
+					item.current_serial_no = item_dict.get("serial_nos")
+
+				item.current_qty = item_dict.get("qty")
+				item.current_valuation_rate = item_dict.get("rate")
 				self.difference_amount += (flt(item.qty, item.precision("qty")) * \
 					flt(item.valuation_rate or rate, item.precision("valuation_rate")) \
-					- flt(qty, item.precision("qty")) * flt(rate, item.precision("valuation_rate")))
+					- flt(item_dict.get("qty"), item.precision("qty")) * flt(item_dict.get("rate"), item.precision("valuation_rate")))
 				return True
 
 		items = list(filter(lambda d: _changed(d), self.items))
@@ -89,7 +95,7 @@
 			else:
 				item_warehouse_combinations.append([row.item_code, row.warehouse])
 
-			self.validate_item(row.item_code, row_num+1)
+			self.validate_item(row.item_code, row)
 
 			# validate warehouse
 			if not frappe.db.get_value("Warehouse", row.warehouse):
@@ -131,7 +137,7 @@
 
 			raise frappe.ValidationError(self.validation_messages)
 
-	def validate_item(self, item_code, row_num):
+	def validate_item(self, item_code, row):
 		from erpnext.stock.doctype.item.item import validate_end_of_life, \
 			validate_is_stock_item, validate_cancelled_item
 
@@ -145,51 +151,121 @@
 			validate_is_stock_item(item_code, item.is_stock_item, verbose=0)
 
 			# item should not be serialized
-			if item.has_serial_no == 1:
-				raise frappe.ValidationError(_("Serialized Item {0} cannot be updated using Stock Reconciliation, please use Stock Entry").format(item_code))
+			if item.has_serial_no and not row.serial_no:
+				raise frappe.ValidationError(_("Serial nos are required for serialized item {0}").format(item_code))
 
 			# item managed batch-wise not allowed
-			if item.has_batch_no == 1:
-				raise frappe.ValidationError(_("Batched Item {0} cannot be updated using Stock Reconciliation, instead use Stock Entry").format(item_code))
+			if item.has_batch_no and not row.batch:
+				raise frappe.ValidationError(_("Batch no is required for batched item {0}").format(item_code))
 
 			# docstatus should be < 2
 			validate_cancelled_item(item_code, item.docstatus, verbose=0)
 
 		except Exception as e:
-			self.validation_messages.append(_("Row # ") + ("%d: " % (row_num)) + cstr(e))
+			self.validation_messages.append(_("Row # ") + ("%d: " % (row.idx)) + cstr(e))
 
 	def update_stock_ledger(self):
 		"""	find difference between current and expected entries
 			and create stock ledger entries based on the difference"""
 		from erpnext.stock.stock_ledger import get_previous_sle
 
+		sl_entries = []
 		for row in self.items:
+			if row.serial_no:
+				self.get_sle_for_serialized_items(row, sl_entries)
+			else:
+				previous_sle = get_previous_sle({
+					"item_code": row.item_code,
+					"warehouse": row.warehouse,
+					"posting_date": self.posting_date,
+					"posting_time": self.posting_time
+				})
+
+				if previous_sle:
+					if row.qty in ("", None):
+						row.qty = previous_sle.get("qty_after_transaction", 0)
+
+					if row.valuation_rate in ("", None):
+						row.valuation_rate = previous_sle.get("valuation_rate", 0)
+
+				if row.qty and not row.valuation_rate:
+					frappe.throw(_("Valuation Rate required for Item in row {0}").format(row.idx))
+
+				if ((previous_sle and row.qty == previous_sle.get("qty_after_transaction")
+					and (row.valuation_rate == previous_sle.get("valuation_rate") or row.qty == 0))
+					or (not previous_sle and not row.qty)):
+						continue
+
+				sl_entries.append(self.get_sle_for_items(row))
+
+		if sl_entries:
+			self.make_sl_entries(sl_entries)
+
+	def get_sle_for_serialized_items(self, row, sl_entries):
+		from erpnext.stock.stock_ledger import get_previous_sle
+
+		# To issue existing serial nos
+		if row.current_serial_no:
+			args = self.get_sle_for_items(row)
+			args.update({
+				'actual_qty': -1 * row.current_qty,
+				'serial_no': row.current_serial_no,
+				'qty_after_transaction': 0,
+				'valuation_rate': row.current_valuation_rate
+			})
+
+			sl_entries.append(args)
+
+		for serial_no in get_serial_nos(row.serial_no):
+			args = self.get_sle_for_items(row, [serial_no])
+
 			previous_sle = get_previous_sle({
 				"item_code": row.item_code,
-				"warehouse": row.warehouse,
 				"posting_date": self.posting_date,
-				"posting_time": self.posting_time
+				"posting_time": self.posting_time,
+				"serial_no": serial_no
 			})
-			if previous_sle:
-				if row.qty in ("", None):
-					row.qty = previous_sle.get("qty_after_transaction", 0)
 
-				if row.valuation_rate in ("", None):
-					row.valuation_rate = previous_sle.get("valuation_rate", 0)
+			if previous_sle and row.warehouse != previous_sle.get("warehouse"):
+				# If serial no exists in different warehouse
 
-			if row.qty and not row.valuation_rate:
-				frappe.throw(_("Valuation Rate required for Item in row {0}").format(row.idx))
+				new_args = args.copy()
+				new_args.update({
+					'actual_qty': -1,
+					'qty_after_transaction': cint(previous_sle.get('qty_after_transaction')) - 1,
+					'warehouse': previous_sle.get("warehouse", '') or row.warehouse,
+					'valuation_rate': previous_sle.get("valuation_rate")
+				})
 
-			if ((previous_sle and row.qty == previous_sle.get("qty_after_transaction")
-				and (row.valuation_rate == previous_sle.get("valuation_rate") or row.qty == 0))
-				or (not previous_sle and not row.qty)):
-					continue
+				sl_entries.append(new_args)
 
-			self.insert_entries(row)
+			if self.docstatus == 2:
+				args.update({
+					'actual_qty': 1,
+					'incoming_rate': row.valuation_rate,
+					'valuation_rate': row.valuation_rate
+				})
 
-	def insert_entries(self, row):
+				sl_entries.append(args)
+
+		if self.docstatus == 1:
+			args = self.get_sle_for_items(row)
+
+			args.update({
+				'actual_qty': row.qty,
+				'incoming_rate': row.valuation_rate,
+				'valuation_rate': row.valuation_rate
+			})
+
+			sl_entries.append(args)
+
+	def get_sle_for_items(self, row, serial_nos=None):
 		"""Insert Stock Ledger Entries"""
-		args = frappe._dict({
+
+		if not serial_nos and row.serial_no:
+			serial_nos = get_serial_nos(row.serial_no)
+
+		return frappe._dict({
 			"doctype": "Stock Ledger Entry",
 			"item_code": row.item_code,
 			"warehouse": row.warehouse,
@@ -199,11 +275,11 @@
 			"voucher_no": self.name,
 			"company": self.company,
 			"stock_uom": frappe.db.get_value("Item", row.item_code, "stock_uom"),
-			"is_cancelled": "No",
+			"is_cancelled": "No" if self.docstatus != 2 else "Yes",
 			"qty_after_transaction": flt(row.qty, row.precision("qty")),
+			"serial_no": '\n'.join(serial_nos) if serial_nos else '',
 			"valuation_rate": flt(row.valuation_rate, row.precision("valuation_rate"))
 		})
-		self.make_sl_entries([args])
 
 	def delete_and_repost_sle(self):
 		"""	Delete Stock Ledger Entries related to this voucher
@@ -217,6 +293,15 @@
 		frappe.db.sql("""delete from `tabStock Ledger Entry`
 			where voucher_type=%s and voucher_no=%s""", (self.doctype, self.name))
 
+		sl_entries = []
+		for row in self.items:
+			if row.serial_no:
+				self.get_sle_for_serialized_items(row, sl_entries)
+
+		if sl_entries:
+			sl_entries.reverse()
+			self.make_sl_entries(sl_entries)
+
 		# repost future entries for selected item_code, warehouse
 		for entries in existing_entries:
 			update_entries_after({
@@ -310,17 +395,43 @@
 	return res
 
 @frappe.whitelist()
-def get_stock_balance_for(item_code, warehouse, posting_date, posting_time):
+def get_stock_balance_for(item_code, warehouse, posting_date, posting_time, with_valuation_rate= True):
 	frappe.has_permission("Stock Reconciliation", "write", throw = True)
 
-	qty, rate = get_stock_balance(item_code, warehouse,
-		posting_date, posting_time, with_valuation_rate=True)
+	has_serial_no = frappe.get_cached_value("Item", item_code, "has_serial_no")
+
+	serial_nos = ""
+	if has_serial_no:
+		qty, rate, serial_nos = get_qty_rate_for_serial_nos(item_code,
+			warehouse, posting_date, posting_time)
+	else:
+		qty, rate = get_stock_balance(item_code, warehouse,
+			posting_date, posting_time, with_valuation_rate=with_valuation_rate)
 
 	return {
 		'qty': qty,
-		'rate': rate
+		'rate': rate,
+		'serial_nos': serial_nos
 	}
 
+def get_qty_rate_for_serial_nos(item_code, warehouse, posting_date, posting_time):
+	serial_nos_list = [serial_no.get("name")
+			for serial_no in get_available_serial_nos(item_code, warehouse)]
+
+	qty = len(serial_nos_list)
+	serial_nos = '\n'.join(serial_nos_list)
+
+	rate = get_incoming_rate({
+		"item_code": item_code,
+		"warehouse": warehouse,
+		"posting_date": posting_date,
+		"posting_time": posting_time,
+		"qty": qty,
+		"serial_no":serial_nos,
+	})
+
+	return qty, rate, serial_nos
+
 @frappe.whitelist()
 def get_difference_account(purpose, company):
 	if purpose == 'Stock Reconciliation':
diff --git a/erpnext/stock/doctype/stock_reconciliation_item/stock_reconciliation_item.json b/erpnext/stock/doctype/stock_reconciliation_item/stock_reconciliation_item.json
index 0fafe83..d64c218 100644
--- a/erpnext/stock/doctype/stock_reconciliation_item/stock_reconciliation_item.json
+++ b/erpnext/stock/doctype/stock_reconciliation_item/stock_reconciliation_item.json
@@ -1,5 +1,6 @@
 {
  "allow_copy": 0, 
+ "allow_events_in_timeline": 0, 
  "allow_guest_to_view": 0, 
  "allow_import": 0, 
  "allow_rename": 0, 
@@ -14,10 +15,12 @@
  "fields": [
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "barcode", 
    "fieldtype": "Data", 
    "hidden": 0, 
@@ -40,14 +43,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 3, 
+   "fetch_if_empty": 0, 
    "fieldname": "item_code", 
    "fieldtype": "Link", 
    "hidden": 0, 
@@ -71,14 +77,17 @@
    "reqd": 1, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "item_name", 
    "fieldtype": "Data", 
    "hidden": 0, 
@@ -101,14 +110,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 3, 
+   "fetch_if_empty": 0, 
    "fieldname": "warehouse", 
    "fieldtype": "Link", 
    "hidden": 0, 
@@ -132,14 +144,17 @@
    "reqd": 1, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "column_break_6", 
    "fieldtype": "Column Break", 
    "hidden": 0, 
@@ -161,15 +176,18 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 2, 
    "description": "", 
+   "fetch_if_empty": 0, 
    "fieldname": "qty", 
    "fieldtype": "Float", 
    "hidden": 0, 
@@ -192,15 +210,18 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 2, 
    "description": "", 
+   "fetch_if_empty": 0, 
    "fieldname": "valuation_rate", 
    "fieldtype": "Currency", 
    "hidden": 0, 
@@ -224,14 +245,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "amount", 
    "fieldtype": "Currency", 
    "hidden": 0, 
@@ -255,14 +279,149 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "serial_no_and_batch_section", 
+   "fieldtype": "Section Break", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "label": "Serial No and Batch", 
+   "length": 0, 
+   "no_copy": 0, 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 0, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 0, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "serial_no", 
+   "fieldtype": "Small Text", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "label": "Serial No", 
+   "length": 0, 
+   "no_copy": 0, 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 0, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 0, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "column_break_11", 
+   "fieldtype": "Column Break", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "length": 0, 
+   "no_copy": 0, 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 0, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 0, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "batch", 
+   "fieldtype": "Link", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "label": "Batch", 
+   "length": 0, 
+   "no_copy": 0, 
+   "options": "Batch", 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 0, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 0, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "section_break_3", 
    "fieldtype": "Section Break", 
    "hidden": 0, 
@@ -285,15 +444,18 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
    "description": "", 
+   "fetch_if_empty": 0, 
    "fieldname": "current_qty", 
    "fieldtype": "Float", 
    "hidden": 0, 
@@ -316,14 +478,85 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "current_batch", 
+   "fieldtype": "Small Text", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "label": "Current Batch No", 
+   "length": 0, 
+   "no_copy": 1, 
+   "options": "", 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 1, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 1, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
+   "fieldname": "current_serial_no", 
+   "fieldtype": "Small Text", 
+   "hidden": 0, 
+   "ignore_user_permissions": 0, 
+   "ignore_xss_filter": 0, 
+   "in_filter": 0, 
+   "in_global_search": 0, 
+   "in_list_view": 0, 
+   "in_standard_filter": 0, 
+   "label": "Current Serial No", 
+   "length": 0, 
+   "no_copy": 1, 
+   "options": "", 
+   "permlevel": 0, 
+   "precision": "", 
+   "print_hide": 1, 
+   "print_hide_if_no_value": 0, 
+   "read_only": 1, 
+   "remember_last_selected_value": 0, 
+   "report_hide": 0, 
+   "reqd": 0, 
+   "search_index": 0, 
+   "set_only_once": 0, 
+   "translatable": 0, 
+   "unique": 0
+  }, 
+  {
+   "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
+   "allow_on_submit": 0, 
+   "bold": 0, 
+   "collapsible": 0, 
+   "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "column_break_9", 
    "fieldtype": "Column Break", 
    "hidden": 0, 
@@ -345,15 +578,18 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
    "description": "", 
+   "fetch_if_empty": 0, 
    "fieldname": "current_valuation_rate", 
    "fieldtype": "Currency", 
    "hidden": 0, 
@@ -377,15 +613,18 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
    "description": "", 
+   "fetch_if_empty": 0, 
    "fieldname": "current_amount", 
    "fieldtype": "Currency", 
    "hidden": 0, 
@@ -409,14 +648,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "section_break_14", 
    "fieldtype": "Section Break", 
    "hidden": 0, 
@@ -438,14 +680,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "quantity_difference", 
    "fieldtype": "Read Only", 
    "hidden": 0, 
@@ -468,14 +713,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "column_break_16", 
    "fieldtype": "Column Break", 
    "hidden": 0, 
@@ -497,14 +745,17 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }, 
   {
    "allow_bulk_edit": 0, 
+   "allow_in_quick_entry": 0, 
    "allow_on_submit": 0, 
    "bold": 0, 
    "collapsible": 0, 
    "columns": 0, 
+   "fetch_if_empty": 0, 
    "fieldname": "amount_difference", 
    "fieldtype": "Currency", 
    "hidden": 0, 
@@ -528,21 +779,20 @@
    "reqd": 0, 
    "search_index": 0, 
    "set_only_once": 0, 
+   "translatable": 0, 
    "unique": 0
   }
  ], 
  "has_web_view": 0, 
- "hide_heading": 0, 
  "hide_toolbar": 0, 
  "idx": 0, 
- "image_view": 0, 
  "in_create": 0, 
  "is_submittable": 0, 
  "issingle": 0, 
  "istable": 1, 
  "max_attachments": 0, 
  "menu_index": 0, 
- "modified": "2017-08-03 00:03:40.412071", 
+ "modified": "2019-04-24 19:07:59.113660", 
  "modified_by": "Administrator", 
  "module": "Stock", 
  "name": "Stock Reconciliation Item", 
@@ -551,10 +801,10 @@
  "permissions": [], 
  "quick_entry": 1, 
  "read_only": 0, 
- "read_only_onload": 0, 
  "show_name_in_global_search": 0, 
  "sort_field": "modified", 
  "sort_order": "DESC", 
  "track_changes": 1, 
- "track_seen": 0
+ "track_seen": 0, 
+ "track_views": 0
 }
\ No newline at end of file
diff --git a/erpnext/stock/stock_ledger.py b/erpnext/stock/stock_ledger.py
index c8706b2..6a92ce8 100644
--- a/erpnext/stock/stock_ledger.py
+++ b/erpnext/stock/stock_ledger.py
@@ -157,7 +157,11 @@
 		if sle.serial_no:
 			self.get_serialized_values(sle)
 			self.qty_after_transaction += flt(sle.actual_qty)
+			if sle.voucher_type == "Stock Reconciliation":
+				self.qty_after_transaction = sle.qty_after_transaction
+
 			self.stock_value = flt(self.qty_after_transaction) * flt(self.valuation_rate)
+			frappe.errprint([self.stock_value, self.qty_after_transaction, self.valuation_rate])
 		else:
 			if sle.voucher_type=="Stock Reconciliation":
 				# assert
@@ -177,6 +181,7 @@
 
 		# rounding as per precision
 		self.stock_value = flt(self.stock_value, self.precision)
+		frappe.errprint([self.stock_value, self.qty_after_transaction, self.valuation_rate, "wefjlk"])
 
 		if self.prev_stock_value < 0 and self.stock_value >= 0 and sle.voucher_type != 'Stock Reconciliation':
 			stock_value_difference = sle.actual_qty * self.valuation_rate
@@ -420,6 +425,9 @@
 	elif previous_sle.get("warehouse_condition"):
 		conditions += " and " + previous_sle.get("warehouse_condition")
 
+	if previous_sle.get("serial_no"):
+		conditions += " and serial_no like {}".format(frappe.db.escape('%{0}%'.format(previous_sle.get("serial_no"))))
+
 	if not previous_sle.get("posting_date"):
 		previous_sle["posting_date"] = "1900-01-01"
 	if not previous_sle.get("posting_time"):
diff --git a/erpnext/stock/utils.py b/erpnext/stock/utils.py
index 76631fa..ea8e880 100644
--- a/erpnext/stock/utils.py
+++ b/erpnext/stock/utils.py
@@ -277,3 +277,7 @@
 					new_row.append(None)
 
 		result[row_idx] = new_row
+
+def get_available_serial_nos(item_code, warehouse):
+	return frappe.get_all("Serial No", filters = {'item_code': item_code,
+		'warehouse': warehouse, 'delivery_document_no': ''}) or []
\ No newline at end of file