Merge branch 'master' into edge
diff --git a/accounts/doctype/sales_invoice/sales_invoice.py b/accounts/doctype/sales_invoice/sales_invoice.py
index 47e3195..b31d549 100644
--- a/accounts/doctype/sales_invoice/sales_invoice.py
+++ b/accounts/doctype/sales_invoice/sales_invoice.py
@@ -8,7 +8,7 @@
 # 
 # This program is distributed in the hope that it will be useful,
 # but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 # GNU General Public License for more details.
 # 
 # You should have received a copy of the GNU General Public License
diff --git a/accounts/doctype/sales_invoice/test_sales_invoice.py b/accounts/doctype/sales_invoice/test_sales_invoice.py
index fb290d2..1f165f0 100644
--- a/accounts/doctype/sales_invoice/test_sales_invoice.py
+++ b/accounts/doctype/sales_invoice/test_sales_invoice.py
@@ -38,72 +38,199 @@
 		si.insert()
 		si.submit()
 		
-		self.assertEquals(webnotes.conn.get_value("Time Log Batch", "_T-Time Log Batch-00001", "status"), 
-			"Billed")
+		self.assertEquals(webnotes.conn.get_value("Time Log Batch", "_T-Time Log Batch-00001",
+		 	"status"), "Billed")
 
 		self.assertEquals(webnotes.conn.get_value("Time Log", "_T-Time Log-00001", "status"), 
 			"Billed")
 
 		si.cancel()
 
-		self.assertEquals(webnotes.conn.get_value("Time Log Batch", "_T-Time Log Batch-00001", "status"), 
-			"Submitted")
+		self.assertEquals(webnotes.conn.get_value("Time Log Batch", "_T-Time Log Batch-00001", 
+			"status"), "Submitted")
 
 		self.assertEquals(webnotes.conn.get_value("Time Log", "_T-Time Log-00001", "status"), 
 			"Batched for Billing")
 			
+	def test_sales_invoice_gl_entry_without_aii(self):
+		si = webnotes.bean(webnotes.copy_doclist(test_records[1]))
+		si.insert()
+		si.submit()
 		
+		webnotes.defaults.set_global_default("auto_inventory_accounting", 0)
+		
+		gl_entries = webnotes.conn.sql("""select account, debit, credit
+			from `tabGL Entry` where voucher_type='Sales Invoice' and voucher_no=%s
+			order by account asc""", si.doc.name, as_dict=1)
+		self.assertTrue(gl_entries)
+		expected_values = sorted([
+			[si.doc.debit_to, 630.0, 0.0],
+			[test_records[1][1]["income_account"], 0.0, 500.0],
+			[test_records[1][2]["account_head"], 0.0, 80.0],
+			[test_records[1][3]["account_head"], 0.0, 50.0],
+		])
+		
+		for i, gle in enumerate(gl_entries):
+			self.assertEquals(expected_values[i][0], gle.account)
+			self.assertEquals(expected_values[i][1], gle.debit)
+			self.assertEquals(expected_values[i][2], gle.credit)
+		
+	def test_sales_invoice_gl_entry_with_aii(self):
+		webnotes.defaults.set_global_default("auto_inventory_accounting", 1)
+		
+		self._insert_purchase_receipt()
+		dn = self._insert_delivery_note()
+		
+		si_against_dn = webnotes.copy_doclist(test_records[1])
+		si_against_dn[1]["delivery_note"] = dn.doc.name
+		si = webnotes.bean(si_against_dn)
+		si.insert()
+		si.submit()
+		
+		gl_entries = webnotes.conn.sql("""select account, debit, credit
+			from `tabGL Entry` where voucher_type='Sales Invoice' and voucher_no=%s
+			order by account asc""", si.doc.name, as_dict=1)
+		self.assertTrue(gl_entries)
+		
+		expected_values = sorted([
+			[si.doc.debit_to, 630.0, 0.0],
+			[test_records[1][1]["income_account"], 0.0, 500.0],
+			[test_records[1][2]["account_head"], 0.0, 80.0],
+			[test_records[1][3]["account_head"], 0.0, 50.0],
+			["Stock Delivered But Not Billed - _TC", 0.0, 375.0],
+			[test_records[1][1]["expense_account"], 375.0, 0.0]
+		])
+		print expected_values
+		print gl_entries
+		for i, gle in enumerate(gl_entries):
+			self.assertEquals(expected_values[i][0], gle.account)
+			self.assertEquals(expected_values[i][1], gle.debit)
+			self.assertEquals(expected_values[i][2], gle.credit)
+			
+		webnotes.defaults.set_global_default("auto_inventory_accounting", 1)
+		
+		
+	def _insert_purchase_receipt(self):
+		from stock.doctype.purchase_receipt.test_purchase_receipt import test_records \
+			as pr_test_records
+		pr = webnotes.bean(copy=pr_test_records[0])
+		pr.run_method("calculate_taxes_and_totals")
+		pr.insert()
+		pr.submit()
+		
+	def _insert_delivery_note(self):
+		from stock.doctype.delivery_note.test_delivery_note import test_records \
+			as dn_test_records
+		dn = webnotes.bean(copy=dn_test_records[0])
+		dn.insert()
+		dn.submit()
+		return dn
 		
 test_dependencies = ["Journal Voucher"]
 
-test_records = [[
-	{
-		"naming_series": "_T-Sales Invoice-",
-		"company": "_Test Company", 
-		"conversion_rate": 1.0, 
-		"currency": "INR", 
-		"debit_to": "_Test Customer - _TC",
-		"customer": "_Test Customer",
-		"customer_name": "_Test Customer",
-		"doctype": "Sales Invoice", 
-		"due_date": "2013-01-23", 
-		"fiscal_year": "_Test Fiscal Year 2013", 
-		"grand_total": 561.8, 
-		"grand_total_export": 561.8, 
-		"net_total": 500.0, 
-		"plc_conversion_rate": 1.0, 
-		"posting_date": "2013-01-23", 
-		"price_list_currency": "INR", 
-		"price_list_name": "_Test Price List", 
-		"territory": "_Test Territory"
-	}, 
-	{
-		"amount": 500.0, 
-		"basic_rate": 500.0, 
-		"description": "138-CMS Shoe", 
-		"doctype": "Sales Invoice Item", 
-		"export_amount": 500.0, 
-		"export_rate": 500.0, 
-		"income_account": "Sales - _TC",
-		"cost_center": "_Test Cost Center - _TC",
-		"item_name": "138-CMS Shoe", 
-		"parentfield": "entries",
-		"qty": 1.0
-	}, 
-	{
-		"account_head": "_Test Account VAT - _TC", 
-		"charge_type": "On Net Total", 
-		"description": "VAT", 
-		"doctype": "Sales Taxes and Charges", 
-		"parentfield": "other_charges",
-		"tax_amount": 30.0,
-	}, 
-	{
-		"account_head": "_Test Account Service Tax - _TC", 
-		"charge_type": "On Net Total", 
-		"description": "Service Tax", 
-		"doctype": "Sales Taxes and Charges", 
-		"parentfield": "other_charges",
-		"tax_amount": 31.8,
-	}
-]]
\ No newline at end of file
+test_records = [
+	[
+		{
+			"naming_series": "_T-Sales Invoice-",
+			"company": "_Test Company", 
+			"conversion_rate": 1.0, 
+			"currency": "INR", 
+			"debit_to": "_Test Customer - _TC",
+			"customer": "_Test Customer",
+			"customer_name": "_Test Customer",
+			"doctype": "Sales Invoice", 
+			"due_date": "2013-01-23", 
+			"fiscal_year": "_Test Fiscal Year 2013", 
+			"grand_total": 561.8, 
+			"grand_total_export": 561.8, 
+			"net_total": 500.0, 
+			"plc_conversion_rate": 1.0, 
+			"posting_date": "2013-01-23", 
+			"price_list_currency": "INR", 
+			"price_list_name": "_Test Price List", 
+			"territory": "_Test Territory"
+		}, 
+		{
+			"amount": 500.0, 
+			"basic_rate": 500.0, 
+			"description": "138-CMS Shoe", 
+			"doctype": "Sales Invoice Item", 
+			"export_amount": 500.0, 
+			"export_rate": 500.0, 
+			"income_account": "Sales - _TC",
+			"cost_center": "_Test Cost Center - _TC",
+			"item_name": "138-CMS Shoe", 
+			"parentfield": "entries",
+			"qty": 1.0
+		}, 
+		{
+			"account_head": "_Test Account VAT - _TC", 
+			"charge_type": "On Net Total", 
+			"description": "VAT", 
+			"doctype": "Sales Taxes and Charges", 
+			"parentfield": "other_charges",
+			"tax_amount": 30.0,
+		}, 
+		{
+			"account_head": "_Test Account Service Tax - _TC", 
+			"charge_type": "On Net Total", 
+			"description": "Service Tax", 
+			"doctype": "Sales Taxes and Charges", 
+			"parentfield": "other_charges",
+			"tax_amount": 31.8,
+		}
+	],
+	[
+		{
+			"naming_series": "_T-Sales Invoice-",
+			"company": "_Test Company", 
+			"conversion_rate": 1.0, 
+			"currency": "INR", 
+			"debit_to": "_Test Customer - _TC",
+			"customer": "_Test Customer",
+			"customer_name": "_Test Customer",
+			"doctype": "Sales Invoice", 
+			"due_date": "2013-01-23", 
+			"fiscal_year": "_Test Fiscal Year 2013", 
+			"grand_total": 630.0, 
+			"grand_total_export": 630.0, 
+			"net_total": 500.0, 
+			"plc_conversion_rate": 1.0, 
+			"posting_date": "2013-03-07", 
+			"price_list_currency": "INR", 
+			"price_list_name": "_Test Price List", 
+			"territory": "_Test Territory"
+		}, 
+		{
+			"item_code": "_Test Item",
+			"item_name": "_Test Item", 
+			"description": "_Test Item", 
+			"doctype": "Sales Invoice Item", 
+			"parentfield": "entries",
+			"qty": 1.0,
+			"basic_rate": 500.0,
+			"amount": 500.0, 
+			"export_rate": 500.0, 
+			"export_amount": 500.0, 
+			"income_account": "Sales - _TC",
+			"expense_account": "_Test Account Cost for Goods Sold",
+			"cost_center": "_Test Cost Center - _TC",
+		}, 
+		{
+			"account_head": "_Test Account VAT - _TC", 
+			"charge_type": "On Net Total", 
+			"description": "VAT", 
+			"doctype": "Sales Taxes and Charges", 
+			"parentfield": "other_charges",
+			"tax_amount": 80.0,
+		}, 
+		{
+			"account_head": "_Test Account Service Tax - _TC", 
+			"charge_type": "On Net Total", 
+			"description": "Service Tax", 
+			"doctype": "Sales Taxes and Charges", 
+			"parentfield": "other_charges",
+			"tax_amount": 50.0,
+		}
+	],
+]
\ No newline at end of file
diff --git a/patches/patch_list.py b/patches/patch_list.py
index d136820..2751854e 100644
--- a/patches/patch_list.py
+++ b/patches/patch_list.py
@@ -16,7 +16,6 @@
 
 from __future__ import unicode_literals
 patch_list = [
-	"execute:webnotes.reload_doc('core', 'doctype', 'report') # 2013-03-07",
 	"patches.mar_2012.so_rv_mapper_fix", 
 	"patches.mar_2012.clean_property_setter", 
 	"patches.april_2012.naming_series_patch", 
@@ -209,4 +208,5 @@
 	"execute:webnotes.conn.sql('update tabDocPerm set `submit`=1, `cancel`=1, `amend`=1 where parent=\"Time Log\"')",
 	"execute:webnotes.delete_doc('DocType', 'Attendance Control Panel')",
 	"patches.march_2013.p02_get_global_default",
+	"execute:webnotes.bean('Style Settings', 'Style Settings').save()"
 ]
\ No newline at end of file
diff --git a/selling/doctype/sales_common/sales_common.py b/selling/doctype/sales_common/sales_common.py
index 47d139f..12ae4a8 100644
--- a/selling/doctype/sales_common/sales_common.py
+++ b/selling/doctype/sales_common/sales_common.py
@@ -341,12 +341,10 @@
 	# ========================================================================
 	# it indicates % contribution of sales person in sales
 	def get_allocated_sum(self,obj):
-		sum = 0
-		for d in getlist(obj.doclist,'sales_team'):
-			sum += flt(d.allocated_percentage)
-		if (flt(sum) != 100) and getlist(obj.doclist,'sales_team'):
-			msgprint("Total Allocated % of Sales Persons should be 100%")
-			raise Exception
+		sales_team_list = obj.doclist.get({"parentfield": "sales_team"})
+		total_allocation = sum([flt(d.allocated_percentage) for d in sales_team_list])
+		if sales_team_list and total_allocation != 100.0:
+			msgprint("Total Allocated %% of Sales Persons should be 100%", raise_exception=True)
 			
 	# Check Conversion Rate (i.e. it will not allow conversion rate to be 1 for Currency other than default currency set in Global Defaults)
 	# ===========================================================================
diff --git a/stock/doctype/delivery_note/test_delivery_note.py b/stock/doctype/delivery_note/test_delivery_note.py
index c2bb5d0..acdf8b9 100644
--- a/stock/doctype/delivery_note/test_delivery_note.py
+++ b/stock/doctype/delivery_note/test_delivery_note.py
@@ -109,7 +109,7 @@
 			"description": "CPU", 
 			"doctype": "Delivery Note Item", 
 			"item_code": "_Test Item", 
-			"item_name": "CPU", 
+			"item_name": "_Test Item", 
 			"parentfield": "delivery_note_details", 
 			"qty": 5.0, 
 			"basic_rate": 100.0,
diff --git a/stock/doctype/stock_ledger/stock_ledger.py b/stock/doctype/stock_ledger/stock_ledger.py
index 05fc0e0..5dff992 100644
--- a/stock/doctype/stock_ledger/stock_ledger.py
+++ b/stock/doctype/stock_ledger/stock_ledger.py
@@ -17,7 +17,7 @@
 from __future__ import unicode_literals
 import webnotes
 
-from webnotes.utils import add_days, cstr, flt, nowdate, cint
+from webnotes.utils import add_days, cstr, flt, nowdate, cint, now
 from webnotes.model.doc import Document
 from webnotes.model.bean import getlist
 from webnotes.model.code import get_obj
@@ -49,7 +49,7 @@
 				serial_nos = get_valid_serial_nos(d.serial_no)
 				for s in serial_nos:
 					s = s.strip()
-					sr_war = sql("select warehouse,name from `tabSerial No` where name = '%s'" % (s))
+					sr_war = webnotes.conn.sql("select warehouse,name from `tabSerial No` where name = '%s'" % (s))
 					if not sr_war:
 						msgprint("Serial No %s does not exists"%s, raise_exception = 1)
 					elif not sr_war[0][0]:
@@ -81,7 +81,7 @@
 				
 
 	def set_pur_serial_no_values(self, obj, serial_no, d, s, new_rec, rejected=None):
-		item_details = sql("""select item_group, warranty_period 
+		item_details = webnotes.conn.sql("""select item_group, warranty_period 
 			from `tabItem` where name = '%s' and (ifnull(end_of_life,'')='' or 
 			end_of_life = '0000-00-00' or end_of_life > now()) """ %(d.item_code), as_dict=1)
 		
@@ -112,7 +112,7 @@
 
 
 	def update_serial_purchase_details(self, obj, d, serial_no, is_submit, purpose = '', rejected=None):
-		exists = sql("select name, status, docstatus from `tabSerial No` where name = '%s'" % (serial_no))
+		exists = webnotes.conn.sql("select name, status, docstatus from `tabSerial No` where name = '%s'" % (serial_no))
 		if is_submit:
 			if exists and exists[0][2] != 2 and purpose not in ['Material Transfer', 'Sales Return']:
 				msgprint("Serial No: %s already %s" % (serial_no, exists and exists[0][1]), raise_exception = 1)
@@ -126,15 +126,15 @@
 			if exists and exists[0][1] == 'Delivered' and exists[0][2] != 2:
 				msgprint("Serial No: %s is already delivered, you can not cancel the document." % serial_no, raise_exception=1)
 			elif purpose == 'Material Transfer':
-				sql("update `tabSerial No` set status = 'In Store', purchase_document_type = '', purchase_document_no = '', warehouse = '%s' where name = '%s'" % (d.s_warehouse, serial_no))				
+				webnotes.conn.sql("update `tabSerial No` set status = 'In Store', purchase_document_type = '', purchase_document_no = '', warehouse = '%s' where name = '%s'" % (d.s_warehouse, serial_no))				
 			elif purpose == 'Sales Return':
-				sql("update `tabSerial No` set status = 'Delivered', purchase_document_type = '', purchase_document_no = '' where name = '%s'" % serial_no)
+				webnotes.conn.sql("update `tabSerial No` set status = 'Delivered', purchase_document_type = '', purchase_document_no = '' where name = '%s'" % serial_no)
 			else:
-				sql("update `tabSerial No` set docstatus = 2, status = 'Not in Use', purchase_document_type = '', purchase_document_no = '', purchase_date = null, purchase_rate = 0, supplier = null, supplier_name = '', supplier_address = '', warehouse = '' where name = '%s'" % serial_no)
+				webnotes.conn.sql("update `tabSerial No` set docstatus = 2, status = 'Not in Use', purchase_document_type = '', purchase_document_no = '', purchase_date = null, purchase_rate = 0, supplier = null, supplier_name = '', supplier_address = '', warehouse = '' where name = '%s'" % serial_no)
 
 
 	def check_serial_no_exists(self, serial_no, item_code):
-		chk = sql("select name, status, docstatus, item_code from `tabSerial No` where name = %s", (serial_no), as_dict=1)
+		chk = webnotes.conn.sql("select name, status, docstatus, item_code from `tabSerial No` where name = %s", (serial_no), as_dict=1)
 		if not chk:
 			msgprint("Serial No: %s does not exists in the system" % serial_no, raise_exception=1)
 		elif chk and chk[0]['item_code'] != item_code:
@@ -169,7 +169,7 @@
 			self.check_serial_no_exists(serial_no, d.item_code)
 			self.set_delivery_serial_no_values(obj, serial_no)
 		else:
-			sql("update `tabSerial No` set docstatus = 0, status = 'In Store', delivery_document_type = '', delivery_document_no = '', delivery_date = null, customer = null, customer_name = '', delivery_address = '', territory = null where name = '%s'" % (serial_no))
+			webnotes.conn.sql("update `tabSerial No` set docstatus = 0, status = 'In Store', delivery_document_type = '', delivery_document_no = '', delivery_date = null, customer = null, customer_name = '', delivery_address = '', territory = null where name = '%s'" % (serial_no))
 
 
 	def update_serial_record(self, obj, fname, is_submit = 1, is_incoming = 0):
@@ -202,8 +202,10 @@
 			if v.get('is_cancelled') == 'Yes':
 				v['actual_qty'] = -flt(v['actual_qty'])
 				# cancel matching entry
-				sql("update `tabStock Ledger Entry` set is_cancelled='Yes' where voucher_no=%s \
-					and voucher_type=%s", (v['voucher_no'], v['voucher_type']))
+				webnotes.conn.sql("""update `tabStock Ledger Entry` set is_cancelled='Yes',
+					modified=%s, modified_by=%s
+					where voucher_no=%s and voucher_type=%s""", 
+					(now(), webnotes.session.user, v['voucher_no'], v['voucher_type']))
 
 			if v.get("actual_qty"):
 				sle_id = self.make_entry(v)
@@ -230,5 +232,5 @@
 		"""
 		Repost everything!
 		"""
-		for wh in sql("select name from tabWarehouse"):
+		for wh in webnotes.conn.sql("select name from tabWarehouse"):
 			get_obj('Warehouse', wh[0]).repost_stock()
diff --git a/website/css/website.css b/website/css/website.css
index 956f22e..dc5b967 100644
--- a/website/css/website.css
+++ b/website/css/website.css
@@ -1,17 +1,12 @@
 div.outer {
-	-moz-box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
-	-webkit-box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
-	box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
-	background-color: #fff;
-	border-radius: 5px;
-	padding: 20px;
-	margin: 30px -20px 10px -20px;
+	padding: 30px;
+	margin: 30px -30px 10px -30px;
 	min-height: 400px;
 	overflow: hidden;
 }
 
 .outer .navbar {
-	margin: -20px -20px 10px -20px;
+	margin: -30px -30px 10px -30px;
 }
 
 footer {
@@ -24,6 +19,8 @@
 	border: 0px;
 	border-bottom: 1px solid #ddd;
 	border-radius: 0px;
+	padding-right: 30px;
+	padding-left: 30px;
 }
 
 p, li {
@@ -98,6 +95,18 @@
 	width: 30px; 
 }
 
+.avatar-medium {
+	margin-right: 5px;
+	width: 48px;
+	height: 48px;
+	border-radius: 48px;
+	-moz-border-radius: 48px;
+	-webkit-border-radius: 48px;
+}
+.avatar-medium img {
+	width: 48px; 
+}
+
 .avatar-large {
 	margin-right: 10px;
 	width: 72px;
@@ -121,5 +130,3 @@
 .avatar-x-large img {
 	width: 100px; 
 }
-
-/* */
\ No newline at end of file
diff --git a/website/doctype/blog/blog.py b/website/doctype/blog/blog.py
index cfc0ca6..d7ffdac 100644
--- a/website/doctype/blog/blog.py
+++ b/website/doctype/blog/blog.py
@@ -18,6 +18,7 @@
 
 import webnotes
 import website.utils
+from webnotes import _
 
 class DocType:
 	def __init__(self, d, dl):
@@ -27,6 +28,9 @@
 		from website.utils import page_name
 		self.doc.name = page_name(self.doc.title)
 
+	def validate(self):
+		self.doc.blog_intro = self.doc.blog_intro[:140]
+
 	def on_update(self):
 		from website.utils import update_page_name
 		update_page_name(self.doc, self.doc.title)
@@ -66,6 +70,20 @@
 		self.doc.full_name = get_fullname(self.doc.owner)
 		self.doc.updated = global_date_format(self.doc.creation)
 		self.doc.content_html = self.doc.content
+		if self.doc.blogger:
+			self.doc.blogger_info = webnotes.doc("blogger", self.doc.blogger).fields
+			if self.doc.blogger_info.avatar and not "/" in self.doc.blogger_info.avatar:
+				self.doc.blogger_info.avatar = "files/" + self.doc.blogger_info.avatar
+		
+		self.doc.categories = webnotes.conn.sql_list("select name from `tabBlog Category` order by name")
+		
+		self.doc.texts = {
+			"comments": _("Comments"),
+			"first_comment": _("Be the first one to comment"),
+			"add_comment": _("Add Comment"),
+			"submit": _("Submit"),
+			"all_posts_by": _("All posts by"),
+		}
 
 		comment_list = webnotes.conn.sql("""\
 			select comment, comment_by_fullname, creation
diff --git a/website/doctype/blog/blog.txt b/website/doctype/blog/blog.txt
index af9606a..e4c92c2 100644
--- a/website/doctype/blog/blog.txt
+++ b/website/doctype/blog/blog.txt
@@ -2,7 +2,7 @@
  {
   "creation": "2013-01-25 11:35:09", 
   "docstatus": 0, 
-  "modified": "2013-02-21 16:54:04", 
+  "modified": "2013-03-08 09:41:37", 
   "modified_by": "Administrator", 
   "owner": "Administrator"
  }, 
@@ -50,18 +50,44 @@
   "label": "Published"
  }, 
  {
-  "description": "Description for listing page, in plain text, only a couple of lines.", 
+  "doctype": "DocField", 
+  "fieldname": "column_break_3", 
+  "fieldtype": "Column Break"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "blogger", 
+  "fieldtype": "Link", 
+  "label": "Blogger", 
+  "options": "Blogger", 
+  "reqd": 1
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "blog_category", 
+  "fieldtype": "Link", 
+  "label": "Blog Category", 
+  "options": "Blog Category"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "section_break_5", 
+  "fieldtype": "Section Break"
+ }, 
+ {
+  "description": "Description for listing page, in plain text, only a couple of lines. (max 140 characters)", 
   "doctype": "DocField", 
   "fieldname": "blog_intro", 
   "fieldtype": "Small Text", 
-  "label": "Blog Intro"
+  "label": "Blog Intro", 
+  "reqd": 1
  }, 
  {
   "doctype": "DocField", 
   "fieldname": "content", 
   "fieldtype": "Text Editor", 
   "label": "Content", 
-  "reqd": 0
+  "reqd": 1
  }, 
  {
   "doctype": "DocField", 
diff --git a/website/doctype/blog_category/__init__.py b/website/doctype/blog_category/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/website/doctype/blog_category/__init__.py
diff --git a/website/doctype/blog_category/blog_category.py b/website/doctype/blog_category/blog_category.py
new file mode 100644
index 0000000..c8c369c
--- /dev/null
+++ b/website/doctype/blog_category/blog_category.py
@@ -0,0 +1,14 @@
+# For license information, please see license.txt
+
+from __future__ import unicode_literals
+import webnotes
+
+class DocType:
+	def __init__(self, d, dl):
+		self.doc, self.doclist = d, dl
+		
+	def on_update(self):
+		# for blog footer
+		from website.utils import clear_cache
+		clear_cache()
+		
\ No newline at end of file
diff --git a/website/doctype/blog_category/blog_category.txt b/website/doctype/blog_category/blog_category.txt
new file mode 100644
index 0000000..cf8cad6
--- /dev/null
+++ b/website/doctype/blog_category/blog_category.txt
@@ -0,0 +1,51 @@
+[
+ {
+  "creation": "2013-03-08 09:41:11", 
+  "docstatus": 0, 
+  "modified": "2013-03-08 09:41:11", 
+  "modified_by": "Administrator", 
+  "owner": "Administrator"
+ }, 
+ {
+  "autoname": "field:category_name", 
+  "doctype": "DocType", 
+  "document_type": "Master", 
+  "module": "Website", 
+  "name": "__common__"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "category_name", 
+  "fieldtype": "Data", 
+  "label": "Category Name", 
+  "name": "__common__", 
+  "parent": "Blog Category", 
+  "parentfield": "fields", 
+  "parenttype": "DocType", 
+  "permlevel": 0, 
+  "reqd": 1
+ }, 
+ {
+  "cancel": 1, 
+  "create": 1, 
+  "doctype": "DocPerm", 
+  "name": "__common__", 
+  "parent": "Blog Category", 
+  "parentfield": "permissions", 
+  "parenttype": "DocType", 
+  "permlevel": 0, 
+  "read": 1, 
+  "role": "Website Manager", 
+  "write": 1
+ }, 
+ {
+  "doctype": "DocType", 
+  "name": "Blog Category"
+ }, 
+ {
+  "doctype": "DocField"
+ }, 
+ {
+  "doctype": "DocPerm"
+ }
+]
\ No newline at end of file
diff --git a/website/doctype/blogger/__init__.py b/website/doctype/blogger/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/website/doctype/blogger/__init__.py
diff --git a/website/doctype/blogger/blogger.py b/website/doctype/blogger/blogger.py
new file mode 100644
index 0000000..28d0f29
--- /dev/null
+++ b/website/doctype/blogger/blogger.py
@@ -0,0 +1,18 @@
+# For license information, please see license.txt
+
+from __future__ import unicode_literals
+import webnotes
+
+class DocType:
+	def __init__(self, d, dl):
+		self.doc, self.doclist = d, dl
+		
+	def on_update(self):
+		"if profile is set, then update all older blogs"
+		if self.doc.profile:
+			for blog in webnotes.conn.sql_list("""select name from tabBlog where owner=%s 
+				and ifnull(blogger,'')=''""", self.doc.profile):
+				b = webnotes.bean("Blog", blog)
+				b.blogger = self.doc.name
+				b.save()
+				
diff --git a/website/doctype/blogger/blogger.txt b/website/doctype/blogger/blogger.txt
new file mode 100644
index 0000000..01e0cea
--- /dev/null
+++ b/website/doctype/blogger/blogger.txt
@@ -0,0 +1,95 @@
+[
+ {
+  "creation": "2013-03-07 16:28:19", 
+  "docstatus": 0, 
+  "modified": "2013-03-07 16:33:37", 
+  "modified_by": "Administrator", 
+  "owner": "Administrator"
+ }, 
+ {
+  "allow_attach": 1, 
+  "autoname": "field:short_name", 
+  "description": "Profile of a Blogger", 
+  "doctype": "DocType", 
+  "document_type": "Master", 
+  "max_attachments": 1, 
+  "module": "Website", 
+  "name": "__common__"
+ }, 
+ {
+  "doctype": "DocField", 
+  "name": "__common__", 
+  "parent": "Blogger", 
+  "parentfield": "fields", 
+  "parenttype": "DocType", 
+  "permlevel": 0
+ }, 
+ {
+  "doctype": "DocPerm", 
+  "name": "__common__", 
+  "parent": "Blogger", 
+  "parentfield": "permissions", 
+  "parenttype": "DocType", 
+  "permlevel": 0, 
+  "read": 1, 
+  "write": 1
+ }, 
+ {
+  "doctype": "DocType", 
+  "name": "Blogger"
+ }, 
+ {
+  "description": "Will be used in url (usually first name).", 
+  "doctype": "DocField", 
+  "fieldname": "short_name", 
+  "fieldtype": "Data", 
+  "label": "Short Name", 
+  "reqd": 1
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "full_name", 
+  "fieldtype": "Data", 
+  "label": "Full Name", 
+  "reqd": 1
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "profile", 
+  "fieldtype": "Link", 
+  "label": "Profile", 
+  "options": "Profile"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "bio", 
+  "fieldtype": "Small Text", 
+  "label": "Bio"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "avatar", 
+  "fieldtype": "Select", 
+  "label": "Avatar", 
+  "options": "attach_files:"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "file_list", 
+  "fieldtype": "Text", 
+  "hidden": 1, 
+  "label": "File List", 
+  "no_copy": 1, 
+  "print_hide": 1
+ }, 
+ {
+  "create": 1, 
+  "doctype": "DocPerm", 
+  "role": "Website Manager"
+ }, 
+ {
+  "doctype": "DocPerm", 
+  "match": "owner:profile", 
+  "role": "Blogger"
+ }
+]
\ No newline at end of file
diff --git a/website/doctype/style_settings/custom_template.css b/website/doctype/style_settings/custom_template.css
index 9009bbe..e625f95 100644
--- a/website/doctype/style_settings/custom_template.css
+++ b/website/doctype/style_settings/custom_template.css
@@ -1,3 +1,7 @@
+{% if doc.at_import %}
+{{ doc.at_import }}
+{% endif %}
+
 body {
 {% if doc.background_image %}
 	background: url("../files/{{ doc.background_image }}") repeat;
@@ -7,8 +11,8 @@
 {% else %}
 	background-color: #edede7;
 {% endif %}	
-{% if doc.font %}
-	font-family: '{{ doc.font }}', Verdana, Sans !important;
+{% if doc.font or doc.google_web_font_for_text %}
+	font-family: '{{ doc.google_web_font_for_text or doc.font }}', Verdana, Sans !important;
 {% endif %}
 {% if doc.font_size %}
 	font-size: {{ doc.font_size }} !important;
@@ -21,8 +25,106 @@
 }
 {% endif %}
 
-{% if doc.heading_font %}
+div.outer {
+	background-color: #{{ doc.page_background or "fff" }};
+}
+
+{% if doc.google_web_font_for_heading or doc.heading_font %}
 h1, h2, h3, h4, h5 {
-	font-family: '{{ doc.heading_font}}', Arial, 'Helvetica Neue' !important;
+	font-family: '{{ doc.google_web_font_for_heading or doc.heading_font }}', Arial, 'Helvetica Neue' !important;
+}
+{% endif %}
+{% if doc.heading_text_as %}
+h1, h2, h3, h4, h5 {
+	text-transform: {{ doc.heading_text_as }};
 }	
 {% endif %}
+
+{% if doc.page_border %}
+/* Page Border*/
+div.outer {
+	-moz-box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
+	-webkit-box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
+	box-shadow: 0px 0px 3px rgba(0,0,0,0.9);
+	border-radius: 5px;
+}
+{% else %}
+div.web-footer {
+	border-top: 1px solid #eee;
+	padding-top: 10px;
+}
+{% endif %}
+
+/* Bootstrap Navbar */
+.navbar-inverse .navbar-inner {
+    background-color: #{{ doc.top_bar_background or "444"}};
+    background-repeat: repeat-x;
+	border-color: transparent;
+	background-image: none;
+}
+
+.navbar-inverse .brand,
+.navbar-inverse .nav > li > a {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+  text-shadow: none;
+}
+
+.navbar-inverse .brand:hover,
+.navbar-inverse .nav > li > a:hover,
+.navbar-inverse .brand:focus,
+.navbar-inverse .nav > li > a:focus {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+}
+
+.navbar-inverse .brand {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+}
+
+.navbar-inverse .navbar-text {
+  color: #999999;
+}
+
+.navbar-inverse .nav > li > a:focus,
+.navbar-inverse .nav > li > a:hover {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+  background-color: transparent;
+}
+
+.navbar-inverse .nav .active > a,
+.navbar-inverse .nav .active > a:hover,
+.navbar-inverse .nav .active > a:focus {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+  background-color: transparent;
+}
+
+.navbar-inverse .navbar-link {
+  color: #999999;
+}
+
+.navbar-inverse .navbar-link:hover,
+.navbar-inverse .navbar-link:focus {
+  color: #{{ doc.top_bar_foreground or "fff"}};
+}
+
+.navbar-fixed-top .navbar-inner,
+.navbar-static-top .navbar-inner {
+  -webkit-box-shadow: none;
+     -moz-box-shadow: none;
+          box-shadow: none;
+        
+}
+.navbar .nav > .active > a,
+.navbar .nav > .active > a:hover,
+.navbar .nav > .active > a:focus {
+  color: #424242;
+  text-decoration: none;
+  background-color: transparent;
+  -webkit-box-shadow: none;
+     -moz-box-shadow: none;
+          box-shadow: none;
+}
+
+.navbar-inverse .nav li.dropdown > .dropdown-toggle .caret {
+	border-top-color: #{{ doc.top_bar_foreground or "fff"}};
+	border-bottom-color: #{{ doc.top_bar_foreground or "fff"}};
+}
diff --git a/website/doctype/style_settings/style_settings.js b/website/doctype/style_settings/style_settings.js
index 54091a3..e8ee908 100644
--- a/website/doctype/style_settings/style_settings.js
+++ b/website/doctype/style_settings/style_settings.js
@@ -18,5 +18,7 @@
 cur_frm.cscript.onload_post_render = function() {
 	wn.require('lib/public/js/lib/jscolor/jscolor.js');
 	cur_frm.fields_dict.background_color.input.className = 'color';
+	cur_frm.fields_dict.page_background.input.className = 'color';
+	cur_frm.fields_dict.top_bar_background.input.className = 'color';
 	jscolor.bind();
 }
\ No newline at end of file
diff --git a/website/doctype/style_settings/style_settings.py b/website/doctype/style_settings/style_settings.py
index 5179948..0a1a2e0 100644
--- a/website/doctype/style_settings/style_settings.py
+++ b/website/doctype/style_settings/style_settings.py
@@ -15,6 +15,8 @@
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
 from __future__ import unicode_literals
+from webnotes.utils import cint, cstr
+
 class DocType:
 	def __init__(self, d, dl):
 		self.doc, self.doclist = d, dl
@@ -29,10 +31,7 @@
 				'custom_template.css'), 'r') as f:
 			temp = Template(f.read())
 		
-		if not self.doc.font_size:
-			self.doc.font_size = '13px'
-			
-		self.doc.small_font_size = str(int(self.doc.font_size[:-2])-2) + 'px'
+		self.prepare()
 		
 		self.doc.custom_css = temp.render(doc = self.doc)
 		if self.doc.add_css:
@@ -41,7 +40,36 @@
 		from webnotes.sessions import clear_cache
 		clear_cache('Guest')
 		
-		del self.doc.fields['small_font_size']
+		for f in ["small_font_size", "at_import"]:
+			if f in self.doc.fields:
+				del self.doc.fields[f]
+	
+	def prepare(self):
+		if not self.doc.font_size:
+			self.doc.font_size = '13px'
+			
+		self.doc.small_font_size = cstr(cint(self.doc.font_size[:-2])-2) + 'px'
+		self.doc.page_border = cint(self.doc.page_border)
+		
+		fonts = []
+		if self.doc.google_web_font_for_heading:
+			fonts.append(self.doc.google_web_font_for_heading)
+		if self.doc.google_web_font_for_text:
+			fonts.append(self.doc.google_web_font_for_text)
+			
+		fonts = list(set(fonts))
+		
+		if self.doc.heading_text_as:
+			self.doc.heading_text_as = {
+				"UPPERCASE": "uppercase",
+				"Title Case":"capitalize",
+				"lowercase": "lowercase"
+			}[self.doc.heading_text_as]
+		
+		self.doc.at_import = ""
+		for f in fonts:
+			self.doc.at_import += "\n@import url(http://fonts.googleapis.com/css?family=%s);" % f.replace(" ", "+")
+
 	
 	def on_update(self):
 		"""rebuild pages"""
diff --git a/website/doctype/style_settings/style_settings.txt b/website/doctype/style_settings/style_settings.txt
index 5f53441..e58ae09 100644
--- a/website/doctype/style_settings/style_settings.txt
+++ b/website/doctype/style_settings/style_settings.txt
@@ -1,8 +1,8 @@
 [
  {
-  "creation": "2013-01-10 16:34:32", 
+  "creation": "2013-01-25 11:35:10", 
   "docstatus": 0, 
-  "modified": "2013-01-22 14:57:25", 
+  "modified": "2013-03-08 09:58:49", 
   "modified_by": "Administrator", 
   "owner": "Administrator"
  }, 
@@ -24,24 +24,27 @@
   "permlevel": 0
  }, 
  {
-  "create": 1, 
   "doctype": "DocPerm", 
   "name": "__common__", 
   "parent": "Style Settings", 
   "parentfield": "permissions", 
   "parenttype": "DocType", 
-  "permlevel": 0, 
   "read": 1, 
-  "report": 1, 
+  "report": 0, 
   "role": "Website Manager", 
-  "submit": 0, 
-  "write": 1
+  "submit": 0
  }, 
  {
   "doctype": "DocType", 
   "name": "Style Settings"
  }, 
  {
+  "doctype": "DocField", 
+  "fieldname": "color", 
+  "fieldtype": "Section Break", 
+  "label": "Color"
+ }, 
+ {
   "description": "If image is selected, color will be ignored (attach first)", 
   "doctype": "DocField", 
   "fieldname": "background_image", 
@@ -58,6 +61,18 @@
  }, 
  {
   "doctype": "DocField", 
+  "fieldname": "page_background", 
+  "fieldtype": "Data", 
+  "label": "Page Background"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "page_border", 
+  "fieldtype": "Check", 
+  "label": "Page Border"
+ }, 
+ {
+  "doctype": "DocField", 
   "fieldname": "cb0", 
   "fieldtype": "Column Break", 
   "print_width": "50%", 
@@ -65,24 +80,70 @@
  }, 
  {
   "doctype": "DocField", 
+  "fieldname": "top_bar_background", 
+  "fieldtype": "Data", 
+  "label": "Top Bar Background"
+ }, 
+ {
+  "description": "000 is black, fff is white", 
+  "doctype": "DocField", 
+  "fieldname": "top_bar_foreground", 
+  "fieldtype": "Select", 
+  "label": "Top Bar Foreground", 
+  "options": "000\nFFF"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "fonts", 
+  "fieldtype": "Section Break", 
+  "label": "Fonts"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "heading_font", 
+  "fieldtype": "Select", 
+  "label": "Font (Heading)", 
+  "options": "\nHelvetica Neue\nLucida Grande\nVerdana\nArial\nGeorgia\nTahoma\nLato\nOpen Sans"
+ }, 
+ {
+  "doctype": "DocField", 
   "fieldname": "font", 
   "fieldtype": "Select", 
-  "label": "Font", 
+  "label": "Font (Text)", 
   "options": "\nHelvetica Neue\nLucida Grande\nVerdana\nArial\nGeorgia\nTahoma"
  }, 
  {
   "doctype": "DocField", 
   "fieldname": "font_size", 
   "fieldtype": "Select", 
-  "label": "Font Size", 
+  "label": "Font Size (Text)", 
   "options": "\n12px\n13px\n14px\n15px\n16px"
  }, 
  {
   "doctype": "DocField", 
-  "fieldname": "heading_font", 
+  "fieldname": "heading_text_as", 
   "fieldtype": "Select", 
-  "label": "Heading Font", 
-  "options": "\nHelvetica Neue\nLucida Grande\nVerdana\nArial\nGeorgia\nTahoma\nLato\nOpen Sans"
+  "label": "Heading Text As", 
+  "options": "\nUPPERCASE\nTitle Case\nlowercase"
+ }, 
+ {
+  "doctype": "DocField", 
+  "fieldname": "column_break_13", 
+  "fieldtype": "Column Break"
+ }, 
+ {
+  "description": "Add the name of Google Web Font e.g. \"Open Sans\"", 
+  "doctype": "DocField", 
+  "fieldname": "google_web_font_for_heading", 
+  "fieldtype": "Data", 
+  "label": "Google Web Font (Heading)"
+ }, 
+ {
+  "description": "Add the name of Google Web Font e.g. \"Open Sans\"", 
+  "doctype": "DocField", 
+  "fieldname": "google_web_font_for_text", 
+  "fieldtype": "Data", 
+  "label": "Google Web Font (Text)"
  }, 
  {
   "doctype": "DocField", 
@@ -115,6 +176,16 @@
   "print_hide": 1
  }, 
  {
-  "doctype": "DocPerm"
+  "create": 1, 
+  "doctype": "DocPerm", 
+  "permlevel": 0, 
+  "write": 1
+ }, 
+ {
+  "amend": 0, 
+  "cancel": 0, 
+  "create": 0, 
+  "doctype": "DocPerm", 
+  "permlevel": 1
  }
 ]
\ No newline at end of file
diff --git a/website/doctype/website_settings/website_settings.py b/website/doctype/website_settings/website_settings.py
index 88af634..714b75a 100644
--- a/website/doctype/website_settings/website_settings.py
+++ b/website/doctype/website_settings/website_settings.py
@@ -31,9 +31,6 @@
 		from website.utils import clear_cache
 		clear_cache()
 
-		from webnotes.sessions import clear_cache
-		clear_cache('Guest')
-
 	def set_home_page(self):
 
 		import webnotes
diff --git a/website/helpers/blog.py b/website/helpers/blog.py
index 2bff6e5..d90c85a 100644
--- a/website/helpers/blog.py
+++ b/website/helpers/blog.py
@@ -4,41 +4,44 @@
 from __future__ import unicode_literals
 import webnotes
 import website.utils
+from webnotes import _
 
 @webnotes.whitelist(allow_guest=True)
-def get_blog_list(args=None):
-	"""
-		args = {
-			'start': 0,
-		}
-	"""
+def get_blog_list(start=0, by=None, category=None):
 	import webnotes
-	
-	if not args: args = webnotes.form_dict
-	
+	condition = ""
+	if by:
+		condition = " and t1.blogger='%s'" % by.replace("'", "\'")
+	if category:
+		condition += " and t1.blog_category='%s'" % category.replace("'", "\'")
 	query = """\
 		select
-			name, page_name, content, owner, creation as creation,
-			title, (select count(name) from `tabComment` where
-				comment_doctype='Blog' and comment_docname=`tabBlog`.name) as comments
-		from `tabBlog`
-		where ifnull(published,0)=1
+			t1.title, t1.name, t1.page_name, t1.creation as creation, 
+				ifnull(t1.blog_intro, t1.content) as content, 
+				t2.full_name, t2.avatar, t1.blogger,
+				(select count(name) from `tabComment` where
+					comment_doctype='Blog' and comment_docname=t1.name) as comments
+		from `tabBlog` t1, `tabBlogger` t2
+		where ifnull(t1.published,0)=1
+		and t1.blogger = t2.name
+		%(condition)s
 		order by creation desc, name asc
-		limit %s, 5""" % args.start
+		limit %(start)s, 5""" % {"start": start, "condition": condition}
 		
-	result = webnotes.conn.sql(query, args, as_dict=1)
+	result = webnotes.conn.sql(query, as_dict=1)
 
 	# strip html tags from content
 	import webnotes.utils
 	
 	for res in result:
 		from webnotes.utils import global_date_format, get_fullname
-		res['full_name'] = get_fullname(res['owner'])
 		res['published'] = global_date_format(res['creation'])
 		if not res['content']:
 			res['content'] = website.utils.get_html(res['page_name'])
-		res['content'] = split_blog_content(res['content'])
-
+		res['content'] = res['content'][:140]
+		if res.avatar and not "/" in res.avatar:
+			res.avatar = "files/" + res.avatar
+		
 	return result
 
 @webnotes.whitelist(allow_guest=True)
@@ -115,10 +118,22 @@
 	import webnotes.utils
 	content = webnotes.utils.escape_html(content)
 	return content
+
+def get_blog_template_args():
+	return {
+		"categories": webnotes.conn.sql_list("select name from `tabBlog Category` order by name")
+	}
 	
-def split_blog_content(content):
-	content = content.split("<!-- begin blog content -->")
-	content = len(content) > 1 and content[1] or content[0]
-	content = content.split("<!-- end blog content -->")
-	content = content[0]
-	return content
\ No newline at end of file
+def get_writers_args():
+	bloggers = webnotes.conn.sql("select * from `tabBlogger` order by full_name", as_dict=1)
+	for blogger in bloggers:
+		if blogger.avatar and not "/" in blogger.avatar:
+			blogger.avatar = "files/" + blogger.avatar
+		
+	return {
+		"bloggers": bloggers,
+		"texts": {
+			"all_posts_by": _("All posts by")
+		},
+		"categories": webnotes.conn.sql_list("select name from `tabBlog Category` order by name")
+	}
\ No newline at end of file
diff --git a/website/page/website_home/website_home.js b/website/page/website_home/website_home.js
index c6b2253..40e29e8 100644
--- a/website/page/website_home/website_home.js
+++ b/website/page/website_home/website_home.js
@@ -12,11 +12,6 @@
 				doctype:"Web Page"
 			},
 			{
-				label: wn._("Blog"),
-				description: wn._("Blog entry."),
-				doctype:"Blog"
-			},
-			{
 				label: wn._("Website Slideshow"),
 				description: wn._("Embed image slideshows in website pages."),
 				doctype:"Website Slideshow"
@@ -24,6 +19,28 @@
 		]
 	},
 	{
+		title: wn._("Blog"),
+		icon: "icon-edit",
+		items: [
+			{
+				label: wn._("Blog"),
+				description: wn._("Blog post."),
+				doctype:"Blog"
+			},
+			{
+				label: wn._("Blogger"),
+				description: wn._("Profile of a blog writer."),
+				doctype:"Blogger"
+			},
+			{
+				label: wn._("Blog Category"),
+				description: wn._("Categorize blog posts."),
+				doctype:"Blogger"
+			},
+		]
+	},
+
+	{
 		title: wn._("Website Overall Settings"),
 		icon: "icon-wrench",
 		right: true,
diff --git a/website/templates/html/blog_footer.html b/website/templates/html/blog_footer.html
new file mode 100644
index 0000000..e439d14
--- /dev/null
+++ b/website/templates/html/blog_footer.html
@@ -0,0 +1,13 @@
+<div class="span12">
+	<hr />
+	{% if categories %}
+	<h5>Explore posts by categories</h5>
+	<ul class="breadcrumb" style="background-color: transparent; padding-left: 0px;">
+	{% for category in categories %}
+		<li><a href="blog?category={{ category }}">{{ category }}</a> 
+		{% if not loop.last %}<span class="divider">/</span>{% endif %}</li>
+	{% endfor %}
+	<br><br>
+	{% endif %}
+	<p>Show posts by <a href="blog">everyone</a>. Meet the <a href="writers">writers</a> of this blog</p>
+</div>
diff --git a/website/templates/html/blog_page.html b/website/templates/html/blog_page.html
index 24dd8d7..e605a12 100644
--- a/website/templates/html/blog_page.html
+++ b/website/templates/html/blog_page.html
@@ -13,41 +13,41 @@
 	<h2>{{ title }}</h2>
 
 	<!-- begin blog content -->
-	<div class="help">By {{ full_name }} on {{ updated }}</div>
+	<div class="help" style="color: #aaa">
+		{{ blogger_info and blogger_info.full_name or full_name }} / {{ updated }}</div>
 	<br>
 	{{ content_html }}
 	<!-- end blog content -->
-
+	{% if blogger_info %}
+	<hr />
+	{% include "html/blogger.html" %}
+	{% endif %}
 	<hr>
-	<h3>Comments</h3><br>
+	<h3>{{ texts.comments }}</h3><br>
 	<div class="blog-comments">
 		
 		{% if not comment_list %}
-		<div class="alert no-comment">
-			<p>Be the first one to comment</p>
+		<div class="no-comment">
+			<p>{{ texts.first_comment }}</p>
 		</div>
 		{% endif %}
 		
 		{% include 'html/comment.html' %}
 	</div>
-	<div><button class="btn add-comment">Add Comment</button></div>
+	<div><button class="btn add-comment">{{ texts.add_comment }}</button></div>
 	<div style="display: none; margin-top: 10px;" 
-		id="comment-form" class="well">
+		id="comment-form">
 		<div class="alert" style="display:none;"></div>
 		<form>
-			<p>
-				<input name="comment_by_fullname" placeholder="Your Name" />
-			</p>
-			<p>
-				<input name="comment_by" placeholder="Your Email Id" />
-			</p>
-			<p>
+			<fieldset>
+				<input name="comment_by_fullname" placeholder="Your Name" type="text"/><br>
+				<input name="comment_by" placeholder="Your Email Id" type="text"/><br>
 				<textarea name="comment" placeholder="Comment" style="width: 300px; height: 120px;"/>
-				</textarea>
-			</p>
-			<p>
-				<button class="btn btn-info" id="submit-comment">Submit</button>
+				</textarea><br>
+				<button class="btn btn-info" id="submit-comment">{{ texts.submit }}</button>
+			</fieldset>
 		</form>
 	</div>
 </div>
+{% include 'html/blog_footer.html' %}
 {% endblock %}
\ No newline at end of file
diff --git a/website/templates/html/blogger.html b/website/templates/html/blogger.html
new file mode 100644
index 0000000..eab371e
--- /dev/null
+++ b/website/templates/html/blogger.html
@@ -0,0 +1,13 @@
+<div class="row">
+	<div class="span2">
+		<div class="avatar avatar-large">
+			<img src="{{ blogger_info.avatar }}" />
+		</div>
+	</div>
+	<div class="span10">
+		<h4>{{ blogger_info.full_name }}</h4>
+		<p style="color: #999">{{ blogger_info.bio }}</p>
+		<p><a href="blog?by={{ blogger_info.name }}&by_name={{ blogger_info.full_name }}">
+			{{ texts.all_posts_by }} {{ blogger_info.full_name }}</a></p>
+	</div>
+</div>
\ No newline at end of file
diff --git a/website/templates/html/outer.html b/website/templates/html/outer.html
index de96122..e582d0a 100644
--- a/website/templates/html/outer.html
+++ b/website/templates/html/outer.html
@@ -6,7 +6,7 @@
 	<div class="container">
 		<div class="outer">
 			<div class="navbar{% if top_bar_background=="Black" %} navbar-inverse{% endif %}" 
-				style="margin-bottom: 0px;">
+				style="">
 				<div class="navbar-inner">
 					<a class="brand" href="index">{{ brand_html }}</a>
 					<div class="container">
diff --git a/website/templates/js/blog.js b/website/templates/js/blog.js
index 6c006de..3cfb234 100644
--- a/website/templates/js/blog.js
+++ b/website/templates/js/blog.js
@@ -23,6 +23,15 @@
 	$("#next-page").click(function() {
 		blog.get_list();
 	})
+	
+	if(get_url_arg("by_name")) {
+		$("#blog-title").html("Posts by " + get_url_arg("by_name"));
+	}
+
+	if(get_url_arg("category")) {
+		$("#blog-title").html("Posts filed under " + get_url_arg("category"));
+	}
+
 });
 
 var blog = {
@@ -33,10 +42,13 @@
 			url: "server.py",
 			data: {
 				cmd: "website.helpers.blog.get_blog_list",
-				start: blog.start
+				start: blog.start,
+				by: get_url_arg("by"),
+				category: get_url_arg("category")
 			},
 			dataType: "json",
 			success: function(data) {
+				if(data.exc) console.log(data.exc);
 				blog.render(data.message);
 			}
 		});
@@ -53,11 +65,20 @@
 				b.comment_text = b.comments + ' comments.'
 			} 
 			
-			$(repl('<h2><a href="%(page_name)s">%(title)s</a></h2>\
-				<div class="help">%(comment_text)s</div>\
-				%(content)s<br />\
-				<p><a href="%(page_name)s">Read with comments...</a></p>\
-				<hr /><br />', b)).appendTo($wrap);
+			$(repl('<div class="row">\
+					<div class="span1">\
+						<div class="avatar avatar-medium" style="margin-top: 6px;">\
+							<img src="%(avatar)s" />\
+						</div>\
+					</div>\
+					<div class="span11">\
+						<h4><a href="%(page_name)s">%(title)s</a></h4>\
+						<p>%(content)s</p>\
+						<p style="color: #aaa; font-size: 90%">\
+							<a href="blog?by=%(blogger)s&by_name=%(full_name)s">\
+								%(full_name)s</a> wrote this on %(published)s / %(comment_text)s</p>\
+					</div>\
+				</div><hr>', b)).appendTo($wrap);
 		});
 		blog.start += (data.length || 0);
 		if(!data.length) {
diff --git a/website/templates/pages/blog.html b/website/templates/pages/blog.html
index 3c2a579..05302c6 100644
--- a/website/templates/pages/blog.html
+++ b/website/templates/pages/blog.html
@@ -12,7 +12,7 @@
 
 {% block content %}
 <div class="span12">
-	<h1>Blog</h1>
+	<h2 id="blog-title">Blog</h2>
 	<br>
 	<div id="blog-list">
 		<!-- blog list will be generated dynamically -->
@@ -22,4 +22,5 @@
 			style="display:none;">More...</button>
 	</div>
 </div>
+{% include 'html/blog_footer.html' %}
 {% endblock %}
\ No newline at end of file
diff --git a/website/templates/pages/writers.html b/website/templates/pages/writers.html
new file mode 100644
index 0000000..0ae8549
--- /dev/null
+++ b/website/templates/pages/writers.html
@@ -0,0 +1,14 @@
+{% extends "html/page.html" %}
+
+{% set title="Blog Writers" %}
+
+{% block content %}
+<div class="span12">
+	<h2 id="blog-title">Blog Writers</h2>
+	<hr>
+	{% for blogger_info in bloggers %}
+	{% include "html/blogger.html" %}	
+	{% endfor %}
+</div>
+{% include 'html/blog_footer.html' %}
+{% endblock %}
\ No newline at end of file
diff --git a/website/utils.py b/website/utils.py
index 97c03bc..a9569b4 100644
--- a/website/utils.py
+++ b/website/utils.py
@@ -41,7 +41,9 @@
 
 page_settings_map = {
 	"about": "About Us Settings",
-	"contact": "Contact Us Settings"
+	"contact": "Contact Us Settings",
+	"blog": "website.helpers.blog.get_blog_template_args",
+	"writers": "website.helpers.blog.get_writers_args"
 }
 
 def render(page_name):
@@ -155,7 +157,11 @@
 			'name': page_name,
 		})
 		if page_name in page_settings_map:
-			args.obj = webnotes.bean(page_settings_map[page_name]).obj
+			target = page_settings_map[page_name]
+			if "." in target:
+				args.update(webnotes.get_method(target)())
+			else:
+				args.obj = webnotes.bean(page_settings_map[page_name]).obj
 	else:
 		args = get_doc_fields(page_name)