[mapper] quotation-sales order for mapping in parent + child items
diff --git a/controllers/selling_controller.py b/controllers/selling_controller.py
index 087df34..140e0c0 100644
--- a/controllers/selling_controller.py
+++ b/controllers/selling_controller.py
@@ -262,7 +262,9 @@
 			
 	def validate_order_type(self):
 		valid_types = ["Sales", "Maintenance", "Shopping Cart"]
-		if self.doc.order_type not in valid_types:
+		if not self.doc.order_type:
+			self.doc.order_type = "Sales"
+		elif self.doc.order_type not in valid_types:
 			msgprint(_(self.meta.get_label("order_type")) + " " + 
 				_("must be one of") + ": " + comma_or(valid_types),
 				raise_exception=True)
diff --git a/selling/doctype/lead/lead.py b/selling/doctype/lead/lead.py
index c702375..3a3d8e5 100644
--- a/selling/doctype/lead/lead.py
+++ b/selling/doctype/lead/lead.py
@@ -113,6 +113,6 @@
 				"contact_no": "phone_1",
 				"fax": "fax_1"
 			}
-		}})
+		}}, target_doclist)
 		
 	return [d.fields for d in doclist]
\ No newline at end of file
diff --git a/selling/doctype/quotation/quotation.js b/selling/doctype/quotation/quotation.js
index 66d4d0b..259c810 100644
--- a/selling/doctype/quotation/quotation.js
+++ b/selling/doctype/quotation/quotation.js
@@ -119,20 +119,10 @@
 // Make Sales Order
 // =====================================================================================
 cur_frm.cscript['Make Sales Order'] = function() {
-	var doc = cur_frm.doc;
-
-	if (doc.docstatus == 1) {
-		var n = wn.model.make_new_doc_and_get_name("Sales Order");
-		$c('dt_map', args={
-			'docs':wn.model.compress([locals["Sales Order"][n]]),
-			'from_doctype':'Quotation',
-			'to_doctype':'Sales Order',
-			'from_docname':doc.name,
-			'from_to_list':"[['Quotation', 'Sales Order'], ['Quotation Item', 'Sales Order Item'],['Sales Taxes and Charges','Sales Taxes and Charges'], ['Sales Team', 'Sales Team'], ['TC Detail', 'TC Detail']]"
-		}, function(r,rt) {
-			loaddoc("Sales Order", n);
-		});
-	}
+	wn.model.open_mapped_doc({
+		method: "selling.doctype.quotation.quotation.make_sales_order",
+		source_name: cur_frm.doc.name
+	})
 }
 
 //pull enquiry details
diff --git a/selling/doctype/quotation/quotation.py b/selling/doctype/quotation/quotation.py
index 24242de..1adce20 100644
--- a/selling/doctype/quotation/quotation.py
+++ b/selling/doctype/quotation/quotation.py
@@ -250,3 +250,37 @@
 		sql("delete from `tabCommunication Log` where parent = '%s'"%self.doc.name)
 		for d in getlist(self.doclist, 'follow_up'):
 			d.save()
+
+@webnotes.whitelist()
+def make_sales_order(source_name, target_doclist=None):
+	from webnotes.model.mapper import get_mapped_doclist
+	
+	if target_doclist:
+		target_doclist = json.loads(target_doclist)
+
+	doclist = get_mapped_doclist("Quotation", source_name, {
+			"Quotation": {
+				"doctype": "Sales Order", 
+				"field_map": {
+					"name": "quotation_no", 
+					"transaction_date": "quotation_date"
+				},
+				"validation": {
+					"docstatus": ["=", 1]
+				}
+			}, 
+			"Quotation Item": {
+				"doctype": "Sales Order Item", 
+				"field_map": {
+					"parent": "prevdoc_docname"
+				}
+			}, 
+			"Sales Taxes and Charges": {
+				"doctype": "Sales Taxes and Charges",
+			}, 
+			"Sales Team": {
+				"doctype": "Sales Team",
+			}
+		}, target_doclist)
+		
+	return [d.fields for d in doclist]
\ No newline at end of file
diff --git a/selling/doctype/quotation/test_quotation.py b/selling/doctype/quotation/test_quotation.py
index 2c9264d..de609b8 100644
--- a/selling/doctype/quotation/test_quotation.py
+++ b/selling/doctype/quotation/test_quotation.py
@@ -1,17 +1,31 @@
-import webnotes
+import webnotes, json
 from webnotes.utils import flt
 import unittest
 
 test_dependencies = ["Sales BOM"]
 
-class TestLead(unittest.TestCase):
+class TestQuotation(unittest.TestCase):
 	def test_make_sales_order(self):
-		lead = webnotes.bean("Lead", "_T-Lead-00001")
-		lead.make_controller()
-		customer = lead.controller.make_customer()
-		self.assertEquals(customer[0].doctype, "Customer")
-		self.assertEquals(customer[0].lead_name, lead.doc.name)
-		webnotes.bean(customer).insert()
+		from selling.doctype.quotation.quotation import make_sales_order
+		
+		self.assertRaises(webnotes.ValidationError, make_sales_order, "_T-Quotation-00001")
+		
+		quotation = webnotes.bean("Quotation","_T-Quotation-00001")
+		quotation.submit()
+
+		sales_order = make_sales_order("_T-Quotation-00001")
+				
+		self.assertEquals(sales_order[0]["doctype"], "Sales Order")
+		self.assertEquals(len(sales_order), 2)
+		self.assertEquals(sales_order[1]["doctype"], "Sales Order Item")
+		self.assertEquals(sales_order[1]["prevdoc_docname"], "_T-Quotation-00001")
+		self.assertEquals(sales_order[0]["customer"], "_Test Customer")
+		
+		sales_order[0]["delivery_date"] = "2014-01-01"
+		
+
+		webnotes.print_messages = True
+		webnotes.bean(sales_order).insert()
 
 
 test_records = [
diff --git a/selling/doctype/sales_order/sales_order.py b/selling/doctype/sales_order/sales_order.py
index 461965a..ec365a2 100644
--- a/selling/doctype/sales_order/sales_order.py
+++ b/selling/doctype/sales_order/sales_order.py
@@ -167,7 +167,7 @@
 	def validate_order_type(self):
 		super(DocType, self).validate_order_type()
 		
-		#validate delivery date
+	def validate_delivery_date(self):
 		if self.doc.order_type == 'Sales' and not self.doc.delivery_date:
 			msgprint("Please enter 'Expected Delivery Date'")
 			raise Exception
@@ -186,6 +186,7 @@
 		
 		self.validate_fiscal_year()
 		self.validate_order_type()
+		self.validate_delivery_date()
 		self.validate_mandatory()
 		self.validate_proj_cust()
 		self.validate_po()