001/**
002 * Copyright 2005-2016 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.rule.service.impl;
017
018import java.io.InputStream;
019import java.util.ArrayList;
020import java.util.Collection;
021import java.util.List;
022
023import org.jdom.Element;
024import org.kuali.rice.core.api.impex.ExportDataSet;
025import org.kuali.rice.kew.exception.WorkflowServiceErrorException;
026import org.kuali.rice.kew.exception.WorkflowServiceErrorImpl;
027import org.kuali.rice.kew.rule.RuleBaseValues;
028import org.kuali.rice.kew.rule.RuleDelegationBo;
029import org.kuali.rice.kew.rule.RuleTemplateOptionBo;
030import org.kuali.rice.kew.rule.bo.RuleTemplateBo;
031import org.kuali.rice.kew.rule.bo.RuleTemplateAttributeBo;
032import org.kuali.rice.kew.rule.dao.RuleDAO;
033import org.kuali.rice.kew.rule.dao.RuleDelegationDAO;
034import org.kuali.rice.kew.rule.dao.RuleTemplateAttributeDAO;
035import org.kuali.rice.kew.rule.dao.RuleTemplateDAO;
036import org.kuali.rice.kew.rule.dao.RuleTemplateOptionDAO;
037import org.kuali.rice.kew.rule.service.RuleAttributeService;
038import org.kuali.rice.kew.rule.service.RuleTemplateService;
039import org.kuali.rice.kew.service.KEWServiceLocator;
040import org.kuali.rice.kew.xml.RuleTemplateXmlParser;
041import org.kuali.rice.kew.xml.export.RuleTemplateXmlExporter;
042import org.kuali.rice.krad.data.DataObjectService;
043import org.springframework.beans.factory.annotation.Required;
044
045public class RuleTemplateServiceImpl implements RuleTemplateService {
046
047    private static final org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(RuleTemplateServiceImpl.class);
048
049    private static final String RULE_TEMPLATE_NAME_REQUIRED = "rule.template.name.required";
050
051    private static final String RULE_TEMPLATE_DESCRIPTION_REQUIRED = "rule.template.description.required";
052
053    private static final String XML_PARSE_ERROR = "general.error.parsexml";
054
055    private RuleTemplateDAO ruleTemplateDAO;
056
057    private RuleDAO ruleDAO;
058
059    private RuleDelegationDAO ruleDelegationDAO;
060
061    private DataObjectService dataObjectService;
062
063
064    public void deleteRuleTemplateOption(String ruleTemplateOptionId) {
065        RuleTemplateOptionBo ruleTemplateOptionBo = getDataObjectService().find(
066                RuleTemplateOptionBo.class,ruleTemplateOptionId);
067        getDataObjectService().delete(ruleTemplateOptionBo);
068    }
069
070    public RuleTemplateBo findByRuleTemplateName(String ruleTemplateName) {
071        return (getRuleTemplateDAO().findByRuleTemplateName(ruleTemplateName));
072    }
073
074    /*
075     * (non-Javadoc)
076     *
077     * @see org.kuali.rice.kew.rule.RuleTemplateAttributeService#findByRuleTemplateAttributeId(java.lang.Long)
078     */
079    public RuleTemplateAttributeBo findByRuleTemplateAttributeId(String ruleTemplateAttributeId) {
080        return getDataObjectService().find(RuleTemplateAttributeBo.class,ruleTemplateAttributeId);
081    }
082
083    public List<RuleTemplateBo> findAll() {
084        return ruleTemplateDAO.findAll();
085    }
086
087    public List findByRuleTemplate(RuleTemplateBo ruleTemplate) {
088        return ruleTemplateDAO.findByRuleTemplate(ruleTemplate);
089    }
090
091    public RuleTemplateBo save(RuleTemplateBo ruleTemplate) {
092        LOG.debug("save RuleTemplateServiceImpl");
093        validate(ruleTemplate);
094        fixAssociations(ruleTemplate);
095
096
097        LOG.debug("end save RuleTemplateServiceImpl");
098        return getRuleTemplateDAO().save(ruleTemplate);
099    }
100
101    public void save(RuleTemplateAttributeBo ruleTemplateAttribute) {
102        getDataObjectService().save(ruleTemplateAttribute);
103    }
104
105    /**
106     * Saves the given RuleDelegation and RuleBaseValues as the defaults for this RuleTemplate
107     */
108    public void saveRuleDefaults(RuleDelegationBo ruleDelegation, RuleBaseValues ruleBaseValues) {
109        KEWServiceLocator.getRuleService().saveRule(ruleBaseValues, false);
110        if (ruleDelegation != null) {
111                KEWServiceLocator.getRuleService().saveRule(ruleDelegation.getDelegationRule(), false);
112            KEWServiceLocator.getRuleDelegationService().save(ruleDelegation);
113        }
114    }
115
116    /**
117     * Ensures that dependent objects have a reference to the specified rule template
118     * @param ruleTemplate the rule template whose associates to check
119     */
120    private void fixAssociations(RuleTemplateBo ruleTemplate) {
121        // if it's a valid rule template instance
122        if (ruleTemplate != null && ruleTemplate.getId() != null) {
123            // for every rule template attribute
124            for (RuleTemplateAttributeBo ruleTemplateAttribute: ruleTemplate.getRuleTemplateAttributes()) {
125                // if the rule template is not set on the attribute, set it
126                if (ruleTemplateAttribute.getRuleTemplate() == null || ruleTemplateAttribute.getRuleTemplateId() == null) {
127                    ruleTemplateAttribute.setRuleTemplate(ruleTemplate);
128                }
129                // if the rule attribute is set, load up the rule attribute and set the BO on the ruletemplateattribute association object
130                if (ruleTemplateAttribute.getRuleAttribute() == null) {
131                    RuleAttributeService ruleAttributeService = (RuleAttributeService) KEWServiceLocator.getService(KEWServiceLocator.RULE_ATTRIBUTE_SERVICE);
132                    ruleTemplateAttribute.setRuleAttribute(ruleAttributeService.findByRuleAttributeId(ruleTemplateAttribute.getRuleAttributeId()));
133                }
134            }
135            // for every rule template option
136            for (RuleTemplateOptionBo option: ruleTemplate.getRuleTemplateOptions()) {
137                // if the rule template is not set on the option, set it
138                if (option.getRuleTemplate() == null || option.getRuleTemplateId() == null) {
139                    option.setRuleTemplate(ruleTemplate);
140                }
141            }
142        }
143    }
144
145    private void validate(RuleTemplateBo ruleTemplate) {
146        LOG.debug("validating ruleTemplate");
147        Collection errors = new ArrayList();
148        if (ruleTemplate.getName() == null || ruleTemplate.getName().trim().equals("")) {
149            errors.add(new WorkflowServiceErrorImpl("Please enter a rule template name.", RULE_TEMPLATE_NAME_REQUIRED));
150            LOG.error("Rule template name is missing");
151        } else {
152            ruleTemplate.setName(ruleTemplate.getName().trim());
153            if (ruleTemplate.getId() == null) {
154                RuleTemplateBo nameInUse = findByRuleTemplateName(ruleTemplate.getName());
155                if (nameInUse != null) {
156                    errors.add(new WorkflowServiceErrorImpl("Rule template name already in use", "rule.template.name.duplicate"));
157                    LOG.error("Rule template name already in use");
158                }
159            }
160        }
161        if (ruleTemplate.getDescription() == null || ruleTemplate.getDescription().equals("")) {
162            errors.add(new WorkflowServiceErrorImpl("Please enter a rule template description.", RULE_TEMPLATE_DESCRIPTION_REQUIRED));
163            LOG.error("Rule template description is missing");
164        }
165        //        if (ruleTemplate.getRuleTemplateAttributes() == null ||
166        // ruleTemplate.getRuleTemplateAttributes().isEmpty()) {
167        //            errors.add(new WorkflowServiceErrorImpl("Please select at least one a
168        // rule template attribute.", RULE_TEMPLATE_ATTRIBUTE_REQUIRED));
169        //        }
170
171        LOG.debug("end validating ruleTemplate");
172        if (!errors.isEmpty()) {
173            throw new WorkflowServiceErrorException("RuleTemplate Validation Error", errors);
174        }
175    }
176
177    public RuleTemplateBo findByRuleTemplateId(String ruleTemplateId) {
178        LOG.debug("findByRuleTemplateId RuleTemplateServiceImpl");
179        return getRuleTemplateDAO().findByRuleTemplateId(ruleTemplateId);
180    }
181
182    public void delete(String ruleTemplateId) {
183        LOG.debug("delete RuleTemplateServiceImpl");
184        getRuleTemplateDAO().delete(ruleTemplateId);
185        LOG.debug("end delete RuleTemplateServiceImpl");
186    }
187
188    public RuleTemplateDAO getRuleTemplateDAO() {
189        return ruleTemplateDAO;
190    }
191
192    public void setRuleTemplateDAO(RuleTemplateDAO ruleTemplateDAO) {
193        this.ruleTemplateDAO = ruleTemplateDAO;
194    }
195
196    public RuleDAO getRuleDAO() {
197        return ruleDAO;
198    }
199
200    public void setRuleDAO(RuleDAO ruleDAO) {
201        this.ruleDAO = ruleDAO;
202    }
203
204    public RuleDelegationDAO getRuleDelegationDAO() {
205        return ruleDelegationDAO;
206    }
207
208    public void setRuleDelegationDAO(RuleDelegationDAO ruleDelegationDAO) {
209        this.ruleDelegationDAO = ruleDelegationDAO;
210    }
211
212    public void loadXml(InputStream inputStream, String principalId) {
213        RuleTemplateXmlParser parser = new RuleTemplateXmlParser();
214        try {
215            parser.parseRuleTemplates(inputStream);
216        } catch (Exception e) { //any other exception
217            LOG.error("Error loading xml file", e);
218            WorkflowServiceErrorException wsee = new WorkflowServiceErrorException("Error loading xml file", new WorkflowServiceErrorImpl("Error loading xml file", XML_PARSE_ERROR));
219            wsee.initCause(e);
220            throw wsee;
221        }
222    }
223
224    public Element export(ExportDataSet dataSet) {
225        RuleTemplateXmlExporter exporter = new RuleTemplateXmlExporter();
226        return exporter.export(dataSet);
227    }
228    
229    @Override
230        public boolean supportPrettyPrint() {
231                return true;
232        }
233
234    public String getNextRuleTemplateId() {
235        return getRuleTemplateDAO().getNextRuleTemplateId();
236    }
237
238
239    public DataObjectService getDataObjectService() {
240        return dataObjectService;
241    }
242
243    @Required
244    public void setDataObjectService(DataObjectService dataObjectService) {
245        this.dataObjectService = dataObjectService;
246    }
247
248}