001/** 002 * Copyright 2005-2015 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 */ 016package org.kuali.rice.kew.xml; 017 018import org.apache.commons.lang.BooleanUtils; 019import org.apache.commons.lang.StringUtils; 020import org.jdom.Attribute; 021import org.jdom.Document; 022import org.jdom.Element; 023import org.jdom.JDOMException; 024import org.kuali.rice.core.api.delegation.DelegationType; 025import org.kuali.rice.core.api.util.RiceConstants; 026import org.kuali.rice.core.api.util.xml.XmlException; 027import org.kuali.rice.core.api.util.xml.XmlHelper; 028import org.kuali.rice.kew.rule.RuleBaseValues; 029import org.kuali.rice.kew.rule.RuleDelegationBo; 030import org.kuali.rice.kew.rule.RuleTemplateOptionBo; 031import org.kuali.rice.kew.rule.bo.RuleAttribute; 032import org.kuali.rice.kew.rule.bo.RuleTemplateBo; 033import org.kuali.rice.kew.rule.bo.RuleTemplateAttributeBo; 034import org.kuali.rice.kew.service.KEWServiceLocator; 035import org.kuali.rice.kew.api.KewApiConstants; 036import org.xml.sax.SAXException; 037 038import javax.xml.parsers.ParserConfigurationException; 039import java.io.IOException; 040import java.io.InputStream; 041import java.sql.Timestamp; 042import java.text.ParseException; 043import java.util.ArrayList; 044import java.util.Collection; 045import java.util.Iterator; 046import java.util.List; 047 048import static org.kuali.rice.core.api.impex.xml.XmlConstants.*; 049/** 050 * Parses {@link org.kuali.rice.kew.rule.bo.RuleTemplateBo}s from XML. 051 * 052 * @see org.kuali.rice.kew.rule.bo.RuleTemplateBo 053 * 054 * @author Kuali Rice Team (rice.collab@kuali.org) 055 */ 056public class RuleTemplateXmlParser { 057 058 private static final org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(RuleTemplateXmlParser.class); 059 060 /** 061 * By default make attributes defined without a <required> element 062 */ 063 private static final boolean DEFAULT_ATTRIBUTE_REQUIRED = true; 064 private static final boolean DEFAULT_ATTRIBUTE_ACTIVE = true; 065 066 /** 067 * A dummy document type used in the default rule 068 */ 069 private static final String DUMMY_DOCUMENT_TYPE = "dummyDocumentType"; 070 071 /** 072 * Used to set the display order of attributes encountered in parsing runs during the lifetime of this object 073 */ 074 private int templateAttributeCounter = 0; 075 076 public List<RuleTemplateBo> parseRuleTemplates(InputStream input) throws IOException, XmlException { 077 078 try { 079 Document doc = XmlHelper.trimSAXXml(input); 080 Element root = doc.getRootElement(); 081 return parseRuleTemplates(root); 082 } catch (JDOMException e) { 083 throw new XmlException("Parse error.", e); 084 } catch (SAXException e) { 085 throw new XmlException("Parse error.", e); 086 } catch (ParserConfigurationException e) { 087 throw new XmlException("Parse error.", e); 088 } 089 } 090 091 public List<RuleTemplateBo> parseRuleTemplates(Element element) throws XmlException { 092 List<RuleTemplateBo> ruleTemplates = new ArrayList<RuleTemplateBo>(); 093 094 // iterate over any RULE_TEMPLATES elements 095 Collection<Element> ruleTemplatesElements = XmlHelper.findElements(element, RULE_TEMPLATES); 096 Iterator ruleTemplatesIterator = ruleTemplatesElements.iterator(); 097 while (ruleTemplatesIterator.hasNext()) { 098 Element ruleTemplatesElement = (Element) ruleTemplatesIterator.next(); 099 Collection<Element> ruleTemplateElements = XmlHelper.findElements(ruleTemplatesElement, RULE_TEMPLATE); 100 for (Iterator iterator = ruleTemplateElements.iterator(); iterator.hasNext();) { 101 ruleTemplates.add(parseRuleTemplate((Element) iterator.next(), ruleTemplates)); 102 } 103 } 104 return ruleTemplates; 105 } 106 107 private RuleTemplateBo parseRuleTemplate(Element element, List<RuleTemplateBo> ruleTemplates) throws XmlException { 108 String name = element.getChildText(NAME, RULE_TEMPLATE_NAMESPACE); 109 String description = element.getChildText(DESCRIPTION, RULE_TEMPLATE_NAMESPACE); 110 Attribute allowOverwriteAttrib = element.getAttribute("allowOverwrite"); 111 112 boolean allowOverwrite = false; 113 if (allowOverwriteAttrib != null) { 114 allowOverwrite = Boolean.valueOf(allowOverwriteAttrib.getValue()).booleanValue(); 115 } 116 if (org.apache.commons.lang.StringUtils.isEmpty(name)) { 117 throw new XmlException("RuleTemplate must have a name"); 118 } 119 if (org.apache.commons.lang.StringUtils.isEmpty(description)) { 120 throw new XmlException("RuleTemplate must have a description"); 121 } 122 123 // look up the rule template by name first 124 RuleTemplateBo ruleTemplate = KEWServiceLocator.getRuleTemplateService().findByRuleTemplateName(name); 125 126 if (ruleTemplate == null) { 127 // if it does not exist create a new one 128 ruleTemplate = new RuleTemplateBo(); 129 } else { 130 // if it does exist, update it, only if allowOverwrite is set 131 if (!allowOverwrite) { 132 throw new RuntimeException("Attempting to overwrite template " + name + " without allowOverwrite set"); 133 } 134 135 // the name should be equal if one was actually found 136 assert(name.equals(ruleTemplate.getName())) : "Existing template definition name does not match incoming definition name"; 137 } 138 139 // overwrite simple properties 140 ruleTemplate.setName(name); 141 ruleTemplate.setDescription(description); 142 143 // update the delegation template 144 updateDelegationTemplate(element, ruleTemplate, ruleTemplates); 145 146 // update the attribute relationships 147 updateRuleTemplateAttributes(element, ruleTemplate); 148 149 // save the rule template first so that the default/template rule that is generated 150 // in the process of setting defaults is associated properly with this rule template 151 KEWServiceLocator.getRuleTemplateService().save(ruleTemplate); 152 153 // update the default options 154 updateRuleTemplateDefaultOptions(element, ruleTemplate); 155 156 KEWServiceLocator.getRuleTemplateService().save(ruleTemplate); 157 158 return ruleTemplate; 159 } 160 161 /** 162 * Updates the rule template default options. Updates any existing options, removes any omitted ones. 163 * @param ruleTemplateElement the rule template XML element 164 * @param updatedRuleTemplate the RuleTemplate being updated 165 * @throws XmlException 166 */ 167 /* 168 <element name="description" type="c:LongStringType"/> 169 <element name="fromDate" type="c:ShortStringType" minOccurs="0"/> 170 <element name="toDate" type="c:ShortStringType" minOccurs="0"/> 171 <element name="forceAction" type="boolean"/> 172 <element name="active" type="boolean"/> 173 <element name="defaultActionRequested" type="c:ShortStringType"/> 174 <element name="supportsComplete" type="boolean" default="true"/> 175 <element name="supportsApprove" type="boolean" default="true"/> 176 <element name="supportsAcknowledge" type="boolean" default="true"/> 177 <element name="supportsFYI" type="boolean" default="true"/> 178 */ 179 protected void updateRuleTemplateDefaultOptions(Element ruleTemplateElement, RuleTemplateBo updatedRuleTemplate) throws XmlException { 180 Element defaultsElement = ruleTemplateElement.getChild(RULE_DEFAULTS, RULE_TEMPLATE_NAMESPACE); 181 182 // update the rule defaults; this yields whether or not this is a delegation rule template 183 boolean isDelegation = updateRuleDefaults(defaultsElement, updatedRuleTemplate); 184 185 // update the rule template options 186 updateRuleTemplateOptions(defaultsElement, updatedRuleTemplate, isDelegation); 187 188 } 189 190 /** 191 * Updates the rule template defaults options with those in the defaults element 192 * @param defaultsElement the ruleDefaults element 193 * @param updatedRuleTemplate the Rule Template being updated 194 */ 195 protected void updateRuleTemplateOptions(Element defaultsElement, RuleTemplateBo updatedRuleTemplate, boolean isDelegation) throws XmlException { 196 // the possible defaults options 197 // NOTE: the current implementation will remove any existing RuleTemplateOption records for any values which are null, i.e. not set in the incoming XML. 198 // to pro-actively set default values for omitted options, simply set those values here, and records will be added if not present 199 String defaultActionRequested = null; 200 Boolean supportsComplete = null; 201 Boolean supportsApprove = null; 202 Boolean supportsAcknowledge = null; 203 Boolean supportsFYI = null; 204 205 // remove any RuleTemplateOptions the template may have but that we know we aren't going to update/reset 206 // (not sure if this case even exists...does anything else set rule template options?) 207 updatedRuleTemplate.removeNonDefaultOptions(); 208 209 // read in new settings 210 if (defaultsElement != null) { 211 212 defaultActionRequested = defaultsElement.getChildText(DEFAULT_ACTION_REQUESTED, RULE_TEMPLATE_NAMESPACE); 213 supportsComplete = BooleanUtils.toBooleanObject(defaultsElement.getChildText(SUPPORTS_COMPLETE, RULE_TEMPLATE_NAMESPACE)); 214 supportsApprove = BooleanUtils.toBooleanObject(defaultsElement.getChildText(SUPPORTS_APPROVE, RULE_TEMPLATE_NAMESPACE)); 215 supportsAcknowledge = BooleanUtils.toBooleanObject(defaultsElement.getChildText(SUPPORTS_ACKNOWLEDGE, RULE_TEMPLATE_NAMESPACE)); 216 supportsFYI = BooleanUtils.toBooleanObject(defaultsElement.getChildText(SUPPORTS_FYI, RULE_TEMPLATE_NAMESPACE)); 217 } 218 219 if (!isDelegation) { 220 // if this is not a delegation template, store the template options that govern rule action constraints 221 // in the RuleTemplateOptions of the template 222 // we have two options for this behavior: 223 // 1) conditionally parse above, and then unconditionally set/unset the properties; this will have the effect of REMOVING 224 // any of these previously specified rule template options (and is arguably the right thing to do) 225 // 2) unconditionally parse above, and then conditionally set/unset the properties; this will have the effect of PRESERVING 226 // the existing rule template options on this template if it is a delegation template (which of course will be overwritten 227 // by this very same code if they subsequently upload without the delegation flag) 228 // This is a minor point, but the second implementation is chosen as it preserved the current behavior 229 updateOrDeleteRuleTemplateOption(updatedRuleTemplate, KewApiConstants.ACTION_REQUEST_DEFAULT_CD, defaultActionRequested); 230 updateOrDeleteRuleTemplateOption(updatedRuleTemplate, KewApiConstants.ACTION_REQUEST_APPROVE_REQ, supportsApprove); 231 updateOrDeleteRuleTemplateOption(updatedRuleTemplate, KewApiConstants.ACTION_REQUEST_ACKNOWLEDGE_REQ, supportsAcknowledge); 232 updateOrDeleteRuleTemplateOption(updatedRuleTemplate, KewApiConstants.ACTION_REQUEST_FYI_REQ, supportsFYI); 233 updateOrDeleteRuleTemplateOption(updatedRuleTemplate, KewApiConstants.ACTION_REQUEST_COMPLETE_REQ, supportsComplete); 234 } 235 236 } 237 238 /** 239 * 240 * Updates the default/template rule options with those in the defaults element 241 * @param defaultsElement the ruleDefaults element 242 * @param updatedRuleTemplate the Rule Template being updated 243 * @return whether this is a delegation rule template 244 */ 245 protected boolean updateRuleDefaults(Element defaultsElement, RuleTemplateBo updatedRuleTemplate) throws XmlException { 246 // NOTE: implementation detail: in contrast with the other options, the delegate template, and the rule attributes, 247 // we unconditionally blow away the default rule and re-create it (we don't update the existing one, if there is one) 248 if (updatedRuleTemplate.getId() != null) { 249 RuleBaseValues ruleDefaults = KEWServiceLocator.getRuleService().findDefaultRuleByRuleTemplateId(updatedRuleTemplate.getId()); 250 if (ruleDefaults != null) { 251 List ruleDelegationDefaults = KEWServiceLocator.getRuleDelegationService().findByDelegateRuleId(ruleDefaults.getId()); 252 // delete the rule 253 KEWServiceLocator.getRuleService().delete(ruleDefaults.getId()); 254 // delete the associated rule delegation defaults 255 for (Iterator iterator = ruleDelegationDefaults.iterator(); iterator.hasNext();) { 256 RuleDelegationBo ruleDelegation = (RuleDelegationBo) iterator.next(); 257 KEWServiceLocator.getRuleDelegationService().delete(ruleDelegation.getRuleDelegationId()); 258 } 259 } 260 } 261 262 boolean isDelegation = false; 263 264 if (defaultsElement != null) { 265 String delegationTypeCode = defaultsElement.getChildText(DELEGATION_TYPE, RULE_TEMPLATE_NAMESPACE); 266 DelegationType delegationType = null; 267 isDelegation = !org.apache.commons.lang.StringUtils.isEmpty(delegationTypeCode); 268 269 String description = defaultsElement.getChildText(DESCRIPTION, RULE_TEMPLATE_NAMESPACE); 270 271 // would normally be validated via schema but might not be present if invoking RuleXmlParser directly 272 if (description == null) { 273 throw new XmlException("Description must be specified in rule defaults"); 274 } 275 276 String fromDate = defaultsElement.getChildText(FROM_DATE, RULE_TEMPLATE_NAMESPACE); 277 String toDate = defaultsElement.getChildText(TO_DATE, RULE_TEMPLATE_NAMESPACE); 278 // toBooleanObject ensures that if the value is null (not set) that the Boolean object will likewise be null (will not default to a value) 279 Boolean forceAction = BooleanUtils.toBooleanObject(defaultsElement.getChildText(FORCE_ACTION, RULE_TEMPLATE_NAMESPACE)); 280 Boolean active = BooleanUtils.toBooleanObject(defaultsElement.getChildText(ACTIVE, RULE_TEMPLATE_NAMESPACE)); 281 282 if (isDelegation) { 283 delegationType = DelegationType.parseCode(delegationTypeCode); 284 if (delegationType == null) { 285 throw new XmlException("Invalid delegation type '" + delegationType + "'." + " Expected one of: " 286 + DelegationType.PRIMARY.getCode() + "," + DelegationType.SECONDARY.getCode()); 287 } 288 } 289 290 // create our "default rule" which encapsulates the defaults for the rule 291 RuleBaseValues ruleDefaults = new RuleBaseValues(); 292 293 // set simple values 294 ruleDefaults.setRuleTemplate(updatedRuleTemplate); 295 ruleDefaults.setDocTypeName(DUMMY_DOCUMENT_TYPE); 296 ruleDefaults.setTemplateRuleInd(Boolean.TRUE); 297 ruleDefaults.setCurrentInd(Boolean.TRUE); 298 ruleDefaults.setVersionNbr(new Integer(0)); 299 ruleDefaults.setDescription(description); 300 301 // these are non-nullable fields, so default them if they were not set in the defaults section 302 ruleDefaults.setForceAction(Boolean.valueOf(BooleanUtils.isTrue(forceAction))); 303 ruleDefaults.setActive(Boolean.valueOf(BooleanUtils.isTrue(active))); 304 305 if (ruleDefaults.getActivationDate() == null) { 306 ruleDefaults.setActivationDate(new Timestamp(System.currentTimeMillis())); 307 } 308 309 ruleDefaults.setFromDateValue(formatDate("fromDate", fromDate)); 310 ruleDefaults.setToDateValue(formatDate("toDate", toDate)); 311 312 // ok, if this is a "Delegate Template", then we need to set this other RuleDelegation object which contains 313 // some delegation-related info 314 RuleDelegationBo ruleDelegationDefaults = null; 315 if (isDelegation) { 316 ruleDelegationDefaults = new RuleDelegationBo(); 317 ruleDelegationDefaults.setDelegationRule(ruleDefaults); 318 ruleDelegationDefaults.setDelegationType(delegationType); 319 ruleDelegationDefaults.setResponsibilityId(KewApiConstants.ADHOC_REQUEST_RESPONSIBILITY_ID); 320 } 321 322 // explicitly save the new rule delegation defaults and default rule 323 KEWServiceLocator.getRuleTemplateService().saveRuleDefaults(ruleDelegationDefaults, ruleDefaults); 324 } else { 325 // do nothing, rule defaults will be deleted if ruleDefaults element is omitted 326 } 327 328 return isDelegation; 329 } 330 331 332 /** 333 * Updates or deletes a specified rule template option on the rule template 334 * @param updatedRuleTemplate the RuleTemplate being updated 335 * @param key the option key 336 * @param value the option value 337 */ 338 protected void updateOrDeleteRuleTemplateOption(RuleTemplateBo updatedRuleTemplate, String key, Object value) { 339 if (value != null) { 340 // if the option exists and the incoming value is non-null (it's set), update it 341 RuleTemplateOptionBo option = updatedRuleTemplate.getRuleTemplateOption(key); 342 if (option != null) { 343 option.setValue(value.toString()); 344 } else { 345 updatedRuleTemplate.getRuleTemplateOptions().add(new RuleTemplateOptionBo(key, value.toString())); 346 } 347 } else { 348 // otherwise if the incoming value IS null (not set), then explicitly remove the entry (if it exists) 349 Iterator<RuleTemplateOptionBo> options = updatedRuleTemplate.getRuleTemplateOptions().iterator(); 350 while (options.hasNext()) { 351 RuleTemplateOptionBo opt = options.next(); 352 if (key.equals(opt.getCode())) { 353 options.remove(); 354 break; 355 } 356 } 357 } 358 } 359 360 /** 361 * Updates the rule template delegation template with the one specified in the XML (if any) 362 * @param ruleTemplateElement the XML ruleTemplate element 363 * @param updatedRuleTemplate the rule template to update 364 * @param parsedRuleTemplates the rule templates parsed in this parsing run 365 * @throws XmlException if a delegation template was specified but could not be found 366 */ 367 protected void updateDelegationTemplate(Element ruleTemplateElement, RuleTemplateBo updatedRuleTemplate, List<RuleTemplateBo> parsedRuleTemplates) throws XmlException { 368 String delegateTemplateName = ruleTemplateElement.getChildText(DELEGATION_TEMPLATE, RULE_TEMPLATE_NAMESPACE); 369 370 if (delegateTemplateName != null) { 371 // if a delegateTemplate was set in the XML, then look it up and set it on the RuleTemplate object 372 // first try looking up an existing delegateTemplate in the system 373 RuleTemplateBo delegateTemplate = KEWServiceLocator.getRuleTemplateService().findByRuleTemplateName(delegateTemplateName); 374 375 // if not found, try the list of templates currently parsed 376 if (delegateTemplate == null) { 377 for (RuleTemplateBo rt: parsedRuleTemplates) { 378 if (delegateTemplateName.equalsIgnoreCase(rt.getName())) { 379 // set the expected next rule template id on the target delegateTemplate 380 String ruleTemplateId = KEWServiceLocator.getRuleTemplateService().getNextRuleTemplateId(); 381 rt.setId(ruleTemplateId); 382 delegateTemplate = rt; 383 break; 384 } 385 } 386 } 387 388 if (delegateTemplate == null) { 389 throw new XmlException("Cannot find delegation template " + delegateTemplateName); 390 } 391 392 updatedRuleTemplate.setDelegationTemplateId(delegateTemplate.getDelegationTemplateId()); 393 updatedRuleTemplate.setDelegationTemplate(delegateTemplate); 394 } else { 395 // the previously referenced template is left in the system 396 } 397 } 398 399 /** 400 * Updates the attributes set on the RuleTemplate 401 * @param ruleTemplateElement the XML ruleTemplate element 402 * @param updatedRuleTemplate the RuleTemplate being updated 403 * @throws XmlException if there was a problem parsing the rule template attributes 404 */ 405 protected void updateRuleTemplateAttributes(Element ruleTemplateElement, RuleTemplateBo updatedRuleTemplate) throws XmlException { 406 // add any newly defined rule template attributes to the rule template, 407 // update the active and required flags of any existing ones. 408 // if this is an update of an existing rule template, related attribute objects will be present in this rule template object, 409 // otherwise none will be present (so they'll all be new) 410 411 Element attributesElement = ruleTemplateElement.getChild(ATTRIBUTES, RULE_TEMPLATE_NAMESPACE); 412 List<RuleTemplateAttributeBo> incomingAttributes = new ArrayList<RuleTemplateAttributeBo>(); 413 if (attributesElement != null) { 414 incomingAttributes.addAll(parseRuleTemplateAttributes(attributesElement, updatedRuleTemplate)); 415 } 416 417 // inactivate all current attributes 418 for (RuleTemplateAttributeBo currentRuleTemplateAttribute: updatedRuleTemplate.getRuleTemplateAttributes()) { 419 String ruleAttributeName = (currentRuleTemplateAttribute.getRuleAttribute() != null) ? currentRuleTemplateAttribute.getRuleAttribute().getName() : "(null)"; 420 LOG.debug("Inactivating rule template attribute with id " + currentRuleTemplateAttribute.getId() + " and rule attribute with name " + ruleAttributeName); 421 currentRuleTemplateAttribute.setActive(Boolean.FALSE); 422 } 423 // NOTE: attributes are deactivated, not removed 424 425 // add/update any new attributes 426 for (RuleTemplateAttributeBo ruleTemplateAttribute: incomingAttributes) { 427 RuleTemplateAttributeBo potentialExistingTemplateAttribute = updatedRuleTemplate.getRuleTemplateAttribute(ruleTemplateAttribute); 428 if (potentialExistingTemplateAttribute != null) { 429 // template attribute exists on rule template already; update the options 430 potentialExistingTemplateAttribute.setActive(ruleTemplateAttribute.getActive()); 431 potentialExistingTemplateAttribute.setRequired(ruleTemplateAttribute.getRequired()); 432 } else { 433 // template attribute does not yet exist on template so add it 434 updatedRuleTemplate.getRuleTemplateAttributes().add(ruleTemplateAttribute); 435 } 436 } 437 } 438 439 /** 440 * Parses the RuleTemplateAttributes defined on the rule template element 441 * @param attributesElement the jdom Element object for the Rule Template attributes 442 * @param ruleTemplate the RuleTemplate object 443 * @return the RuleTemplateAttributes defined on the rule template element 444 * @throws XmlException 445 */ 446 private List<RuleTemplateAttributeBo> parseRuleTemplateAttributes(Element attributesElement, RuleTemplateBo ruleTemplate) throws XmlException { 447 List<RuleTemplateAttributeBo> ruleTemplateAttributes = new ArrayList<RuleTemplateAttributeBo>(); 448 Collection<Element> attributeElements = XmlHelper.findElements(attributesElement, ATTRIBUTE); 449 for (Iterator iterator = attributeElements.iterator(); iterator.hasNext();) { 450 ruleTemplateAttributes.add(parseRuleTemplateAttribute((Element) iterator.next(), ruleTemplate)); 451 } 452 return ruleTemplateAttributes; 453 } 454 455 /** 456 * Parses a rule template attribute 457 * @param element the attribute XML element 458 * @param ruleTemplate the ruleTemplate to update 459 * @return a parsed rule template attribute 460 * @throws XmlException if the attribute does not exist 461 */ 462 private RuleTemplateAttributeBo parseRuleTemplateAttribute(Element element, RuleTemplateBo ruleTemplate) throws XmlException { 463 String attributeName = element.getChildText(NAME, RULE_TEMPLATE_NAMESPACE); 464 String requiredValue = element.getChildText(REQUIRED, RULE_TEMPLATE_NAMESPACE); 465 String activeValue = element.getChildText(ACTIVE, RULE_TEMPLATE_NAMESPACE); 466 if (org.apache.commons.lang.StringUtils.isEmpty(attributeName)) { 467 throw new XmlException("Attribute name must be non-empty"); 468 } 469 boolean required = DEFAULT_ATTRIBUTE_REQUIRED; 470 if (requiredValue != null) { 471 required = Boolean.parseBoolean(requiredValue); 472 } 473 boolean active = DEFAULT_ATTRIBUTE_ACTIVE; 474 if (activeValue != null) { 475 active = Boolean.parseBoolean(activeValue); 476 } 477 RuleAttribute ruleAttribute = KEWServiceLocator.getRuleAttributeService().findByName(attributeName); 478 if (ruleAttribute == null) { 479 throw new XmlException("Could not locate rule attribute for name '" + attributeName + "'"); 480 } 481 RuleTemplateAttributeBo templateAttribute = new RuleTemplateAttributeBo(); 482 templateAttribute.setRuleAttribute(ruleAttribute); 483 templateAttribute.setRuleAttributeId(ruleAttribute.getId()); 484 templateAttribute.setRuleTemplate(ruleTemplate); 485 templateAttribute.setRequired(Boolean.valueOf(required)); 486 templateAttribute.setActive(Boolean.valueOf(active)); 487 templateAttribute.setDisplayOrder(new Integer(templateAttributeCounter++)); 488 return templateAttribute; 489 } 490 491 public Timestamp formatDate(String dateLabel, String dateString) throws XmlException { 492 if (StringUtils.isBlank(dateString)) { 493 return null; 494 } 495 try { 496 return new Timestamp(RiceConstants.getDefaultDateFormat().parse(dateString).getTime()); 497 } catch (ParseException e) { 498 throw new XmlException(dateLabel + " is not in the proper format. Should have been: " + RiceConstants.DEFAULT_DATE_FORMAT_PATTERN); 499 } 500 } 501 502}