diff --git a/home/page/latest_updates/latest_updates.js b/home/page/latest_updates/latest_updates.js index c47a6fd0d37..24cab01fdf4 100644 --- a/home/page/latest_updates/latest_updates.js +++ b/home/page/latest_updates/latest_updates.js @@ -1,6 +1,8 @@ erpnext.updates = [ ["30th November 2012", [ "Auto Notifications: System will prompt user with pre-set message for auto-notification.", + "Employee: Users with role Employee will only be able to see their Employee Records.", + "Leave Application: Users with role Employee can now apply for leaves. HR User will be able to set Approval or Rejection.", ]], ["29th November 2012", [ "EMail: Form Emails are now via Communication (with Rich Text Etc.).", diff --git a/hr/doctype/leave_application/leave_application.js b/hr/doctype/leave_application/leave_application.js index e8952ca7106..00df476edef 100755 --- a/hr/doctype/leave_application/leave_application.js +++ b/hr/doctype/leave_application/leave_application.js @@ -14,39 +14,49 @@ // You should have received a copy of the GNU General Public License // along with this program. If not, see . -// ****************************************** onload ******************************************************** cur_frm.cscript.onload = function(doc, dt, dn) { if(!doc.posting_date) set_multiple(dt,dn,{posting_date:get_today()}); } +cur_frm.cscript.refresh = function(doc, dt, dn) { + cur_frm.set_intro(""); + if(doc.__islocal && !in_list(user_roles, "HR User")) { + cur_frm.set_intro("Fill the form and save it") + } else { + if(in_list(user_roles, "HR User")) { + if(doc.status=="Open") { + cur_frm.set_intro("Please Approve (and Submit) or Reject, or re-assign to applicant for further review."); + } + } else { + if(doc.status=="Open") { + cur_frm.set_intro("Leave application is pending approval."); + } else if(doc.status=="Approved") { + cur_frm.set_intro("Leave application has been approved."); + } else if(doc.status=="Rejected") { + cur_frm.set_intro("Leave application has been rejected."); + } + } + } + + if(doc.status=="Approved" && doc.docstatus!=1) { + cur_frm.savesubmit() + } +} -// ************************************** client triggers *************************************************** -// --------- -// employee -// --------- cur_frm.add_fetch('employee','employee_name','employee_name'); cur_frm.cscript.employee = function (doc, dt, dn){ get_leave_balance(doc, dt, dn); } -// ------------ -// fiscal_year -// ------------ cur_frm.cscript.fiscal_year = function (doc, dt, dn){ get_leave_balance(doc, dt, dn); } -// ----------- -// leave type -// ----------- cur_frm.cscript.leave_type = function (doc, dt, dn){ get_leave_balance(doc, dt, dn); } -// --------- -// half day -// --------- cur_frm.cscript.half_day = function(doc, dt, dn) { if(doc.from_date) { set_multiple(dt,dn,{to_date:doc.from_date}); @@ -54,9 +64,6 @@ cur_frm.cscript.half_day = function(doc, dt, dn) { } } -// --------- -// from date -// --------- cur_frm.cscript.from_date = function(doc, dt, dn) { if(cint(doc.half_day) == 1){ set_multiple(dt,dn,{to_date:doc.from_date}); @@ -64,9 +71,6 @@ cur_frm.cscript.from_date = function(doc, dt, dn) { calculate_total_days(doc, dt, dn); } -// -------- -// to date -// -------- cur_frm.cscript.to_date = function(doc, dt, dn) { if(cint(doc.half_day) == 1 && cstr(doc.from_date) && doc.from_date != doc.to_date){ msgprint("To Date should be same as From Date for Half Day leave"); @@ -75,20 +79,11 @@ cur_frm.cscript.to_date = function(doc, dt, dn) { calculate_total_days(doc, dt, dn); } - -// ******************************************* utilities **************************************************** - -// ------------------ -// get leave balance -// ------------------ get_leave_balance = function(doc, dt, dn) { if(doc.employee && doc.leave_type && doc.fiscal_year) get_server_fields('get_leave_balance', '','', doc, dt, dn, 1); } -// --------------- -// calculate days -// --------------- 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}); diff --git a/hr/doctype/leave_application/leave_application.py b/hr/doctype/leave_application/leave_application.py index e71a26a368d..2f7e4a8dc00 100755 --- a/hr/doctype/leave_application/leave_application.py +++ b/hr/doctype/leave_application/leave_application.py @@ -38,12 +38,6 @@ class DocType: self.doc = doc self.doclist = doclist - -# ******************************************** client triggers *********************************************** - - # ------------------ - # get leave balance - # ------------------ def get_leave_balance(self): leave_all = sql("select total_leaves_allocated from `tabLeave Allocation` where employee = '%s' and leave_type = '%s' and fiscal_year = '%s' and docstatus = 1" % (self.doc.employee, self.doc.leave_type, self.doc.fiscal_year)) leave_all = leave_all and flt(leave_all[0][0]) or 0 @@ -52,10 +46,6 @@ class DocType: ret = {'leave_balance':leave_all - leave_app} return ret - -# ************************************************ utilities ************************************************* - - # ------------------- def get_holidays(self): """ get total holidays @@ -65,10 +55,6 @@ class DocType: tot_hol = sql("select count(*) from `tabHoliday` h1, `tabHoliday List` h2 where h1.parent = h2.name and h1.holiday_date between '%s' and '%s' and ifnull(h2.is_default,0) = 1 and h2.fiscal_year = %s"% (self.doc.from_date, self.doc.to_date, self.doc.fiscal_year)) return tot_hol and flt(tot_hol[0][0]) or 0 - - # --------------------- - # get total leave days - # --------------------- def get_total_leave_days(self): """ Calculates total leave days based on input and holidays @@ -82,27 +68,15 @@ class DocType: } return ret - -# ************************************************ validate ************************************************* - - # ----------------- - # validate to date - # ----------------- 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)): msgprint("To date cannot be before from date") raise Exception - - # -------------------------------- - # check whether leave type is lwp - # -------------------------------- + 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 - # ------------------------ - # validate balance leaves - # ------------------------ def validate_balance_leaves(self): if self.doc.from_date and self.doc.to_date and not self.is_lwp(): bal = self.get_leave_balance() @@ -111,12 +85,8 @@ class DocType: set(self.doc,'leave_balance',flt(bal['leave_balance'])) set(self.doc,'total_leave_days',flt(tot_leaves['total_leave_days'])) if flt(bal['leave_balance']) < flt(tot_leaves['total_leave_days']): - msgprint("Employee : %s cannot apply for %s of more than %s days" % (self.doc.employee, self.doc.leave_type, flt(bal['leave_balance']))) - raise Exception + msgprint("Warning : There is not enough leave balance") - # - # validate overlapping leaves - # def validate_leave_overlap(self): for d in sql("""select name, leave_type, posting_date, from_date, to_date from `tabLeave Application` @@ -128,9 +98,6 @@ class DocType: msgprint("Employee : %s has already applied for %s between %s and %s on %s. Please refer Leave Application : %s" % (self.doc.employee, cstr(d['leave_type']), formatdate(d['from_date']), formatdate(d['to_date']), formatdate(d['posting_date']), d['name']), raise_exception = 1) - # --------------------------------------------------------------------- - # validate max days for which leave can be applied for particular type - # --------------------------------------------------------------------- def validate_max_days(self): max_days = sql("select max_days_allowed from `tabLeave Type` where name = '%s'" %(self.doc.leave_type)) max_days = max_days and flt(max_days[0][0]) or 0 @@ -138,12 +105,13 @@ class DocType: msgprint("Sorry ! You cannot apply for %s for more than %s days" % (self.doc.leave_type, max_days)) raise Exception - - # --------- - # validate - # --------- def validate(self): 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) diff --git a/hr/doctype/leave_application/leave_application.txt b/hr/doctype/leave_application/leave_application.txt index c87c746b2f0..6a33df61bc7 100644 --- a/hr/doctype/leave_application/leave_application.txt +++ b/hr/doctype/leave_application/leave_application.txt @@ -1,285 +1,239 @@ -# DocType, Leave Application [ - - # These values are common in all dictionaries - { - u'creation': '2012-05-15 12:14:45', - u'docstatus': 0, - u'modified': '2012-10-02 11:19:44', - u'modified_by': u'Administrator', - u'owner': u'Administrator' - }, - - # These values are common for all DocType - { - '_last_update': u'1310019491', - 'autoname': u'LAP/.#####', - 'colour': u'White:FFF', - u'doctype': u'DocType', - 'document_type': u'Transaction', - 'is_submittable': 1, - 'module': u'HR', - u'name': u'__common__', - 'search_fields': u'employee,employee_name,leave_type,from_date,to_date,total_leave_days,fiscal_year', - 'section_style': u'Simple', - 'show_in_menu': 0, - 'subject': u'From %(employee_name)s, %(designation)s', - 'tag_fields': u'leave_type', - 'version': 1 - }, - - # These values are common for all DocField - { - u'doctype': u'DocField', - u'name': u'__common__', - 'parent': u'Leave Application', - 'parentfield': u'fields', - 'parenttype': u'DocType' - }, - - # These values are common for all DocPerm - { - u'doctype': u'DocPerm', - u'name': u'__common__', - 'parent': u'Leave Application', - 'parentfield': u'permissions', - 'parenttype': u'DocType', - 'read': 1 - }, - - # DocType, Leave Application - { - u'doctype': u'DocType', - u'name': u'Leave Application' - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'column_break0', - 'fieldtype': u'Column Break', - 'permlevel': 0, - 'width': u'50%' - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'employee', - 'fieldtype': u'Link', - 'in_filter': 1, - 'label': u'Employee', - 'options': u'Employee', - 'permlevel': 0, - 'reqd': 1, - 'search_index': 1 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'employee_name', - 'fieldtype': u'Data', - 'in_filter': 1, - 'label': u'Employee Name', - 'permlevel': 1, - 'search_index': 0 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'leave_type', - 'fieldtype': u'Select', - 'in_filter': 1, - 'label': u'Leave Type', - 'options': u'link:Leave Type', - 'permlevel': 0, - 'reqd': 1, - 'search_index': 1 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'leave_balance', - 'fieldtype': u'Currency', - 'label': u'Leave Balance', - 'permlevel': 1 - }, - - # DocField - { - 'colour': u'White:FFF', - 'default': u'Today', - u'doctype': u'DocField', - 'fieldname': u'posting_date', - 'fieldtype': u'Date', - 'label': u'Posting Date', - 'no_copy': 1, - 'permlevel': 1, - 'reqd': 1 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'fiscal_year', - 'fieldtype': u'Select', - 'in_filter': 1, - 'label': u'Fiscal Year', - 'options': u'link:Fiscal Year', - 'permlevel': 0, - 'reqd': 1, - 'search_index': 0 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'column_break1', - 'fieldtype': u'Column Break', - 'permlevel': 0, - 'width': u'50%' - }, - - # DocField - { - 'colour': u'White:FFF', - u'doctype': u'DocField', - 'fieldname': u'half_day', - 'fieldtype': u'Check', - 'label': u'Half Day', - 'permlevel': 0, - 'trigger': u'Client' - }, - - # DocField - { - 'colour': u'White:FFF', - u'doctype': u'DocField', - 'fieldname': u'from_date', - 'fieldtype': u'Date', - 'label': u'From Date', - 'permlevel': 0, - 'search_index': 1, - 'trigger': u'Client' - }, - - # DocField - { - 'colour': u'White:FFF', - u'doctype': u'DocField', - 'fieldname': u'to_date', - 'fieldtype': u'Date', - 'label': u'To Date', - 'permlevel': 0, - 'search_index': 1, - 'trigger': u'Client' - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'total_leave_days', - 'fieldtype': u'Currency', - 'label': u'Total Leave Days', - 'permlevel': 1 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'description', - 'fieldtype': u'Small Text', - 'label': u'Description', - 'permlevel': 0, - 'width': u'300px' - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'letter_head', - 'fieldtype': u'Link', - 'label': u'Letter Head', - 'options': u'Letter Head', - 'permlevel': 0 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'amended_from', - 'fieldtype': u'Data', - 'label': u'Amended From', - 'permlevel': 1 - }, - - # DocField - { - u'doctype': u'DocField', - 'fieldname': u'amendment_date', - 'fieldtype': u'Date', - 'label': u'Amendment Date', - 'permlevel': 1 - }, - - # DocPerm - { - 'amend': 0, - 'cancel': 0, - 'create': 0, - u'doctype': u'DocPerm', - 'match': u'owner', - 'permlevel': 0, - 'role': u'Employee', - 'submit': 0, - 'write': 0 - }, - - # DocPerm - { - 'amend': 1, - 'cancel': 1, - 'create': 1, - u'doctype': u'DocPerm', - 'permlevel': 0, - 'role': u'HR User', - 'submit': 1, - 'write': 1 - }, - - # DocPerm - { - 'amend': 1, - 'cancel': 1, - 'create': 1, - u'doctype': u'DocPerm', - 'permlevel': 0, - 'role': u'HR Manager', - 'submit': 1, - 'write': 1 - }, - - # DocPerm - { - u'doctype': u'DocPerm', - 'permlevel': 1, - 'role': u'HR User' - }, - - # DocPerm - { - u'doctype': u'DocPerm', - 'permlevel': 1, - 'role': u'HR Manager' - }, - - # DocPerm - { - u'doctype': u'DocPerm', - 'permlevel': 1, - 'role': u'Employee' - } + { + "owner": "Administrator", + "docstatus": 0, + "creation": "2012-11-02 17:16:54", + "modified_by": "Administrator", + "modified": "2012-11-30 12:17:27" + }, + { + "is_submittable": 1, + "autoname": "LAP/.#####", + "name": "__common__", + "search_fields": "employee,employee_name,leave_type,from_date,to_date,total_leave_days,fiscal_year", + "module": "HR", + "doctype": "DocType", + "document_type": "Transaction" + }, + { + "name": "__common__", + "parent": "Leave Application", + "doctype": "DocField", + "parenttype": "DocType", + "parentfield": "fields" + }, + { + "name": "__common__", + "parent": "Leave Application", + "read": 1, + "doctype": "DocPerm", + "parenttype": "DocType", + "parentfield": "permissions" + }, + { + "name": "Leave Application", + "doctype": "DocType" + }, + { + "default": "Open", + "colour": "White:FFF", + "doctype": "DocField", + "label": "Status", + "options": "Open\nApproved\nRejected", + "fieldname": "status", + "fieldtype": "Select", + "permlevel": 3 + }, + { + "search_index": 1, + "doctype": "DocField", + "label": "Leave Type", + "options": "link:Leave Type", + "fieldname": "leave_type", + "fieldtype": "Select", + "reqd": 1, + "permlevel": 0, + "in_filter": 1 + }, + { + "search_index": 1, + "colour": "White:FFF", + "doctype": "DocField", + "label": "From Date", + "trigger": "Client", + "fieldname": "from_date", + "fieldtype": "Date", + "reqd": 1, + "permlevel": 0 + }, + { + "search_index": 1, + "colour": "White:FFF", + "doctype": "DocField", + "label": "To Date", + "trigger": "Client", + "fieldname": "to_date", + "fieldtype": "Date", + "reqd": 1, + "permlevel": 0 + }, + { + "colour": "White:FFF", + "doctype": "DocField", + "label": "Half Day", + "trigger": "Client", + "fieldname": "half_day", + "fieldtype": "Check", + "permlevel": 0 + }, + { + "doctype": "DocField", + "width": "50%", + "fieldname": "column_break1", + "fieldtype": "Column Break", + "permlevel": 0 + }, + { + "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 + }, + { + "search_index": 1, + "doctype": "DocField", + "label": "Employee", + "options": "Employee", + "fieldname": "employee", + "fieldtype": "Link", + "reqd": 1, + "permlevel": 0, + "in_filter": 1 + }, + { + "search_index": 0, + "doctype": "DocField", + "label": "Employee Name", + "fieldname": "employee_name", + "fieldtype": "Data", + "permlevel": 1, + "in_filter": 1 + }, + { + "doctype": "DocField", + "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", + "doctype": "DocField", + "label": "Posting Date", + "no_copy": 1, + "fieldname": "posting_date", + "fieldtype": "Date", + "reqd": 1, + "permlevel": 2 + }, + { + "search_index": 0, + "doctype": "DocField", + "label": "Fiscal Year", + "options": "link:Fiscal Year", + "fieldname": "fiscal_year", + "fieldtype": "Select", + "reqd": 1, + "permlevel": 2, + "in_filter": 1 + }, + { + "doctype": "DocField", + "label": "Letter Head", + "options": "Letter Head", + "fieldname": "letter_head", + "fieldtype": "Link", + "permlevel": 2 + }, + { + "doctype": "DocField", + "label": "Amended From", + "fieldname": "amended_from", + "fieldtype": "Data", + "permlevel": 2 + }, + { + "doctype": "DocField", + "label": "Amendment Date", + "fieldname": "amendment_date", + "fieldtype": "Date", + "permlevel": 2 + }, + { + "create": 1, + "doctype": "DocPerm", + "write": 1, + "role": "Employee", + "permlevel": 0, + "match": "employee" + }, + { + "doctype": "DocPerm", + "role": "All", + "permlevel": 1 + }, + { + "amend": 1, + "create": 1, + "doctype": "DocPerm", + "submit": 1, + "write": 1, + "role": "HR User", + "cancel": 1, + "permlevel": 0 + }, + { + "amend": 0, + "create": 0, + "doctype": "DocPerm", + "submit": 0, + "write": 1, + "role": "HR User", + "cancel": 0, + "permlevel": 2 + }, + { + "doctype": "DocPerm", + "role": "All", + "permlevel": 3 + }, + { + "doctype": "DocPerm", + "write": 1, + "role": "HR User", + "permlevel": 3 + } ] \ No newline at end of file diff --git a/hr/doctype/leave_application/leave_application_list.js b/hr/doctype/leave_application/leave_application_list.js index 4bcbab83c2b..4c80e7fefe9 100644 --- a/hr/doctype/leave_application/leave_application_list.js +++ b/hr/doctype/leave_application/leave_application_list.js @@ -3,6 +3,7 @@ wn.doclistviews['Leave Application'] = wn.views.ListView.extend({ init: function(d) { this._super(d) this.fields = this.fields.concat([ + "`tabLeave Application`.status", "`tabLeave Application`.employee_name", "`tabLeave Application`.total_leave_days", "`tabLeave Application`.from_date", @@ -12,8 +13,21 @@ wn.doclistviews['Leave Application'] = wn.views.ListView.extend({ this.stats = this.stats.concat(['company']); }, + label_style: { + "status": { + "Open": "danger", + "Approved": "success", + "Rejected": "info", + } + }, + prepare_data: function(data) { this._super(data); + + data.label_style = this.label_style.status[data.status]; + data.status_html = repl('%(status)s', data); + data.from_date = wn.datetime.str_to_user(data.from_date); data.to_date = wn.datetime.str_to_user(data.to_date); data.date_range = (data.from_date === data.to_date) @@ -28,10 +42,10 @@ wn.doclistviews['Leave Application'] = wn.views.ListView.extend({ {width: '3%', content: 'check'}, {width: '5%', content:'avatar'}, {width: '3%', content:'docstatus'}, + {width: '15%', content:'status_html'}, {width: '12%', content:'name'}, - {width: '37%', content:'employee_name+tags'}, - {width: '10%', content:'total_leave_days', - css: {'color':'#777'}}, - {width: '30%', content:'date_range'}, + {width: '25%', content:'employee_name+tags'}, + {width: '25%', content:'date_range'}, + {width: '12%', content:'modified'}, ] }); \ No newline at end of file diff --git a/patches/november_2012/leave_application_cleanup.py b/patches/november_2012/leave_application_cleanup.py new file mode 100644 index 00000000000..18e69cfa8d7 --- /dev/null +++ b/patches/november_2012/leave_application_cleanup.py @@ -0,0 +1,9 @@ +import webnotes + +def execute(): + webnotes.clear_perms("Leave Application") + webnotes.reload_doc("hr", "doctype", "leave_application") + webnotes.conn.sql("""update `tabLeave Application` set status='Approved' + where docstatus=1""") + webnotes.conn.sql("""update `tabLeave Application` set status='Open' + where docstatus=0""") \ No newline at end of file diff --git a/patches/patch_list.py b/patches/patch_list.py index 14921244aa7..100f25b98f0 100644 --- a/patches/patch_list.py +++ b/patches/patch_list.py @@ -693,4 +693,8 @@ patch_list = [ 'patch_module': 'patches.november_2012', 'patch_file': 'add_employee_field_in_employee', }, + { + 'patch_module': 'patches.november_2012', + 'patch_file': 'leave_application_cleanup', + }, ] \ No newline at end of file