diff --git a/hr/doctype/expense_claim/expense_claim.js b/hr/doctype/expense_claim/expense_claim.js index 28487a801e..4c9a5c504c 100644 --- a/hr/doctype/expense_claim/expense_claim.js +++ b/hr/doctype/expense_claim/expense_claim.js @@ -52,13 +52,14 @@ cur_frm.cscript.refresh = function(doc,cdt,cdn){ if(doc.__islocal && !in_list(user_roles, "HR User")) { cur_frm.set_intro("Fill the form and save it") } else { - if(doc.approval_status=="Draft") { + if(doc.docstatus==0 && doc.approval_status=="Draft") { if(user==doc.exp_approver) { cur_frm.set_intro("You are the Expense Approver for this record. Please Update the 'Status' and Save"); cur_frm.toggle_enable("approval_status", true); } else { cur_frm.set_intro("Expense Claim is pending approval. Only the Expense Approver can update status."); cur_frm.toggle_enable("approval_status", false); + if(!doc.__islocal) cur_frm.frm_head.appframe.buttons.Submit.toggle(false); } } else { if(doc.approval_status=="Approved") { @@ -98,6 +99,9 @@ cur_frm.cscript.calculate_total_amount = function(doc,cdt,cdn){ } cur_frm.cscript.claim_amount = function(doc,cdt,cdn){ cur_frm.cscript.calculate_total(doc,cdt,cdn); + + var child = locals[cdt][cdn]; + refresh_field("sanctioned_amount", child.name, child.parentfield); } cur_frm.cscript.sanctioned_amount = function(doc,cdt,cdn){ cur_frm.cscript.calculate_total(doc,cdt,cdn); diff --git a/hr/doctype/expense_claim/expense_claim.txt b/hr/doctype/expense_claim/expense_claim.txt index 638a9f7571..5ef2c59785 100644 --- a/hr/doctype/expense_claim/expense_claim.txt +++ b/hr/doctype/expense_claim/expense_claim.txt @@ -4,7 +4,7 @@ "docstatus": 0, "creation": "2012-12-05 16:53:59", "modified_by": "Administrator", - "modified": "2012-12-06 17:34:37" + "modified": "2012-12-07 13:25:44" }, { "is_submittable": 1, @@ -34,14 +34,6 @@ "name": "Expense Claim", "doctype": "DocType" }, - { - "oldfieldtype": "Section Break", - "doctype": "DocField", - "label": "Details", - "fieldname": "details", - "fieldtype": "Section Break", - "permlevel": 0 - }, { "permlevel": 0, "no_copy": 1, @@ -67,17 +59,6 @@ "fieldtype": "Select", "permlevel": 0 }, - { - "oldfieldtype": "Date", - "doctype": "DocField", - "label": "Posting Date", - "oldfieldname": "posting_date", - "fieldname": "posting_date", - "fieldtype": "Date", - "reqd": 1, - "permlevel": 0, - "in_filter": 1 - }, { "oldfieldtype": "Column Break", "doctype": "DocField", @@ -87,17 +68,70 @@ "permlevel": 0 }, { + "reqd": 0, + "no_copy": 1, + "oldfieldtype": "Currency", + "colour": "White:FFF", + "doctype": "DocField", + "label": "Total Claimed Amount", + "oldfieldname": "total_claimed_amount", + "width": "160px", + "fieldname": "total_claimed_amount", + "fieldtype": "Currency", + "permlevel": 1, + "in_filter": 0 + }, + { + "no_copy": 1, + "oldfieldtype": "Currency", + "colour": "White:FFF", + "doctype": "DocField", + "label": "Total Sanctioned Amount", + "oldfieldname": "total_sanctioned_amount", + "width": "160px", + "fieldname": "total_sanctioned_amount", + "fieldtype": "Currency", + "permlevel": 1, + "in_filter": 0 + }, + { + "oldfieldtype": "Section Break", + "doctype": "DocField", + "label": "Expense Details", + "fieldname": "expense_details", + "fieldtype": "Section Break", + "permlevel": 0 + }, + { + "oldfieldtype": "Table", + "allow_on_submit": 0, + "doctype": "DocField", + "label": "Expense Claim Details", + "oldfieldname": "expense_voucher_details", + "options": "Expense Claim Detail", + "fieldname": "expense_voucher_details", + "fieldtype": "Table", + "permlevel": 0 + }, + { + "doctype": "DocField", + "options": "Simple", + "fieldname": "sb1", + "fieldtype": "Section Break", + "permlevel": 0 + }, + { + "permlevel": 0, "oldfieldtype": "Link", "colour": "White:FFF", "doctype": "DocField", "label": "From Employee", "oldfieldname": "employee", - "permlevel": 0, + "reqd": 1, "trigger": "Client", "fieldname": "employee", "fieldtype": "Link", "search_index": 1, - "reqd": 1, "options": "Employee", "in_filter": 1 }, @@ -114,10 +148,51 @@ "in_filter": 1 }, { + "oldfieldtype": "Select", + "doctype": "DocField", + "label": "Fiscal Year", + "oldfieldname": "fiscal_year", + "options": "link:Fiscal Year", + "fieldname": "fiscal_year", + "fieldtype": "Select", + "reqd": 1, + "permlevel": 0, + "in_filter": 1 + }, + { + "oldfieldtype": "Link", + "doctype": "DocField", + "label": "Company", + "oldfieldname": "company", + "options": "link:Company", + "fieldname": "company", + "fieldtype": "Select", + "reqd": 1, + "permlevel": 0, + "in_filter": 1 + }, + { + "doctype": "DocField", + "fieldname": "cb1", + "fieldtype": "Column Break", + "permlevel": 0 + }, + { + "oldfieldtype": "Date", + "doctype": "DocField", + "label": "Posting Date", + "oldfieldname": "posting_date", + "fieldname": "posting_date", + "fieldtype": "Date", + "reqd": 1, + "permlevel": 0, + "in_filter": 1 + }, + { + "allow_on_submit": 0, "no_copy": 1, "oldfieldtype": "Small Text", "colour": "White:FFF", - "allow_on_submit": 0, "doctype": "DocField", "label": "Remark", "oldfieldname": "remark", @@ -125,6 +200,17 @@ "fieldtype": "Small Text", "permlevel": 0 }, + { + "print_hide": 1, + "oldfieldtype": "Data", + "doctype": "DocField", + "label": "Employees Email Id", + "oldfieldname": "email_id", + "fieldname": "email_id", + "fieldtype": "Data", + "hidden": 1, + "permlevel": 0 + }, { "print_hide": 1, "no_copy": 1, @@ -153,87 +239,6 @@ "permlevel": 1, "report_hide": 1 }, - { - "oldfieldtype": "Section Break", - "doctype": "DocField", - "label": "Expense Details", - "fieldname": "expense_details", - "fieldtype": "Section Break", - "permlevel": 0 - }, - { - "oldfieldtype": "Table", - "allow_on_submit": 0, - "doctype": "DocField", - "label": "Expense Claim Details", - "oldfieldname": "expense_voucher_details", - "options": "Expense Claim Detail", - "fieldname": "expense_voucher_details", - "fieldtype": "Table", - "permlevel": 0 - }, - { - "no_copy": 1, - "oldfieldtype": "Currency", - "colour": "White:FFF", - "doctype": "DocField", - "label": "Total Claimed Amount", - "oldfieldname": "total_claimed_amount", - "width": "160px", - "fieldname": "total_claimed_amount", - "fieldtype": "Currency", - "reqd": 0, - "permlevel": 1, - "in_filter": 0 - }, - { - "no_copy": 1, - "oldfieldtype": "Currency", - "colour": "White:FFF", - "doctype": "DocField", - "label": "Total Sanctioned Amount", - "oldfieldname": "total_sanctioned_amount", - "width": "160px", - "fieldname": "total_sanctioned_amount", - "fieldtype": "Currency", - "permlevel": 1, - "in_filter": 0 - }, - { - "print_hide": 1, - "oldfieldtype": "Data", - "doctype": "DocField", - "label": "Employees Email Id", - "oldfieldname": "email_id", - "fieldname": "email_id", - "fieldtype": "Data", - "hidden": 1, - "permlevel": 0 - }, - { - "oldfieldtype": "Select", - "doctype": "DocField", - "label": "Fiscal Year", - "oldfieldname": "fiscal_year", - "options": "link:Fiscal Year", - "fieldname": "fiscal_year", - "fieldtype": "Select", - "reqd": 1, - "permlevel": 0, - "in_filter": 1 - }, - { - "oldfieldtype": "Link", - "doctype": "DocField", - "label": "Company", - "oldfieldname": "company", - "options": "link:Company", - "fieldname": "company", - "fieldtype": "Select", - "reqd": 1, - "permlevel": 0, - "in_filter": 1 - }, { "create": 1, "doctype": "DocPerm", diff --git a/hr/doctype/leave_application/leave_application.js b/hr/doctype/leave_application/leave_application.js index f3560c026b..042cccad8d 100755 --- a/hr/doctype/leave_application/leave_application.js +++ b/hr/doctype/leave_application/leave_application.js @@ -26,7 +26,7 @@ cur_frm.cscript.onload = function(doc, dt, dn) { method:"get_approver_list", callback: function(r) { cur_frm.set_df_property("leave_approver", "options", r.message); - get_leave_balance(cur_frm.doc); + cur_frm.cscript.get_leave_balance(cur_frm.doc); } }); } @@ -39,13 +39,14 @@ cur_frm.cscript.refresh = function(doc, dt, dn) { if(doc.__islocal && !in_list(user_roles, "HR User")) { cur_frm.set_intro("Fill the form and save it") } else { - if(doc.status=="Open") { + if(doc.docstatus==0 && doc.status=="Open") { if(user==doc.leave_approver) { cur_frm.set_intro("You are the Leave Approver for this record. Please Update the 'Status' and Save"); cur_frm.toggle_enable("status", true); } else { cur_frm.set_intro("This Leave Application is pending approval. Only the Leave Apporver can update status.") cur_frm.toggle_enable("status", false); + if(!doc.__islocal) cur_frm.frm_head.appframe.buttons.Submit.toggle(false); } } else { if(doc.status=="Approved") { @@ -62,21 +63,21 @@ cur_frm.cscript.refresh = function(doc, dt, dn) { } cur_frm.cscript.employee = function (doc, dt, dn){ - get_leave_balance(doc, dt, dn); + cur_frm.cscript.get_leave_balance(doc, dt, dn); } cur_frm.cscript.fiscal_year = function (doc, dt, dn){ - get_leave_balance(doc, dt, dn); + cur_frm.cscript.get_leave_balance(doc, dt, dn); } cur_frm.cscript.leave_type = function (doc, dt, dn){ - get_leave_balance(doc, dt, dn); + cur_frm.cscript.get_leave_balance(doc, dt, dn); } cur_frm.cscript.half_day = function(doc, dt, dn) { if(doc.from_date) { set_multiple(dt,dn,{to_date:doc.from_date}); - calculate_total_days(doc, dt, dn); + cur_frm.cscript.calculate_total_days(doc, dt, dn); } } @@ -84,7 +85,7 @@ cur_frm.cscript.from_date = function(doc, dt, dn) { if(cint(doc.half_day) == 1){ set_multiple(dt,dn,{to_date:doc.from_date}); } - calculate_total_days(doc, dt, dn); + cur_frm.cscript.calculate_total_days(doc, dt, dn); } cur_frm.cscript.to_date = function(doc, dt, dn) { @@ -92,11 +93,11 @@ cur_frm.cscript.to_date = function(doc, dt, dn) { msgprint("To Date should be same as From Date for Half Day leave"); set_multiple(dt,dn,{to_date:doc.from_date}); } - calculate_total_days(doc, dt, dn); + cur_frm.cscript.calculate_total_days(doc, dt, dn); } -get_leave_balance = function(doc, dt, dn) { - if(doc.employee && doc.leave_type && doc.fiscal_year) { +cur_frm.cscript.get_leave_balance = function(doc, dt, dn) { + if(doc.docstatus==0 && doc.employee && doc.leave_type && doc.fiscal_year) { cur_frm.call({ method: "get_leave_balance", args: { @@ -104,16 +105,15 @@ get_leave_balance = function(doc, dt, dn) { fiscal_year: doc.fiscal_year, leave_type: doc.leave_type } - }) + }); } } -calculate_total_days = function(doc, dt, dn) { +cur_frm.cscript.calculate_total_days = function(doc, dt, dn) { if(doc.from_date && doc.to_date){ if(cint(doc.half_day) == 1) set_multiple(dt,dn,{total_leave_days:0.5}); else{ - //d = new DateFn(); - //set_multiple(dt,dn,{total_leave_days:d.get_diff(d.str_to_obj(doc.to_date),d.str_to_obj(doc.from_date))+1}); + // server call is done to include holidays in leave days calculations get_server_fields('get_total_leave_days', '', '', doc, dt, dn, 1); } } diff --git a/hr/doctype/leave_application/leave_application.py b/hr/doctype/leave_application/leave_application.py index 47cdae80a5..c0a51799fe 100755 --- a/hr/doctype/leave_application/leave_application.py +++ b/hr/doctype/leave_application/leave_application.py @@ -28,7 +28,21 @@ import datetime class DocType: def __init__(self, doc, doclist): self.doc = doc - self.doclist = doclist + self.doclist = doclist + + def validate(self): + # if self.doc.leave_approver == self.doc.owner: + # webnotes.msgprint("""Self Approval is not allowed.""", raise_exception=1) + + self.validate_to_date() + self.validate_balance_leaves() + self.validate_leave_overlap() + self.validate_max_days() + + def on_submit(self): + if self.doc.status != "Approved": + webnotes.msgprint("""Only Approved Leave Applications can be Submitted.""", + raise_exception=True) def get_holidays(self): """ @@ -40,9 +54,7 @@ class DocType: return tot_hol and flt(tot_hol[0][0]) or 0 def get_total_leave_days(self): - """ - Calculates total leave days based on input and holidays - """ + """Calculates total leave days based on input and holidays""" ret = {'total_leave_days' : 0.5} if not self.doc.half_day: tot_days = date_diff(self.doc.to_date, self.doc.from_date) + 1 @@ -53,24 +65,20 @@ class DocType: return ret def validate_to_date(self): - if self.doc.from_date and self.doc.to_date and (getdate(self.doc.to_date) < getdate(self.doc.from_date)): + if self.doc.from_date and self.doc.to_date and \ + (getdate(self.doc.to_date) < getdate(self.doc.from_date)): msgprint("To date cannot be before from date") raise Exception - def is_lwp(self): - lwp = sql("select is_lwp from `tabLeave Type` where name = %s", self.doc.leave_type) - return lwp and cint(lwp[0][0]) or 0 - def validate_balance_leaves(self): - if self.doc.from_date and self.doc.to_date and not self.is_lwp(): - bal = get_leave_balance(self.doc.leave_type, self.doc.employee, - self.doc.fiscal_year) - tot_leaves = self.get_total_leave_days() - bal, tot_leaves = bal, tot_leaves - webnotes.conn.set(self.doc, 'leave_balance', flt(bal['leave_balance'])) - webnotes.conn.set(self.doc, 'total_leave_days', flt(tot_leaves['total_leave_days'])) - if flt(bal['leave_balance']) < flt(tot_leaves['total_leave_days']): - msgprint("Warning : There is not enough leave balance") + if self.doc.from_date and self.doc.to_date and not is_lwp(self.doc.leave_type): + self.doc.leave_balance = get_leave_balance(self.doc.employee, + self.doc.leave_type, self.doc.fiscal_year)["leave_balance"] + self.doc.total_leave_days = self.get_total_leave_days()["total_leave_days"] + + if self.doc.leave_balance - self.doc.total_leave_days < 0: + msgprint("There is not enough leave balance for Leave Type: %s" % \ + (self.doc.leave_type,), raise_exception=1) def validate_leave_overlap(self): for d in sql("""select name, leave_type, posting_date, from_date, to_date @@ -90,36 +98,23 @@ class DocType: msgprint("Sorry ! You cannot apply for %s for more than %s days" % (self.doc.leave_type, max_days)) raise Exception - def validate(self): - # if self.doc.leave_approver == self.doc.owner: - # webnotes.msgprint("""Self Approval is not allowed.""", raise_exception=1) - - self.validate_to_date() - self.validate_balance_leaves() - self.validate_leave_overlap() - self.validate_max_days() - - def on_submit(self): - if self.doc.status != "Approved": - webnotes.msgprint("""Only Approved Leave Applications can be Submitted.""", - raise_exception=True) @webnotes.whitelist() def get_leave_balance(employee, leave_type, fiscal_year): leave_all = webnotes.conn.sql("""select total_leaves_allocated from `tabLeave Allocation` where employee = %s and leave_type = %s and fiscal_year = %s and docstatus = 1""", (employee, - leave_type, fiscal_year)) - + leave_type, fiscal_year), debug=1) + leave_all = leave_all and flt(leave_all[0][0]) or 0 leave_app = webnotes.conn.sql("""select SUM(total_leave_days) from `tabLeave Application` where employee = %s and leave_type = %s and fiscal_year = %s - and docstatus = 1""", (employee, leave_type, fiscal_year)) + and docstatus = 1""", (employee, leave_type, fiscal_year), debug=1) leave_app = leave_app and flt(leave_app[0][0]) or 0 - - ret = {'leave_balance':leave_all - leave_app} + + ret = {'leave_balance': leave_all - leave_app} return ret @webnotes.whitelist() @@ -130,3 +125,7 @@ def get_approver_list(): webnotes.msgprint("No Leave Approvers. Please assign 'Leave Approver' Role to atleast one user.") return roles + +def is_lwp(leave_type): + lwp = sql("select is_lwp from `tabLeave Type` where name = %s", leave_type) + return lwp and cint(lwp[0][0]) or 0 \ No newline at end of file diff --git a/hr/doctype/leave_application/leave_application.txt b/hr/doctype/leave_application/leave_application.txt index 556889c887..dd5846a369 100644 --- a/hr/doctype/leave_application/leave_application.txt +++ b/hr/doctype/leave_application/leave_application.txt @@ -2,9 +2,9 @@ { "owner": "Administrator", "docstatus": 0, - "creation": "2012-12-06 15:56:41", + "creation": "2012-12-07 11:51:20", "modified_by": "Administrator", - "modified": "2012-12-07 10:23:53" + "modified": "2012-12-07 13:31:40" }, { "is_submittable": 1, @@ -43,7 +43,7 @@ "options": "Open\nApproved\nRejected", "fieldname": "status", "fieldtype": "Select", - "permlevel": 3 + "permlevel": 2 }, { "description": "Leave can be approved by users with Role, \"Leave Approver\"", @@ -58,7 +58,7 @@ "search_index": 1, "doctype": "DocField", "label": "Leave Type", - "options": "link:Leave Type", + "options": "\nCasual Leave", "fieldname": "leave_type", "fieldtype": "Select", "reqd": 1, @@ -105,17 +105,10 @@ }, { "doctype": "DocField", - "label": "Leave Balance", - "fieldname": "leave_balance", - "fieldtype": "Currency", - "permlevel": 1 - }, - { - "doctype": "DocField", - "label": "Total Leave Days", - "fieldname": "total_leave_days", - "fieldtype": "Currency", - "permlevel": 1 + "label": "Reason", + "fieldname": "description", + "fieldtype": "Small Text", + "permlevel": 0 }, { "search_index": 1, @@ -138,26 +131,28 @@ "in_filter": 1 }, { + "no_copy": 1, "doctype": "DocField", + "label": "Leave Balance Before Application", + "fieldname": "leave_balance", + "fieldtype": "Currency", + "permlevel": 1 + }, + { + "no_copy": 1, + "doctype": "DocField", + "label": "Total Leave Days", + "fieldname": "total_leave_days", + "fieldtype": "Currency", + "permlevel": 1 + }, + { + "doctype": "DocField", + "label": "More Info", "fieldname": "sb10", "fieldtype": "Section Break", "permlevel": 0 }, - { - "doctype": "DocField", - "label": "Reason", - "width": "300px", - "fieldname": "description", - "fieldtype": "Text Editor", - "permlevel": 0 - }, - { - "doctype": "DocField", - "label": "HR Details", - "fieldname": "sb12", - "fieldtype": "Section Break", - "permlevel": 2 - }, { "default": "Today", "colour": "White:FFF", @@ -173,7 +168,7 @@ "search_index": 0, "doctype": "DocField", "label": "Fiscal Year", - "options": "link:Fiscal Year", + "options": "\n2008-2009\n2009-2010\n2010-2011\n2011-2012\n2012-2013\n2013-2014", "fieldname": "fiscal_year", "fieldtype": "Select", "reqd": 1, @@ -181,6 +176,7 @@ "in_filter": 1 }, { + "print_hide": 1, "doctype": "DocField", "label": "Letter Head", "options": "Letter Head", @@ -251,10 +247,5 @@ "role": "Leave Approver", "cancel": 0, "permlevel": 2 - }, - { - "doctype": "DocPerm", - "role": "All", - "permlevel": 3 } ] \ No newline at end of file