Add Items Variants Attributes columns to Stock Balance Report
diff --git a/erpnext/stock/report/stock_balance/stock_balance.js b/erpnext/stock/report/stock_balance/stock_balance.js
index 90f4de0..a648efe 100644
--- a/erpnext/stock/report/stock_balance/stock_balance.js
+++ b/erpnext/stock/report/stock_balance/stock_balance.js
@@ -40,5 +40,10 @@
 			"width": "80",
 			"options": "Warehouse"
 		},
+		{
+			"fieldname": "show_variants",
+			"label": __("Show Variants"),
+			"fieldtype": "Check"
+		},
 	]
 }
diff --git a/erpnext/stock/report/stock_balance/stock_balance.py b/erpnext/stock/report/stock_balance/stock_balance.py
index c3e3cc5..79320fa 100644
--- a/erpnext/stock/report/stock_balance/stock_balance.py
+++ b/erpnext/stock/report/stock_balance/stock_balance.py
@@ -15,6 +15,7 @@
 	item_map = get_item_details(filters)
 	item_reorder_detail_map = get_item_reorder_details(filters)
 	iwb_map = get_item_warehouse_map(filters)
+	
 
 	data = []
 	for (company, item, warehouse) in sorted(iwb_map):
@@ -24,8 +25,8 @@
 		if item + warehouse in item_reorder_detail_map:
 			item_reorder_level = item_reorder_detail_map[item + warehouse]["warehouse_reorder_level"]
 			item_reorder_qty = item_reorder_detail_map[item + warehouse]["warehouse_reorder_qty"]
-			
-		data.append([item, item_map[item]["item_name"],
+
+		report_data = [item, item_map[item]["item_name"],
 			item_map[item]["item_group"],
 			item_map[item]["brand"],
 			item_map[item]["description"], warehouse,
@@ -36,9 +37,17 @@
 			qty_dict.bal_val, qty_dict.val_rate,
 			item_reorder_level,
 			item_reorder_qty,
-			company
-		])
+			company,
 
+		]
+
+		if filters.get('show_variants',0) == 1:
+			variants_attributes = get_variants_attributes()
+			report_data += [item_map[item][i] for i in variants_attributes]			
+		data.append(report_data)
+
+	if filters.get('show_variants',0) == 1:
+		columns += ["{}:Data:100".format(i) for i in get_variants_attributes()]
 	return columns, data
 
 def get_columns():
@@ -63,7 +72,8 @@
 		_("Valuation Rate")+":Float:90",
 		_("Reorder Level")+":Float:80",
 		_("Reorder Qty")+":Float:80",
-		_("Company")+":Link/Company:100"
+		_("Company")+":Link/Company:100",
+
 	]
 
 	return columns
@@ -190,8 +200,11 @@
 
 	items = frappe.db.sql("""select name, item_name, stock_uom, item_group, brand, description
 		from tabItem {condition}""".format(condition=condition), value, as_dict=1)
-
-	return dict((d.name , d) for d in items)
+	item_details = dict((d.name , d) for d in items)
+	if filters.get('show_variants',0) == 1:
+		variant_values = get_variant_values_for_(item_details.keys())
+		item_details = {k:v.update(variant_values[k]) for k,v in item_details.iteritems()}
+	return item_details
 
 def get_item_reorder_details(filters):
 	condition = ''
@@ -210,3 +223,22 @@
 		sle_count = flt(frappe.db.sql("""select count(name) from `tabStock Ledger Entry`""")[0][0])
 		if sle_count > 500000:
 			frappe.throw(_("Please set filter based on Item or Warehouse"))
+
+
+def get_variants_attributes():
+	'''Return all item variant attributes.'''
+	return [i.name for i in frappe.get_all('Item Attribute')]
+
+
+def get_variant_values_for_(items):
+	'''Returns variant values for items.'''
+	attribute_map = {}	
+	for attr in frappe.db.sql('''select parent, attribute, attribute_value 
+									from 
+									`tabItem Variant Attribute` 
+									 where parent in (%s);''' %", ".join(["%s"]*len(items)), 
+									 tuple(items), 
+									 as_dict=1):
+		attribute_map.setdefault(attr['parent'],{})
+		attribute_map[attr['parent']].update({attr['attribute']:attr['attribute_value']})
+	return attribute_map
\ No newline at end of file