001 /**
002 * Copyright 2004-2012 The Kuali Foundation
003 *
004 * Licensed under the Educational Community License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.opensource.org/licenses/ecl2.php
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016 package org.kuali.hr.time.department;
017
018 import java.sql.Date;
019 import java.util.HashMap;
020 import java.util.List;
021 import java.util.Map;
022
023 import org.apache.commons.lang.StringUtils;
024 import org.kuali.hr.time.roles.TkRole;
025 import org.kuali.hr.time.service.base.TkServiceLocator;
026 import org.kuali.hr.time.util.TKUtils;
027 import org.kuali.hr.time.util.TkConstants;
028 import org.kuali.kfs.coa.businessobject.Chart;
029 import org.kuali.kfs.coa.businessobject.Organization;
030 import org.kuali.rice.kns.document.MaintenanceDocument;
031 import org.kuali.rice.kns.maintenance.rules.MaintenanceDocumentRuleBase;
032 import org.kuali.rice.krad.bo.PersistableBusinessObject;
033 import org.kuali.rice.krad.service.KRADServiceLocator;
034
035 public class DepartmentRule extends MaintenanceDocumentRuleBase {
036
037 boolean validateDepartment(Department department) {
038 boolean valid = true;
039 Department existingDept = TkServiceLocator.getDepartmentService().getDepartment(department.getDept(), department.getEffectiveDate());
040
041 if ( department.getHrDeptId() == null ){ //KPME-1456. xichen. Only go through this validation when create a new dept.
042 if (department.getEffectiveDate() != null) {
043 if (existingDept != null){
044 if ( existingDept.getDept().equalsIgnoreCase(department.getDept()) &&
045 existingDept.getLocation().equalsIgnoreCase(department.getLocation()) ){
046 // error.department.duplicate.exists=There is an exact duplicate version of this Department.
047 this.putFieldError("dept", "error.department.duplicate.exists", department.getDept());
048 valid = false;
049 }
050 }
051 }
052 }
053
054 return valid;
055 }
056
057 boolean validateChart(String value) {
058 boolean valid = true;
059 if (value != null) {
060 Chart chart = KRADServiceLocator.getBusinessObjectService()
061 .findBySinglePrimaryKey(Chart.class, value);
062 valid = (chart != null);
063
064 if (!valid) {
065 this.putFieldError("chart", "dept.chart.notfound", value);
066 }
067 }
068 return valid;
069 }
070
071 boolean validateOrg(String value) {
072 boolean valid = true;
073 if (value != null) {
074 Organization org = this.getOrganization(value);
075 valid = (org != null);
076
077 if (!valid) {
078 this.putFieldError("org", "dept.org.notfound", value);
079 }
080 }
081 return valid;
082 }
083
084 boolean validateChartAndOrg(String chartString, String orgString) {
085 if(chartString != null && orgString != null) {
086 Chart chart = KRADServiceLocator.getBusinessObjectService().findBySinglePrimaryKey(Chart.class, chartString);
087 Organization org = this.getOrganization(orgString);
088 if(chart != null && org != null) {
089 Chart chartTemp = org.getChartOfAccounts();
090 if(!chart.getChartOfAccountsCode().equals(chartTemp.getChartOfAccountsCode())) {
091 String[] params = new String[]{orgString, chartString};
092 this.putFieldError("org", "dept.org.chart.notmatch", params);
093 return false;
094 }
095 }
096 }
097 return true;
098 }
099
100 Organization getOrganization(String orgCode) {
101 Map<String, String> primaryKeys = new HashMap<String, String>();
102 primaryKeys.put("organizationCode", orgCode);
103 return (Organization) KRADServiceLocator.getBusinessObjectService().findByPrimaryKey(Organization.class, primaryKeys);
104 }
105
106 /**
107 * Checks for not null and size > 0, but follows the validation pattern
108 * given in this class for future expanding.
109 *
110 * @return true if there is a role, false otherwise.
111 */
112 protected boolean validateRolePresent(List<TkRole> roles, Date effectiveDate) {
113 boolean valid = false;
114
115 if (roles != null && roles.size() > 0) {
116 int pos = 0;
117 for (TkRole role : roles) {
118 valid |= role.isActive()
119 && StringUtils.equals(role.getRoleName(),
120 TkConstants.ROLE_TK_DEPT_ADMIN);
121 if(role.getExpirationDate() != null){
122 StringBuffer prefix = new StringBuffer("roles[");
123 prefix.append(pos).append("].");
124 if (effectiveDate.compareTo(role.getExpirationDate()) >= 0
125 || role.getEffectiveDate().compareTo(
126 role.getExpirationDate()) >= 0) {
127 this.putFieldError(prefix + "expirationDate",
128 "error.role.expiration");
129 } else if (TKUtils.getDaysBetween(role.getEffectiveDate(), role.getExpirationDate()) > 180) {
130 this.putFieldError(prefix + "expirationDate",
131 "error.role.expiration.duration");
132 valid = false;
133 }
134 }
135 pos++;
136 }
137 }
138
139 if (!valid) {
140 this.putGlobalError("role.required");
141 }
142
143 return valid;
144 }
145
146 /**
147 * The calling method doesn't seem to examine the return value.
148 */
149 @Override
150 protected boolean processCustomRouteDocumentBusinessRules(
151 MaintenanceDocument document) {
152 boolean valid = false;
153
154 PersistableBusinessObject pbo = (PersistableBusinessObject) this.getNewBo();
155 if (pbo instanceof Department) {
156 Department clr = (Department) pbo;
157 valid = validateChart(clr.getChart());
158 valid &= validateOrg(clr.getOrg());
159 valid &= validateChartAndOrg(clr.getChart(), clr.getOrg());
160 valid &= validateRolePresent(clr.getRoles(), clr.getEffectiveDate());
161 valid &= validateDepartment(clr); // KPME1400
162 }
163
164 return valid;
165 }
166
167 }