Skip to content

Commit 92e6ebd

Browse files
author
Anand Doshi
committed
allow to change new leave allocation after submit -- raise appropriate validations
1 parent b77ee2f commit 92e6ebd

File tree

2 files changed

+117
-118
lines changed

2 files changed

+117
-118
lines changed

hr/doctype/leave_allocation/leave_allocation.py

Lines changed: 114 additions & 116 deletions
Original file line numberDiff line numberDiff line change
@@ -8,131 +8,129 @@
88
#
99
# This program is distributed in the hope that it will be useful,
1010
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11-
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1212
# GNU General Public License for more details.
1313
#
1414
# You should have received a copy of the GNU General Public License
15-
# along with this program. If not, see <http://www.gnu.org/licenses/>.
15+
# along with this program. If not, see <http://www.gnu.org/licenses/>.
1616

1717
# Please edit this list and import only required elements
1818
from __future__ import unicode_literals
1919
import webnotes
20-
21-
from webnotes.utils import add_days, add_months, add_years, cint, cstr, date_diff, default_fields, flt, fmt_money, formatdate, getTraceback, get_defaults, get_first_day, get_last_day, getdate, has_common, month_name, now, nowdate, replace_newlines, sendmail, set_default, str_esc_quote, user_format, validate_email_add
22-
from webnotes.model import db_exists
23-
from webnotes.model.doc import Document, addchild, getchildren, make_autoname
24-
from webnotes.model.doclist import getlist, copy_doclist
25-
from webnotes.model.code import get_obj, get_server_obj, run_server_obj, updatedb, check_syntax
26-
from webnotes import session, form, msgprint, errprint
27-
20+
from webnotes.utils import cint, flt
21+
from webnotes import msgprint
2822
set = webnotes.conn.set
2923
sql = webnotes.conn.sql
30-
get_value = webnotes.conn.get_value
31-
in_transaction = webnotes.conn.in_transaction
32-
convert_to_lists = webnotes.conn.convert_to_lists
33-
import datetime
3424

35-
# -----------------------------------------------------------------------------------------
3625
class DocType:
37-
def __init__(self, doc, doclist):
38-
self.doc = doc
39-
self.doclist = doclist
40-
41-
42-
# ************************************************ utilities *************************************************
43-
# --------------
44-
# get leave bal
45-
# --------------
46-
def get_leave_bal(self, prev_fyear):
47-
# leaves allocates
48-
tot_leaves_all = sql("select SUM(total_leaves_allocated) from `tabLeave Allocation` where employee = '%s' and leave_type = '%s' and fiscal_year = '%s' and docstatus = 1 and name != '%s'" % (self.doc.employee, self.doc.leave_type, prev_fyear, self.doc.name))
49-
tot_leaves_all = tot_leaves_all and flt(tot_leaves_all[0][0]) or 0
50-
51-
# leaves applied
52-
tot_leaves_app = sql("select SUM(total_leave_days) from `tabLeave Application` where employee = '%s' and leave_type = '%s' and fiscal_year = '%s' and docstatus = 1" % (self.doc.employee, self.doc.leave_type, prev_fyear))
53-
tot_leaves_app = tot_leaves_app and flt(tot_leaves_app[0][0]) or 0
54-
55-
return tot_leaves_all - tot_leaves_app
56-
57-
58-
# ******************************************** client triggers ***********************************************
59-
60-
# ------------------------------------------------------------------
61-
# check whether carry forward is allowed or not for this leave type
62-
# ------------------------------------------------------------------
63-
def allow_carry_forward(self):
64-
cf = sql("select is_carry_forward from `tabLeave Type` where name = %s" , self.doc.leave_type)
65-
cf = cf and cint(cf[0][0]) or 0
66-
if not cf:
67-
set(self.doc,'carry_forward',0)
68-
msgprint("Sorry ! You cannot carry forward %s" % (self.doc.leave_type))
69-
raise Exception
70-
71-
# ---------------------------
72-
# get carry forwarded leaves
73-
# ---------------------------
74-
def get_carry_forwarded_leaves(self):
75-
if self.doc.carry_forward: self.allow_carry_forward()
76-
prev_fiscal_year = sql("select name from `tabFiscal Year` where name < '%s' order by name desc limit 1" % (self.doc.fiscal_year))
77-
prev_fiscal_year = prev_fiscal_year and prev_fiscal_year[0][0] or ''
78-
ret = {}
79-
prev_bal = 0
80-
if prev_fiscal_year and cint(self.doc.carry_forward) == 1:
81-
prev_bal = self.get_leave_bal(prev_fiscal_year)
82-
ret = {
83-
'carry_forwarded_leaves' : prev_bal,
84-
'total_leaves_allocated' : flt(prev_bal) + flt(self.doc.new_leaves_allocated)
85-
}
86-
return ret
87-
88-
89-
# ********************************************** validate *****************************************************
90-
91-
# ---------------------------
92-
# get total allocated leaves
93-
# ---------------------------
94-
def get_total_allocated_leaves(self):
95-
leave_det = self.get_carry_forwarded_leaves()
96-
set(self.doc,'carry_forwarded_leaves',flt(leave_det['carry_forwarded_leaves']))
97-
set(self.doc,'total_leaves_allocated',flt(leave_det['total_leaves_allocated']))
98-
99-
# ------------------------------------------------------------------------------------
100-
# validate leave (i.e. check whether leave for same type is already allocated or not)
101-
# ------------------------------------------------------------------------------------
102-
def validate_allocated_leave(self):
103-
l = sql("select name 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))
104-
l = l and l[0][0] or ''
105-
if l:
106-
msgprint("%s is allocated to Employee: %s for Fiscal Year : %s. Please refer Leave Allocation : %s" % (self.doc.leave_type, self.doc.employee, self.doc.fiscal_year, l))
107-
raise Exception
108-
109-
# ---------
110-
# validate
111-
# ---------
112-
def validate(self):
113-
self.validate_allocated_leave()
114-
115-
# ----------
116-
# on update
117-
# ----------
118-
def on_update(self):
119-
self.get_total_allocated_leaves()
120-
121-
122-
# ********************************************** cancel ********************************************************
123-
124-
# -------------------------
125-
# check for applied leaves
126-
# -------------------------
127-
def check_for_leave_application(self):
128-
chk = sql("select name from `tabLeave Application` 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))
129-
chk = chk and chk[0][0] or ''
130-
if chk:
131-
msgprint("Cannot cancel this Leave Allocation as Employee : %s has already applied for %s. Please check Leave Application : %s" % (self.doc.employee, self.doc.leave_type, chk))
132-
raise Exception
26+
def __init__(self, doc, doclist):
27+
self.doc, self.doclist = doc, doclist
28+
29+
def validate(self):
30+
self.validate_new_leaves_allocated_value()
31+
self.check_existing_leave_allocation()
32+
self.validate_new_leaves_allocated()
33+
34+
def on_update_after_submit(self):
35+
self.validate_new_leaves_allocated_value()
36+
self.validate_new_leaves_allocated()
37+
38+
def on_update(self):
39+
self.get_total_allocated_leaves()
40+
41+
def on_cancel(self):
42+
self.check_for_leave_application()
43+
44+
def validate_new_leaves_allocated_value(self):
45+
"""validate that leave allocation is in multiples of 0.5"""
46+
if flt(self.doc.new_leaves_allocated) % 0.5:
47+
guess = round(flt(self.doc.new_leaves_allocated) * 2.0) / 2.0
48+
49+
msgprint("""New Leaves Allocated should be a multiple of 0.5.
50+
Perhaps you should enter %s or %s""" % (guess, guess + 0.5),
51+
raise_exception=1)
52+
53+
def check_existing_leave_allocation(self):
54+
"""check whether leave for same type is already allocated or not"""
55+
leave_allocation = sql("""select name from `tabLeave Allocation`
56+
where employee=%s and leave_type=%s and fiscal_year=%s and docstatus=1""",
57+
(self.doc.employee, self.doc.leave_type, self.doc.fiscal_year))
58+
if leave_allocation:
59+
msgprint("""%s is already allocated to Employee: %s for Fiscal Year: %s.
60+
Please refere Leave Allocation: \
61+
<a href="#Form/Leave Allocation/%s">%s</a>""" % \
62+
(self.doc.leave_type, self.doc.employee, self.doc.fiscal_year,
63+
leave_allocation[0][0], leave_allocation[0][0]), raise_exception=1)
64+
65+
def validate_new_leaves_allocated(self):
66+
"""check if Total Leaves Allocated >= Leave Applications"""
67+
self.doc.total_leaves_allocated = flt(self.doc.carry_forwarded_leaves) + \
68+
flt(self.doc.new_leaves_allocated)
69+
leaves_applied = self.get_leaves_applied(self.doc.fiscal_year)
70+
if leaves_applied > self.doc.total_leaves_allocated:
71+
expected_new_leaves = flt(self.doc.new_leaves_allocated) + \
72+
(leaves_applied - self.doc.total_leaves_allocated)
73+
msgprint("""Employee: %s has already applied for %s leaves.
74+
Hence, New Leaves Allocated should be atleast %s""" % \
75+
(self.doc.employee, leaves_applied, expected_new_leaves),
76+
raise_exception=1)
77+
78+
def get_leave_bal(self, prev_fyear):
79+
return self.get_leaves_allocated(prev_fyear) - self.get_leaves_applied(prev_fyear)
80+
81+
def get_leaves_applied(self, fiscal_year):
82+
leaves_applied = sql("""select SUM(ifnull(total_leave_days, 0))
83+
from `tabLeave Application` where employee=%s and leave_type=%s
84+
and fiscal_year=%s and docstatus=1""",
85+
(self.doc.employee, self.doc.leave_type, fiscal_year))
86+
return leaves_applied and flt(leaves_applied[0][0]) or 0
87+
88+
def get_leaves_allocated(self, fiscal_year):
89+
leaves_allocated = sql("""select SUM(ifnull(total_leaves_allocated, 0))
90+
from `tabLeave Allocation` where employee=%s and leave_type=%s
91+
and fiscal_year=%s and docstatus=1 and name!=%s""",
92+
(self.doc.employee, self.doc.leave_type, fiscal_year, self.doc.name))
93+
return leaves_allocated and flt(leaves_allocated[0][0]) or 0
94+
95+
def allow_carry_forward(self):
96+
"""check whether carry forward is allowed or not for this leave type"""
97+
cf = sql("""select is_carry_forward from `tabLeave Type` where name = %s""",
98+
self.doc.leave_type)
99+
cf = cf and cint(cf[0][0]) or 0
100+
if not cf:
101+
set(self.doc,'carry_forward',0)
102+
msgprint("Sorry! You cannot carry forward %s" % (self.doc.leave_type),
103+
raise_exception=1)
104+
105+
def get_carry_forwarded_leaves(self):
106+
if self.doc.carry_forward:
107+
self.allow_carry_forward()
108+
prev_fiscal_year = sql("""select name from `tabFiscal Year`
109+
where name < %s order by name desc limit 1""", self.doc.fiscal_year)
110+
prev_fiscal_year = prev_fiscal_year and prev_fiscal_year[0][0] or ''
111+
prev_bal = 0
112+
if prev_fiscal_year and cint(self.doc.carry_forward) == 1:
113+
prev_bal = self.get_leave_bal(prev_fiscal_year)
114+
ret = {
115+
'carry_forwarded_leaves': prev_bal,
116+
'total_leaves_allocated': flt(prev_bal) + flt(self.doc.new_leaves_allocated)
117+
}
118+
return ret
119+
120+
def get_total_allocated_leaves(self):
121+
leave_det = self.get_carry_forwarded_leaves()
122+
set(self.doc,'carry_forwarded_leaves',flt(leave_det['carry_forwarded_leaves']))
123+
set(self.doc,'total_leaves_allocated',flt(leave_det['total_leaves_allocated']))
124+
125+
def check_for_leave_application(self):
126+
exists = sql("""select name from `tabLeave Application`
127+
where employee=%s and leave_type=%s and fiscal_year=%s and docstatus=1""",
128+
(self.doc.employee, self.doc.leave_type, self.doc.fiscal_year))
129+
if exists:
130+
msgprint("""Cannot cancel this Leave Allocation as \
131+
Employee : %s has already applied for %s.
132+
Please check Leave Application: \
133+
<a href="#Form/Leave Application/%s">%s</a>""" % \
134+
(self.doc.employee, self.doc.leave_type, exists[0][0], exists[0][0]))
135+
raise Exception
133136

134-
# -------
135-
# cancel
136-
# -------
137-
def on_cancel(self):
138-
self.check_for_leave_application()

hr/doctype/leave_allocation/leave_allocation.txt

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,9 @@
33

44
# These values are common in all dictionaries
55
{
6-
u'creation': '2012-05-15 12:14:45',
6+
u'creation': '2012-10-02 18:51:49',
77
u'docstatus': 0,
8-
u'modified': '2012-10-02 11:21:31',
8+
u'modified': '2012-10-17 12:51:44',
99
u'modified_by': u'Administrator',
1010
u'owner': u'Administrator'
1111
},
@@ -185,6 +185,7 @@
185185

186186
# DocField
187187
{
188+
'allow_on_submit': 1,
188189
u'doctype': u'DocField',
189190
'fieldname': u'new_leaves_allocated',
190191
'fieldtype': u'Currency',

0 commit comments

Comments
 (0)