Merge branch 'develop' into fix-ignore-pricing-rule
diff --git a/.flake8 b/.flake8
index 56c9b9a..5735456 100644
--- a/.flake8
+++ b/.flake8
@@ -28,6 +28,7 @@
     B007,
     B950,
     W191,
+    E124, # closing bracket, irritating while writing QB code
 
 max-line-length = 200
 exclude=.github/helper/semgrep_rules
diff --git a/erpnext/accounts/doctype/bank_statement_import/bank_statement_import.py b/erpnext/accounts/doctype/bank_statement_import/bank_statement_import.py
index e786d13..1403303 100644
--- a/erpnext/accounts/doctype/bank_statement_import/bank_statement_import.py
+++ b/erpnext/accounts/doctype/bank_statement_import/bank_statement_import.py
@@ -16,6 +16,7 @@
 from openpyxl.styles import Font
 from openpyxl.utils import get_column_letter
 
+INVALID_VALUES = ("", None)
 
 class BankStatementImport(DataImport):
 	def __init__(self, *args, **kwargs):
@@ -95,6 +96,18 @@
 	data_import = frappe.get_doc("Bank Statement Import", data_import_name)
 	data_import.export_errored_rows()
 
+def parse_data_from_template(raw_data):
+	data = []
+
+	for i, row in enumerate(raw_data):
+		if all(v in INVALID_VALUES for v in row):
+			# empty row
+			continue
+
+		data.append(row)
+
+	return data
+
 def start_import(data_import, bank_account, import_file_path, google_sheets_url, bank, template_options):
 	"""This method runs in background job"""
 
@@ -104,7 +117,8 @@
 	file = import_file_path if import_file_path else google_sheets_url
 
 	import_file = ImportFile("Bank Transaction", file = file, import_type="Insert New Records")
-	data = import_file.raw_data
+
+	data = parse_data_from_template(import_file.raw_data)
 
 	if import_file_path:
 		add_bank_account(data, bank_account)
diff --git a/erpnext/accounts/doctype/bank_transaction/bank_transaction.py b/erpnext/accounts/doctype/bank_transaction/bank_transaction.py
index 44cea31..51e1d6e 100644
--- a/erpnext/accounts/doctype/bank_transaction/bank_transaction.py
+++ b/erpnext/accounts/doctype/bank_transaction/bank_transaction.py
@@ -2,9 +2,10 @@
 # For license information, please see license.txt
 
 
+from functools import reduce
+
 import frappe
 from frappe.utils import flt
-from six.moves import reduce
 
 from erpnext.controllers.status_updater import StatusUpdater
 
diff --git a/erpnext/accounts/doctype/opening_invoice_creation_tool/opening_invoice_creation_tool.py b/erpnext/accounts/doctype/opening_invoice_creation_tool/opening_invoice_creation_tool.py
index ddb833f..19d8d49 100644
--- a/erpnext/accounts/doctype/opening_invoice_creation_tool/opening_invoice_creation_tool.py
+++ b/erpnext/accounts/doctype/opening_invoice_creation_tool/opening_invoice_creation_tool.py
@@ -135,7 +135,7 @@
 			default_uom = frappe.db.get_single_value("Stock Settings", "stock_uom") or _("Nos")
 			rate = flt(row.outstanding_amount) / flt(row.qty)
 
-			return frappe._dict({
+			item_dict = frappe._dict({
 				"uom": default_uom,
 				"rate": rate or 0.0,
 				"qty": row.qty,
@@ -146,6 +146,13 @@
 				"cost_center": cost_center
 			})
 
+			for dimension in get_accounting_dimensions():
+				item_dict.update({
+					dimension: row.get(dimension)
+				})
+
+			return item_dict
+
 		item = get_item_dict()
 
 		invoice = frappe._dict({
@@ -166,7 +173,7 @@
 		accounting_dimension = get_accounting_dimensions()
 		for dimension in accounting_dimension:
 			invoice.update({
-				dimension: item.get(dimension)
+				dimension: self.get(dimension) or item.get(dimension)
 			})
 
 		return invoice
diff --git a/erpnext/accounts/doctype/opening_invoice_creation_tool/test_opening_invoice_creation_tool.py b/erpnext/accounts/doctype/opening_invoice_creation_tool/test_opening_invoice_creation_tool.py
index b5aae98..6700e9b 100644
--- a/erpnext/accounts/doctype/opening_invoice_creation_tool/test_opening_invoice_creation_tool.py
+++ b/erpnext/accounts/doctype/opening_invoice_creation_tool/test_opening_invoice_creation_tool.py
@@ -7,21 +7,26 @@
 from frappe.cache_manager import clear_doctype_cache
 from frappe.custom.doctype.property_setter.property_setter import make_property_setter
 
+from erpnext.accounts.doctype.accounting_dimension.test_accounting_dimension import (
+	create_dimension,
+	disable_dimension,
+)
 from erpnext.accounts.doctype.opening_invoice_creation_tool.opening_invoice_creation_tool import (
 	get_temporary_opening_account,
 )
 
-test_dependencies = ["Customer", "Supplier"]
+test_dependencies = ["Customer", "Supplier", "Accounting Dimension"]
 
 class TestOpeningInvoiceCreationTool(unittest.TestCase):
 	def setUp(self):
 		if not frappe.db.exists("Company", "_Test Opening Invoice Company"):
 			make_company()
+		create_dimension()
 
-	def make_invoices(self, invoice_type="Sales", company=None, party_1=None, party_2=None, invoice_number=None):
+	def make_invoices(self, invoice_type="Sales", company=None, party_1=None, party_2=None, invoice_number=None, department=None):
 		doc = frappe.get_single("Opening Invoice Creation Tool")
 		args = get_opening_invoice_creation_dict(invoice_type=invoice_type, company=company,
-			party_1=party_1, party_2=party_2, invoice_number=invoice_number)
+			party_1=party_1, party_2=party_2, invoice_number=invoice_number, department=department)
 		doc.update(args)
 		return doc.make_invoices()
 
@@ -106,6 +111,19 @@
 			doc = frappe.get_doc('Sales Invoice', inv)
 			doc.cancel()
 
+	def test_opening_invoice_with_accounting_dimension(self):
+		invoices = self.make_invoices(invoice_type="Sales", company="_Test Opening Invoice Company", department='Sales - _TOIC')
+
+		expected_value = {
+			"keys": ["customer", "outstanding_amount", "status", "department"],
+			0: ["_Test Customer", 300, "Overdue", "Sales - _TOIC"],
+			1: ["_Test Customer 1", 250, "Overdue", "Sales - _TOIC"],
+		}
+		self.check_expected_values(invoices, expected_value, invoice_type="Sales")
+
+	def tearDown(self):
+		disable_dimension()
+
 def get_opening_invoice_creation_dict(**args):
 	party = "Customer" if args.get("invoice_type", "Sales") == "Sales" else "Supplier"
 	company = args.get("company", "_Test Company")
diff --git a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py
index 98bc953..f04e7ea 100644
--- a/erpnext/accounts/doctype/sales_invoice/sales_invoice.py
+++ b/erpnext/accounts/doctype/sales_invoice/sales_invoice.py
@@ -43,6 +43,7 @@
 from erpnext.stock.doctype.batch.batch import set_batch_nos
 from erpnext.stock.doctype.delivery_note.delivery_note import update_billed_amount_based_on_so
 from erpnext.stock.doctype.serial_no.serial_no import get_delivery_note_serial_no, get_serial_nos
+from erpnext.stock.utils import calculate_mapped_packed_items_return
 
 form_grid_templates = {
 	"items": "templates/form_grid/item_grid.html"
@@ -728,8 +729,11 @@
 
 	def update_packing_list(self):
 		if cint(self.update_stock) == 1:
-			from erpnext.stock.doctype.packed_item.packed_item import make_packing_list
-			make_packing_list(self)
+			if cint(self.is_return) and self.return_against:
+				calculate_mapped_packed_items_return(self)
+			else:
+				from erpnext.stock.doctype.packed_item.packed_item import make_packing_list
+				make_packing_list(self)
 		else:
 			self.set('packed_items', [])
 
diff --git a/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py b/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py
index cfa42f6..55e3853 100644
--- a/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py
+++ b/erpnext/accounts/doctype/sales_invoice/test_sales_invoice.py
@@ -2192,9 +2192,9 @@
 		asset.load_from_db()
 
 		expected_values = [
-			["2020-06-30", 1311.48, 1311.48],
-			["2021-06-30", 20000.0, 21311.48],
-			["2021-09-30", 5041.1, 26352.58]
+			["2020-06-30", 1366.12, 1366.12],
+			["2021-06-30", 20000.0, 21366.12],
+			["2021-09-30", 5041.1, 26407.22]
 		]
 
 		for i, schedule in enumerate(asset.schedules):
@@ -2242,12 +2242,12 @@
 		asset.load_from_db()
 
 		expected_values = [
-			["2020-06-30", 1311.48, 1311.48, True],
-			["2021-06-30", 20000.0, 21311.48, True],
-			["2022-06-30", 20000.0, 41311.48, False],
-			["2023-06-30", 20000.0, 61311.48, False],
-			["2024-06-30",  20000.0, 81311.48,  False],
-			["2025-06-06",  18688.52,  100000.0, False]
+			["2020-06-30", 1366.12, 1366.12, True],
+			["2021-06-30", 20000.0, 21366.12, True],
+			["2022-06-30", 20000.0, 41366.12, False],
+			["2023-06-30", 20000.0, 61366.12, False],
+			["2024-06-30",  20000.0, 81366.12,  False],
+			["2025-06-06",  18633.88,  100000.0, False]
 		]
 
 		for i, schedule in enumerate(asset.schedules):
diff --git a/erpnext/accounts/party.py b/erpnext/accounts/party.py
index 6b4b43d..c13bc23 100644
--- a/erpnext/accounts/party.py
+++ b/erpnext/accounts/party.py
@@ -58,7 +58,7 @@
 		frappe.throw(_("Not permitted for {0}").format(party), frappe.PermissionError)
 
 	party = frappe.get_doc(party_type, party)
-	currency = party.default_currency if party.get("default_currency") else get_company_currency(company)
+	currency = party.get("default_currency") or currency or get_company_currency(company)
 
 	party_address, shipping_address = set_address_details(party_details, party, party_type, doctype, company, party_address, company_address, shipping_address)
 	set_contact_details(party_details, party, party_type)
diff --git a/erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py b/erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py
index 4559fa9..8e3bd8b 100644
--- a/erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py
+++ b/erpnext/accounts/report/accounts_receivable_summary/accounts_receivable_summary.py
@@ -5,7 +5,6 @@
 import frappe
 from frappe import _, scrub
 from frappe.utils import cint, flt
-from six import iteritems
 
 from erpnext.accounts.party import get_partywise_advanced_payment_amount
 from erpnext.accounts.report.accounts_receivable.accounts_receivable import ReceivablePayableReport
@@ -40,7 +39,7 @@
 		if self.filters.show_gl_balance:
 			gl_balance_map = get_gl_balance(self.filters.report_date)
 
-		for party, party_dict in iteritems(self.party_total):
+		for party, party_dict in self.party_total.items():
 			if party_dict.outstanding == 0:
 				continue
 
diff --git a/erpnext/accounts/report/deferred_revenue_and_expense/test_deferred_revenue_and_expense.py b/erpnext/accounts/report/deferred_revenue_and_expense/test_deferred_revenue_and_expense.py
index 1de6fb6..86eb213 100644
--- a/erpnext/accounts/report/deferred_revenue_and_expense/test_deferred_revenue_and_expense.py
+++ b/erpnext/accounts/report/deferred_revenue_and_expense/test_deferred_revenue_and_expense.py
@@ -17,10 +17,42 @@
 class TestDeferredRevenueAndExpense(unittest.TestCase):
 	@classmethod
 	def setUpClass(self):
-		clear_old_entries()
+		clear_accounts_and_items()
 		create_company()
+		self.maxDiff = None
+
+	def clear_old_entries(self):
+		sinv = qb.DocType("Sales Invoice")
+		sinv_item = qb.DocType("Sales Invoice Item")
+		pinv = qb.DocType("Purchase Invoice")
+		pinv_item = qb.DocType("Purchase Invoice Item")
+
+		# delete existing invoices with deferred items
+		deferred_invoices = (
+			qb.from_(sinv)
+			.join(sinv_item)
+			.on(sinv.name == sinv_item.parent)
+			.select(sinv.name)
+			.where(sinv_item.enable_deferred_revenue == 1)
+			.run()
+		)
+		if deferred_invoices:
+			qb.from_(sinv).delete().where(sinv.name.isin(deferred_invoices)).run()
+
+		deferred_invoices = (
+			qb.from_(pinv)
+			.join(pinv_item)
+			.on(pinv.name == pinv_item.parent)
+			.select(pinv.name)
+			.where(pinv_item.enable_deferred_expense == 1)
+			.run()
+		)
+		if deferred_invoices:
+			qb.from_(pinv).delete().where(pinv.name.isin(deferred_invoices)).run()
 
 	def test_deferred_revenue(self):
+		self.clear_old_entries()
+
 		# created deferred expense accounts, if not found
 		deferred_revenue_account = create_account(
 			account_name="Deferred Revenue",
@@ -108,6 +140,8 @@
 		self.assertEqual(report.period_total, expected)
 
 	def test_deferred_expense(self):
+		self.clear_old_entries()
+
 		# created deferred expense accounts, if not found
 		deferred_expense_account = create_account(
 			account_name="Deferred Expense",
@@ -198,6 +232,91 @@
 		]
 		self.assertEqual(report.period_total, expected)
 
+	def test_zero_months(self):
+		self.clear_old_entries()
+		# created deferred expense accounts, if not found
+		deferred_revenue_account = create_account(
+			account_name="Deferred Revenue",
+			parent_account="Current Liabilities - _CD",
+			company="_Test Company DR",
+		)
+
+		acc_settings = frappe.get_doc("Accounts Settings", "Accounts Settings")
+		acc_settings.book_deferred_entries_based_on = "Months"
+		acc_settings.save()
+
+		customer = frappe.new_doc("Customer")
+		customer.customer_name = "_Test Customer DR"
+		customer.type = "Individual"
+		customer.insert()
+
+		item = create_item(
+			"_Test Internet Subscription",
+			is_stock_item=0,
+			warehouse="All Warehouses - _CD",
+			company="_Test Company DR",
+		)
+		item.enable_deferred_revenue = 1
+		item.deferred_revenue_account = deferred_revenue_account
+		item.no_of_months = 0
+		item.save()
+
+		si = create_sales_invoice(
+			item=item.name,
+			company="_Test Company DR",
+			customer="_Test Customer DR",
+			debit_to="Debtors - _CD",
+			posting_date="2021-05-01",
+			parent_cost_center="Main - _CD",
+			cost_center="Main - _CD",
+			do_not_submit=True,
+			rate=300,
+			price_list_rate=300,
+		)
+		si.items[0].enable_deferred_revenue = 1
+		si.items[0].deferred_revenue_account = deferred_revenue_account
+		si.items[0].income_account = "Sales - _CD"
+		si.save()
+		si.submit()
+
+		pda = frappe.get_doc(
+			dict(
+				doctype="Process Deferred Accounting",
+				posting_date=nowdate(),
+				start_date="2021-05-01",
+				end_date="2021-08-01",
+				type="Income",
+				company="_Test Company DR",
+			)
+		)
+		pda.insert()
+		pda.submit()
+
+		# execute report
+		fiscal_year = frappe.get_doc("Fiscal Year", frappe.defaults.get_user_default("fiscal_year"))
+		self.filters = frappe._dict(
+			{
+				"company": frappe.defaults.get_user_default("Company"),
+				"filter_based_on": "Date Range",
+				"period_start_date": "2021-05-01",
+				"period_end_date": "2021-08-01",
+				"from_fiscal_year": fiscal_year.year,
+				"to_fiscal_year": fiscal_year.year,
+				"periodicity": "Monthly",
+				"type": "Revenue",
+				"with_upcoming_postings": False,
+			}
+		)
+
+		report = Deferred_Revenue_and_Expense_Report(filters=self.filters)
+		report.run()
+		expected = [
+			{"key": "may_2021", "total": 300.0, "actual": 300.0},
+			{"key": "jun_2021", "total": 0, "actual": 0},
+			{"key": "jul_2021", "total": 0, "actual": 0},
+			{"key": "aug_2021", "total": 0, "actual": 0},
+		]
+		self.assertEqual(report.period_total, expected)
 
 def create_company():
 	company = frappe.db.exists("Company", "_Test Company DR")
@@ -209,15 +328,11 @@
 		company.insert()
 
 
-def clear_old_entries():
+def clear_accounts_and_items():
 	item = qb.DocType("Item")
 	account = qb.DocType("Account")
 	customer = qb.DocType("Customer")
 	supplier = qb.DocType("Supplier")
-	sinv = qb.DocType("Sales Invoice")
-	sinv_item = qb.DocType("Sales Invoice Item")
-	pinv = qb.DocType("Purchase Invoice")
-	pinv_item = qb.DocType("Purchase Invoice Item")
 
 	qb.from_(account).delete().where(
 		(account.account_name == "Deferred Revenue")
@@ -228,26 +343,3 @@
 	).run()
 	qb.from_(customer).delete().where(customer.customer_name == "_Test Customer DR").run()
 	qb.from_(supplier).delete().where(supplier.supplier_name == "_Test Furniture Supplier").run()
-
-	# delete existing invoices with deferred items
-	deferred_invoices = (
-		qb.from_(sinv)
-		.join(sinv_item)
-		.on(sinv.name == sinv_item.parent)
-		.select(sinv.name)
-		.where(sinv_item.enable_deferred_revenue == 1)
-		.run()
-	)
-	if deferred_invoices:
-		qb.from_(sinv).delete().where(sinv.name.isin(deferred_invoices)).run()
-
-	deferred_invoices = (
-		qb.from_(pinv)
-		.join(pinv_item)
-		.on(pinv.name == pinv_item.parent)
-		.select(pinv.name)
-		.where(pinv_item.enable_deferred_expense == 1)
-		.run()
-	)
-	if deferred_invoices:
-		qb.from_(pinv).delete().where(pinv.name.isin(deferred_invoices)).run()
diff --git a/erpnext/assets/doctype/asset/asset.json b/erpnext/assets/doctype/asset/asset.json
index de06075..0a7c041 100644
--- a/erpnext/assets/doctype/asset/asset.json
+++ b/erpnext/assets/doctype/asset/asset.json
@@ -35,6 +35,7 @@
   "available_for_use_date",
   "column_break_23",
   "gross_purchase_amount",
+  "asset_quantity",
   "purchase_date",
   "section_break_23",
   "calculate_depreciation",
@@ -480,6 +481,12 @@
    "fieldname": "section_break_36",
    "fieldtype": "Section Break",
    "label": "Finance Books"
+  },
+  {
+   "fieldname": "asset_quantity",
+   "fieldtype": "Int",
+   "label": "Asset Quantity",
+   "read_only_depends_on": "eval:!doc.is_existing_asset"
   }
  ],
  "idx": 72,
@@ -502,10 +509,11 @@
    "link_fieldname": "asset"
   }
  ],
- "modified": "2021-06-24 14:58:51.097908",
+ "modified": "2022-01-18 12:57:36.741192",
  "modified_by": "Administrator",
  "module": "Assets",
  "name": "Asset",
+ "naming_rule": "By \"Naming Series\" field",
  "owner": "Administrator",
  "permissions": [
   {
@@ -542,6 +550,7 @@
  "show_name_in_global_search": 1,
  "sort_field": "modified",
  "sort_order": "DESC",
+ "states": [],
  "title_field": "asset_name",
  "track_changes": 1
 }
\ No newline at end of file
diff --git a/erpnext/assets/doctype/asset/asset.py b/erpnext/assets/doctype/asset/asset.py
index ee3ec8e..ac64a95 100644
--- a/erpnext/assets/doctype/asset/asset.py
+++ b/erpnext/assets/doctype/asset/asset.py
@@ -36,6 +36,7 @@
 		self.validate_asset_values()
 		self.validate_asset_and_reference()
 		self.validate_item()
+		self.validate_cost_center()
 		self.set_missing_values()
 		self.prepare_depreciation_data()
 		self.validate_gross_and_purchase_amount()
@@ -95,6 +96,19 @@
 		elif item.is_stock_item:
 			frappe.throw(_("Item {0} must be a non-stock item").format(self.item_code))
 
+	def validate_cost_center(self):
+		if not self.cost_center: return
+
+		cost_center_company = frappe.db.get_value('Cost Center', self.cost_center, 'company')
+		if cost_center_company != self.company:
+			frappe.throw(
+				_("Selected Cost Center {} doesn't belongs to {}").format(
+					frappe.bold(self.cost_center),
+					frappe.bold(self.company)
+				),
+				title=_("Invalid Cost Center")
+			)
+
 	def validate_in_use_date(self):
 		if not self.available_for_use_date:
 			frappe.throw(_("Available for use date is required"))
@@ -242,8 +256,9 @@
 
 				# For first row
 				if has_pro_rata and not self.opening_accumulated_depreciation and n==0:
+					from_date = add_days(self.available_for_use_date, -1) # needed to calc depr amount for available_for_use_date too
 					depreciation_amount, days, months = self.get_pro_rata_amt(finance_book, depreciation_amount,
-						self.available_for_use_date, finance_book.depreciation_start_date)
+						from_date, finance_book.depreciation_start_date)
 
 					# For first depr schedule date will be the start date
 					# so monthly schedule date is calculated by removing month difference between use date and start date
@@ -374,7 +389,9 @@
 
 		if from_date:
 			return from_date
-		return self.available_for_use_date
+
+		# since depr for available_for_use_date is not yet booked
+		return add_days(self.available_for_use_date, -1)
 
 	# if it returns True, depreciation_amount will not be equal for the first and last rows
 	def check_is_pro_rata(self, row):
diff --git a/erpnext/assets/doctype/asset/test_asset.py b/erpnext/assets/doctype/asset/test_asset.py
index 44c4ce5..b9545f4 100644
--- a/erpnext/assets/doctype/asset/test_asset.py
+++ b/erpnext/assets/doctype/asset/test_asset.py
@@ -134,6 +134,29 @@
 		pr.cancel()
 		self.assertEqual(asset.docstatus, 2)
 
+	def test_purchase_of_grouped_asset(self):
+		create_fixed_asset_item("Rack", is_grouped_asset=1)
+		pr = make_purchase_receipt(item_code="Rack", qty=3, rate=100000.0, location="Test Location")
+
+		asset_name = frappe.db.get_value("Asset", {"purchase_receipt": pr.name}, 'name')
+		asset = frappe.get_doc('Asset', asset_name)
+		self.assertEqual(asset.asset_quantity, 3)
+		asset.calculate_depreciation = 1
+
+		month_end_date = get_last_day(nowdate())
+		purchase_date = nowdate() if nowdate() != month_end_date else add_days(nowdate(), -15)
+
+		asset.available_for_use_date = purchase_date
+		asset.purchase_date = purchase_date
+		asset.append("finance_books", {
+			"expected_value_after_useful_life": 10000,
+			"depreciation_method": "Straight Line",
+			"total_number_of_depreciations": 3,
+			"frequency_of_depreciation": 10,
+			"depreciation_start_date": month_end_date
+		})
+		asset.submit()
+
 	def test_is_fixed_asset_set(self):
 		asset = create_asset(is_existing_asset = 1)
 		doc = frappe.new_doc('Purchase Invoice')
@@ -207,9 +230,9 @@
 		self.assertEqual(frappe.db.get_value("Asset", asset.name, "status"), "Sold")
 
 		expected_gle = (
-			("_Test Accumulated Depreciations - _TC", 20392.16, 0.0),
+			("_Test Accumulated Depreciations - _TC", 20490.2, 0.0),
 			("_Test Fixed Asset - _TC", 0.0, 100000.0),
-			("_Test Gain/Loss on Asset Disposal - _TC", 54607.84, 0.0),
+			("_Test Gain/Loss on Asset Disposal - _TC", 54509.8, 0.0),
 			("Debtors - _TC", 25000.0, 0.0)
 		)
 
@@ -491,10 +514,10 @@
 		)
 
 		expected_schedules = [
-			["2030-12-31", 27534.25, 27534.25],
-			["2031-12-31", 30000.0, 57534.25],
-			["2032-12-31", 30000.0, 87534.25],
-			["2033-01-30", 2465.75, 90000.0]
+			['2030-12-31', 27616.44, 27616.44],
+			['2031-12-31', 30000.0, 57616.44],
+			['2032-12-31', 30000.0, 87616.44],
+			['2033-01-30', 2383.56, 90000.0]
 		]
 
 		schedules = [[cstr(d.schedule_date), flt(d.depreciation_amount, 2), flt(d.accumulated_depreciation_amount, 2)]
@@ -544,10 +567,10 @@
 		self.assertEqual(asset.finance_books[0].rate_of_depreciation, 50.0)
 
 		expected_schedules = [
-			["2030-12-31", 28493.15, 28493.15],
-			["2031-12-31", 35753.43, 64246.58],
-			["2032-12-31", 17876.71, 82123.29],
-			["2033-06-06", 5376.71, 87500.0]
+			['2030-12-31', 28630.14, 28630.14],
+			['2031-12-31', 35684.93, 64315.07],
+			['2032-12-31', 17842.47, 82157.54],
+			['2033-06-06', 5342.46, 87500.0]
 		]
 
 		schedules = [[cstr(d.schedule_date), flt(d.depreciation_amount, 2), flt(d.accumulated_depreciation_amount, 2)]
@@ -580,10 +603,10 @@
 		self.assertEqual(asset.finance_books[0].rate_of_depreciation, 50.0)
 
 		expected_schedules = [
-			["2030-12-31", 11780.82, 11780.82],
-			["2031-12-31", 44109.59, 55890.41],
-			["2032-12-31", 22054.8, 77945.21],
-			["2033-07-12", 9554.79, 87500.0]
+			["2030-12-31", 11849.32, 11849.32],
+			["2031-12-31", 44075.34, 55924.66],
+			["2032-12-31", 22037.67, 77962.33],
+			["2033-07-12", 9537.67, 87500.0]
 		]
 
 		schedules = [[cstr(d.schedule_date), flt(d.depreciation_amount, 2), flt(d.accumulated_depreciation_amount, 2)]
@@ -621,7 +644,7 @@
 		asset = create_asset(
 			item_code = "Macbook Pro",
 			calculate_depreciation = 1,
-			available_for_use_date = getdate("2019-12-31"),
+			available_for_use_date = getdate("2020-01-01"),
 			total_number_of_depreciations = 3,
 			expected_value_after_useful_life = 10000,
 			depreciation_start_date = getdate("2020-07-01"),
@@ -632,7 +655,7 @@
 			["2020-07-01", 15000, 15000],
 			["2021-07-01", 30000, 45000],
 			["2022-07-01", 30000, 75000],
-			["2022-12-31", 15000, 90000]
+			["2023-01-01", 15000, 90000]
 		]
 
 		for i, schedule in enumerate(asset.schedules):
@@ -1109,6 +1132,7 @@
 
 		self.assertEqual(gle, expected_gle)
 		self.assertEqual(asset.get("value_after_depreciation"), 0)
+
 	def test_expected_value_change(self):
 		"""
 			tests if changing `expected_value_after_useful_life`
@@ -1130,6 +1154,15 @@
 		asset.reload()
 		self.assertEquals(asset.finance_books[0].value_after_depreciation, 98000.0)
 
+	def test_asset_cost_center(self):
+		asset = create_asset(is_existing_asset = 1, do_not_save=1)
+		asset.cost_center = "Main - WP"
+
+		self.assertRaises(frappe.ValidationError, asset.submit)
+
+		asset.cost_center = "Main - _TC"
+		asset.submit()
+
 def create_asset_data():
 	if not frappe.db.exists("Asset Category", "Computers"):
 		create_asset_category()
@@ -1202,13 +1235,13 @@
 	})
 	asset_category.insert()
 
-def create_fixed_asset_item():
+def create_fixed_asset_item(item_code=None, auto_create_assets=1, is_grouped_asset=0):
 	meta = frappe.get_meta('Asset')
 	naming_series = meta.get_field("naming_series").options.splitlines()[0] or 'ACC-ASS-.YYYY.-'
 	try:
-		frappe.get_doc({
+		item = frappe.get_doc({
 			"doctype": "Item",
-			"item_code": "Macbook Pro",
+			"item_code": item_code or "Macbook Pro",
 			"item_name": "Macbook Pro",
 			"description": "Macbook Pro Retina Display",
 			"asset_category": "Computers",
@@ -1216,11 +1249,14 @@
 			"stock_uom": "Nos",
 			"is_stock_item": 0,
 			"is_fixed_asset": 1,
-			"auto_create_assets": 1,
+			"auto_create_assets": auto_create_assets,
+			"is_grouped_asset": is_grouped_asset,
 			"asset_naming_series": naming_series
-		}).insert()
+		})
+		item.insert()
 	except frappe.DuplicateEntryError:
 		pass
+	return item
 
 def set_depreciation_settings_in_company():
 	company = frappe.get_doc("Company", "_Test Company")
diff --git a/erpnext/controllers/buying_controller.py b/erpnext/controllers/buying_controller.py
index a3d2502..a181af7 100644
--- a/erpnext/controllers/buying_controller.py
+++ b/erpnext/controllers/buying_controller.py
@@ -70,9 +70,18 @@
 
 		# set contact and address details for supplier, if they are not mentioned
 		if getattr(self, "supplier", None):
-			self.update_if_missing(get_party_details(self.supplier, party_type="Supplier", ignore_permissions=self.flags.ignore_permissions,
-			doctype=self.doctype, company=self.company, party_address=self.supplier_address, shipping_address=self.get('shipping_address'),
-			fetch_payment_terms_template= not self.get('ignore_default_payment_terms_template')))
+			self.update_if_missing(
+				get_party_details(
+					self.supplier,
+					party_type="Supplier",
+					doctype=self.doctype,
+					company=self.company,
+					party_address=self.get("supplier_address"),
+					shipping_address=self.get('shipping_address'),
+					fetch_payment_terms_template= not self.get('ignore_default_payment_terms_template'),
+					ignore_permissions=self.flags.ignore_permissions
+				)
+			)
 
 		self.set_missing_item_details(for_validate)
 
@@ -554,10 +563,13 @@
 					# Check for asset naming series
 					if item_data.get('asset_naming_series'):
 						created_assets = []
-
-						for qty in range(cint(d.qty)):
-							asset = self.make_asset(d)
+						if item_data.get('is_grouped_asset'):
+							asset = self.make_asset(d, is_grouped_asset=True)
 							created_assets.append(asset)
+						else:
+							for qty in range(cint(d.qty)):
+								asset = self.make_asset(d)
+								created_assets.append(asset)
 
 						if len(created_assets) > 5:
 							# dont show asset form links if more than 5 assets are created
@@ -580,14 +592,18 @@
 		for message in messages:
 			frappe.msgprint(message, title="Success", indicator="green")
 
-	def make_asset(self, row):
+	def make_asset(self, row, is_grouped_asset=False):
 		if not row.asset_location:
 			frappe.throw(_("Row {0}: Enter location for the asset item {1}").format(row.idx, row.item_code))
 
 		item_data = frappe.db.get_value('Item',
 			row.item_code, ['asset_naming_series', 'asset_category'], as_dict=1)
 
-		purchase_amount = flt(row.base_rate + row.item_tax_amount)
+		if is_grouped_asset:
+			purchase_amount = flt(row.base_amount + row.item_tax_amount)
+		else:
+			purchase_amount = flt(row.base_rate + row.item_tax_amount)
+
 		asset = frappe.get_doc({
 			'doctype': 'Asset',
 			'item_code': row.item_code,
@@ -601,6 +617,7 @@
 			'calculate_depreciation': 1,
 			'purchase_receipt_amount': purchase_amount,
 			'gross_purchase_amount': purchase_amount,
+			'asset_quantity': row.qty if is_grouped_asset else 0,
 			'purchase_receipt': self.name if self.doctype == 'Purchase Receipt' else None,
 			'purchase_invoice': self.name if self.doctype == 'Purchase Invoice' else None
 		})
@@ -687,7 +704,7 @@
 
 def get_asset_item_details(asset_items):
 	asset_items_data = {}
-	for d in frappe.get_all('Item', fields = ["name", "auto_create_assets", "asset_naming_series"],
+	for d in frappe.get_all('Item', fields = ["name", "auto_create_assets", "asset_naming_series", "is_grouped_asset"],
 		filters = {'name': ('in', asset_items)}):
 		asset_items_data.setdefault(d.name, d)
 
diff --git a/erpnext/controllers/stock_controller.py b/erpnext/controllers/stock_controller.py
index f22669b..b97432e 100644
--- a/erpnext/controllers/stock_controller.py
+++ b/erpnext/controllers/stock_controller.py
@@ -256,11 +256,7 @@
 		for d in self.items:
 			if not d.batch_no: continue
 
-			serial_nos = [sr.name for sr in frappe.get_all("Serial No",
-				{'batch_no': d.batch_no, 'status': 'Inactive'})]
-
-			if serial_nos:
-				frappe.db.set_value("Serial No", { 'name': ['in', serial_nos] }, "batch_no", None)
+			frappe.db.set_value("Serial No", {"batch_no": d.batch_no, "status": "Inactive"}, "batch_no", None)
 
 			d.batch_no = None
 			d.db_set("batch_no", None)
diff --git a/erpnext/crm/doctype/linkedin_settings/linkedin_settings.py b/erpnext/crm/doctype/linkedin_settings/linkedin_settings.py
index 8fd4978..d2ac10a 100644
--- a/erpnext/crm/doctype/linkedin_settings/linkedin_settings.py
+++ b/erpnext/crm/doctype/linkedin_settings/linkedin_settings.py
@@ -2,13 +2,14 @@
 # For license information, please see license.txt
 
 
+from urllib.parse import urlencode
+
 import frappe
 import requests
 from frappe import _
 from frappe.model.document import Document
 from frappe.utils import get_url_to_form
 from frappe.utils.file_manager import get_file_path
-from six.moves.urllib.parse import urlencode
 
 
 class LinkedInSettings(Document):
diff --git a/erpnext/domains/hospitality.py b/erpnext/domains/hospitality.py
deleted file mode 100644
index 09b98c2..0000000
--- a/erpnext/domains/hospitality.py
+++ /dev/null
@@ -1,35 +0,0 @@
-data = {
-	'desktop_icons': [
-		'Restaurant',
-		'Hotels',
-		'Accounts',
-		'Buying',
-		'Stock',
-		'HR',
-		'Project',
-		'ToDo'
-	],
-	'restricted_roles': [
-		'Restaurant Manager',
-		'Hotel Manager',
-		'Hotel Reservation User'
-	],
-	'custom_fields': {
-		'Sales Invoice': [
-			{
-				'fieldname': 'restaurant', 'fieldtype': 'Link', 'options': 'Restaurant',
-				'insert_after': 'customer_name', 'label': 'Restaurant',
-			},
-			{
-				'fieldname': 'restaurant_table', 'fieldtype': 'Link', 'options': 'Restaurant Table',
-				'insert_after': 'restaurant', 'label': 'Restaurant Table',
-			}
-		],
-		'Price List': [
-			{
-				'fieldname':'restaurant_menu', 'fieldtype':'Link', 'options':'Restaurant Menu', 'label':'Restaurant Menu',
-				'insert_after':'currency'
-			}
-		]
-	}
-}
diff --git a/erpnext/erpnext_integrations/doctype/amazon_mws_settings/amazon_methods.py b/erpnext/erpnext_integrations/doctype/amazon_mws_settings/amazon_methods.py
index 66826ba..03c1a1a 100644
--- a/erpnext/erpnext_integrations/doctype/amazon_mws_settings/amazon_methods.py
+++ b/erpnext/erpnext_integrations/doctype/amazon_mws_settings/amazon_methods.py
@@ -5,11 +5,11 @@
 import csv
 import math
 import time
+from io import StringIO
 
 import dateutil
 import frappe
 from frappe import _
-from six import StringIO
 
 import erpnext.erpnext_integrations.doctype.amazon_mws_settings.amazon_mws_api as mws
 
diff --git a/erpnext/erpnext_integrations/doctype/gocardless_settings/gocardless_settings.py b/erpnext/erpnext_integrations/doctype/gocardless_settings/gocardless_settings.py
index e242ace..a8119ac 100644
--- a/erpnext/erpnext_integrations/doctype/gocardless_settings/gocardless_settings.py
+++ b/erpnext/erpnext_integrations/doctype/gocardless_settings/gocardless_settings.py
@@ -2,13 +2,14 @@
 # For license information, please see license.txt
 
 
+from urllib.parse import urlencode
+
 import frappe
 import gocardless_pro
 from frappe import _
 from frappe.integrations.utils import create_payment_gateway, create_request_log
 from frappe.model.document import Document
 from frappe.utils import call_hook_method, cint, flt, get_url
-from six.moves.urllib.parse import urlencode
 
 
 class GoCardlessSettings(Document):
diff --git a/erpnext/erpnext_integrations/doctype/woocommerce_settings/woocommerce_settings.py b/erpnext/erpnext_integrations/doctype/woocommerce_settings/woocommerce_settings.py
index 8da52f4..309d2cb 100644
--- a/erpnext/erpnext_integrations/doctype/woocommerce_settings/woocommerce_settings.py
+++ b/erpnext/erpnext_integrations/doctype/woocommerce_settings/woocommerce_settings.py
@@ -2,12 +2,13 @@
 # For license information, please see license.txt
 
 
+from urllib.parse import urlparse
+
 import frappe
 from frappe import _
 from frappe.custom.doctype.custom_field.custom_field import create_custom_field
 from frappe.model.document import Document
 from frappe.utils.nestedset import get_root_of
-from six.moves.urllib.parse import urlparse
 
 
 class WoocommerceSettings(Document):
diff --git a/erpnext/erpnext_integrations/utils.py b/erpnext/erpnext_integrations/utils.py
index d922d87..30d3948 100644
--- a/erpnext/erpnext_integrations/utils.py
+++ b/erpnext/erpnext_integrations/utils.py
@@ -1,10 +1,10 @@
 import base64
 import hashlib
 import hmac
+from urllib.parse import urlparse
 
 import frappe
 from frappe import _
-from six.moves.urllib.parse import urlparse
 
 from erpnext import get_default_company
 
diff --git a/erpnext/hooks.py b/erpnext/hooks.py
index f014b0e..d172da3 100644
--- a/erpnext/hooks.py
+++ b/erpnext/hooks.py
@@ -67,7 +67,6 @@
 domains = {
 	'Distribution': 'erpnext.domains.distribution',
 	'Education': 'erpnext.domains.education',
-	'Hospitality': 'erpnext.domains.hospitality',
 	'Manufacturing': 'erpnext.domains.manufacturing',
 	'Non Profit': 'erpnext.domains.non_profit',
 	'Retail': 'erpnext.domains.retail',
@@ -579,13 +578,6 @@
 		{'doctype': 'Donor Type', 'index': 10},
 		{'doctype': 'Membership Type', 'index': 11}
 	],
-	"Hospitality": [
-		{'doctype': 'Hotel Room', 'index': 0},
-		{'doctype': 'Hotel Room Reservation', 'index': 1},
-		{'doctype': 'Hotel Room Pricing', 'index': 2},
-		{'doctype': 'Hotel Room Package', 'index': 3},
-		{'doctype': 'Hotel Room Type', 'index': 4}
-	]
 }
 
 additional_timeline_content = {
diff --git a/erpnext/hotels/__init__.py b/erpnext/hotels/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/__init__.py b/erpnext/hotels/doctype/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room/__init__.py b/erpnext/hotels/doctype/hotel_room/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room/hotel_room.js b/erpnext/hotels/doctype/hotel_room/hotel_room.js
deleted file mode 100644
index 76f22d5..0000000
--- a/erpnext/hotels/doctype/hotel_room/hotel_room.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room/hotel_room.json b/erpnext/hotels/doctype/hotel_room/hotel_room.json
deleted file mode 100644
index 2567c07..0000000
--- a/erpnext/hotels/doctype/hotel_room/hotel_room.json
+++ /dev/null
@@ -1,175 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 1, 
- "allow_rename": 1, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-12-08 12:33:56.320420", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "hotel_room_type", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Hotel Room Type", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Type", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "capacity", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Capacity", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "extra_bed_capacity", 
-   "fieldtype": "Int", 
-   "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": "Extra Bed Capacity", 
-   "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, 
-   "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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:10:50.670113", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }, 
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Hotel Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room/hotel_room.py b/erpnext/hotels/doctype/hotel_room/hotel_room.py
deleted file mode 100644
index e4bd1c8..0000000
--- a/erpnext/hotels/doctype/hotel_room/hotel_room.py
+++ /dev/null
@@ -1,13 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import frappe
-from frappe.model.document import Document
-
-
-class HotelRoom(Document):
-	def validate(self):
-		if not self.capacity:
-			self.capacity, self.extra_bed_capacity = frappe.db.get_value('Hotel Room Type',
-					self.hotel_room_type, ['capacity', 'extra_bed_capacity'])
diff --git a/erpnext/hotels/doctype/hotel_room/test_hotel_room.py b/erpnext/hotels/doctype/hotel_room/test_hotel_room.py
deleted file mode 100644
index 95efe2c..0000000
--- a/erpnext/hotels/doctype/hotel_room/test_hotel_room.py
+++ /dev/null
@@ -1,23 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-test_dependencies = ["Hotel Room Package"]
-test_records = [
-	dict(doctype="Hotel Room", name="1001",
-		hotel_room_type="Basic Room"),
-	dict(doctype="Hotel Room", name="1002",
-		hotel_room_type="Basic Room"),
-	dict(doctype="Hotel Room", name="1003",
-		hotel_room_type="Basic Room"),
-	dict(doctype="Hotel Room", name="1004",
-		hotel_room_type="Basic Room"),
-	dict(doctype="Hotel Room", name="1005",
-		hotel_room_type="Basic Room"),
-	dict(doctype="Hotel Room", name="1006",
-		hotel_room_type="Basic Room")
-]
-
-class TestHotelRoom(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_amenity/__init__.py b/erpnext/hotels/doctype/hotel_room_amenity/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_amenity/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.json b/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.json
deleted file mode 100644
index 29a0407..0000000
--- a/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.json
+++ /dev/null
@@ -1,103 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 0, 
- "creation": "2017-12-08 12:35:36.572185", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "billable", 
-   "fieldtype": "Check", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Billable", 
-   "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, 
-   "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, 
- "modified": "2017-12-09 12:05:07.125687", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Amenity", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.py b/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.py
deleted file mode 100644
index 1664931..0000000
--- a/erpnext/hotels/doctype/hotel_room_amenity/hotel_room_amenity.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomAmenity(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_package/__init__.py b/erpnext/hotels/doctype/hotel_room_package/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_package/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.js b/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.js
deleted file mode 100644
index 5b09ae5..0000000
--- a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.js
+++ /dev/null
@@ -1,23 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room Package', {
-	hotel_room_type: function(frm) {
-		if (frm.doc.hotel_room_type) {
-			frappe.model.with_doc('Hotel Room Type', frm.doc.hotel_room_type, () => {
-				let hotel_room_type = frappe.get_doc('Hotel Room Type', frm.doc.hotel_room_type);
-
-				// reset the amenities
-				frm.doc.amenities = [];
-
-				for (let amenity of hotel_room_type.amenities) {
-					let d = frm.add_child('amenities');
-					d.item = amenity.item;
-					d.billable = amenity.billable;
-				}
-
-				frm.refresh();
-			});
-		}
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.json b/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.json
deleted file mode 100644
index 57dad44..0000000
--- a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.json
+++ /dev/null
@@ -1,215 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-12-08 12:43:17.211064", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "hotel_room_type", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Hotel Room Type", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Type", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "column_break_2", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "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": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "section_break_4", 
-   "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, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "amenities", 
-   "fieldtype": "Table", 
-   "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": "Amenities", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Amenity", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:10:31.111952", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Package", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 0, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.py b/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.py
deleted file mode 100644
index aedc83a..0000000
--- a/erpnext/hotels/doctype/hotel_room_package/hotel_room_package.py
+++ /dev/null
@@ -1,20 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import frappe
-from frappe.model.document import Document
-
-
-class HotelRoomPackage(Document):
-	def validate(self):
-		if not self.item:
-			item = frappe.get_doc(dict(
-				doctype = 'Item',
-				item_code = self.name,
-				item_group = 'Products',
-				is_stock_item = 0,
-				stock_uom = 'Unit'
-			))
-			item.insert()
-			self.item = item.name
diff --git a/erpnext/hotels/doctype/hotel_room_package/test_hotel_room_package.py b/erpnext/hotels/doctype/hotel_room_package/test_hotel_room_package.py
deleted file mode 100644
index 749731f..0000000
--- a/erpnext/hotels/doctype/hotel_room_package/test_hotel_room_package.py
+++ /dev/null
@@ -1,47 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-test_records = [
-	dict(doctype='Item', item_code='Breakfast',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='Lunch',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='Dinner',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='WiFi',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Hotel Room Type', name="Delux Room",
-		capacity=4,
-		extra_bed_capacity=2,
-		amenities = [
-			dict(item='WiFi', billable=0)
-		]),
-	dict(doctype='Hotel Room Type', name="Basic Room",
-		capacity=4,
-		extra_bed_capacity=2,
-		amenities = [
-			dict(item='Breakfast', billable=0)
-		]),
-	dict(doctype="Hotel Room Package", name="Basic Room with Breakfast",
-		hotel_room_type="Basic Room",
-		amenities = [
-			dict(item="Breakfast", billable=0)
-		]),
-	dict(doctype="Hotel Room Package", name="Basic Room with Lunch",
-		hotel_room_type="Basic Room",
-		amenities = [
-			dict(item="Breakfast", billable=0),
-			dict(item="Lunch", billable=0)
-		]),
-	dict(doctype="Hotel Room Package", name="Basic Room with Dinner",
-		hotel_room_type="Basic Room",
-		amenities = [
-			dict(item="Breakfast", billable=0),
-			dict(item="Dinner", billable=0)
-		])
-]
-
-class TestHotelRoomPackage(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_pricing/__init__.py b/erpnext/hotels/doctype/hotel_room_pricing/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.js b/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.js
deleted file mode 100644
index 87bb192..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room Pricing', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.json b/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.json
deleted file mode 100644
index 0f5a776..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.json
+++ /dev/null
@@ -1,266 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 1, 
- "allow_rename": 0, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-12-08 12:51:47.088174", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "default": "1", 
-   "fieldname": "enabled", 
-   "fieldtype": "Check", 
-   "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": "Enabled", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "currency", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Currency", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Currency", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "from_date", 
-   "fieldtype": "Date", 
-   "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": "From Date", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "to_date", 
-   "fieldtype": "Date", 
-   "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": "To Date", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "section_break_5", 
-   "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, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "items", 
-   "fieldtype": "Table", 
-   "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": "Items", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Pricing Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:10:41.559559", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Pricing", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }, 
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Hotel Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.py b/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.py
deleted file mode 100644
index d28e573..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing/hotel_room_pricing.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomPricing(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_pricing/test_hotel_room_pricing.py b/erpnext/hotels/doctype/hotel_room_pricing/test_hotel_room_pricing.py
deleted file mode 100644
index 3455009..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing/test_hotel_room_pricing.py
+++ /dev/null
@@ -1,19 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-test_dependencies = ["Hotel Room Package"]
-test_records = [
-	dict(doctype="Hotel Room Pricing", enabled=1,
-		name="Winter 2017",
-		from_date="2017-01-01", to_date="2017-01-10",
-		items = [
-			dict(item="Basic Room with Breakfast", rate=10000),
-			dict(item="Basic Room with Lunch", rate=11000),
-			dict(item="Basic Room with Dinner", rate=12000)
-		])
-]
-
-class TestHotelRoomPricing(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_item/__init__.py b/erpnext/hotels/doctype/hotel_room_pricing_item/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_item/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.json b/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.json
deleted file mode 100644
index d6cd826..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.json
+++ /dev/null
@@ -1,103 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 0, 
- "creation": "2017-12-08 12:50:13.486090", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "rate", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Rate", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 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, 
- "modified": "2017-12-09 12:04:58.641703", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Pricing Item", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.py b/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.py
deleted file mode 100644
index 2e6bb5f..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_item/hotel_room_pricing_item.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomPricingItem(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_package/__init__.py b/erpnext/hotels/doctype/hotel_room_pricing_package/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_package/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.js b/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.js
deleted file mode 100644
index f6decd9..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room Pricing Package', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.json b/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.json
deleted file mode 100644
index 1e52932..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.json
+++ /dev/null
@@ -1,173 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_events_in_timeline": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 0, 
- "creation": "2017-12-08 12:50:13.486090", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_in_quick_entry": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "from_date", 
-   "fieldtype": "Date", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "From Date", 
-   "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": 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, 
-   "fieldname": "to_date", 
-   "fieldtype": "Date", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "To Date", 
-   "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": 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, 
-   "fieldname": "hotel_room_package", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Hotel Room Package", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Package", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "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, 
-   "fieldname": "rate", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Rate", 
-   "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": 1, 
-   "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, 
- "modified": "2018-11-04 03:34:02.551811", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Pricing Package", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0, 
- "track_views": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.py b/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.py
deleted file mode 100644
index ebbdb6e..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_package/hotel_room_pricing_package.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomPricingPackage(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_pricing_package/test_hotel_room_pricing_package.py b/erpnext/hotels/doctype/hotel_room_pricing_package/test_hotel_room_pricing_package.py
deleted file mode 100644
index 196e650..0000000
--- a/erpnext/hotels/doctype/hotel_room_pricing_package/test_hotel_room_pricing_package.py
+++ /dev/null
@@ -1,8 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-
-class TestHotelRoomPricingPackage(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/__init__.py b/erpnext/hotels/doctype/hotel_room_reservation/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.js b/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.js
deleted file mode 100644
index e58d763..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.js
+++ /dev/null
@@ -1,68 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room Reservation', {
-	refresh: function(frm) {
-		if(frm.doc.docstatus == 1){
-			frm.add_custom_button(__('Create Invoice'), ()=> {
-				frm.trigger("make_invoice");
-			});
-		}
-	},
-	from_date: function(frm) {
-		frm.trigger("recalculate_rates");
-	},
-	to_date: function(frm) {
-		frm.trigger("recalculate_rates");
-	},
-	recalculate_rates: function(frm) {
-		if (!frm.doc.from_date || !frm.doc.to_date
-			|| !frm.doc.items.length){
-			return;
-		}
-		frappe.call({
-			"method": "erpnext.hotels.doctype.hotel_room_reservation.hotel_room_reservation.get_room_rate",
-			"args": {"hotel_room_reservation": frm.doc}
-		}).done((r)=> {
-			for (var i = 0; i < r.message.items.length; i++) {
-				frm.doc.items[i].rate = r.message.items[i].rate;
-				frm.doc.items[i].amount = r.message.items[i].amount;
-			}
-			frappe.run_serially([
-				()=> frm.set_value("net_total", r.message.net_total),
-				()=> frm.refresh_field("items")
-			]);
-		});
-	},
-	make_invoice: function(frm) {
-		frappe.model.with_doc("Hotel Settings", "Hotel Settings", ()=>{
-			frappe.model.with_doctype("Sales Invoice", ()=>{
-				let hotel_settings = frappe.get_doc("Hotel Settings", "Hotel Settings");
-				let invoice = frappe.model.get_new_doc("Sales Invoice");
-				invoice.customer = frm.doc.customer || hotel_settings.default_customer;
-				if (hotel_settings.default_invoice_naming_series){
-					invoice.naming_series = hotel_settings.default_invoice_naming_series;
-				}
-				for (let d of frm.doc.items){
-					let invoice_item = frappe.model.add_child(invoice, "items")
-					invoice_item.item_code = d.item;
-					invoice_item.qty = d.qty;
-					invoice_item.rate = d.rate;
-				}
-				if (hotel_settings.default_taxes_and_charges){
-					invoice.taxes_and_charges = hotel_settings.default_taxes_and_charges;
-				}
-				frappe.set_route("Form", invoice.doctype, invoice.name);
-			});
-		});
-	}
-});
-
-frappe.ui.form.on('Hotel Room Reservation Item', {
-	item: function(frm, doctype, name) {
-		frm.trigger("recalculate_rates");
-	},
-	qty: function(frm) {
-		frm.trigger("recalculate_rates");
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.json b/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.json
deleted file mode 100644
index fd20efd..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.json
+++ /dev/null
@@ -1,436 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 1, 
- "allow_rename": 0, 
- "autoname": "HTL-RES-.YYYY.-.#####", 
- "beta": 1, 
- "creation": "2017-12-08 13:01:34.829175", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Document", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_in_quick_entry": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "guest_name", 
-   "fieldtype": "Data", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Guest Name", 
-   "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": 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, 
-   "fieldname": "customer", 
-   "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": "Customer", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Customer", 
-   "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, 
-   "fieldname": "from_date", 
-   "fieldtype": "Date", 
-   "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": "From Date", 
-   "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": 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, 
-   "fieldname": "to_date", 
-   "fieldtype": "Date", 
-   "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": "To Date", 
-   "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": 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, 
-   "fieldname": "late_checkin", 
-   "fieldtype": "Check", 
-   "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": "Late Checkin", 
-   "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, 
-   "fieldname": "column_break_6", 
-   "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, 
-   "fieldname": "status", 
-   "fieldtype": "Select", 
-   "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": "Status", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Booked\nAdvance Paid\nInvoiced\nPaid\nCompleted\nCancelled", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "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, 
-   "fieldname": "section_break_8", 
-   "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, 
-   "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, 
-   "fieldname": "items", 
-   "fieldtype": "Table", 
-   "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": "Items", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Reservation Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "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, 
-   "fieldname": "net_total", 
-   "fieldtype": "Currency", 
-   "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": "Net Total", 
-   "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, 
-   "fieldname": "amended_from", 
-   "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": "Amended From", 
-   "length": 0, 
-   "no_copy": 1, 
-   "options": "Hotel Room Reservation", 
-   "permlevel": 0, 
-   "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
-  }
- ], 
- "has_web_view": 0, 
- "hide_heading": 0, 
- "hide_toolbar": 0, 
- "idx": 0, 
- "image_view": 0, 
- "in_create": 0, 
- "is_submittable": 1, 
- "issingle": 0, 
- "istable": 0, 
- "max_attachments": 0, 
- "modified": "2018-08-21 16:15:47.326951", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Reservation", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }, 
-  {
-   "amend": 1, 
-   "cancel": 1, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Hotel Reservation User", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 1, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0, 
- "track_views": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.py b/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.py
deleted file mode 100644
index 7725955..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation.py
+++ /dev/null
@@ -1,111 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import json
-
-import frappe
-from frappe import _
-from frappe.model.document import Document
-from frappe.utils import add_days, date_diff, flt
-
-
-class HotelRoomUnavailableError(frappe.ValidationError): pass
-class HotelRoomPricingNotSetError(frappe.ValidationError): pass
-
-class HotelRoomReservation(Document):
-	def validate(self):
-		self.total_rooms = {}
-		self.set_rates()
-		self.validate_availability()
-
-	def validate_availability(self):
-		for i in range(date_diff(self.to_date, self.from_date)):
-			day = add_days(self.from_date, i)
-			self.rooms_booked = {}
-
-			for d in self.items:
-				if not d.item in self.rooms_booked:
-					self.rooms_booked[d.item] = 0
-
-				room_type = frappe.db.get_value("Hotel Room Package",
-					d.item, 'hotel_room_type')
-				rooms_booked = get_rooms_booked(room_type, day, exclude_reservation=self.name) \
-					+ d.qty + self.rooms_booked.get(d.item)
-				total_rooms = self.get_total_rooms(d.item)
-				if total_rooms < rooms_booked:
-					frappe.throw(_("Hotel Rooms of type {0} are unavailable on {1}").format(d.item,
-						frappe.format(day, dict(fieldtype="Date"))), exc=HotelRoomUnavailableError)
-
-				self.rooms_booked[d.item] += rooms_booked
-
-	def get_total_rooms(self, item):
-		if not item in self.total_rooms:
-			self.total_rooms[item] = frappe.db.sql("""
-				select count(*)
-				from
-					`tabHotel Room Package` package
-				inner join
-					`tabHotel Room` room on package.hotel_room_type = room.hotel_room_type
-				where
-					package.item = %s""", item)[0][0] or 0
-
-		return self.total_rooms[item]
-
-	def set_rates(self):
-		self.net_total = 0
-		for d in self.items:
-			net_rate = 0.0
-			for i in range(date_diff(self.to_date, self.from_date)):
-				day = add_days(self.from_date, i)
-				if not d.item:
-					continue
-				day_rate = frappe.db.sql("""
-					select
-						item.rate
-					from
-						`tabHotel Room Pricing Item` item,
-						`tabHotel Room Pricing` pricing
-					where
-						item.parent = pricing.name
-						and item.item = %s
-						and %s between pricing.from_date
-							and pricing.to_date""", (d.item, day))
-
-				if day_rate:
-					net_rate += day_rate[0][0]
-				else:
-					frappe.throw(
-						_("Please set Hotel Room Rate on {}").format(
-							frappe.format(day, dict(fieldtype="Date"))), exc=HotelRoomPricingNotSetError)
-			d.rate = net_rate
-			d.amount = net_rate * flt(d.qty)
-			self.net_total += d.amount
-
-@frappe.whitelist()
-def get_room_rate(hotel_room_reservation):
-	"""Calculate rate for each day as it may belong to different Hotel Room Pricing Item"""
-	doc = frappe.get_doc(json.loads(hotel_room_reservation))
-	doc.set_rates()
-	return doc.as_dict()
-
-def get_rooms_booked(room_type, day, exclude_reservation=None):
-	exclude_condition = ''
-	if exclude_reservation:
-		exclude_condition = 'and reservation.name != {0}'.format(frappe.db.escape(exclude_reservation))
-
-	return frappe.db.sql("""
-		select sum(item.qty)
-		from
-			`tabHotel Room Package` room_package,
-			`tabHotel Room Reservation Item` item,
-			`tabHotel Room Reservation` reservation
-		where
-			item.parent = reservation.name
-			and room_package.item = item.item
-			and room_package.hotel_room_type = %s
-			and reservation.docstatus = 1
-			{exclude_condition}
-			and %s between reservation.from_date
-				and reservation.to_date""".format(exclude_condition=exclude_condition),
-				(room_type, day))[0][0] or 0
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation_calendar.js b/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation_calendar.js
deleted file mode 100644
index 7bde292..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/hotel_room_reservation_calendar.js
+++ /dev/null
@@ -1,9 +0,0 @@
-frappe.views.calendar["Hotel Room Reservation"] = {
-	field_map: {
-		"start": "from_date",
-		"end": "to_date",
-		"id": "name",
-		"title": "guest_name",
-		"status": "status"
-	}
-}
diff --git a/erpnext/hotels/doctype/hotel_room_reservation/test_hotel_room_reservation.py b/erpnext/hotels/doctype/hotel_room_reservation/test_hotel_room_reservation.py
deleted file mode 100644
index bb32a27..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation/test_hotel_room_reservation.py
+++ /dev/null
@@ -1,65 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-import frappe
-
-from erpnext.hotels.doctype.hotel_room_reservation.hotel_room_reservation import (
-	HotelRoomPricingNotSetError,
-	HotelRoomUnavailableError,
-)
-
-test_dependencies = ["Hotel Room Package", "Hotel Room Pricing", "Hotel Room"]
-
-class TestHotelRoomReservation(unittest.TestCase):
-	def setUp(self):
-		frappe.db.sql("delete from `tabHotel Room Reservation`")
-		frappe.db.sql("delete from `tabHotel Room Reservation Item`")
-
-	def test_reservation(self):
-		reservation = make_reservation(
-			from_date="2017-01-01",
-			to_date="2017-01-03",
-			items=[
-				dict(item="Basic Room with Dinner", qty=2)
-			]
-		)
-		reservation.insert()
-		self.assertEqual(reservation.net_total, 48000)
-
-	def test_price_not_set(self):
-		reservation = make_reservation(
-			from_date="2016-01-01",
-			to_date="2016-01-03",
-			items=[
-				dict(item="Basic Room with Dinner", qty=2)
-			]
-		)
-		self.assertRaises(HotelRoomPricingNotSetError, reservation.insert)
-
-	def test_room_unavailable(self):
-		reservation = make_reservation(
-			from_date="2017-01-01",
-			to_date="2017-01-03",
-			items=[
-				dict(item="Basic Room with Dinner", qty=2),
-			]
-		)
-		reservation.insert()
-
-		reservation = make_reservation(
-			from_date="2017-01-01",
-			to_date="2017-01-03",
-			items=[
-				dict(item="Basic Room with Dinner", qty=20),
-			]
-		)
-		self.assertRaises(HotelRoomUnavailableError, reservation.insert)
-
-def make_reservation(**kwargs):
-	kwargs["doctype"] = "Hotel Room Reservation"
-	if not "guest_name" in kwargs:
-		kwargs["guest_name"] = "Test Guest"
-	doc = frappe.get_doc(kwargs)
-	return doc
diff --git a/erpnext/hotels/doctype/hotel_room_reservation_item/__init__.py b/erpnext/hotels/doctype/hotel_room_reservation_item/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation_item/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.json b/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.json
deleted file mode 100644
index 2b7931e..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.json
+++ /dev/null
@@ -1,195 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "", 
- "beta": 0, 
- "creation": "2017-12-08 12:58:21.733330", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "qty", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Qty", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "currency", 
-   "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": "Currency", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Currency", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "rate", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Rate", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "amount", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Amount", 
-   "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, 
-   "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, 
- "modified": "2017-12-09 12:04:34.562956", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Reservation Item", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.py b/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.py
deleted file mode 100644
index 41d86dd..0000000
--- a/erpnext/hotels/doctype/hotel_room_reservation_item/hotel_room_reservation_item.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomReservationItem(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_type/__init__.py b/erpnext/hotels/doctype/hotel_room_type/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_room_type/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.js b/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.js
deleted file mode 100644
index d73835d..0000000
--- a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Room Type', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.json b/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.json
deleted file mode 100644
index 3d26413..0000000
--- a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.json
+++ /dev/null
@@ -1,204 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 1, 
- "allow_rename": 1, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-12-08 12:38:29.485175", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "capacity", 
-   "fieldtype": "Int", 
-   "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": "Capacity", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "extra_bed_capacity", 
-   "fieldtype": "Int", 
-   "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": "Extra Bed Capacity", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "section_break_3", 
-   "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, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "amenities", 
-   "fieldtype": "Table", 
-   "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": "Amenities", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Hotel Room Amenity", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:10:23.355486", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Type", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }, 
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Hotel Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.py b/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.py
deleted file mode 100644
index 7ab529f..0000000
--- a/erpnext/hotels/doctype/hotel_room_type/hotel_room_type.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelRoomType(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_room_type/test_hotel_room_type.py b/erpnext/hotels/doctype/hotel_room_type/test_hotel_room_type.py
deleted file mode 100644
index 8d1147d..0000000
--- a/erpnext/hotels/doctype/hotel_room_type/test_hotel_room_type.py
+++ /dev/null
@@ -1,8 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-
-class TestHotelRoomType(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_settings/__init__.py b/erpnext/hotels/doctype/hotel_settings/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/doctype/hotel_settings/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/doctype/hotel_settings/hotel_settings.js b/erpnext/hotels/doctype/hotel_settings/hotel_settings.js
deleted file mode 100644
index 0b4a2c3..0000000
--- a/erpnext/hotels/doctype/hotel_settings/hotel_settings.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Hotel Settings', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/hotels/doctype/hotel_settings/hotel_settings.json b/erpnext/hotels/doctype/hotel_settings/hotel_settings.json
deleted file mode 100644
index d9f5572..0000000
--- a/erpnext/hotels/doctype/hotel_settings/hotel_settings.json
+++ /dev/null
@@ -1,175 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 1, 
- "creation": "2017-12-08 17:50:24.523107", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "default_customer", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Default Customer", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Customer", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "default_taxes_and_charges", 
-   "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": "Default Taxes and Charges", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Sales Taxes and Charges Template", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "default_invoice_naming_series", 
-   "fieldtype": "Data", 
-   "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": "Default Invoice Naming Series", 
-   "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, 
-   "unique": 0
-  }
- ], 
- "has_web_view": 0, 
- "hide_heading": 0, 
- "hide_toolbar": 0, 
- "idx": 0, 
- "image_view": 0, 
- "in_create": 0, 
- "is_submittable": 0, 
- "issingle": 1, 
- "istable": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:11:12.857308", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Settings", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 0, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 0, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }, 
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 0, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 0, 
-   "role": "Hotel Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 0, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/hotels/doctype/hotel_settings/hotel_settings.py b/erpnext/hotels/doctype/hotel_settings/hotel_settings.py
deleted file mode 100644
index 8376d50..0000000
--- a/erpnext/hotels/doctype/hotel_settings/hotel_settings.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class HotelSettings(Document):
-	pass
diff --git a/erpnext/hotels/doctype/hotel_settings/test_hotel_settings.py b/erpnext/hotels/doctype/hotel_settings/test_hotel_settings.py
deleted file mode 100644
index e76c00c..0000000
--- a/erpnext/hotels/doctype/hotel_settings/test_hotel_settings.py
+++ /dev/null
@@ -1,8 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-
-class TestHotelSettings(unittest.TestCase):
-	pass
diff --git a/erpnext/hotels/report/__init__.py b/erpnext/hotels/report/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/report/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/report/hotel_room_occupancy/__init__.py b/erpnext/hotels/report/hotel_room_occupancy/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/hotels/report/hotel_room_occupancy/__init__.py
+++ /dev/null
diff --git a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.js b/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.js
deleted file mode 100644
index 81efb2d..0000000
--- a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.js
+++ /dev/null
@@ -1,22 +0,0 @@
-// Copyright (c) 2016, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-/* eslint-disable */
-
-frappe.query_reports["Hotel Room Occupancy"] = {
-	"filters": [
-		{
-			"fieldname":"from_date",
-			"label": __("From Date"),
-			"fieldtype": "Date",
-			"default": frappe.datetime.now_date(),
-			"reqd":1
-		},
-		{
-			"fieldname":"to_date",
-			"label": __("To Date"),
-			"fieldtype": "Date",
-			"default": frappe.datetime.now_date(),
-			"reqd":1
-		}
-	]
-}
diff --git a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.json b/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.json
deleted file mode 100644
index 782a48b..0000000
--- a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.json
+++ /dev/null
@@ -1,26 +0,0 @@
-{
- "add_total_row": 1, 
- "apply_user_permissions": 1, 
- "creation": "2017-12-09 14:31:26.306705", 
- "disabled": 0, 
- "docstatus": 0, 
- "doctype": "Report", 
- "idx": 0, 
- "is_standard": "Yes", 
- "modified": "2017-12-09 14:31:26.306705", 
- "modified_by": "Administrator", 
- "module": "Hotels", 
- "name": "Hotel Room Occupancy", 
- "owner": "Administrator", 
- "ref_doctype": "Hotel Room Reservation", 
- "report_name": "Hotel Room Occupancy", 
- "report_type": "Script Report", 
- "roles": [
-  {
-   "role": "System Manager"
-  }, 
-  {
-   "role": "Hotel Reservation User"
-  }
- ]
-}
\ No newline at end of file
diff --git a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.py b/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.py
deleted file mode 100644
index c43589d..0000000
--- a/erpnext/hotels/report/hotel_room_occupancy/hotel_room_occupancy.py
+++ /dev/null
@@ -1,34 +0,0 @@
-# Copyright (c) 2013, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import frappe
-from frappe import _
-from frappe.utils import add_days, date_diff
-
-from erpnext.hotels.doctype.hotel_room_reservation.hotel_room_reservation import get_rooms_booked
-
-
-def execute(filters=None):
-	columns = get_columns(filters)
-	data = get_data(filters)
-	return columns, data
-
-def get_columns(filters):
-	columns = [
-		dict(label=_("Room Type"), fieldname="room_type"),
-		dict(label=_("Rooms Booked"), fieldtype="Int")
-	]
-	return columns
-
-def get_data(filters):
-	out = []
-	for room_type in frappe.get_all('Hotel Room Type'):
-		total_booked = 0
-		for i in range(date_diff(filters.to_date, filters.from_date)):
-			day = add_days(filters.from_date, i)
-			total_booked += get_rooms_booked(room_type.name, day)
-
-		out.append([room_type.name, total_booked])
-
-	return out
diff --git a/erpnext/hr/doctype/leave_application/leave_application.py b/erpnext/hr/doctype/leave_application/leave_application.py
index 1dc5b31..70250f5 100755
--- a/erpnext/hr/doctype/leave_application/leave_application.py
+++ b/erpnext/hr/doctype/leave_application/leave_application.py
@@ -22,6 +22,7 @@
 from erpnext.hr.doctype.leave_block_list.leave_block_list import get_applicable_block_dates
 from erpnext.hr.doctype.leave_ledger_entry.leave_ledger_entry import create_leave_ledger_entry
 from erpnext.hr.utils import (
+	get_holiday_dates_for_employee,
 	get_leave_period,
 	set_employee_name,
 	share_doc_with_approver,
@@ -159,33 +160,57 @@
 				.format(formatdate(future_allocation[0].from_date), future_allocation[0].name))
 
 	def update_attendance(self):
-		if self.status == "Approved":
-			for dt in daterange(getdate(self.from_date), getdate(self.to_date)):
-				date = dt.strftime("%Y-%m-%d")
-				status = "Half Day" if self.half_day_date and getdate(date) == getdate(self.half_day_date) else "On Leave"
-				attendance_name = frappe.db.exists('Attendance', dict(employee = self.employee,
-					attendance_date = date, docstatus = ('!=', 2)))
+		if self.status != "Approved":
+			return
 
+		holiday_dates = []
+		if not frappe.db.get_value("Leave Type", self.leave_type, "include_holiday"):
+			holiday_dates = get_holiday_dates_for_employee(self.employee, self.from_date, self.to_date)
+
+		for dt in daterange(getdate(self.from_date), getdate(self.to_date)):
+			date = dt.strftime("%Y-%m-%d")
+			attendance_name = frappe.db.exists("Attendance", dict(employee = self.employee,
+				attendance_date = date, docstatus = ('!=', 2)))
+
+			# don't mark attendance for holidays
+			# if leave type does not include holidays within leaves as leaves
+			if date in holiday_dates:
 				if attendance_name:
-					# update existing attendance, change absent to on leave
-					doc = frappe.get_doc('Attendance', attendance_name)
-					if doc.status != status:
-						doc.db_set('status', status)
-						doc.db_set('leave_type', self.leave_type)
-						doc.db_set('leave_application', self.name)
-				else:
-					# make new attendance and submit it
-					doc = frappe.new_doc("Attendance")
-					doc.employee = self.employee
-					doc.employee_name = self.employee_name
-					doc.attendance_date = date
-					doc.company = self.company
-					doc.leave_type = self.leave_type
-					doc.leave_application = self.name
-					doc.status = status
-					doc.flags.ignore_validate = True
-					doc.insert(ignore_permissions=True)
-					doc.submit()
+					# cancel and delete existing attendance for holidays
+					attendance = frappe.get_doc("Attendance", attendance_name)
+					attendance.flags.ignore_permissions = True
+					if attendance.docstatus == 1:
+						attendance.cancel()
+					frappe.delete_doc("Attendance", attendance_name, force=1)
+				continue
+
+			self.create_or_update_attendance(attendance_name, date)
+
+	def create_or_update_attendance(self, attendance_name, date):
+		status = "Half Day" if self.half_day_date and getdate(date) == getdate(self.half_day_date) else "On Leave"
+
+		if attendance_name:
+			# update existing attendance, change absent to on leave
+			doc = frappe.get_doc('Attendance', attendance_name)
+			if doc.status != status:
+				doc.db_set({
+					'status': status,
+					'leave_type': self.leave_type,
+					'leave_application': self.name
+				})
+		else:
+			# make new attendance and submit it
+			doc = frappe.new_doc("Attendance")
+			doc.employee = self.employee
+			doc.employee_name = self.employee_name
+			doc.attendance_date = date
+			doc.company = self.company
+			doc.leave_type = self.leave_type
+			doc.leave_application = self.name
+			doc.status = status
+			doc.flags.ignore_validate = True
+			doc.insert(ignore_permissions=True)
+			doc.submit()
 
 	def cancel_attendance(self):
 		if self.docstatus == 2:
diff --git a/erpnext/hr/doctype/leave_application/test_leave_application.py b/erpnext/hr/doctype/leave_application/test_leave_application.py
index 9b8d638..75e99f8 100644
--- a/erpnext/hr/doctype/leave_application/test_leave_application.py
+++ b/erpnext/hr/doctype/leave_application/test_leave_application.py
@@ -5,7 +5,16 @@
 
 import frappe
 from frappe.permissions import clear_user_permissions_for_doctype
-from frappe.utils import add_days, add_months, getdate, nowdate
+from frappe.utils import (
+	add_days,
+	add_months,
+	get_first_day,
+	get_last_day,
+	get_year_ending,
+	get_year_start,
+	getdate,
+	nowdate,
+)
 
 from erpnext.hr.doctype.employee.test_employee import make_employee
 from erpnext.hr.doctype.leave_allocation.test_leave_allocation import create_leave_allocation
@@ -19,6 +28,10 @@
 	create_assignment_for_multiple_employees,
 )
 from erpnext.hr.doctype.leave_type.test_leave_type import create_leave_type
+from erpnext.payroll.doctype.salary_slip.test_salary_slip import (
+	make_holiday_list,
+	make_leave_application,
+)
 
 test_dependencies = ["Leave Allocation", "Leave Block List", "Employee"]
 
@@ -61,13 +74,15 @@
 		for dt in ["Leave Application", "Leave Allocation", "Salary Slip", "Leave Ledger Entry"]:
 			frappe.db.sql("DELETE FROM `tab%s`" % dt) #nosec
 
+		frappe.set_user("Administrator")
+
 	@classmethod
 	def setUpClass(cls):
 		set_leave_approver()
 		frappe.db.sql("delete from tabAttendance where employee='_T-Employee-00001'")
 
 	def tearDown(self):
-		frappe.set_user("Administrator")
+		frappe.db.rollback()
 
 	def _clear_roles(self):
 		frappe.db.sql("""delete from `tabHas Role` where parent in
@@ -106,6 +121,72 @@
 		for d in ('2018-01-01', '2018-01-02', '2018-01-03'):
 			self.assertTrue(getdate(d) in dates)
 
+	def test_attendance_for_include_holidays(self):
+		# Case 1: leave type with 'Include holidays within leaves as leaves' enabled
+		frappe.delete_doc_if_exists("Leave Type", "Test Include Holidays", force=1)
+		leave_type = frappe.get_doc(dict(
+			leave_type_name="Test Include Holidays",
+			doctype="Leave Type",
+			include_holiday=True
+		)).insert()
+
+		date = getdate()
+		make_allocation_record(leave_type=leave_type.name, from_date=get_year_start(date), to_date=get_year_ending(date))
+
+		holiday_list = make_holiday_list()
+		frappe.db.set_value("Company", "_Test Company", "default_holiday_list", holiday_list)
+		first_sunday = get_first_sunday(holiday_list)
+
+		leave_application = make_leave_application("_T-Employee-00001", first_sunday, add_days(first_sunday, 3), leave_type.name)
+		leave_application.reload()
+		self.assertEqual(leave_application.total_leave_days, 4)
+		self.assertEqual(frappe.db.count('Attendance', {'leave_application': leave_application.name}), 4)
+
+		leave_application.cancel()
+
+	def test_attendance_update_for_exclude_holidays(self):
+		# Case 2: leave type with 'Include holidays within leaves as leaves' disabled
+		frappe.delete_doc_if_exists("Leave Type", "Test Do Not Include Holidays", force=1)
+		leave_type = frappe.get_doc(dict(
+			leave_type_name="Test Do Not Include Holidays",
+			doctype="Leave Type",
+			include_holiday=False
+		)).insert()
+
+		date = getdate()
+		make_allocation_record(leave_type=leave_type.name, from_date=get_year_start(date), to_date=get_year_ending(date))
+
+		holiday_list = make_holiday_list()
+		frappe.db.set_value("Company", "_Test Company", "default_holiday_list", holiday_list)
+		first_sunday = get_first_sunday(holiday_list)
+
+		# already marked attendance on a holiday should be deleted in this case
+		config = {
+			"doctype": "Attendance",
+			"employee": "_T-Employee-00001",
+			"status": "Present"
+		}
+		attendance_on_holiday = frappe.get_doc(config)
+		attendance_on_holiday.attendance_date = first_sunday
+		attendance_on_holiday.save()
+
+		# already marked attendance on a non-holiday should be updated
+		attendance = frappe.get_doc(config)
+		attendance.attendance_date = add_days(first_sunday, 3)
+		attendance.save()
+
+		leave_application = make_leave_application("_T-Employee-00001", first_sunday, add_days(first_sunday, 3), leave_type.name)
+		leave_application.reload()
+		# holiday should be excluded while marking attendance
+		self.assertEqual(leave_application.total_leave_days, 3)
+		self.assertEqual(frappe.db.count("Attendance", {"leave_application": leave_application.name}), 3)
+
+		# attendance on holiday deleted
+		self.assertFalse(frappe.db.exists("Attendance", attendance_on_holiday.name))
+
+		# attendance on non-holiday updated
+		self.assertEqual(frappe.db.get_value("Attendance", attendance.name, "status"), "On Leave")
+
 	def test_block_list(self):
 		self._clear_roles()
 
@@ -241,7 +322,13 @@
 		leave_period = get_leave_period()
 		today = nowdate()
 		holiday_list = 'Test Holiday List for Optional Holiday'
-		optional_leave_date = add_days(today, 7)
+		employee = get_employee()
+
+		default_holiday_list = make_holiday_list()
+		frappe.db.set_value("Company", "_Test Company", "default_holiday_list", default_holiday_list)
+		first_sunday = get_first_sunday(default_holiday_list)
+
+		optional_leave_date = add_days(first_sunday, 1)
 
 		if not frappe.db.exists('Holiday List', holiday_list):
 			frappe.get_doc(dict(
@@ -253,7 +340,6 @@
 					dict(holiday_date = optional_leave_date, description = 'Test')
 				]
 			)).insert()
-		employee = get_employee()
 
 		frappe.db.set_value('Leave Period', leave_period.name, 'optional_holiday_list', holiday_list)
 		leave_type = 'Test Optional Type'
@@ -266,7 +352,7 @@
 
 		allocate_leaves(employee, leave_period, leave_type, 10)
 
-		date = add_days(today, 6)
+		date = add_days(first_sunday, 2)
 
 		leave_application = frappe.get_doc(dict(
 			doctype = 'Leave Application',
@@ -637,13 +723,13 @@
 			carry_forward=1)
 		leave_allocation.submit()
 
-def make_allocation_record(employee=None, leave_type=None):
+def make_allocation_record(employee=None, leave_type=None, from_date=None, to_date=None):
 	allocation = frappe.get_doc({
 		"doctype": "Leave Allocation",
 		"employee": employee or "_T-Employee-00001",
 		"leave_type": leave_type or "_Test Leave Type",
-		"from_date": "2013-01-01",
-		"to_date": "2019-12-31",
+		"from_date": from_date or "2013-01-01",
+		"to_date": to_date or "2019-12-31",
 		"new_leaves_allocated": 30
 	})
 
@@ -692,3 +778,16 @@
 	}).insert()
 
 	allocate_leave.submit()
+
+
+def get_first_sunday(holiday_list):
+	month_start_date = get_first_day(nowdate())
+	month_end_date = get_last_day(nowdate())
+	first_sunday = frappe.db.sql("""
+		select holiday_date from `tabHoliday`
+		where parent = %s
+			and holiday_date between %s and %s
+		order by holiday_date
+	""", (holiday_list, month_start_date, month_end_date))[0][0]
+
+	return first_sunday
\ No newline at end of file
diff --git a/erpnext/maintenance/doctype/maintenance_schedule/test_maintenance_schedule.py b/erpnext/maintenance/doctype/maintenance_schedule/test_maintenance_schedule.py
index 4d3c3f4..6e727e5 100644
--- a/erpnext/maintenance/doctype/maintenance_schedule/test_maintenance_schedule.py
+++ b/erpnext/maintenance/doctype/maintenance_schedule/test_maintenance_schedule.py
@@ -4,6 +4,7 @@
 import unittest
 
 import frappe
+from frappe.utils import format_date
 from frappe.utils.data import add_days, formatdate, today
 
 from erpnext.maintenance.doctype.maintenance_schedule.maintenance_schedule import (
@@ -82,6 +83,13 @@
 
 		#checks if visit status is back updated in schedule
 		self.assertTrue(ms.schedules[1].completion_status, "Partially Completed")
+		self.assertEqual(format_date(visit.mntc_date), format_date(ms.schedules[1].actual_date))
+
+		#checks if visit status is updated on cancel
+		visit.cancel()
+		ms.reload()
+		self.assertTrue(ms.schedules[1].completion_status, "Pending")
+		self.assertEqual(ms.schedules[1].actual_date, None)
 
 	def test_serial_no_filters(self):
 		# Without serial no. set in schedule -> returns None
diff --git a/erpnext/maintenance/doctype/maintenance_visit/maintenance_visit.py b/erpnext/maintenance/doctype/maintenance_visit/maintenance_visit.py
index d5d8753..6fe2466 100644
--- a/erpnext/maintenance/doctype/maintenance_visit/maintenance_visit.py
+++ b/erpnext/maintenance/doctype/maintenance_visit/maintenance_visit.py
@@ -4,7 +4,7 @@
 
 import frappe
 from frappe import _
-from frappe.utils import get_datetime
+from frappe.utils import format_date, get_datetime
 
 from erpnext.utilities.transaction_base import TransactionBase
 
@@ -28,20 +28,24 @@
 			if item_ref:
 				start_date, end_date = frappe.db.get_value('Maintenance Schedule Item', item_ref, ['start_date', 'end_date'])
 				if get_datetime(self.mntc_date) < get_datetime(start_date) or get_datetime(self.mntc_date) > get_datetime(end_date):
-					frappe.throw(_("Date must be between {0} and {1}").format(start_date, end_date))
+					frappe.throw(_("Date must be between {0} and {1}")
+						.format(format_date(start_date), format_date(end_date)))
+
 
 	def validate(self):
 		self.validate_serial_no()
 		self.validate_maintenance_date()
 		self.validate_purpose_table()
 
-	def update_completion_status(self):
+	def update_status_and_actual_date(self, cancel=False):
+		status = "Pending"
+		actual_date = None
+		if not cancel:
+			status = self.completion_status
+			actual_date = self.mntc_date
 		if self.maintenance_schedule_detail:
-			frappe.db.set_value('Maintenance Schedule Detail', self.maintenance_schedule_detail, 'completion_status', self.completion_status)
-
-	def update_actual_date(self):
-		if self.maintenance_schedule_detail:
-			frappe.db.set_value('Maintenance Schedule Detail', self.maintenance_schedule_detail, 'actual_date', self.mntc_date)
+			frappe.db.set_value('Maintenance Schedule Detail', self.maintenance_schedule_detail, 'completion_status', status)
+			frappe.db.set_value('Maintenance Schedule Detail', self.maintenance_schedule_detail, 'actual_date', actual_date)
 
 	def update_customer_issue(self, flag):
 		if not self.maintenance_schedule:
@@ -102,12 +106,12 @@
 	def on_submit(self):
 		self.update_customer_issue(1)
 		frappe.db.set(self, 'status', 'Submitted')
-		self.update_completion_status()
-		self.update_actual_date()
+		self.update_status_and_actual_date()
 
 	def on_cancel(self):
 		self.check_if_last_visit()
 		frappe.db.set(self, 'status', 'Cancelled')
+		self.update_status_and_actual_date(cancel=True)
 
 	def on_update(self):
 		pass
diff --git a/erpnext/manufacturing/doctype/bom/bom.js b/erpnext/manufacturing/doctype/bom/bom.js
index 6d35d65..fc3b971 100644
--- a/erpnext/manufacturing/doctype/bom/bom.js
+++ b/erpnext/manufacturing/doctype/bom/bom.js
@@ -331,7 +331,7 @@
 			});
 		});
 
-		if (has_template_rm) {
+		if (has_template_rm && has_template_rm.length) {
 			dialog.fields_dict.items.grid.refresh();
 		}
 	},
@@ -467,7 +467,8 @@
 				"uom": d.uom,
 				"stock_uom": d.stock_uom,
 				"conversion_factor": d.conversion_factor,
-				"sourced_by_supplier": d.sourced_by_supplier
+				"sourced_by_supplier": d.sourced_by_supplier,
+				"do_not_explode": d.do_not_explode
 			},
 			callback: function(r) {
 				d = locals[cdt][cdn];
@@ -640,6 +641,13 @@
 	});
 });
 
+frappe.ui.form.on("BOM Item", {
+	do_not_explode: function(frm, cdt, cdn) {
+		get_bom_material_detail(frm.doc, cdt, cdn, false);
+	}
+})
+
+
 frappe.ui.form.on("BOM Item", "qty", function(frm, cdt, cdn) {
 	var d = locals[cdt][cdn];
 	d.stock_qty = d.qty * d.conversion_factor;
diff --git a/erpnext/manufacturing/doctype/bom/bom.py b/erpnext/manufacturing/doctype/bom/bom.py
index 5a60fb7..045e5bc 100644
--- a/erpnext/manufacturing/doctype/bom/bom.py
+++ b/erpnext/manufacturing/doctype/bom/bom.py
@@ -149,6 +149,7 @@
 		self.set_bom_material_details()
 		self.set_bom_scrap_items_detail()
 		self.validate_materials()
+		self.validate_transfer_against()
 		self.set_routing_operations()
 		self.validate_operations()
 		self.calculate_cost()
@@ -203,6 +204,10 @@
 		for item in self.get("items"):
 			self.validate_bom_currency(item)
 
+			item.bom_no = ''
+			if not item.do_not_explode:
+				item.bom_no = item.bom_no
+
 			ret = self.get_bom_material_detail({
 				"company": self.company,
 				"item_code": item.item_code,
@@ -214,8 +219,10 @@
 				"uom": item.uom,
 				"stock_uom": item.stock_uom,
 				"conversion_factor": item.conversion_factor,
-				"sourced_by_supplier": item.sourced_by_supplier
+				"sourced_by_supplier": item.sourced_by_supplier,
+				"do_not_explode": item.do_not_explode
 			})
+
 			for r in ret:
 				if not item.get(r):
 					item.set(r, ret[r])
@@ -267,6 +274,9 @@
 			 'sourced_by_supplier'		: args.get('sourced_by_supplier', 0)
 		}
 
+		if args.get('do_not_explode'):
+			ret_item['bom_no'] = ''
+
 		return ret_item
 
 	def validate_bom_currency(self, item):
@@ -681,6 +691,12 @@
 			if act_pbom and act_pbom[0][0]:
 				frappe.throw(_("Cannot deactivate or cancel BOM as it is linked with other BOMs"))
 
+	def validate_transfer_against(self):
+		if not self.with_operations:
+			self.transfer_material_against = "Work Order"
+		if not self.transfer_material_against and not self.is_new():
+			frappe.throw(_("Setting {} is required").format(self.meta.get_label("transfer_material_against")), title=_("Missing value"))
+
 	def set_routing_operations(self):
 		if self.routing and self.with_operations and not self.operations:
 			self.get_routing()
diff --git a/erpnext/manufacturing/doctype/bom/test_bom.py b/erpnext/manufacturing/doctype/bom/test_bom.py
index 178d92c..53437c8 100644
--- a/erpnext/manufacturing/doctype/bom/test_bom.py
+++ b/erpnext/manufacturing/doctype/bom/test_bom.py
@@ -385,6 +385,53 @@
 		self.assertNotEqual(len(test_items), len(filtered), msg="Item filtering showing excessive results")
 		self.assertTrue(0 < len(filtered) <= 3, msg="Item filtering showing excessive results")
 
+	def test_exclude_exploded_items_from_bom(self):
+		bom_no = get_default_bom()
+		new_bom = frappe.copy_doc(frappe.get_doc('BOM', bom_no))
+		for row in new_bom.items:
+			if row.item_code == '_Test Item Home Desktop Manufactured':
+				self.assertTrue(row.bom_no)
+				row.do_not_explode = True
+
+		new_bom.docstatus = 0
+		new_bom.save()
+		new_bom.load_from_db()
+
+		for row in new_bom.items:
+			if row.item_code == '_Test Item Home Desktop Manufactured' and row.do_not_explode:
+				self.assertFalse(row.bom_no)
+
+		new_bom.delete()
+
+	def test_valid_transfer_defaults(self):
+		bom_with_op = frappe.db.get_value("BOM", {"item": "_Test FG Item 2", "with_operations": 1, "is_active": 1})
+		bom = frappe.copy_doc(frappe.get_doc("BOM", bom_with_op), ignore_no_copy=False)
+
+		# test defaults
+		bom.docstatus = 0
+		bom.transfer_material_against = None
+		bom.insert()
+		self.assertEqual(bom.transfer_material_against, "Work Order")
+
+		bom.reload()
+		bom.transfer_material_against = None
+		with self.assertRaises(frappe.ValidationError):
+			bom.save()
+		bom.reload()
+
+		# test saner default
+		bom.transfer_material_against = "Job Card"
+		bom.with_operations = 0
+		bom.save()
+		self.assertEqual(bom.transfer_material_against, "Work Order")
+
+		# test no value on existing doc
+		bom.transfer_material_against = None
+		bom.with_operations = 0
+		bom.save()
+		self.assertEqual(bom.transfer_material_against, "Work Order")
+		bom.delete()
+
 
 def get_default_bom(item_code="_Test FG Item 2"):
 	return frappe.db.get_value("BOM", {"item": item_code, "is_active": 1, "is_default": 1})
diff --git a/erpnext/manufacturing/doctype/bom_item/bom_item.json b/erpnext/manufacturing/doctype/bom_item/bom_item.json
index 4c9877f..3406215 100644
--- a/erpnext/manufacturing/doctype/bom_item/bom_item.json
+++ b/erpnext/manufacturing/doctype/bom_item/bom_item.json
@@ -10,6 +10,7 @@
   "item_name",
   "operation",
   "column_break_3",
+  "do_not_explode",
   "bom_no",
   "source_warehouse",
   "allow_alternative_item",
@@ -73,6 +74,7 @@
    "fieldtype": "Column Break"
   },
   {
+   "depends_on": "eval:!doc.do_not_explode",
    "fieldname": "bom_no",
    "fieldtype": "Link",
    "in_filter": 1,
@@ -284,18 +286,25 @@
    "fieldname": "sourced_by_supplier",
    "fieldtype": "Check",
    "label": "Sourced by Supplier"
+  },
+  {
+   "default": "0",
+   "fieldname": "do_not_explode",
+   "fieldtype": "Check",
+   "label": "Do Not Explode"
   }
  ],
  "idx": 1,
  "index_web_pages_for_search": 1,
  "istable": 1,
  "links": [],
- "modified": "2020-10-08 14:19:37.563300",
+ "modified": "2022-01-24 16:57:57.020232",
  "modified_by": "Administrator",
  "module": "Manufacturing",
  "name": "BOM Item",
  "owner": "Administrator",
  "permissions": [],
  "sort_field": "modified",
- "sort_order": "DESC"
+ "sort_order": "DESC",
+ "states": []
 }
\ No newline at end of file
diff --git a/erpnext/manufacturing/doctype/production_plan/production_plan.py b/erpnext/manufacturing/doctype/production_plan/production_plan.py
index 19a0694..8b1dbd0 100644
--- a/erpnext/manufacturing/doctype/production_plan/production_plan.py
+++ b/erpnext/manufacturing/doctype/production_plan/production_plan.py
@@ -948,6 +948,7 @@
 		warehouses, item.get("quantity"), company, ignore_validation=True)
 
 	required_qty = item.get("quantity")
+	# get available material by transferring to production warehouse
 	for d in locations:
 		if required_qty <=0: return
 
@@ -958,12 +959,14 @@
 			new_dict.update({
 				"quantity": quantity,
 				"material_request_type": "Material Transfer",
+				"uom": new_dict.get("stock_uom"),  # internal transfer should be in stock UOM
 				"from_warehouse": d.get("warehouse")
 			})
 
 			required_qty -= quantity
 			new_mr_items.append(new_dict)
 
+	# raise purchase request for remaining qty
 	if required_qty:
 		stock_uom, purchase_uom = frappe.db.get_value(
 			'Item',
diff --git a/erpnext/manufacturing/doctype/work_order/test_work_order.py b/erpnext/manufacturing/doctype/work_order/test_work_order.py
index e7eb9c6..a399edd 100644
--- a/erpnext/manufacturing/doctype/work_order/test_work_order.py
+++ b/erpnext/manufacturing/doctype/work_order/test_work_order.py
@@ -911,6 +911,54 @@
 
 		self.assertEqual(wo1.operations[0].time_in_mins, wo2.operations[0].time_in_mins)
 
+	def test_partial_manufacture_entries(self):
+		cancel_stock_entry = []
+
+		frappe.db.set_value("Manufacturing Settings", None,
+			"backflush_raw_materials_based_on", "Material Transferred for Manufacture")
+
+		wo_order = make_wo_order_test_record(planned_start_date=now(), qty=100)
+		ste1 = test_stock_entry.make_stock_entry(item_code="_Test Item",
+			target="_Test Warehouse - _TC", qty=120, basic_rate=5000.0)
+		ste2 = test_stock_entry.make_stock_entry(item_code="_Test Item Home Desktop 100",
+			target="_Test Warehouse - _TC", qty=240, basic_rate=1000.0)
+
+		cancel_stock_entry.extend([ste1.name, ste2.name])
+
+		sm = frappe.get_doc(make_stock_entry(wo_order.name, "Material Transfer for Manufacture", 100))
+		for row in sm.get('items'):
+			if row.get('item_code') == '_Test Item':
+				row.qty = 110
+
+		sm.submit()
+		cancel_stock_entry.append(sm.name)
+
+		s = frappe.get_doc(make_stock_entry(wo_order.name, "Manufacture", 90))
+		for row in s.get('items'):
+			if row.get('item_code') == '_Test Item':
+				self.assertEqual(row.get('qty'), 100)
+		s.submit()
+		cancel_stock_entry.append(s.name)
+
+		s1 = frappe.get_doc(make_stock_entry(wo_order.name, "Manufacture", 5))
+		for row in s1.get('items'):
+			if row.get('item_code') == '_Test Item':
+				self.assertEqual(row.get('qty'), 5)
+		s1.submit()
+		cancel_stock_entry.append(s1.name)
+
+		s2 = frappe.get_doc(make_stock_entry(wo_order.name, "Manufacture", 5))
+		for row in s2.get('items'):
+			if row.get('item_code') == '_Test Item':
+				self.assertEqual(row.get('qty'), 5)
+
+		cancel_stock_entry.reverse()
+		for ste in cancel_stock_entry:
+			doc = frappe.get_doc("Stock Entry", ste)
+			doc.cancel()
+
+		frappe.db.set_value("Manufacturing Settings", None,
+			"backflush_raw_materials_based_on", "BOM")
 
 def update_job_card(job_card, jc_qty=None):
 	employee = frappe.db.get_value('Employee', {'status': 'Active'}, 'name')
diff --git a/erpnext/manufacturing/doctype/work_order/work_order.json b/erpnext/manufacturing/doctype/work_order/work_order.json
index 12cd58f..9452a63 100644
--- a/erpnext/manufacturing/doctype/work_order/work_order.json
+++ b/erpnext/manufacturing/doctype/work_order/work_order.json
@@ -333,12 +333,13 @@
    "options": "fa fa-wrench"
   },
   {
-   "default": "Work Order",
    "depends_on": "operations",
+   "fetch_from": "bom_no.transfer_material_against",
+   "fetch_if_empty": 1,
    "fieldname": "transfer_material_against",
    "fieldtype": "Select",
    "label": "Transfer Material Against",
-   "options": "Work Order\nJob Card"
+   "options": "\nWork Order\nJob Card"
   },
   {
    "fieldname": "operations",
@@ -574,7 +575,7 @@
  "image_field": "image",
  "is_submittable": 1,
  "links": [],
- "modified": "2021-11-08 17:36:07.016300",
+ "modified": "2022-01-24 21:18:12.160114",
  "modified_by": "Administrator",
  "module": "Manufacturing",
  "name": "Work Order",
@@ -607,6 +608,7 @@
  ],
  "sort_field": "modified",
  "sort_order": "ASC",
+ "states": [],
  "title_field": "production_item",
  "track_changes": 1,
  "track_seen": 1
diff --git a/erpnext/manufacturing/doctype/work_order/work_order.py b/erpnext/manufacturing/doctype/work_order/work_order.py
index 170454c..93ca805 100644
--- a/erpnext/manufacturing/doctype/work_order/work_order.py
+++ b/erpnext/manufacturing/doctype/work_order/work_order.py
@@ -65,6 +65,7 @@
 		self.validate_warehouse_belongs_to_company()
 		self.calculate_operating_cost()
 		self.validate_qty()
+		self.validate_transfer_against()
 		self.validate_operation_time()
 		self.status = self.get_status()
 
@@ -72,6 +73,7 @@
 
 		self.set_required_items(reset_only_qty = len(self.get("required_items")))
 
+
 	def validate_sales_order(self):
 		if self.sales_order:
 			self.check_sales_order_on_hold_or_close()
@@ -625,6 +627,16 @@
 		if not self.qty > 0:
 			frappe.throw(_("Quantity to Manufacture must be greater than 0."))
 
+	def validate_transfer_against(self):
+		if not self.docstatus == 1:
+			# let user configure operations until they're ready to submit
+			return
+		if not self.operations:
+			self.transfer_material_against = "Work Order"
+		if not self.transfer_material_against:
+			frappe.throw(_("Setting {} is required").format(self.meta.get_label("transfer_material_against")), title=_("Missing value"))
+
+
 	def validate_operation_time(self):
 		for d in self.operations:
 			if not d.time_in_mins > 0:
diff --git a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.js b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.js
index 7468e34..0eb22a2 100644
--- a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.js
+++ b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.js
@@ -4,6 +4,39 @@
 
 frappe.query_reports["BOM Operations Time"] = {
 	"filters": [
-
+		{
+			"fieldname": "item_code",
+			"label": __("Item Code"),
+			"fieldtype": "Link",
+			"width": "100",
+			"options": "Item",
+			"get_query": () =>{
+				return {
+					filters: { "disabled": 0, "is_stock_item": 1 }
+				}
+			}
+		},
+		{
+			"fieldname": "bom_id",
+			"label": __("BOM ID"),
+			"fieldtype": "MultiSelectList",
+			"width": "100",
+			"options": "BOM",
+			"get_data": function(txt) {
+				return frappe.db.get_link_options("BOM", txt);
+			},
+			"get_query": () =>{
+				return {
+					filters: { "docstatus": 1, "is_active": 1, "with_operations": 1 }
+				}
+			}
+		},
+		{
+			"fieldname": "workstation",
+			"label": __("Workstation"),
+			"fieldtype": "Link",
+			"width": "100",
+			"options": "Workstation"
+		},
 	]
 };
diff --git a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.json b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.json
index 665c5b9..8162017 100644
--- a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.json
+++ b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.json
@@ -1,14 +1,16 @@
 {
- "add_total_row": 0,
+ "add_total_row": 1,
+ "columns": [],
  "creation": "2020-03-03 01:41:20.862521",
  "disable_prepared_report": 0,
  "disabled": 0,
  "docstatus": 0,
  "doctype": "Report",
+ "filters": [],
  "idx": 0,
  "is_standard": "Yes",
  "letter_head": "",
- "modified": "2020-03-03 01:41:20.862521",
+ "modified": "2022-01-20 14:21:47.771591",
  "modified_by": "Administrator",
  "module": "Manufacturing",
  "name": "BOM Operations Time",
diff --git a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.py b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.py
index e7a818a..eda9eb9 100644
--- a/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.py
+++ b/erpnext/manufacturing/report/bom_operations_time/bom_operations_time.py
@@ -12,19 +12,15 @@
 	return columns, data
 
 def get_data(filters):
-	data = []
+	bom_wise_data = {}
+	bom_data, report_data = [], []
 
-	bom_data = []
-	for d in frappe.db.sql("""
-		SELECT
-			bom.name, bom.item, bom.item_name, bom.uom,
-			bomps.operation, bomps.workstation, bomps.time_in_mins
-		FROM `tabBOM` bom, `tabBOM Operation` bomps
-		WHERE
-			bom.docstatus = 1 and bom.is_active = 1 and bom.name = bomps.parent
-		""", as_dict=1):
+	bom_operation_data = get_filtered_data(filters)
+
+	for d in bom_operation_data:
 		row = get_args()
 		if d.name not in bom_data:
+			bom_wise_data[d.name] = []
 			bom_data.append(d.name)
 			row.update(d)
 		else:
@@ -34,14 +30,49 @@
 				"time_in_mins": d.time_in_mins
 			})
 
-		data.append(row)
+		# maintain BOM wise data for grouping such as:
+		# {"BOM A": [{Row1}, {Row2}], "BOM B": ...}
+		bom_wise_data[d.name].append(row)
 
 	used_as_subassembly_items = get_bom_count(bom_data)
 
-	for d in data:
-		d.used_as_subassembly_items = used_as_subassembly_items.get(d.name, 0)
+	for d in bom_wise_data:
+		for row in bom_wise_data[d]:
+			row.used_as_subassembly_items = used_as_subassembly_items.get(row.name, 0)
+			report_data.append(row)
 
-	return data
+	return report_data
+
+def get_filtered_data(filters):
+	bom = frappe.qb.DocType("BOM")
+	bom_ops = frappe.qb.DocType("BOM Operation")
+
+	bom_ops_query = (
+		frappe.qb.from_(bom)
+		.join(bom_ops).on(bom.name == bom_ops.parent)
+		.select(
+			bom.name, bom.item, bom.item_name, bom.uom,
+			bom_ops.operation, bom_ops.workstation, bom_ops.time_in_mins
+		).where(
+			(bom.docstatus == 1)
+			& (bom.is_active == 1)
+		)
+	)
+
+	if filters.get("item_code"):
+		bom_ops_query = bom_ops_query.where(bom.item == filters.get("item_code"))
+
+	if filters.get("bom_id"):
+		bom_ops_query = bom_ops_query.where(bom.name.isin(filters.get("bom_id")))
+
+	if filters.get("workstation"):
+		bom_ops_query = bom_ops_query.where(
+			bom_ops.workstation == filters.get("workstation")
+		)
+
+	bom_operation_data = bom_ops_query.run(as_dict=True)
+
+	return bom_operation_data
 
 def get_bom_count(bom_data):
 	data = frappe.get_all("BOM Item",
@@ -68,13 +99,13 @@
 		"options": "BOM",
 		"fieldname": "name",
 		"fieldtype": "Link",
-		"width": 140
+		"width": 220
 	}, {
-		"label": _("BOM Item Code"),
+		"label": _("Item Code"),
 		"options": "Item",
 		"fieldname": "item",
 		"fieldtype": "Link",
-		"width": 140
+		"width": 150
 	}, {
 		"label": _("Item Name"),
 		"fieldname": "item_name",
@@ -85,13 +116,13 @@
 		"options": "UOM",
 		"fieldname": "uom",
 		"fieldtype": "Link",
-		"width": 140
+		"width": 100
 	}, {
 		"label": _("Operation"),
 		"options": "Operation",
 		"fieldname": "operation",
 		"fieldtype": "Link",
-		"width": 120
+		"width": 140
 	}, {
 		"label": _("Workstation"),
 		"options": "Workstation",
@@ -101,11 +132,11 @@
 	}, {
 		"label": _("Time (In Mins)"),
 		"fieldname": "time_in_mins",
-		"fieldtype": "Int",
-		"width": 140
+		"fieldtype": "Float",
+		"width": 120
 	}, {
 		"label": _("Sub-assembly BOM Count"),
 		"fieldname": "used_as_subassembly_items",
 		"fieldtype": "Int",
-		"width": 180
+		"width": 200
 	}]
diff --git a/erpnext/modules.txt b/erpnext/modules.txt
index ae0bb2d..e62e2bc 100644
--- a/erpnext/modules.txt
+++ b/erpnext/modules.txt
@@ -15,10 +15,8 @@
 Maintenance
 Education
 Regional
-Restaurant
 ERPNext Integrations
 Non Profit
-Hotels
 Quality Management
 Communication
 Loan Management
diff --git a/erpnext/patches.txt b/erpnext/patches.txt
index 1f83c4f..ad5062f 100644
--- a/erpnext/patches.txt
+++ b/erpnext/patches.txt
@@ -1,3 +1,4 @@
+[pre_model_sync]
 erpnext.patches.v12_0.update_is_cancelled_field
 erpnext.patches.v11_0.rename_production_order_to_work_order
 erpnext.patches.v11_0.refactor_naming_series
@@ -226,7 +227,6 @@
 erpnext.patches.v13_0.update_reason_for_resignation_in_employee
 execute:frappe.delete_doc("Report", "Quoted Item Comparison")
 erpnext.patches.v13_0.update_member_email_address
-erpnext.patches.v13_0.updates_for_multi_currency_payroll
 erpnext.patches.v13_0.create_leave_policy_assignment_based_on_employee_current_leave_policy
 erpnext.patches.v13_0.update_pos_closing_entry_in_merge_log
 erpnext.patches.v13_0.add_po_to_global_search
@@ -252,7 +252,7 @@
 erpnext.patches.v12_0.purchase_receipt_status
 erpnext.patches.v13_0.fix_non_unique_represents_company
 erpnext.patches.v12_0.add_document_type_field_for_italy_einvoicing
-erpnext.patches.v13_0.make_non_standard_user_type #13-04-2021
+erpnext.patches.v13_0.make_non_standard_user_type #13-04-2021 #17-01-2022
 erpnext.patches.v13_0.update_shipment_status
 erpnext.patches.v13_0.remove_attribute_field_from_item_variant_setting
 erpnext.patches.v13_0.germany_make_custom_fields
@@ -266,7 +266,6 @@
 erpnext.patches.v13_0.bill_for_rejected_quantity_in_purchase_invoice
 erpnext.patches.v13_0.rename_issue_status_hold_to_on_hold
 erpnext.patches.v13_0.update_response_by_variance
-erpnext.patches.v13_0.bill_for_rejected_quantity_in_purchase_invoice
 erpnext.patches.v13_0.update_job_card_details
 erpnext.patches.v13_0.update_level_in_bom #1234sswef
 erpnext.patches.v13_0.add_missing_fg_item_for_stock_entry
@@ -285,11 +284,9 @@
 erpnext.patches.v13_0.einvoicing_deprecation_warning
 execute:frappe.reload_doc("erpnext_integrations", "doctype", "TaxJar Settings")
 execute:frappe.reload_doc("erpnext_integrations", "doctype", "Product Tax Category")
-erpnext.patches.v14_0.delete_einvoicing_doctypes
 erpnext.patches.v13_0.custom_fields_for_taxjar_integration          #08-11-2021
 erpnext.patches.v13_0.set_operation_time_based_on_operating_cost
 erpnext.patches.v13_0.create_gst_payment_entry_fields #27-11-2021
-erpnext.patches.v14_0.delete_shopify_doctypes
 erpnext.patches.v13_0.fix_invoice_statuses
 erpnext.patches.v13_0.replace_supplier_item_group_with_party_specific_item
 erpnext.patches.v13_0.update_dates_in_tax_withholding_category
@@ -312,19 +309,29 @@
 erpnext.patches.v14_0.delete_healthcare_doctypes
 erpnext.patches.v13_0.update_category_in_ltds_certificate
 erpnext.patches.v13_0.create_pan_field_for_india #2
-erpnext.patches.v14_0.delete_hub_doctypes
 erpnext.patches.v13_0.update_maintenance_schedule_field_in_visit
 erpnext.patches.v13_0.create_ksa_vat_custom_fields # 07-01-2022
-erpnext.patches.v14_0.rename_ongoing_status_in_sla_documents
 erpnext.patches.v14_0.migrate_crm_settings
 erpnext.patches.v13_0.rename_ksa_qr_field
+erpnext.patches.v13_0.wipe_serial_no_field_for_0_qty
 erpnext.patches.v13_0.disable_ksa_print_format_for_others # 16-12-2021
-erpnext.patches.v14_0.add_default_exit_questionnaire_notification_template
 erpnext.patches.v13_0.update_tax_category_for_rcm
 execute:frappe.delete_doc_if_exists('Workspace', 'ERPNext Integrations Settings')
 erpnext.patches.v14_0.set_payroll_cost_centers
 erpnext.patches.v13_0.agriculture_deprecation_warning
-erpnext.patches.v14_0.delete_agriculture_doctypes
+erpnext.patches.v13_0.hospitality_deprecation_warning
 erpnext.patches.v13_0.update_exchange_rate_settings
+erpnext.patches.v13_0.update_asset_quantity_field
+erpnext.patches.v13_0.delete_bank_reconciliation_detail
+
+[post_model_sync]
+erpnext.patches.v14_0.rename_ongoing_status_in_sla_documents
+erpnext.patches.v14_0.add_default_exit_questionnaire_notification_template
+erpnext.patches.v14_0.delete_einvoicing_doctypes
+erpnext.patches.v14_0.delete_shopify_doctypes
+erpnext.patches.v14_0.delete_hub_doctypes
+erpnext.patches.v14_0.delete_hospitality_doctypes # 20-01-2022
+erpnext.patches.v14_0.delete_agriculture_doctypes
 erpnext.patches.v14_0.rearrange_company_fields
-erpnext.patches.v14_0.update_leave_notification_template
\ No newline at end of file
+erpnext.patches.v14_0.update_leave_notification_template
+erpnext.patches.v13_0.update_sane_transfer_against
diff --git a/erpnext/patches/v12_0/update_is_cancelled_field.py b/erpnext/patches/v12_0/update_is_cancelled_field.py
index df78750..0401034 100644
--- a/erpnext/patches/v12_0/update_is_cancelled_field.py
+++ b/erpnext/patches/v12_0/update_is_cancelled_field.py
@@ -2,14 +2,28 @@
 
 
 def execute():
-	try:
-		frappe.db.sql("UPDATE `tabStock Ledger Entry` SET is_cancelled = 0 where is_cancelled in ('', NULL, 'No')")
-		frappe.db.sql("UPDATE `tabSerial No` SET is_cancelled = 0 where is_cancelled in ('', NULL, 'No')")
+	#handle type casting for is_cancelled field
+	module_doctypes = (
+		('stock', 'Stock Ledger Entry'),
+		('stock', 'Serial No'),
+		('accounts', 'GL Entry')
+	)
 
-		frappe.db.sql("UPDATE `tabStock Ledger Entry` SET is_cancelled = 1 where is_cancelled = 'Yes'")
-		frappe.db.sql("UPDATE `tabSerial No` SET is_cancelled = 1 where is_cancelled = 'Yes'")
+	for module, doctype in module_doctypes:
+		if (not frappe.db.has_column(doctype, "is_cancelled")
+			or frappe.db.get_column_type(doctype, "is_cancelled").lower() == "int(1)"
+		):
+			continue
 
-		frappe.reload_doc("stock", "doctype", "stock_ledger_entry")
-		frappe.reload_doc("stock", "doctype", "serial_no")
-	except Exception:
-		pass
+		frappe.db.sql("""
+				UPDATE `tab{doctype}`
+				SET is_cancelled = 0
+				where is_cancelled in ('', NULL, 'No')"""
+				.format(doctype=doctype))
+		frappe.db.sql("""
+				UPDATE `tab{doctype}`
+				SET is_cancelled = 1
+				where is_cancelled = 'Yes'"""
+				.format(doctype=doctype))
+
+		frappe.reload_doc(module, "doctype", frappe.scrub(doctype))
diff --git a/erpnext/patches/v13_0/delete_bank_reconciliation_detail.py b/erpnext/patches/v13_0/delete_bank_reconciliation_detail.py
new file mode 100644
index 0000000..75953b0
--- /dev/null
+++ b/erpnext/patches/v13_0/delete_bank_reconciliation_detail.py
@@ -0,0 +1,13 @@
+# Copyright (c) 2019, Frappe and Contributors
+# License: GNU General Public License v3. See license.txt
+
+
+import frappe
+
+
+def execute():
+
+	if frappe.db.exists('DocType', 'Bank Reconciliation Detail') and \
+		frappe.db.exists('DocType', 'Bank Clearance Detail'):
+
+		frappe.delete_doc("DocType", 'Bank Reconciliation Detail', force=1)
diff --git a/erpnext/patches/v13_0/delete_old_sales_reports.py b/erpnext/patches/v13_0/delete_old_sales_reports.py
index c597fe8..e6eba0a 100644
--- a/erpnext/patches/v13_0/delete_old_sales_reports.py
+++ b/erpnext/patches/v13_0/delete_old_sales_reports.py
@@ -12,6 +12,7 @@
 
 	for report in reports_to_delete:
 		if frappe.db.exists("Report", report):
+			delete_links_from_desktop_icons(report)
 			delete_auto_email_reports(report)
 			check_and_delete_linked_reports(report)
 
@@ -22,3 +23,9 @@
 	auto_email_reports = frappe.db.get_values("Auto Email Report", {"report": report}, ["name"])
 	for auto_email_report in auto_email_reports:
 		frappe.delete_doc("Auto Email Report", auto_email_report[0])
+
+def delete_links_from_desktop_icons(report):
+	""" Check for one or multiple Desktop Icons and delete """
+	desktop_icons = frappe.db.get_values("Desktop Icon", {"_report": report}, ["name"])
+	for desktop_icon in desktop_icons:
+		frappe.delete_doc("Desktop Icon", desktop_icon[0])
\ No newline at end of file
diff --git a/erpnext/patches/v13_0/hospitality_deprecation_warning.py b/erpnext/patches/v13_0/hospitality_deprecation_warning.py
new file mode 100644
index 0000000..2708b2c
--- /dev/null
+++ b/erpnext/patches/v13_0/hospitality_deprecation_warning.py
@@ -0,0 +1,10 @@
+import click
+
+
+def execute():
+
+	click.secho(
+		"Hospitality domain is moved to a separate app and will be removed from ERPNext in version-14.\n"
+		"When upgrading to ERPNext version-14, please install the app to continue using the Hospitality domain: https://github.com/frappe/hospitality",
+		fg="yellow",
+	)
diff --git a/erpnext/patches/v13_0/make_non_standard_user_type.py b/erpnext/patches/v13_0/make_non_standard_user_type.py
index a7bdf93..ff241a3 100644
--- a/erpnext/patches/v13_0/make_non_standard_user_type.py
+++ b/erpnext/patches/v13_0/make_non_standard_user_type.py
@@ -10,8 +10,15 @@
 def execute():
 	doctype_dict = {
 		'projects': ['Timesheet'],
-		'payroll': ['Salary Slip', 'Employee Tax Exemption Declaration', 'Employee Tax Exemption Proof Submission'],
-		'hr': ['Employee', 'Expense Claim', 'Leave Application', 'Attendance Request', 'Compensatory Leave Request']
+		'payroll': [
+			'Salary Slip', 'Employee Tax Exemption Declaration', 'Employee Tax Exemption Proof Submission',
+			'Employee Benefit Application', 'Employee Benefit Claim'
+		],
+		'hr': [
+			'Employee', 'Expense Claim', 'Leave Application', 'Attendance Request', 'Compensatory Leave Request',
+			'Holiday List', 'Employee Advance', 'Training Program', 'Training Feedback',
+			'Shift Request', 'Employee Grievance', 'Employee Referral', 'Travel Request'
+		]
 	}
 
 	for module, doctypes in doctype_dict.items():
diff --git a/erpnext/patches/v13_0/setup_fields_for_80g_certificate_and_donation.py b/erpnext/patches/v13_0/setup_fields_for_80g_certificate_and_donation.py
index 7a2a253..2d35ea3 100644
--- a/erpnext/patches/v13_0/setup_fields_for_80g_certificate_and_donation.py
+++ b/erpnext/patches/v13_0/setup_fields_for_80g_certificate_and_donation.py
@@ -5,6 +5,9 @@
 
 def execute():
 	if frappe.get_all('Company', filters = {'country': 'India'}):
+		frappe.reload_doc('accounts', 'doctype', 'POS Invoice')
+		frappe.reload_doc('accounts', 'doctype', 'POS Invoice Item')
+
 		make_custom_fields()
 
 		if not frappe.db.exists('Party Type', 'Donor'):
diff --git a/erpnext/patches/v13_0/update_actual_start_and_end_date_in_wo.py b/erpnext/patches/v13_0/update_actual_start_and_end_date_in_wo.py
index 55fd465..60466eb 100644
--- a/erpnext/patches/v13_0/update_actual_start_and_end_date_in_wo.py
+++ b/erpnext/patches/v13_0/update_actual_start_and_end_date_in_wo.py
@@ -37,4 +37,4 @@
 			jc.production_item = wo.production_item, jc.item_name = wo.item_name
 		WHERE
 			jc.work_order = wo.name and IFNULL(jc.production_item, "") = ""
-	""")
+	""")
\ No newline at end of file
diff --git a/erpnext/patches/v13_0/update_asset_quantity_field.py b/erpnext/patches/v13_0/update_asset_quantity_field.py
new file mode 100644
index 0000000..47884d1
--- /dev/null
+++ b/erpnext/patches/v13_0/update_asset_quantity_field.py
@@ -0,0 +1,8 @@
+import frappe
+
+
+def execute():
+	if frappe.db.count('Asset'):
+		frappe.reload_doc("assets", "doctype", "Asset")
+		asset = frappe.qb.DocType('Asset')
+		frappe.qb.update(asset).set(asset.asset_quantity, 1).run()
\ No newline at end of file
diff --git a/erpnext/patches/v13_0/update_sane_transfer_against.py b/erpnext/patches/v13_0/update_sane_transfer_against.py
new file mode 100644
index 0000000..a163d38
--- /dev/null
+++ b/erpnext/patches/v13_0/update_sane_transfer_against.py
@@ -0,0 +1,11 @@
+import frappe
+
+
+def execute():
+	bom = frappe.qb.DocType("BOM")
+
+	(frappe.qb
+		.update(bom)
+		.set(bom.transfer_material_against, "Work Order")
+		.where(bom.with_operations == 0)
+	).run()
diff --git a/erpnext/patches/v13_0/wipe_serial_no_field_for_0_qty.py b/erpnext/patches/v13_0/wipe_serial_no_field_for_0_qty.py
new file mode 100644
index 0000000..e43a8ba
--- /dev/null
+++ b/erpnext/patches/v13_0/wipe_serial_no_field_for_0_qty.py
@@ -0,0 +1,18 @@
+import frappe
+
+
+def execute():
+
+	doctype = "Stock Reconciliation Item"
+
+	if not frappe.db.has_column(doctype, "current_serial_no"):
+		# nothing to fix if column doesn't exist
+		return
+
+	sr_item = frappe.qb.DocType(doctype)
+
+	(frappe.qb
+		.update(sr_item)
+		.set(sr_item.current_serial_no, None)
+		.where(sr_item.current_qty == 0)
+	).run()
diff --git a/erpnext/patches/v14_0/add_default_exit_questionnaire_notification_template.py b/erpnext/patches/v14_0/add_default_exit_questionnaire_notification_template.py
index 120182a..2a8b6ef 100644
--- a/erpnext/patches/v14_0/add_default_exit_questionnaire_notification_template.py
+++ b/erpnext/patches/v14_0/add_default_exit_questionnaire_notification_template.py
@@ -5,9 +5,6 @@
 
 
 def execute():
-	frappe.reload_doc("email", "doctype", "email_template")
-	frappe.reload_doc("hr", "doctype", "hr_settings")
-
 	template = frappe.db.exists("Email Template", _("Exit Questionnaire Notification"))
 	if not template:
 		base_path = frappe.get_app_path("erpnext", "hr", "doctype")
diff --git a/erpnext/patches/v14_0/delete_hospitality_doctypes.py b/erpnext/patches/v14_0/delete_hospitality_doctypes.py
new file mode 100644
index 0000000..d0216f8
--- /dev/null
+++ b/erpnext/patches/v14_0/delete_hospitality_doctypes.py
@@ -0,0 +1,32 @@
+import frappe
+
+
+def execute():
+	modules = ['Hotels', 'Restaurant']
+
+	for module in modules:
+		frappe.delete_doc("Module Def", module, ignore_missing=True, force=True)
+
+		frappe.delete_doc("Workspace", module, ignore_missing=True, force=True)
+
+		reports = frappe.get_all("Report", {"module": module, "is_standard": "Yes"}, pluck='name')
+		for report in reports:
+			frappe.delete_doc("Report", report, ignore_missing=True, force=True)
+
+		dashboards = frappe.get_all("Dashboard", {"module": module, "is_standard": 1}, pluck='name')
+		for dashboard in dashboards:
+			frappe.delete_doc("Dashboard", dashboard, ignore_missing=True, force=True)
+
+		doctypes = frappe.get_all("DocType", {"module": module, "custom": 0}, pluck='name')
+		for doctype in doctypes:
+			frappe.delete_doc("DocType", doctype, ignore_missing=True)
+
+	custom_fields = [
+		{"dt": "Sales Invoice", "fieldname": "restaurant"},
+		{"dt": "Sales Invoice", "fieldname": "restaurant_table"},
+		{"dt": "Price List", "fieldname": "restaurant_menu"},
+	]
+
+	for field in custom_fields:
+		custom_field = frappe.db.get_value("Custom Field", field)
+		frappe.delete_doc("Custom Field", custom_field, ignore_missing=True)
diff --git a/erpnext/patches/v14_0/rearrange_company_fields.py b/erpnext/patches/v14_0/rearrange_company_fields.py
index dd953ff..fd7eb7f 100644
--- a/erpnext/patches/v14_0/rearrange_company_fields.py
+++ b/erpnext/patches/v14_0/rearrange_company_fields.py
@@ -1,10 +1,7 @@
-import frappe
 from frappe.custom.doctype.custom_field.custom_field import create_custom_fields
 
 
 def execute():
-	frappe.reload_doc('setup', 'doctype', 'company')
-
 	custom_fields = {
 		'Company': [
 			dict(fieldname='hra_section', label='HRA Settings',
@@ -28,4 +25,4 @@
 		]
 	}
 
-	create_custom_fields(custom_fields, update=True)
\ No newline at end of file
+	create_custom_fields(custom_fields, update=True)
diff --git a/erpnext/payroll/doctype/salary_slip/test_salary_slip.py b/erpnext/payroll/doctype/salary_slip/test_salary_slip.py
index c0e005a..bcf981b 100644
--- a/erpnext/payroll/doctype/salary_slip/test_salary_slip.py
+++ b/erpnext/payroll/doctype/salary_slip/test_salary_slip.py
@@ -994,6 +994,8 @@
 	))
 	leave_application.submit()
 
+	return leave_application
+
 def setup_test():
 	make_earning_salary_component(setup=True, company_list=["_Test Company"])
 	make_deduction_salary_component(setup=True, company_list=["_Test Company"])
diff --git a/erpnext/projects/doctype/timesheet/test_timesheet.py b/erpnext/projects/doctype/timesheet/test_timesheet.py
index 148d8ba..989bcd1 100644
--- a/erpnext/projects/doctype/timesheet/test_timesheet.py
+++ b/erpnext/projects/doctype/timesheet/test_timesheet.py
@@ -5,7 +5,7 @@
 import unittest
 
 import frappe
-from frappe.utils import add_months, now_datetime, nowdate
+from frappe.utils import add_months, add_to_date, now_datetime, nowdate
 
 from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
 from erpnext.hr.doctype.employee.test_employee import make_employee
@@ -151,6 +151,27 @@
 		settings.ignore_employee_time_overlap = initial_setting
 		settings.save()
 
+	def test_to_time(self):
+		emp = make_employee("test_employee_6@salary.com")
+		from_time = now_datetime()
+
+		timesheet = frappe.new_doc("Timesheet")
+		timesheet.employee = emp
+		timesheet.append(
+			'time_logs',
+			{
+				"billable": 1,
+				"activity_type": "_Test Activity Type",
+				"from_time": from_time,
+				"hours": 2,
+				"company": "_Test Company"
+			}
+		)
+		timesheet.save()
+
+		to_time = timesheet.time_logs[0].to_time
+		self.assertEqual(to_time, add_to_date(from_time, hours=2, as_datetime=True))
+
 
 def make_salary_structure_for_timesheet(employee, company=None):
 	salary_structure_name = "Timesheet Salary Structure Test"
diff --git a/erpnext/projects/doctype/timesheet/timesheet.py b/erpnext/projects/doctype/timesheet/timesheet.py
index e92785e..dd0b5f9 100644
--- a/erpnext/projects/doctype/timesheet/timesheet.py
+++ b/erpnext/projects/doctype/timesheet/timesheet.py
@@ -7,7 +7,7 @@
 import frappe
 from frappe import _
 from frappe.model.document import Document
-from frappe.utils import flt, getdate, time_diff_in_hours
+from frappe.utils import add_to_date, flt, getdate, time_diff_in_hours
 
 from erpnext.controllers.queries import get_match_cond
 from erpnext.hr.utils import validate_active_employee
@@ -136,10 +136,19 @@
 
 	def validate_time_logs(self):
 		for data in self.get('time_logs'):
+			self.set_to_time(data)
 			self.validate_overlap(data)
 			self.set_project(data)
 			self.validate_project(data)
 
+	def set_to_time(self, data):
+		if not (data.from_time and data.hours):
+			return
+
+		_to_time = add_to_date(data.from_time, hours=data.hours, as_datetime=True)
+		if data.to_time != _to_time:
+			data.to_time = _to_time
+
 	def validate_overlap(self, data):
 		settings = frappe.get_single('Projects Settings')
 		self.validate_overlap_for("user", data, self.user, settings.ignore_user_time_overlap)
diff --git a/erpnext/regional/germany/utils/datev/datev_csv.py b/erpnext/regional/germany/utils/datev/datev_csv.py
index 2d1e02e..ec271a1 100644
--- a/erpnext/regional/germany/utils/datev/datev_csv.py
+++ b/erpnext/regional/germany/utils/datev/datev_csv.py
@@ -1,11 +1,11 @@
 import datetime
 import zipfile
 from csv import QUOTE_NONNUMERIC
+from io import BytesIO
 
 import frappe
 import pandas as pd
 from frappe import _
-from six import BytesIO
 
 from .datev_constants import DataCategory
 
diff --git a/erpnext/regional/report/datev/test_datev.py b/erpnext/regional/report/datev/test_datev.py
index 14d5495..052fb2a 100644
--- a/erpnext/regional/report/datev/test_datev.py
+++ b/erpnext/regional/report/datev/test_datev.py
@@ -1,9 +1,9 @@
 import zipfile
+from io import BytesIO
 from unittest import TestCase
 
 import frappe
 from frappe.utils import cstr, now_datetime, today
-from six import BytesIO
 
 from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
 from erpnext.regional.germany.utils.datev.datev_constants import (
diff --git a/erpnext/restaurant/__init__.py b/erpnext/restaurant/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/__init__.py b/erpnext/restaurant/doctype/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant/__init__.py b/erpnext/restaurant/doctype/restaurant/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant/restaurant.js b/erpnext/restaurant/doctype/restaurant/restaurant.js
deleted file mode 100644
index 13fda73..0000000
--- a/erpnext/restaurant/doctype/restaurant/restaurant.js
+++ /dev/null
@@ -1,10 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Restaurant', {
-	refresh: function(frm) {
-		frm.add_custom_button(__('Order Entry'), () => {
-			frappe.set_route('Form', 'Restaurant Order Entry');
-		});
-	}
-});
diff --git a/erpnext/restaurant/doctype/restaurant/restaurant.json b/erpnext/restaurant/doctype/restaurant/restaurant.json
deleted file mode 100644
index 8572687..0000000
--- a/erpnext/restaurant/doctype/restaurant/restaurant.json
+++ /dev/null
@@ -1,309 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-09-15 12:40:41.546933", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "image", 
-   "fieldtype": "Attach Image", 
-   "hidden": 1, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 0, 
-   "in_standard_filter": 0, 
-   "label": "Image", 
-   "length": 0, 
-   "no_copy": 0, 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 1, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "company", 
-   "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": "Company", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Company", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "default_customer", 
-   "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": "Default Customer", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Customer", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "invoice_series_prefix", 
-   "fieldtype": "Data", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Invoice Series Prefix", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "column_break_4", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "active_menu", 
-   "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": "Active Menu", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant Menu", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "default_tax_template", 
-   "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": "Default Tax Template", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Sales Taxes and Charges Template", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "address", 
-   "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": "Address", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Address", 
-   "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, 
-   "unique": 0
-  }
- ], 
- "has_web_view": 0, 
- "hide_heading": 0, 
- "hide_toolbar": 0, 
- "idx": 0, 
- "image_field": "image", 
- "image_view": 0, 
- "in_create": 0, 
- "is_submittable": 0, 
- "issingle": 0, 
- "istable": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:13:10.185496", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "System Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 0, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant/restaurant.py b/erpnext/restaurant/doctype/restaurant/restaurant.py
deleted file mode 100644
index 67838d2..0000000
--- a/erpnext/restaurant/doctype/restaurant/restaurant.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class Restaurant(Document):
-	pass
diff --git a/erpnext/restaurant/doctype/restaurant/restaurant_dashboard.py b/erpnext/restaurant/doctype/restaurant/restaurant_dashboard.py
deleted file mode 100644
index bfdd052..0000000
--- a/erpnext/restaurant/doctype/restaurant/restaurant_dashboard.py
+++ /dev/null
@@ -1,17 +0,0 @@
-from frappe import _
-
-
-def get_data():
-	return {
-		'fieldname': 'restaurant',
-		'transactions': [
-			{
-				'label': _('Setup'),
-				'items': ['Restaurant Menu', 'Restaurant Table']
-			},
-			{
-				'label': _('Operations'),
-				'items': ['Restaurant Reservation', 'Sales Invoice']
-			}
-		]
-	}
diff --git a/erpnext/restaurant/doctype/restaurant/test_restaurant.py b/erpnext/restaurant/doctype/restaurant/test_restaurant.py
deleted file mode 100644
index f88f980..0000000
--- a/erpnext/restaurant/doctype/restaurant/test_restaurant.py
+++ /dev/null
@@ -1,14 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-test_records = [
-	dict(doctype='Restaurant', name='Test Restaurant 1', company='_Test Company 1',
-		invoice_series_prefix='Test-Rest-1-Inv-', default_customer='_Test Customer 1'),
-	dict(doctype='Restaurant', name='Test Restaurant 2', company='_Test Company 1',
-		invoice_series_prefix='Test-Rest-2-Inv-', default_customer='_Test Customer 1'),
-]
-
-class TestRestaurant(unittest.TestCase):
-	pass
diff --git a/erpnext/restaurant/doctype/restaurant_menu/__init__.py b/erpnext/restaurant/doctype/restaurant_menu/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.js b/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.js
deleted file mode 100644
index da7d43f..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Restaurant Menu', {
-	setup: function(frm) {
-		frm.add_fetch('item', 'standard_rate', 'rate');
-	},
-});
diff --git a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.json b/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.json
deleted file mode 100644
index 1b1610d..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.json
+++ /dev/null
@@ -1,247 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "prompt", 
- "beta": 1, 
- "creation": "2017-09-15 12:48:29.818715", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "restaurant", 
-   "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": "Restaurant", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "default": "1", 
-   "fieldname": "enabled", 
-   "fieldtype": "Check", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Enabled", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "column_break_3", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "price_list", 
-   "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": "Price List (Auto created)", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Price List", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "items_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": "Items", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "items", 
-   "fieldtype": "Table", 
-   "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": "Items", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant Menu Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:13:13.684500", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Menu", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Restaurant Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.py b/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.py
deleted file mode 100644
index 64eb40f..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu/restaurant_menu.py
+++ /dev/null
@@ -1,59 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import frappe
-from frappe.model.document import Document
-
-
-class RestaurantMenu(Document):
-	def validate(self):
-		for d in self.items:
-			if not d.rate:
-				d.rate = frappe.db.get_value('Item', d.item, 'standard_rate')
-
-	def on_update(self):
-		'''Sync Price List'''
-		self.make_price_list()
-
-	def on_trash(self):
-		'''clear prices'''
-		self.clear_item_price()
-
-	def clear_item_price(self, price_list=None):
-		'''clear all item prices for this menu'''
-		if not price_list:
-			price_list = self.get_price_list().name
-		frappe.db.sql('delete from `tabItem Price` where price_list = %s', price_list)
-
-	def make_price_list(self):
-		# create price list for menu
-		price_list = self.get_price_list()
-		self.db_set('price_list', price_list.name)
-
-		# delete old items
-		self.clear_item_price(price_list.name)
-
-		for d in self.items:
-			frappe.get_doc(dict(
-				doctype = 'Item Price',
-				price_list = price_list.name,
-				item_code = d.item,
-				price_list_rate = d.rate
-			)).insert()
-
-	def get_price_list(self):
-		'''Create price list for menu if missing'''
-		price_list_name = frappe.db.get_value('Price List', dict(restaurant_menu=self.name))
-		if price_list_name:
-			price_list = frappe.get_doc('Price List', price_list_name)
-		else:
-			price_list = frappe.new_doc('Price List')
-			price_list.restaurant_menu = self.name
-			price_list.price_list_name = self.name
-
-		price_list.enabled = 1
-		price_list.selling = 1
-		price_list.save()
-
-		return price_list
diff --git a/erpnext/restaurant/doctype/restaurant_menu/test_restaurant_menu.py b/erpnext/restaurant/doctype/restaurant_menu/test_restaurant_menu.py
deleted file mode 100644
index 27020eb..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu/test_restaurant_menu.py
+++ /dev/null
@@ -1,52 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-import frappe
-
-test_records = [
-	dict(doctype='Item', item_code='Food Item 1',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='Food Item 2',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='Food Item 3',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Item', item_code='Food Item 4',
-		item_group='Products', is_stock_item=0),
-	dict(doctype='Restaurant Menu', restaurant='Test Restaurant 1', name='Test Restaurant 1 Menu 1',
-		items = [
-			dict(item='Food Item 1', rate=400),
-			dict(item='Food Item 2', rate=300),
-			dict(item='Food Item 3', rate=200),
-			dict(item='Food Item 4', rate=100),
-		]),
-	dict(doctype='Restaurant Menu', restaurant='Test Restaurant 1', name='Test Restaurant 1 Menu 2',
-		items = [
-			dict(item='Food Item 1', rate=450),
-			dict(item='Food Item 2', rate=350),
-		])
-]
-
-class TestRestaurantMenu(unittest.TestCase):
-	def test_price_list_creation_and_editing(self):
-		menu1 = frappe.get_doc('Restaurant Menu', 'Test Restaurant 1 Menu 1')
-		menu1.save()
-
-		menu2 = frappe.get_doc('Restaurant Menu', 'Test Restaurant 1 Menu 2')
-		menu2.save()
-
-		self.assertTrue(frappe.db.get_value('Price List', 'Test Restaurant 1 Menu 1'))
-		self.assertEqual(frappe.db.get_value('Item Price',
-			dict(price_list = 'Test Restaurant 1 Menu 1', item_code='Food Item 1'), 'price_list_rate'), 400)
-		self.assertEqual(frappe.db.get_value('Item Price',
-			dict(price_list = 'Test Restaurant 1 Menu 2', item_code='Food Item 1'), 'price_list_rate'), 450)
-
-		menu1.items[0].rate = 401
-		menu1.save()
-
-		self.assertEqual(frappe.db.get_value('Item Price',
-			dict(price_list = 'Test Restaurant 1 Menu 1', item_code='Food Item 1'), 'price_list_rate'), 401)
-
-		menu1.items[0].rate = 400
-		menu1.save()
diff --git a/erpnext/restaurant/doctype/restaurant_menu_item/__init__.py b/erpnext/restaurant/doctype/restaurant_menu_item/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu_item/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.json b/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.json
deleted file mode 100644
index 87568bf..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.json
+++ /dev/null
@@ -1,105 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "", 
- "beta": 0, 
- "creation": "2017-09-15 12:49:36.072636", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "rate", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Rate", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "", 
-   "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, 
-   "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, 
- "modified": "2017-09-15 14:18:55.145088", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Menu Item", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.py b/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.py
deleted file mode 100644
index 98b245e..0000000
--- a/erpnext/restaurant/doctype/restaurant_menu_item/restaurant_menu_item.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class RestaurantMenuItem(Document):
-	pass
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry/__init__.py b/erpnext/restaurant/doctype/restaurant_order_entry/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.js b/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.js
deleted file mode 100644
index 8df851c..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.js
+++ /dev/null
@@ -1,162 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Restaurant Order Entry', {
-	setup: function(frm) {
-		let get_item_query = () => {
-			return {
-				query: 'erpnext.restaurant.doctype.restaurant_order_entry.restaurant_order_entry.item_query_restaurant',
-				filters: {
-					'table': frm.doc.restaurant_table
-				}
-			};
-		};
-		frm.set_query('item', 'items', get_item_query);
-		frm.set_query('add_item', get_item_query);
-	},
-	onload_post_render: function(frm) {
-		if(!frm.item_selector) {
-			frm.item_selector = new erpnext.ItemSelector({
-				frm: frm,
-				item_field: 'item',
-				item_query: 'erpnext.restaurant.doctype.restaurant_order_entry.restaurant_order_entry.item_query_restaurant',
-				get_filters: () => {
-					return {table: frm.doc.restaurant_table};
-				}
-			});
-		}
-
-		let $input = frm.get_field('add_item').$input;
-
-		$input.on('keyup', function(e) {
-			if (e.which===13) {
-				if (frm.clear_item_timeout) {
-					clearTimeout (frm.clear_item_timeout);
-				}
-
-				// clear the item input so user can enter a new item
-				frm.clear_item_timeout = setTimeout (() => {
-					frm.set_value('add_item', '');
-				}, 1000);
-
-				let item = $input.val();
-
-				if (!item) return;
-
-				var added = false;
-				(frm.doc.items || []).forEach((d) => {
-					if (d.item===item) {
-						d.qty += 1;
-						added = true;
-					}
-				});
-
-				return frappe.run_serially([
-					() => {
-						if (!added) {
-							return frm.add_child('items', {item: item, qty: 1});
-						}
-					},
-					() => frm.get_field("items").refresh()
-				]);
-			}
-		});
-	},
-	refresh: function(frm) {
-		frm.disable_save();
-		frm.add_custom_button(__('Update'), () => {
-			return frm.trigger('sync');
-		});
-		frm.add_custom_button(__('Clear'), () => {
-			return frm.trigger('clear');
-		});
-		frm.add_custom_button(__('Bill'), () => {
-			return frm.trigger('make_invoice');
-		});
-	},
-	clear: function(frm) {
-		frm.doc.add_item = '';
-		frm.doc.grand_total = 0;
-		frm.doc.items = [];
-		frm.refresh();
-		frm.get_field('add_item').$input.focus();
-	},
-	restaurant_table: function(frm) {
-		// select the open sales order items for this table
-		if (!frm.doc.restaurant_table) {
-			return;
-		}
-		return frappe.call({
-			method: 'erpnext.restaurant.doctype.restaurant_order_entry.restaurant_order_entry.get_invoice',
-			args: {
-				table: frm.doc.restaurant_table
-			},
-			callback: (r) => {
-				frm.events.set_invoice_items(frm, r);
-			}
-		});
-	},
-	sync: function(frm) {
-		return frappe.call({
-			method: 'erpnext.restaurant.doctype.restaurant_order_entry.restaurant_order_entry.sync',
-			args: {
-				table: frm.doc.restaurant_table,
-				items: frm.doc.items
-			},
-			callback: (r) => {
-				frm.events.set_invoice_items(frm, r);
-				frappe.show_alert({message: __('Saved'), indicator: 'green'});
-			}
-		});
-
-	},
-	make_invoice: function(frm) {
-		frm.trigger('sync').then(() => {
-			frappe.prompt([
-				{
-					fieldname: 'customer',
-					label: __('Customer'),
-					fieldtype: 'Link',
-					reqd: 1,
-					options: 'Customer',
-					'default': frm.invoice.customer
-				},
-				{
-					fieldname: 'mode_of_payment',
-					label: __('Mode of Payment'),
-					fieldtype: 'Link',
-					reqd: 1,
-					options: 'Mode of Payment',
-					'default': frm.mode_of_payment || ''
-				}
-			], (data) => {
-				// cache this for next entry
-				frm.mode_of_payment = data.mode_of_payment;
-				return frappe.call({
-					method: 'erpnext.restaurant.doctype.restaurant_order_entry.restaurant_order_entry.make_invoice',
-					args: {
-						table: frm.doc.restaurant_table,
-						customer: data.customer,
-						mode_of_payment: data.mode_of_payment
-					},
-					callback: (r) => {
-						frm.set_value('last_sales_invoice', r.message);
-						frm.trigger('clear');
-					}
-				});
-			},
-			__("Select Customer"));
-		});
-	},
-	set_invoice_items: function(frm, r) {
-		let invoice = r.message;
-		frm.doc.items = [];
-		(invoice.items || []).forEach((d) => {
-			frm.add_child('items', {item: d.item_code, qty: d.qty, rate: d.rate});
-		});
-		frm.set_value('grand_total', invoice.grand_total);
-		frm.set_value('last_sales_invoice', invoice.name);
-		frm.invoice = invoice;
-		frm.refresh();
-	}
-});
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.json b/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.json
deleted file mode 100644
index 3e4d593..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.json
+++ /dev/null
@@ -1,280 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 1, 
- "creation": "2017-09-15 15:10:24.530365", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "restaurant_table", 
-   "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": "Restaurant Table", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant Table", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "depends_on": "restaurant_table", 
-   "description": "Click Enter To Add", 
-   "fieldname": "add_item", 
-   "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": "Add Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "column_break_3", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "grand_total", 
-   "fieldtype": "Currency", 
-   "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": "Grand Total", 
-   "length": 0, 
-   "no_copy": 0, 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "last_sales_invoice", 
-   "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": "Last Sales Invoice", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Sales Invoice", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "depends_on": "restaurant_table", 
-   "fieldname": "current_order", 
-   "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": "Current Order", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "depends_on": "restaurant_table", 
-   "fieldname": "items", 
-   "fieldtype": "Table", 
-   "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": "Items", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant Order Entry Item", 
-   "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, 
-   "unique": 0
-  }
- ], 
- "has_web_view": 0, 
- "hide_heading": 0, 
- "hide_toolbar": 0, 
- "idx": 0, 
- "image_view": 0, 
- "in_create": 0, 
- "is_submittable": 0, 
- "issingle": 1, 
- "istable": 0, 
- "max_attachments": 0, 
- "modified": "2017-10-04 17:06:20.926999", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Order Entry", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 0, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 0, 
-   "role": "Restaurant Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.py b/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.py
deleted file mode 100644
index f9e75b4..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry/restaurant_order_entry.py
+++ /dev/null
@@ -1,91 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import json
-
-import frappe
-from frappe import _
-from frappe.model.document import Document
-
-from erpnext.controllers.queries import item_query
-
-
-class RestaurantOrderEntry(Document):
-	pass
-
-@frappe.whitelist()
-def get_invoice(table):
-	'''returns the active invoice linked to the given table'''
-	invoice_name = frappe.get_value('Sales Invoice', dict(restaurant_table = table, docstatus=0))
-	restaurant, menu_name = get_restaurant_and_menu_name(table)
-	if invoice_name:
-		invoice = frappe.get_doc('Sales Invoice', invoice_name)
-	else:
-		invoice = frappe.new_doc('Sales Invoice')
-		invoice.naming_series = frappe.db.get_value('Restaurant', restaurant, 'invoice_series_prefix')
-		invoice.is_pos = 1
-		default_customer = frappe.db.get_value('Restaurant', restaurant, 'default_customer')
-		if not default_customer:
-			frappe.throw(_('Please set default customer in Restaurant Settings'))
-		invoice.customer = default_customer
-
-	invoice.taxes_and_charges = frappe.db.get_value('Restaurant', restaurant, 'default_tax_template')
-	invoice.selling_price_list = frappe.db.get_value('Price List', dict(restaurant_menu=menu_name, enabled=1))
-
-	return invoice
-
-@frappe.whitelist()
-def sync(table, items):
-	'''Sync the sales order related to the table'''
-	invoice = get_invoice(table)
-	items = json.loads(items)
-
-	invoice.items = []
-	invoice.restaurant_table = table
-	for d in items:
-		invoice.append('items', dict(
-			item_code = d.get('item'),
-			qty = d.get('qty')
-		))
-
-	invoice.save()
-	return invoice.as_dict()
-
-@frappe.whitelist()
-def make_invoice(table, customer, mode_of_payment):
-	'''Make table based on Sales Order'''
-	restaurant, menu = get_restaurant_and_menu_name(table)
-	invoice = get_invoice(table)
-	invoice.customer = customer
-	invoice.restaurant = restaurant
-	invoice.calculate_taxes_and_totals()
-	invoice.append('payments', dict(mode_of_payment=mode_of_payment, amount=invoice.grand_total))
-	invoice.save()
-	invoice.submit()
-
-	frappe.msgprint(_('Invoice Created'), indicator='green', alert=True)
-
-	return invoice.name
-
-@frappe.whitelist()
-def item_query_restaurant(doctype='Item', txt='', searchfield='name', start=0, page_len=20, filters=None, as_dict=False):
-	'''Return items that are selected in active menu of the restaurant'''
-	restaurant, menu = get_restaurant_and_menu_name(filters['table'])
-	items = frappe.db.get_all('Restaurant Menu Item', ['item'], dict(parent = menu))
-	del filters['table']
-	filters['name'] = ('in', [d.item for d in items])
-
-	return item_query('Item', txt, searchfield, start, page_len, filters, as_dict)
-
-def get_restaurant_and_menu_name(table):
-	if not table:
-		frappe.throw(_('Please select a table'))
-
-	restaurant = frappe.db.get_value('Restaurant Table', table, 'restaurant')
-	menu = frappe.db.get_value('Restaurant', restaurant, 'active_menu')
-
-	if not menu:
-		frappe.throw(_('Please set an active menu for Restaurant {0}').format(restaurant))
-
-	return restaurant, menu
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry_item/__init__.py b/erpnext/restaurant/doctype/restaurant_order_entry_item/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry_item/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.json b/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.json
deleted file mode 100644
index 0240013..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.json
+++ /dev/null
@@ -1,163 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "beta": 0, 
- "creation": "2017-09-15 15:11:50.313241", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "item", 
-   "fieldtype": "Link", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Item", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Item", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "qty", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Qty", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "served", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Served", 
-   "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, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "rate", 
-   "fieldtype": "Currency", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Rate", 
-   "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, 
-   "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, 
- "modified": "2017-09-21 08:39:27.232175", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Order Entry Item", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.py b/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.py
deleted file mode 100644
index 0d9c236..0000000
--- a/erpnext/restaurant/doctype/restaurant_order_entry_item/restaurant_order_entry_item.py
+++ /dev/null
@@ -1,9 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from frappe.model.document import Document
-
-
-class RestaurantOrderEntryItem(Document):
-	pass
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/__init__.py b/erpnext/restaurant/doctype/restaurant_reservation/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.js b/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.js
deleted file mode 100644
index cebd105..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.js
+++ /dev/null
@@ -1,11 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Restaurant Reservation', {
-	setup: function(frm) {
-		frm.add_fetch('customer', 'customer_name', 'customer_name');
-	},
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.json b/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.json
deleted file mode 100644
index 17df2b9..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.json
+++ /dev/null
@@ -1,355 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "RES-RES-.YYYY.-.#####", 
- "beta": 1, 
- "creation": "2017-09-15 13:05:51.063661", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_in_quick_entry": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "status", 
-   "fieldtype": "Select", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Status", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Open\nWaitlisted\nCancelled\nNo Show\nSuccess", 
-   "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, 
-   "fieldname": "restaurant", 
-   "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": "Restaurant", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "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, 
-   "fieldname": "no_of_people", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "No of People", 
-   "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": 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, 
-   "fieldname": "reservation_time", 
-   "fieldtype": "Datetime", 
-   "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": "Reservation Time", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "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, 
-   "fieldname": "reservation_end_time", 
-   "fieldtype": "Datetime", 
-   "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": "Reservation End Time", 
-   "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, 
-   "fieldname": "column_break_4", 
-   "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, 
-   "fieldname": "customer", 
-   "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": "Customer", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Customer", 
-   "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, 
-   "fieldname": "customer_name", 
-   "fieldtype": "Data", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 1, 
-   "in_list_view": 1, 
-   "in_standard_filter": 1, 
-   "label": "Customer Name", 
-   "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": 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, 
-   "fieldname": "contact_number", 
-   "fieldtype": "Data", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Contact Number", 
-   "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
-  }
- ], 
- "has_web_view": 0, 
- "hide_heading": 0, 
- "hide_toolbar": 0, 
- "idx": 0, 
- "image_view": 0, 
- "in_create": 0, 
- "is_submittable": 0, 
- "issingle": 0, 
- "istable": 0, 
- "max_attachments": 0, 
- "modified": "2018-08-21 16:15:38.435656", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Reservation", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Restaurant Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0, 
- "track_views": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.py b/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.py
deleted file mode 100644
index 02ffaf6..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation.py
+++ /dev/null
@@ -1,14 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-from datetime import timedelta
-
-from frappe.model.document import Document
-from frappe.utils import get_datetime
-
-
-class RestaurantReservation(Document):
-	def validate(self):
-		if not self.reservation_end_time:
-			self.reservation_end_time = get_datetime(self.reservation_time) + timedelta(hours=1)
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation_calendar.js b/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation_calendar.js
deleted file mode 100644
index fe3dc57..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/restaurant_reservation_calendar.js
+++ /dev/null
@@ -1,18 +0,0 @@
-frappe.views.calendar["Restaurant Reservation"] = {
-	field_map: {
-		"start": "reservation_time",
-		"end": "reservation_end_time",
-		"id": "name",
-		"title": "customer_name",
-		"allDay": "allDay",
-	},
-	gantt: true,
-	filters: [
-		{
-			"fieldtype": "Data",
-			"fieldname": "customer_name",
-			"label": __("Customer Name")
-		}
-	],
-	get_events_method: "frappe.desk.calendar.get_events"
-};
diff --git a/erpnext/restaurant/doctype/restaurant_reservation/test_restaurant_reservation.py b/erpnext/restaurant/doctype/restaurant_reservation/test_restaurant_reservation.py
deleted file mode 100644
index 11a3541..0000000
--- a/erpnext/restaurant/doctype/restaurant_reservation/test_restaurant_reservation.py
+++ /dev/null
@@ -1,8 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-
-class TestRestaurantReservation(unittest.TestCase):
-	pass
diff --git a/erpnext/restaurant/doctype/restaurant_table/__init__.py b/erpnext/restaurant/doctype/restaurant_table/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/restaurant/doctype/restaurant_table/__init__.py
+++ /dev/null
diff --git a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.js b/erpnext/restaurant/doctype/restaurant_table/restaurant_table.js
deleted file mode 100644
index a55605c..0000000
--- a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.js
+++ /dev/null
@@ -1,8 +0,0 @@
-// Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-// For license information, please see license.txt
-
-frappe.ui.form.on('Restaurant Table', {
-	refresh: function(frm) {
-
-	}
-});
diff --git a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.json b/erpnext/restaurant/doctype/restaurant_table/restaurant_table.json
deleted file mode 100644
index 5fc6e62..0000000
--- a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.json
+++ /dev/null
@@ -1,156 +0,0 @@
-{
- "allow_copy": 0, 
- "allow_guest_to_view": 0, 
- "allow_import": 0, 
- "allow_rename": 0, 
- "autoname": "", 
- "beta": 1, 
- "creation": "2017-09-15 12:45:24.717355", 
- "custom": 0, 
- "docstatus": 0, 
- "doctype": "DocType", 
- "document_type": "Setup", 
- "editable_grid": 1, 
- "engine": "InnoDB", 
- "fields": [
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "restaurant", 
-   "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": "Restaurant", 
-   "length": 0, 
-   "no_copy": 0, 
-   "options": "Restaurant", 
-   "permlevel": 0, 
-   "precision": "", 
-   "print_hide": 0, 
-   "print_hide_if_no_value": 0, 
-   "read_only": 0, 
-   "remember_last_selected_value": 0, 
-   "report_hide": 0, 
-   "reqd": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "fieldname": "no_of_seats", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "No of Seats", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 0, 
-   "unique": 0
-  }, 
-  {
-   "allow_bulk_edit": 0, 
-   "allow_on_submit": 0, 
-   "bold": 0, 
-   "collapsible": 0, 
-   "columns": 0, 
-   "default": "1", 
-   "fieldname": "minimum_seating", 
-   "fieldtype": "Int", 
-   "hidden": 0, 
-   "ignore_user_permissions": 0, 
-   "ignore_xss_filter": 0, 
-   "in_filter": 0, 
-   "in_global_search": 0, 
-   "in_list_view": 1, 
-   "in_standard_filter": 0, 
-   "label": "Minimum Seating", 
-   "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": 1, 
-   "search_index": 0, 
-   "set_only_once": 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": 0, 
- "max_attachments": 0, 
- "modified": "2017-12-09 12:13:24.382345", 
- "modified_by": "Administrator", 
- "module": "Restaurant", 
- "name": "Restaurant Table", 
- "name_case": "", 
- "owner": "Administrator", 
- "permissions": [
-  {
-   "amend": 0, 
-   "apply_user_permissions": 0, 
-   "cancel": 0, 
-   "create": 1, 
-   "delete": 1, 
-   "email": 1, 
-   "export": 1, 
-   "if_owner": 0, 
-   "import": 0, 
-   "permlevel": 0, 
-   "print": 1, 
-   "read": 1, 
-   "report": 1, 
-   "role": "Restaurant Manager", 
-   "set_user_permissions": 0, 
-   "share": 1, 
-   "submit": 0, 
-   "write": 1
-  }
- ], 
- "quick_entry": 1, 
- "read_only": 0, 
- "read_only_onload": 0, 
- "restrict_to_domain": "Hospitality", 
- "show_name_in_global_search": 0, 
- "sort_field": "modified", 
- "sort_order": "DESC", 
- "track_changes": 1, 
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.py b/erpnext/restaurant/doctype/restaurant_table/restaurant_table.py
deleted file mode 100644
index 29f8a1a..0000000
--- a/erpnext/restaurant/doctype/restaurant_table/restaurant_table.py
+++ /dev/null
@@ -1,14 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and contributors
-# For license information, please see license.txt
-
-
-import re
-
-from frappe.model.document import Document
-from frappe.model.naming import make_autoname
-
-
-class RestaurantTable(Document):
-	def autoname(self):
-		prefix = re.sub('-+', '-', self.restaurant.replace(' ', '-'))
-		self.name = make_autoname(prefix + '-.##')
diff --git a/erpnext/restaurant/doctype/restaurant_table/test_restaurant_table.py b/erpnext/restaurant/doctype/restaurant_table/test_restaurant_table.py
deleted file mode 100644
index 00d14d2..0000000
--- a/erpnext/restaurant/doctype/restaurant_table/test_restaurant_table.py
+++ /dev/null
@@ -1,14 +0,0 @@
-# Copyright (c) 2017, Frappe Technologies Pvt. Ltd. and Contributors
-# See license.txt
-
-import unittest
-
-test_records = [
-	dict(restaurant='Test Restaurant 1', no_of_seats=5, minimum_seating=1),
-	dict(restaurant='Test Restaurant 1', no_of_seats=5, minimum_seating=1),
-	dict(restaurant='Test Restaurant 1', no_of_seats=5, minimum_seating=1),
-	dict(restaurant='Test Restaurant 1', no_of_seats=5, minimum_seating=1),
-]
-
-class TestRestaurantTable(unittest.TestCase):
-	pass
diff --git a/erpnext/selling/doctype/customer/customer.py b/erpnext/selling/doctype/customer/customer.py
index b7f74df..d74d5a6 100644
--- a/erpnext/selling/doctype/customer/customer.py
+++ b/erpnext/selling/doctype/customer/customer.py
@@ -142,7 +142,7 @@
 			self.update_lead_status()
 
 		if self.flags.is_new_doc:
-			self.create_lead_address_contact()
+			self.link_lead_address_and_contact()
 
 		self.update_customer_groups()
 
@@ -176,62 +176,24 @@
 		if self.lead_name:
 			frappe.db.set_value("Lead", self.lead_name, "status", "Converted")
 
-	def create_lead_address_contact(self):
+	def link_lead_address_and_contact(self):
 		if self.lead_name:
-			# assign lead address to customer (if already not set)
-			address_names = frappe.get_all('Dynamic Link', filters={
-								"parenttype":"Address",
-								"link_doctype":"Lead",
-								"link_name":self.lead_name
-							}, fields=["parent as name"])
+			# assign lead address and contact to customer (if already not set)
+			linked_contacts_and_addresses = frappe.get_all(
+				"Dynamic Link",
+				filters=[
+					["parenttype", "in", ["Contact", "Address"]],
+					["link_doctype", "=", "Lead"],
+					["link_name", "=", self.lead_name],
+				],
+				fields=["parent as name", "parenttype as doctype"],
+			)
 
-			for address_name in address_names:
-				address = frappe.get_doc('Address', address_name.get('name'))
-				if not address.has_link('Customer', self.name):
-					address.append('links', dict(link_doctype='Customer', link_name=self.name))
-					address.save(ignore_permissions=self.flags.ignore_permissions)
-
-			lead = frappe.db.get_value("Lead", self.lead_name, ["company_name", "lead_name", "email_id", "phone", "mobile_no", "gender", "salutation"], as_dict=True)
-
-			if not lead.lead_name:
-				frappe.throw(_("Please mention the Lead Name in Lead {0}").format(self.lead_name))
-
-			contact_names = frappe.get_all('Dynamic Link', filters={
-								"parenttype":"Contact",
-								"link_doctype":"Lead",
-								"link_name":self.lead_name
-							}, fields=["parent as name"])
-
-			for contact_name in contact_names:
-				contact = frappe.get_doc('Contact', contact_name.get('name'))
-				if not contact.has_link('Customer', self.name):
-					contact.append('links', dict(link_doctype='Customer', link_name=self.name))
-					contact.save(ignore_permissions=self.flags.ignore_permissions)
-
-			if not contact_names:
-				lead.lead_name = lead.lead_name.lstrip().split(" ")
-				lead.first_name = lead.lead_name[0]
-				lead.last_name = " ".join(lead.lead_name[1:])
-
-				# create contact from lead
-				contact = frappe.new_doc('Contact')
-				contact.first_name = lead.first_name
-				contact.last_name = lead.last_name
-				contact.gender = lead.gender
-				contact.salutation = lead.salutation
-				contact.email_id = lead.email_id
-				contact.phone = lead.phone
-				contact.mobile_no = lead.mobile_no
-				contact.is_primary_contact = 1
-				contact.append('links', dict(link_doctype='Customer', link_name=self.name))
-				if lead.email_id:
-					contact.append('email_ids', dict(email_id=lead.email_id, is_primary=1))
-				if lead.mobile_no:
-					contact.append('phone_nos', dict(phone=lead.mobile_no, is_primary_mobile_no=1))
-				contact.flags.ignore_permissions = self.flags.ignore_permissions
-				contact.autoname()
-				if not frappe.db.exists("Contact", contact.name):
-					contact.insert()
+			for row in linked_contacts_and_addresses:
+				linked_doc = frappe.get_doc(row.doctype, row.name)
+				if not linked_doc.has_link('Customer', self.name):
+					linked_doc.append('links', dict(link_doctype='Customer', link_name=self.name))
+					linked_doc.save(ignore_permissions=self.flags.ignore_permissions)
 
 	def validate_name_with_customer_group(self):
 		if frappe.db.exists("Customer Group", self.name):
diff --git a/erpnext/selling/report/customer_credit_balance/customer_credit_balance.py b/erpnext/selling/report/customer_credit_balance/customer_credit_balance.py
index 777b02c..dd49f13 100644
--- a/erpnext/selling/report/customer_credit_balance/customer_credit_balance.py
+++ b/erpnext/selling/report/customer_credit_balance/customer_credit_balance.py
@@ -23,19 +23,24 @@
 		row = []
 
 		outstanding_amt = get_customer_outstanding(d.name, filters.get("company"),
-			ignore_outstanding_sales_order=d.bypass_credit_limit_check_at_sales_order)
+			ignore_outstanding_sales_order=d.bypass_credit_limit_check)
 
 		credit_limit = get_credit_limit(d.name, filters.get("company"))
 
 		bal = flt(credit_limit) - flt(outstanding_amt)
 
 		if customer_naming_type == "Naming Series":
-			row = [d.name, d.customer_name, credit_limit, outstanding_amt, bal,
-				d.bypass_credit_limit_check, d.is_frozen,
-          d.disabled]
+			row = [
+				d.name, d.customer_name, credit_limit,
+				outstanding_amt, bal, d.bypass_credit_limit_check,
+				d.is_frozen, d.disabled
+			]
 		else:
-			row = [d.name, credit_limit, outstanding_amt, bal,
-          d.bypass_credit_limit_check_at_sales_order, d.is_frozen, d.disabled]
+			row = [
+				d.name, credit_limit, outstanding_amt, bal,
+				d.bypass_credit_limit_check, d.is_frozen,
+				d.disabled
+			]
 
 		if credit_limit:
 			data.append(row)
diff --git a/erpnext/selling/report/sales_order_analysis/sales_order_analysis.py b/erpnext/selling/report/sales_order_analysis/sales_order_analysis.py
index b2bf546..3e22d0f 100644
--- a/erpnext/selling/report/sales_order_analysis/sales_order_analysis.py
+++ b/erpnext/selling/report/sales_order_analysis/sales_order_analysis.py
@@ -85,7 +85,7 @@
 			and so.docstatus = 1
 			{conditions}
 		GROUP BY soi.name
-		ORDER BY so.transaction_date ASC
+		ORDER BY so.transaction_date ASC, soi.item_code ASC
 	""".format(conditions=conditions), filters, as_dict=1)
 
 	return data
diff --git a/erpnext/setup/doctype/item_group/item_group.py b/erpnext/setup/doctype/item_group/item_group.py
index c94b346..9f1eb75 100644
--- a/erpnext/setup/doctype/item_group/item_group.py
+++ b/erpnext/setup/doctype/item_group/item_group.py
@@ -3,6 +3,7 @@
 
 
 import copy
+from urllib.parse import quote
 
 import frappe
 from frappe import _
@@ -10,7 +11,6 @@
 from frappe.utils.nestedset import NestedSet
 from frappe.website.utils import clear_cache
 from frappe.website.website_generator import WebsiteGenerator
-from six.moves.urllib.parse import quote
 
 from erpnext.shopping_cart.filters import ProductFiltersBuilder
 from erpnext.shopping_cart.product_info import set_product_info_for_website
diff --git a/erpnext/setup/install.py b/erpnext/setup/install.py
index bafaab8..1d7bad2 100644
--- a/erpnext/setup/install.py
+++ b/erpnext/setup/install.py
@@ -189,7 +189,7 @@
 
 	user_type_limit = {}
 	for user_type, data in user_types.items():
-		user_type_limit.setdefault(frappe.scrub(user_type), 10)
+		user_type_limit.setdefault(frappe.scrub(user_type), 20)
 
 	update_site_config('user_type_doctype_limit', user_type_limit)
 
@@ -204,15 +204,33 @@
 			'apply_user_permission_on': 'Employee',
 			'user_id_field': 'user_id',
 			'doctypes': {
-				'Salary Slip': ['read'],
+				# masters
+				'Holiday List': ['read'],
 				'Employee': ['read', 'write'],
+				# payroll
+				'Salary Slip': ['read'],
+				'Employee Benefit Application': ['read', 'write', 'create', 'delete'],
+				# expenses
 				'Expense Claim': ['read', 'write', 'create', 'delete'],
+				'Employee Advance': ['read', 'write', 'create', 'delete'],
+				# leave and attendance
 				'Leave Application': ['read', 'write', 'create', 'delete'],
 				'Attendance Request': ['read', 'write', 'create', 'delete'],
 				'Compensatory Leave Request': ['read', 'write', 'create', 'delete'],
+				# tax
 				'Employee Tax Exemption Declaration': ['read', 'write', 'create', 'delete'],
 				'Employee Tax Exemption Proof Submission': ['read', 'write', 'create', 'delete'],
-				'Timesheet': ['read', 'write', 'create', 'delete', 'submit', 'cancel', 'amend']
+				# projects
+				'Timesheet': ['read', 'write', 'create', 'delete', 'submit', 'cancel', 'amend'],
+				# trainings
+				'Training Program': ['read'],
+				'Training Feedback': ['read', 'write', 'create', 'delete', 'submit', 'cancel', 'amend'],
+				# shifts
+				'Shift Request': ['read', 'write', 'create', 'delete', 'submit', 'cancel', 'amend'],
+				# misc
+				'Employee Grievance': ['read', 'write', 'create', 'delete'],
+				'Employee Referral': ['read', 'write', 'create', 'delete'],
+				'Travel Request': ['read', 'write', 'create', 'delete']
 			}
 		}
 	}
diff --git a/erpnext/stock/doctype/delivery_note/delivery_note.py b/erpnext/stock/doctype/delivery_note/delivery_note.py
index 70d48a4..d1e2244 100644
--- a/erpnext/stock/doctype/delivery_note/delivery_note.py
+++ b/erpnext/stock/doctype/delivery_note/delivery_note.py
@@ -14,6 +14,7 @@
 from erpnext.controllers.selling_controller import SellingController
 from erpnext.stock.doctype.batch.batch import set_batch_nos
 from erpnext.stock.doctype.serial_no.serial_no import get_delivery_note_serial_no
+from erpnext.stock.utils import calculate_mapped_packed_items_return
 
 form_grid_templates = {
 	"items": "templates/form_grid/item_grid.html"
@@ -128,8 +129,12 @@
 		self.validate_uom_is_integer("uom", "qty")
 		self.validate_with_previous_doc()
 
-		from erpnext.stock.doctype.packed_item.packed_item import make_packing_list
-		make_packing_list(self)
+		# Keeps mapped packed_items in case product bundle is updated.
+		if self.is_return and self.return_against:
+			calculate_mapped_packed_items_return(self)
+		else:
+			from erpnext.stock.doctype.packed_item.packed_item import make_packing_list
+			make_packing_list(self)
 
 		if self._action != 'submit' and not self.is_return:
 			set_batch_nos(self, 'warehouse', throw=True)
diff --git a/erpnext/stock/doctype/delivery_note/test_delivery_note.py b/erpnext/stock/doctype/delivery_note/test_delivery_note.py
index 4f89a19..bd18e78 100644
--- a/erpnext/stock/doctype/delivery_note/test_delivery_note.py
+++ b/erpnext/stock/doctype/delivery_note/test_delivery_note.py
@@ -386,8 +386,7 @@
 		self.assertEqual(actual_qty, 25)
 
 		#  return bundled item
-		dn1 = create_delivery_note(item_code='_Test Product Bundle Item', is_return=1,
-			return_against=dn.name, qty=-2, rate=500, company=company, warehouse="Stores - TCP1", expense_account="Cost of Goods Sold - TCP1", cost_center="Main - TCP1")
+		dn1 = create_return_delivery_note(source_name=dn.name, rate=500, qty=-2)
 
 		# qty after return
 		actual_qty = get_qty_after_transaction(warehouse="Stores - TCP1")
@@ -823,6 +822,15 @@
 
 		automatically_fetch_payment_terms(enable=0)
 
+def create_return_delivery_note(**args):
+	args = frappe._dict(args)
+	from erpnext.controllers.sales_and_purchase_return import make_return_doc
+	doc = make_return_doc("Delivery Note", args.source_name, None)
+	doc.items[0].rate = args.rate
+	doc.items[0].qty = args.qty
+	doc.submit()
+	return doc
+
 def create_delivery_note(**args):
 	dn = frappe.new_doc("Delivery Note")
 	args = frappe._dict(args)
diff --git a/erpnext/stock/doctype/item/item.json b/erpnext/stock/doctype/item/item.json
index 29abd45..2d28cc0 100644
--- a/erpnext/stock/doctype/item/item.json
+++ b/erpnext/stock/doctype/item/item.json
@@ -28,6 +28,7 @@
   "standard_rate",
   "is_fixed_asset",
   "auto_create_assets",
+  "is_grouped_asset",
   "asset_category",
   "asset_naming_series",
   "over_delivery_receipt_allowance",
@@ -1026,6 +1027,13 @@
    "fieldname": "grant_commission",
    "fieldtype": "Check",
    "label": "Grant Commission"
+  },
+  {
+   "default": "0",
+   "depends_on": "auto_create_assets",
+   "fieldname": "is_grouped_asset",
+   "fieldtype": "Check",
+   "label": "Create Grouped Asset"
   }
  ],
  "has_web_view": 1,
@@ -1034,7 +1042,7 @@
  "image_field": "image",
  "index_web_pages_for_search": 1,
  "links": [],
- "modified": "2021-12-14 04:13:16.857534",
+ "modified": "2022-01-18 12:57:54.273202",
  "modified_by": "Administrator",
  "module": "Stock",
  "name": "Item",
@@ -1104,6 +1112,7 @@
  "show_preview_popup": 1,
  "sort_field": "modified",
  "sort_order": "DESC",
+ "states": [],
  "title_field": "item_name",
  "track_changes": 1
 }
\ No newline at end of file
diff --git a/erpnext/stock/doctype/item/item.py b/erpnext/stock/doctype/item/item.py
index 281e881..d99fadc 100644
--- a/erpnext/stock/doctype/item/item.py
+++ b/erpnext/stock/doctype/item/item.py
@@ -602,14 +602,6 @@
 							frappe.throw(_("Barcode {0} is not a valid {1} code").format(
 								item_barcode.barcode, item_barcode.barcode_type), InvalidBarcode)
 
-					if item_barcode.barcode != item_barcode.name:
-						# if barcode is getting updated , the row name has to reset.
-						# Delete previous old row doc and re-enter row as if new to reset name in db.
-						item_barcode.set("__islocal", True)
-						item_barcode_entry_name = item_barcode.name
-						item_barcode.name = None
-						frappe.delete_doc("Item Barcode", item_barcode_entry_name)
-
 	def validate_warehouse_for_reorder(self):
 		'''Validate Reorder level table for duplicate and conditional mandatory'''
 		warehouse = []
diff --git a/erpnext/stock/doctype/stock_entry/stock_entry.py b/erpnext/stock/doctype/stock_entry/stock_entry.py
index a61b319..60154af 100644
--- a/erpnext/stock/doctype/stock_entry/stock_entry.py
+++ b/erpnext/stock/doctype/stock_entry/stock_entry.py
@@ -1445,14 +1445,15 @@
 							qty = req_qty_each * flt(self.fg_completed_qty)
 
 			elif backflushed_materials.get(item.item_code):
+				precision = frappe.get_precision("Stock Entry Detail", "qty")
 				for d in backflushed_materials.get(item.item_code):
-					if d.get(item.warehouse):
+					if d.get(item.warehouse) > 0:
 						if (qty > req_qty):
-							qty = (qty/trans_qty) * flt(self.fg_completed_qty)
+							qty = ((flt(qty, precision) - flt(d.get(item.warehouse), precision))
+								/ (flt(trans_qty, precision) - flt(produced_qty, precision))
+							) * flt(self.fg_completed_qty)
 
-						if consumed_qty and frappe.db.get_single_value("Manufacturing Settings",
-							"material_consumption"):
-							qty -= consumed_qty
+							d[item.warehouse] -= qty
 
 			if cint(frappe.get_cached_value('UOM', item.stock_uom, 'must_be_whole_number')):
 				qty = frappe.utils.ceil(qty)
diff --git a/erpnext/stock/doctype/stock_ledger_entry/test_stock_ledger_entry.py b/erpnext/stock/doctype/stock_ledger_entry/test_stock_ledger_entry.py
index cafbd75..a1030d5 100644
--- a/erpnext/stock/doctype/stock_ledger_entry/test_stock_ledger_entry.py
+++ b/erpnext/stock/doctype/stock_ledger_entry/test_stock_ledger_entry.py
@@ -5,7 +5,10 @@
 from frappe.core.page.permission_manager.permission_manager import reset
 from frappe.utils import add_days, today
 
-from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note
+from erpnext.stock.doctype.delivery_note.test_delivery_note import (
+	create_delivery_note,
+	create_return_delivery_note,
+)
 from erpnext.stock.doctype.item.test_item import make_item
 from erpnext.stock.doctype.landed_cost_voucher.test_landed_cost_voucher import (
 	create_landed_cost_voucher,
@@ -232,8 +235,7 @@
 		self.assertEqual(outgoing_rate, 100)
 
 		# Return Entry: Qty = -2, Rate = 150
-		return_dn = create_delivery_note(is_return=1, return_against=dn.name, item_code=bundled_item, qty=-2, rate=150,
-			company=company, warehouse="Stores - _TC", expense_account="Cost of Goods Sold - _TC", cost_center="Main - _TC")
+		return_dn = create_return_delivery_note(source_name=dn.name, rate=150, qty=-2)
 
 		# check incoming rate for Return entry
 		incoming_rate, stock_value_difference = frappe.db.get_value("Stock Ledger Entry",
diff --git a/erpnext/stock/doctype/stock_reconciliation/test_stock_reconciliation.py b/erpnext/stock/doctype/stock_reconciliation/test_stock_reconciliation.py
index c4ddc9e..428370c 100644
--- a/erpnext/stock/doctype/stock_reconciliation/test_stock_reconciliation.py
+++ b/erpnext/stock/doctype/stock_reconciliation/test_stock_reconciliation.py
@@ -6,7 +6,7 @@
 
 
 import frappe
-from frappe.utils import add_days, flt, nowdate, nowtime, random_string
+from frappe.utils import add_days, cstr, flt, nowdate, nowtime, random_string
 
 from erpnext.accounts.utils import get_stock_and_account_balance
 from erpnext.stock.doctype.item.test_item import create_item
@@ -439,8 +439,8 @@
 		self.assertRaises(frappe.ValidationError, sr.submit)
 
 	def test_serial_no_cancellation(self):
-
 		from erpnext.stock.doctype.stock_entry.test_stock_entry import make_stock_entry
+
 		item = create_item("Stock-Reco-Serial-Item-9", is_stock_item=1)
 		if not item.has_serial_no:
 			item.has_serial_no = 1
@@ -466,6 +466,31 @@
 		self.assertEqual(len(active_sr_no), 10)
 
 
+	def test_serial_no_creation_and_inactivation(self):
+		item = create_item("_TestItemCreatedWithStockReco", is_stock_item=1)
+		if not item.has_serial_no:
+			item.has_serial_no = 1
+			item.save()
+
+		item_code = item.name
+		warehouse = "_Test Warehouse - _TC"
+
+		sr = create_stock_reconciliation(item_code=item.name, warehouse=warehouse,
+				serial_no="SR-CREATED-SR-NO", qty=1, do_not_submit=True, rate=100)
+		sr.save()
+		self.assertEqual(cstr(sr.items[0].current_serial_no), "")
+		sr.submit()
+
+		active_sr_no = frappe.get_all("Serial No",
+				filters={"item_code": item_code, "warehouse": warehouse, "status": "Active"})
+		self.assertEqual(len(active_sr_no), 1)
+
+		sr.cancel()
+		active_sr_no = frappe.get_all("Serial No",
+				filters={"item_code": item_code, "warehouse": warehouse, "status": "Active"})
+		self.assertEqual(len(active_sr_no), 0)
+
+
 def create_batch_item_with_batch(item_name, batch_id):
 	batch_item_doc = create_item(item_name, is_stock_item=1)
 	if not batch_item_doc.has_batch_no:
diff --git a/erpnext/stock/report/stock_ledger/stock_ledger.js b/erpnext/stock/report/stock_ledger/stock_ledger.js
index fe2417b..ef7c2cc 100644
--- a/erpnext/stock/report/stock_ledger/stock_ledger.js
+++ b/erpnext/stock/report/stock_ledger/stock_ledger.js
@@ -86,10 +86,10 @@
 	],
 	"formatter": function (value, row, column, data, default_formatter) {
 		value = default_formatter(value, row, column, data);
-		if (column.fieldname == "out_qty" && data.out_qty < 0) {
+		if (column.fieldname == "out_qty" && data && data.out_qty < 0) {
 			value = "<span style='color:red'>" + value + "</span>";
 		}
-		else if (column.fieldname == "in_qty" && data.in_qty > 0) {
+		else if (column.fieldname == "in_qty" && data && data.in_qty > 0) {
 			value = "<span style='color:green'>" + value + "</span>";
 		}
 
diff --git a/erpnext/stock/report/test_reports.py b/erpnext/stock/report/test_reports.py
index 1dcf863..525af40 100644
--- a/erpnext/stock/report/test_reports.py
+++ b/erpnext/stock/report/test_reports.py
@@ -1,6 +1,8 @@
 import unittest
 from typing import List, Tuple
 
+import frappe
+
 from erpnext.tests.utils import ReportFilters, ReportName, execute_script_report
 
 DEFAULT_FILTERS = {
@@ -10,8 +12,12 @@
 }
 
 
+batch = frappe.db.get_value("Batch", fieldname=["name"], as_dict=True, order_by="creation desc")
+
 REPORT_FILTER_TEST_CASES: List[Tuple[ReportName, ReportFilters]] = [
 	("Stock Ledger", {"_optional": True}),
+	("Stock Ledger", {"batch_no": batch}),
+	("Stock Ledger", {"item_code": "_Test Item", "warehouse": "_Test Warehouse - _TC"}),
 	("Stock Balance", {"_optional": True}),
 	("Stock Projected Qty", {"_optional": True}),
 	("Batch-Wise Balance History", {}),
@@ -40,6 +46,13 @@
 	("Item Variant Details", {"item": "_Test Variant Item",}),
 	("Total Stock Summary", {"group_by": "warehouse",}),
 	("Batch Item Expiry Status", {}),
+	("Incorrect Stock Value Report", {"company": "_Test Company with perpetual inventory"}),
+	("Incorrect Serial No Valuation", {}),
+	("Incorrect Balance Qty After Transaction", {}),
+	("Supplier-Wise Sales Analytics", {}),
+	("Item Prices", {"items": "Enabled Items only"}),
+	("Delayed Item Report", {"based_on": "Sales Invoice"}),
+	("Delayed Item Report", {"based_on": "Delivery Note"}),
 	("Stock Ageing", {"range1": 30, "range2": 60, "range3": 90, "_optional": True}),
 	("Stock Ledger Invariant Check",
 		{
diff --git a/erpnext/stock/utils.py b/erpnext/stock/utils.py
index 3c70b41..f620c18 100644
--- a/erpnext/stock/utils.py
+++ b/erpnext/stock/utils.py
@@ -103,7 +103,7 @@
 			serial_nos = get_serial_nos_data_after_transactions(args)
 
 			return ((last_entry.qty_after_transaction, last_entry.valuation_rate, serial_nos)
-				if last_entry else (0.0, 0.0, 0.0))
+				if last_entry else (0.0, 0.0, None))
 		else:
 			return (last_entry.qty_after_transaction, last_entry.valuation_rate) if last_entry else (0.0, 0.0)
 	else:
@@ -419,6 +419,19 @@
 	if reposting_in_progress:
 		frappe.msgprint(_("Item valuation reposting in progress. Report might show incorrect item valuation."), alert=1)
 
+
+def calculate_mapped_packed_items_return(return_doc):
+	parent_items = set([item.parent_item for item in return_doc.packed_items])
+	against_doc = frappe.get_doc(return_doc.doctype, return_doc.return_against)
+
+	for original_bundle, returned_bundle in zip(against_doc.items, return_doc.items):
+		if original_bundle.item_code in parent_items:
+			for returned_packed_item, original_packed_item in zip(return_doc.packed_items, against_doc.packed_items):
+				if returned_packed_item.parent_item == original_bundle.item_code:
+					returned_packed_item.parent_detail_docname = returned_bundle.name
+					returned_packed_item.qty = (original_packed_item.qty / original_bundle.qty) * returned_bundle.qty
+
+
 def check_pending_reposting(posting_date: str, throw_error: bool = True) -> bool:
 	"""Check if there are pending reposting job till the specified posting date."""
 
diff --git a/erpnext/tests/utils.py b/erpnext/tests/utils.py
index bc9f04e..2bd7e9e 100644
--- a/erpnext/tests/utils.py
+++ b/erpnext/tests/utils.py
@@ -92,6 +92,8 @@
 		for key, value in settings_dict.items():
 			setattr(settings, key, value)
 		settings.save()
+		# singles are cached by default, clear to avoid flake
+		frappe.db.value_cache[settings] = {}
 		yield # yield control to calling function
 
 	finally: