001package org.kuali.ole.select.executor;
002
003import org.kuali.ole.OLEConstants;
004import org.kuali.ole.ingest.pojo.MatchBo;
005import org.kuali.ole.select.bo.OleAgreementMethod;
006import org.kuali.ole.select.bo.OleLicenseRequestType;
007import org.kuali.ole.select.bo.OleLicenseRequestWorkflowType;
008import org.kuali.rice.core.api.exception.RiceRuntimeException;
009import org.kuali.rice.core.api.util.xml.XmlHelper;
010import org.kuali.rice.kew.engine.RouteContext;
011import org.kuali.rice.kew.framework.support.krms.RulesEngineExecutor;
012import org.kuali.rice.kew.rule.xmlrouting.XPathHelper;
013import org.kuali.rice.kim.impl.role.RoleBo;
014import org.kuali.rice.kim.impl.role.RoleMemberBo;
015import org.kuali.rice.krad.service.KRADServiceLocator;
016import org.kuali.rice.krms.api.engine.*;
017import org.kuali.rice.krms.impl.repository.AgendaBo;
018import org.w3c.dom.Document;
019
020import javax.xml.xpath.XPath;
021import javax.xml.xpath.XPathConstants;
022import java.io.ByteArrayInputStream;
023import java.util.*;
024
025/**
026 * OleLicenseRulesEngineExecutor validates rules from krms and executes people flow action.
027 */
028public class OleLicenseRulesEngineExecutor implements RulesEngineExecutor {
029    private static final String NAMESPACE_CODE_SELECTOR = "namespaceCode";
030    private static final String NAME_SELECTOR = "name";
031
032    /**
033     * This method validates rules from krms and execute people flow action
034     *
035     * @param routeContext
036     * @param engine
037     * @return EngineResults
038     */
039    @Override
040    public EngineResults execute(RouteContext routeContext, Engine engine) {
041        EngineResults engineResult = null;
042        HashMap<String, Object> agendaValue = new HashMap<String, Object>();
043        agendaValue.put("nm", OLEConstants.OleLicenseRequest.LICENSE_AGENDA_NM);
044        List<AgendaBo> agendaBos = (List<AgendaBo>) KRADServiceLocator.getBusinessObjectService().findMatching(AgendaBo.class, agendaValue);
045        if (agendaBos != null && agendaBos.size() > 0) {
046            AgendaBo agendaBo = agendaBos.get(0);
047            HashMap<String, String> map = new HashMap<String, String>();
048            map.put("AGENDA_NAME", agendaBo.getName());
049            List<MatchBo> matchBos = (List<MatchBo>) KRADServiceLocator.getBusinessObjectService().findMatching(MatchBo.class, map);
050
051            SelectionCriteria selectionCriteria =
052                    SelectionCriteria.createCriteria(null, getSelectionContext(agendaBo.getContext().getName()),
053                            getAgendaContext(OLEConstants.OleLicenseRequest.LICENSE_AGENDA_NM));
054
055            ExecutionOptions executionOptions = new ExecutionOptions();
056            executionOptions.setFlag(ExecutionFlag.LOG_EXECUTION, true);
057
058            Facts.Builder factBuilder = Facts.Builder.create();
059
060            String docContent = routeContext.getDocument().getDocContent();
061
062            String licenseRequestWorkflowTypeCode =
063                    getElementValue(docContent, "//newMaintainableObject/dataObject/licenseRequestWorkflowTypeCode");
064
065            String agreementMethodId =
066                    getElementValue(docContent, "//newMaintainableObject/dataObject/agreementMethodId");
067            String licenseRequestTypeId =
068                    getElementValue(docContent, "//newMaintainableObject/dataObject/licenseRequestTypeId");
069            String owner =
070                    getElementValue(docContent, "//newMaintainableObject/dataObject/assignee");
071            String licenseType = "";
072            String workflowName = "";
073            String agreementMethod = "";
074            if (licenseRequestTypeId != null && !licenseRequestTypeId.isEmpty()) {
075                licenseType = getLicenseType(licenseRequestTypeId);
076            }
077            if (licenseRequestWorkflowTypeCode != null && !licenseRequestWorkflowTypeCode.isEmpty()) {
078                workflowName = getWorkFlowName(licenseRequestWorkflowTypeCode);
079            }
080            if (agreementMethodId != null && !agreementMethodId.isEmpty()) {
081                agreementMethod = getAgreementMethod(agreementMethodId);
082            }
083
084            HashMap<String, Object> termValues = new HashMap<String, Object>();
085            termValues.put("licenseType", licenseType);
086            termValues.put("agreementMethod", agreementMethod);
087            termValues.put("workflowName", workflowName);
088
089
090            for (Iterator<MatchBo> matchBoIterator = matchBos.iterator(); matchBoIterator.hasNext(); ) {
091                MatchBo matchBo = matchBoIterator.next();
092                factBuilder.addFact(matchBo.getTermName(), termValues.get((matchBo.getTermName())));
093            }
094
095
096            engineResult = engine.execute(selectionCriteria, factBuilder.build(), executionOptions);
097            if (owner != null && !owner.isEmpty()) {
098                changeLicenseMangerRoleToOwner(owner);
099            }
100        }
101        return engineResult;  //To change body of implemented methods use File | Settings | File Templates.
102    }
103
104    private String getAgreementMethod(String agreementMethodId) {
105        OleAgreementMethod agreementMethod = KRADServiceLocator.getBusinessObjectService().findBySinglePrimaryKey(OleAgreementMethod.class, agreementMethodId);
106        return agreementMethod.getAgreementMethodName();
107    }
108
109    /**
110     * This method returns LicenseType using licenseRequestTypeId.
111     *
112     * @param licenseRequestTypeId
113     * @return oleLicenseRequestType
114     */
115    private String getLicenseType(String licenseRequestTypeId) {
116        OleLicenseRequestType oleLicenseRequestType = KRADServiceLocator.getBusinessObjectService().findBySinglePrimaryKey(OleLicenseRequestType.class, licenseRequestTypeId);
117        return oleLicenseRequestType.getName();
118    }
119
120    /**
121     * This method returns WorkFlowName using licenseRequestWorkflowTypeCode.
122     *
123     * @param licenseRequestWorkflowTypeCode
124     * @return oleLicenseRequestWorkflowType
125     */
126    private String getWorkFlowName(String licenseRequestWorkflowTypeCode) {
127        OleLicenseRequestWorkflowType oleLicenseRequestWorkflowType = KRADServiceLocator.getBusinessObjectService().findBySinglePrimaryKey(OleLicenseRequestWorkflowType.class, licenseRequestWorkflowTypeCode);
128        return oleLicenseRequestWorkflowType.getName();
129    }
130
131    /**
132     * This method returns ElementValue using docContent and xpathExpression..
133     *
134     * @param docContent
135     * @param xpathExpression
136     * @return value
137     */
138    private String getElementValue(String docContent, String xpathExpression) {
139        try {
140            Document document = XmlHelper.trimXml(new ByteArrayInputStream(docContent.getBytes()));
141
142            XPath xpath = XPathHelper.newXPath();
143            String value = (String) xpath.evaluate(xpathExpression, document, XPathConstants.STRING);
144
145            return value;
146
147        } catch (Exception e) {
148            throw new RiceRuntimeException();
149        }
150    }
151
152    /**
153     * This method returns SelectionContext using contextName.
154     *
155     * @param contextName
156     * @return Map
157     */
158    protected Map<String, String> getSelectionContext(String contextName) {
159        Map<String, String> selector = new HashMap<String, String>();
160        selector.put(NAMESPACE_CODE_SELECTOR, OLEConstants.OLE_NAMESPACE);
161        selector.put(NAME_SELECTOR, contextName);
162        return selector;
163    }
164
165    /**
166     * This method returns AgendaContext using agendaName..
167     *
168     * @param agendaName
169     * @return Map
170     */
171    protected Map<String, String> getAgendaContext(String agendaName) {
172        Map<String, String> selector = new HashMap<String, String>();
173        selector.put(NAME_SELECTOR, agendaName);
174        return selector;
175    }
176
177    /**
178     * This method change the license role using owner.
179     *
180     * @param owner
181     */
182    private void changeLicenseMangerRoleToOwner(String owner) {
183        HashMap<String, String> map = new HashMap<String, String>();
184        map.put("ROLE_NM", OLEConstants.OleLicenseRequest.LICENSE_MNGR_ROLE_NM);
185        List<RoleBo> roleBos = (List<RoleBo>) KRADServiceLocator.getBusinessObjectService().findMatching(RoleBo.class, map);
186        List<RoleMemberBo> roleMemberBos = roleBos != null && roleBos.size() > 0 ? roleBos.get(0).getMembers() : new ArrayList<RoleMemberBo>();
187        RoleMemberBo roleMemberBo = roleMemberBos.size() > 0 ? roleMemberBos.get(0) : null;
188        if (roleMemberBo != null) {
189            roleMemberBo.setMemberId(owner);
190            KRADServiceLocator.getBusinessObjectService().save(roleMemberBo);
191        }
192    }
193}