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.dao.impl;
017
018import org.apache.commons.lang.StringUtils;
019import org.kuali.rice.core.api.criteria.OrderByField;
020import org.kuali.rice.core.api.criteria.OrderDirection;
021import org.kuali.rice.core.api.criteria.Predicate;
022import org.kuali.rice.core.api.criteria.QueryResults;
023import org.kuali.rice.core.api.exception.RiceRuntimeException;
024import org.kuali.rice.kew.api.KewApiConstants;
025import org.kuali.rice.kew.rule.RuleBaseValues;
026import org.kuali.rice.kew.rule.RuleExtensionBo;
027import org.kuali.rice.kew.rule.RuleResponsibilityBo;
028import org.kuali.rice.kew.rule.dao.RuleDAO;
029import org.kuali.rice.kim.api.identity.principal.Principal;
030import org.kuali.rice.kim.api.services.KimApiServiceLocator;
031import org.kuali.rice.krad.data.DataObjectService;
032import org.springframework.beans.factory.annotation.Required;
033
034import javax.persistence.EntityManager;
035import javax.persistence.Query;
036import javax.persistence.TypedQuery;
037import javax.persistence.criteria.CriteriaBuilder;
038import javax.persistence.criteria.CriteriaQuery;
039import javax.persistence.criteria.Expression;
040import javax.persistence.criteria.Root;
041import javax.persistence.criteria.Subquery;
042import java.sql.Timestamp;
043import java.util.ArrayList;
044import java.util.Collection;
045import java.util.Date;
046import java.util.HashSet;
047import java.util.Iterator;
048import java.util.List;
049import java.util.Map;
050
051import static org.kuali.rice.core.api.criteria.PredicateFactory.*;
052
053public class RuleDAOJpa implements RuleDAO {
054
055        private static final org.apache.log4j.Logger LOG = org.apache.log4j.Logger.getLogger(RuleDAOJpa.class);
056
057        private EntityManager entityManager;
058
059    private DataObjectService dataObjectService;
060
061        private static final String OLD_DELEGATIONS_SQL =
062                "select oldDel.dlgn_rule_id "+
063                "from krew_rule_rsp_t oldRsp, krew_dlgn_rsp_t oldDel "+
064                "where oldRsp.rule_id=? and "+
065                "oldRsp.rule_rsp_id=oldDel.rule_rsp_id and "+
066                "oldDel.dlgn_rule_base_val_id not in "+
067                "(select newDel.dlgn_rule_base_val_id from krew_rule_rsp_t newRsp, krew_dlgn_rsp_t newDel "+
068                "where newRsp.rule_id=? and "+
069                "newRsp.rule_rsp_id=newDel.rule_rsp_id)";
070
071    @Override
072    public RuleBaseValues save(RuleBaseValues ruleBaseValues) {
073        if ( ruleBaseValues == null ) {
074            return null;
075        }
076
077        ruleBaseValues = getDataObjectService().save(ruleBaseValues);
078
079        if ( ruleBaseValues.getRoleResponsibilities() != null ) {
080            for ( RuleResponsibilityBo resp : ruleBaseValues.getRuleResponsibilities() ) {
081                resp.setRuleBaseValues(ruleBaseValues);
082                resp.setRuleBaseValuesId(ruleBaseValues.getId());
083            }
084        }
085
086        if ( ruleBaseValues.getRuleResponsibilities() != null && ruleBaseValues.getRuleResponsibilities().size() > 0 ) {
087            return getDataObjectService().save(ruleBaseValues);
088        } else {
089            return ruleBaseValues;
090        }
091    }
092
093        @Override
094    public List<RuleBaseValues> fetchAllCurrentRulesForTemplateDocCombination(String ruleTemplateId, List documentTypes) {
095        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
096                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
097        List<Predicate> datePredicateList = generateFromToDatePredicate(new Date());
098        Predicate[] datePreds = generateFromToDatePredicate(new Date()).
099                            toArray(new Predicate[datePredicateList.size()]);
100        builder.setPredicates(in("docTypeName", documentTypes),
101                               equal("ruleTemplateId",ruleTemplateId),
102                               equal("currentInd",Boolean.TRUE),
103                               equal("active",Boolean.TRUE),
104                               equal("delegateRule",Boolean.FALSE),
105                               equal("templateRuleInd",Boolean.FALSE),
106                               and(datePreds));
107
108        return getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
109        }
110
111        @Override
112    public List<RuleBaseValues> fetchAllCurrentRulesForTemplateDocCombination(String ruleTemplateId, List documentTypes, Timestamp effectiveDate) {
113        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
114                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
115        List<Predicate> predicates = new ArrayList<Predicate>();
116        predicates.add(equal("ruleTemplateId",ruleTemplateId));
117        predicates.add(in("docTypeName", documentTypes));
118        predicates.add(equal("active", Boolean.TRUE));
119        predicates.add(equal("delegateRule",Boolean.FALSE));
120        predicates.add(equal("templateRuleInd",Boolean.FALSE));
121
122        if(effectiveDate != null){
123            predicates.add(lessThanOrEqual("activationDate",effectiveDate));
124            predicates.add(greaterThanOrEqual("deactivationDate", effectiveDate));
125        }
126        List<Predicate> datePredicateList = generateFromToDatePredicate(new Date());
127        Predicate[] datePreds = generateFromToDatePredicate(new Date()).
128                toArray(new Predicate[datePredicateList.size()]);
129        predicates.add(and(datePreds));
130        Predicate[] preds = predicates.toArray(new Predicate[predicates.size()]);
131        builder.setPredicates(preds);
132        QueryResults<RuleBaseValues> results = getDataObjectService().findMatching(RuleBaseValues.class,
133                                            builder.build());
134        return results.getResults();
135        }
136
137    public List<Predicate> generateFromToDatePredicate(Date date){
138        List<Predicate> datePredicates = new ArrayList<Predicate>();
139
140        Predicate orFromDateValue = or(lessThanOrEqual("fromDateValue",new Timestamp(date.getTime())),
141              isNull("fromDateValue"));
142        Predicate orToDateValue = or(greaterThanOrEqual("toDateValue",new Timestamp(date.getTime())),
143              isNull("toDateValue"));
144
145        datePredicates.add(orFromDateValue);
146        datePredicates.add(orToDateValue);
147
148        return datePredicates;
149    }
150
151        @Override
152    public List<RuleBaseValues> fetchAllRules(boolean currentRules) {
153        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
154                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
155        builder.setPredicates(equal("currentInd",new Boolean(currentRules)),
156                        equal("templateRuleInd",Boolean.FALSE));
157        builder.setOrderByFields(OrderByField.Builder.create("activationDate", OrderDirection.DESCENDING).build()) ;
158        return getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
159        }
160
161        @Override
162    public void delete(String ruleBaseValuesId) {
163        getDataObjectService().delete(getDataObjectService().find(RuleBaseValues.class, ruleBaseValuesId));
164        }
165
166        @Override
167    public List<RuleBaseValues> findByDocumentId(String documentId) {
168        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
169                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
170        builder.setPredicates(equal("documentId",documentId));
171        return getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
172        }
173
174    @Override
175    public RuleBaseValues findRuleBaseValuesByName(String name) {
176        if (name == null) {
177                return null;
178        }
179        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
180                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
181        builder.setPredicates(equal("name",name),equal("currentInd",Boolean.TRUE));
182
183        QueryResults<RuleBaseValues> results = getDataObjectService().findMatching(RuleBaseValues.class,
184                builder.build());
185        if(results != null && !results.getResults().isEmpty()) {
186            return results.getResults().get(0);
187        }
188        return null;
189    }
190
191        @Override
192    public RuleBaseValues findRuleBaseValuesById(String ruleBaseValuesId) {
193                if (ruleBaseValuesId == null) {
194                        return null;
195                }
196
197        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
198                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
199        builder.setPredicates(equal("id",ruleBaseValuesId));
200
201        QueryResults<RuleBaseValues> results = getDataObjectService().findMatching(
202                RuleBaseValues.class,builder.build());
203        if(results != null && !results.getResults().isEmpty()) {
204            return results.getResults().get(0);
205        }
206        return null;
207        }
208
209        @Override
210    public List<RuleBaseValues> findRuleBaseValuesByResponsibilityReviewer(String reviewerName, String type) {
211        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
212                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
213        builder.setPredicates(equal("ruleResponsibilityName",reviewerName),
214                               equal("ruleResponsibilityType",type));
215
216                List responsibilities = getDataObjectService().findMatching(
217                                    RuleResponsibilityBo.class,builder.build()).getResults();
218                List rules = new ArrayList();
219
220                for (Iterator iter = responsibilities.iterator(); iter.hasNext();) {
221                        RuleResponsibilityBo responsibility = (RuleResponsibilityBo) iter.next();
222                        RuleBaseValues rule = responsibility.getRuleBaseValues();
223                        if (rule != null && rule.getCurrentInd() != null && rule.getCurrentInd().booleanValue()) {
224                                rules.add(rule);
225                        }
226                }
227                return rules;
228        }
229
230        @Override
231    public List<RuleBaseValues> findRuleBaseValuesByResponsibilityReviewerTemplateDoc(String ruleTemplateName,
232            String documentType, String reviewerName, String type) {
233
234        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
235                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
236        List<Predicate> predicates = new ArrayList<Predicate>();
237        predicates.add(equal("ruleResponsibilityName",reviewerName));
238        predicates.add(equal("ruleResponsibilityType",type));
239        predicates.add(equal("ruleBaseValues.currentInd",Boolean.TRUE));
240        if (!StringUtils.isBlank(ruleTemplateName)) {
241            predicates.add(like("ruleBaseValues.ruleTemplate.name", ruleTemplateName.replace("*", "%").concat("%")));
242        }
243
244        if (!StringUtils.isBlank(documentType)) {
245            predicates.add(like("ruleBaseValues.docTypeName", documentType.replace("*", "%").concat("%")));
246        }
247
248                List responsibilities = getDataObjectService().findMatching(
249                                RuleResponsibilityBo.class,builder.build()).getResults();
250                List rules = new ArrayList();
251
252                for (Iterator iter = responsibilities.iterator(); iter.hasNext();) {
253                        RuleResponsibilityBo responsibility = (RuleResponsibilityBo) iter.next();
254                        RuleBaseValues rule = responsibility.getRuleBaseValues();
255                        if (rule != null && rule.getCurrentInd() != null && rule.getCurrentInd().booleanValue()) {
256                                rules.add(rule);
257                        }
258                }
259                return rules;
260        }
261
262        @Override
263    public RuleResponsibilityBo findRuleResponsibility(String responsibilityId) {
264        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
265                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
266        builder.setPredicates(equal("responsibilityId",responsibilityId));
267                Collection responsibilities = getDataObjectService().findMatching(
268                RuleResponsibilityBo.class,builder.build()).getResults();
269                for (Iterator iterator = responsibilities.iterator(); iterator.hasNext();) {
270                        RuleResponsibilityBo responsibility = (RuleResponsibilityBo) iterator.next();
271                        if (responsibility.getRuleBaseValues().getCurrentInd().booleanValue()) {
272                                return responsibility;
273                        }
274                }
275                return null;
276        }
277
278        @Override
279    public List<RuleBaseValues> search(String docTypeName, String ruleId, String ruleTemplateId, String ruleDescription, String groupId, String principalId, Boolean delegateRule, Boolean activeInd, Map extensionValues, String workflowIdDirective) {
280        CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
281        CriteriaQuery<RuleBaseValues> cq = cb.createQuery(RuleBaseValues.class);
282        Root<RuleBaseValues> root = cq.from(RuleBaseValues.class);
283        List<javax.persistence.criteria.Predicate> predicates = getSearchCriteria(root,cq,docTypeName, ruleTemplateId, ruleDescription, delegateRule, activeInd, extensionValues);
284
285        if (ruleId != null) {
286            predicates.add(cb.equal(root.get("id"),ruleId));
287        }
288        if (groupId != null) {
289            predicates.add(cb.in(root.get("id")).value(getRuleResponsibilitySubQuery(
290                    groupId, cq)));
291        }
292        Collection<String> kimGroupIds = new HashSet<String>();
293        Boolean searchUser = Boolean.FALSE;
294        Boolean searchUserInWorkgroups = Boolean.FALSE;
295
296        if ("group".equals(workflowIdDirective)) {
297            searchUserInWorkgroups = Boolean.TRUE;
298        } else if (StringUtils.isBlank(workflowIdDirective)) {
299            searchUser = Boolean.TRUE;
300            searchUserInWorkgroups = Boolean.TRUE;
301        } else {
302            searchUser = Boolean.TRUE;
303        }
304
305        if (!org.apache.commons.lang.StringUtils.isEmpty(principalId) && searchUserInWorkgroups) {
306            Principal principal = null;
307
308            principal = KimApiServiceLocator.getIdentityService().getPrincipal(principalId);
309
310            if (principal == null)
311            {
312                throw new RiceRuntimeException("Failed to locate user for the given principal id: " + principalId);
313            }
314            kimGroupIds = KimApiServiceLocator.getGroupService().getGroupIdsByPrincipalId(principalId);
315        }
316        Subquery<RuleResponsibilityBo> subquery = addResponsibilityCriteria(cq,kimGroupIds, principalId, searchUser, searchUserInWorkgroups);
317
318        if(subquery != null){
319            predicates.add(cb.in(root.get("id")).value(subquery));
320        }
321        cq.distinct(true);
322        javax.persistence.criteria.Predicate[] preds = predicates.toArray(
323                new javax.persistence.criteria.Predicate[predicates.size()]);
324        cq.where(preds);
325        TypedQuery<RuleBaseValues> q = getEntityManager().createQuery(cq);
326
327        return q.getResultList();
328        }
329
330    @Override
331    public List<RuleBaseValues> search(String docTypeName, String ruleTemplateId, String ruleDescription, Collection<String> workgroupIds, String workflowId, Boolean delegateRule, Boolean activeInd, Map extensionValues, Collection actionRequestCodes) {
332        CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
333        CriteriaQuery<RuleBaseValues> cq = cb.createQuery(RuleBaseValues.class);
334        Root<RuleBaseValues> root = cq.from(RuleBaseValues.class);
335        List<javax.persistence.criteria.Predicate> predicates = getSearchCriteria(root,cq,docTypeName,
336                        ruleTemplateId, ruleDescription, delegateRule, activeInd, extensionValues);
337        Subquery<RuleResponsibilityBo> subquery = addResponsibilityCriteria(cq,workgroupIds, workflowId, actionRequestCodes,
338                        (workflowId != null), ((workgroupIds != null) && !workgroupIds.isEmpty()));
339        if (subquery != null){
340            predicates.add(cb.in(root.get("id")).value(subquery));
341        }
342        javax.persistence.criteria.Predicate[] preds = predicates.toArray(new javax.persistence.criteria.Predicate[predicates.size()]);
343        cq.where(preds);
344        TypedQuery<RuleBaseValues> q = getEntityManager().createQuery(cq);
345
346        return q.getResultList();
347    }
348
349    private Subquery<RuleResponsibilityBo> addResponsibilityCriteria(CriteriaQuery<RuleBaseValues> query, Collection<String> kimGroupIds,
350            String principalId, Boolean searchUser, Boolean searchUserInWorkgroups) {
351        Collection<String> workgroupIdStrings = new ArrayList<String>();
352        for (String workgroupId : kimGroupIds) {
353            workgroupIdStrings.add(workgroupId.toString());
354        }
355        return addResponsibilityCriteria(query, workgroupIdStrings,principalId,new ArrayList<String>(),
356                                        searchUser, searchUserInWorkgroups);
357    }
358
359    private Subquery<RuleResponsibilityBo> addResponsibilityCriteria(CriteriaQuery<RuleBaseValues> query, Collection<String> workgroupIds, String workflowId, Collection actionRequestCodes, Boolean searchUser, Boolean searchUserInWorkgroups) {
360
361        CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
362        Subquery<RuleResponsibilityBo> subquery = query.subquery(RuleResponsibilityBo.class);
363        Root fromResp = subquery.from(RuleResponsibilityBo.class);
364
365        List<javax.persistence.criteria.Predicate> respPredicates = new
366                        ArrayList<javax.persistence.criteria.Predicate>();
367
368        List<javax.persistence.criteria.Predicate> ruleRespNamePredicates = new
369                ArrayList<javax.persistence.criteria.Predicate>();
370
371        List<javax.persistence.criteria.Predicate> userNamePreds =
372                new ArrayList<javax.persistence.criteria.Predicate>();
373
374        List<javax.persistence.criteria.Predicate> workgroupPreds =
375                new ArrayList<javax.persistence.criteria.Predicate>();
376
377
378        if ( (actionRequestCodes != null) && (!actionRequestCodes.isEmpty()) ) {
379            Expression<String> exp = fromResp.get("actionRequestedCd");
380            javax.persistence.criteria.Predicate actionRequestPredicate = exp.in(actionRequestCodes);
381
382            respPredicates.add(actionRequestPredicate);
383        }
384
385        if (!org.apache.commons.lang.StringUtils.isEmpty(workflowId)) {
386            // workflow user id exists
387            if (searchUser != null && searchUser) {
388                // searching user wishes to search for rules specific to user
389                userNamePreds.add(cb.like(fromResp.get("ruleResponsibilityName"),workflowId));
390                userNamePreds.add(cb.equal(fromResp.get("ruleResponsibilityType"),KewApiConstants.RULE_RESPONSIBILITY_WORKFLOW_ID));
391
392                javax.persistence.criteria.Predicate[] preds = userNamePreds.toArray(new javax.persistence.criteria.Predicate[userNamePreds.size()]);
393                ruleRespNamePredicates.add(cb.and(preds));
394
395            }
396            if ( (searchUserInWorkgroups != null && searchUserInWorkgroups) && (workgroupIds != null) && (!workgroupIds.isEmpty()) ) {
397                // at least one workgroup id exists and user wishes to search on workgroups
398
399                Expression<String> exp = fromResp.get("ruleResponsibilityName");
400                javax.persistence.criteria.Predicate groupIdPredicate = exp.in(workgroupIds);
401                workgroupPreds.add(groupIdPredicate);
402                workgroupPreds.add(cb.equal(fromResp.get("ruleResponsibilityType"),
403                        KewApiConstants.RULE_RESPONSIBILITY_GROUP_ID));
404                javax.persistence.criteria.Predicate[] preds = workgroupPreds.toArray(new javax.persistence.criteria.Predicate[workgroupPreds.size()]);
405                ruleRespNamePredicates.add(cb.and(preds));
406            }
407        } else if ( (workgroupIds != null) && (workgroupIds.size() == 1) ) {
408            // no user and one workgroup id
409            workgroupPreds.add(cb.like(fromResp.get("ruleResponsibilityName"),
410                                workgroupIds.iterator().next()));
411            workgroupPreds.add(cb.equal(fromResp.get("ruleResponsibilityType"),
412                        KewApiConstants.RULE_RESPONSIBILITY_GROUP_ID));
413            javax.persistence.criteria.Predicate[] preds = workgroupPreds.toArray(new javax.persistence.criteria.Predicate[workgroupPreds.size()]);
414            ruleRespNamePredicates.add(cb.and(preds));
415
416        } else if ( (workgroupIds != null) && (workgroupIds.size() > 1) ) {
417            // no user and more than one workgroup id
418
419            Expression<String> exp = fromResp.get("ruleResponsibilityName");
420            javax.persistence.criteria.Predicate groupIdPredicate = exp.in(workgroupIds);
421            workgroupPreds.add(cb.equal(fromResp.get("ruleResponsibilityType"),
422                                        KewApiConstants.RULE_RESPONSIBILITY_GROUP_ID));
423            javax.persistence.criteria.Predicate[] preds = workgroupPreds.toArray(new javax.persistence.criteria.Predicate[workgroupPreds.size()]);
424            ruleRespNamePredicates.add(cb.and(preds));
425        }
426
427        if (!ruleRespNamePredicates.isEmpty()) {
428            javax.persistence.criteria.Predicate[] preds = ruleRespNamePredicates.toArray(new javax.persistence.criteria.Predicate[ruleRespNamePredicates.size()]);
429            respPredicates.add(cb.or(preds));
430        }
431
432        if (!respPredicates.isEmpty()) {
433
434            javax.persistence.criteria.Predicate[] preds = respPredicates.toArray(
435                    new javax.persistence.criteria.Predicate[respPredicates.size()]);
436            subquery.where(preds);
437            subquery.select(fromResp.get("ruleBaseValuesId"));
438            return subquery;
439        }
440        return null;
441    }
442
443    private List<javax.persistence.criteria.Predicate> getSearchCriteria(Root<RuleBaseValues> root,CriteriaQuery<RuleBaseValues> query,
444            String docTypeName, String ruleTemplateId,
445            String ruleDescription, Boolean delegateRule, Boolean activeInd, Map extensionValues) {
446        List<javax.persistence.criteria.Predicate> predicates = new ArrayList<javax.persistence.criteria.Predicate>();
447        CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
448
449        predicates.add(cb.equal(root.get("currentInd"),Boolean.TRUE));
450        predicates.add(cb.equal(root.get("templateRuleInd"), Boolean.FALSE));
451        if (activeInd != null) {
452            predicates.add(cb.equal(root.get("active"),activeInd));
453        }
454        if (docTypeName != null) {
455            predicates.add(cb.like(cb.upper(root.<String>get("docTypeName")), docTypeName.toUpperCase()));
456        }
457        if (ruleDescription != null && !ruleDescription.trim().equals("")) {
458            predicates.add(cb.like(cb.upper(root.<String>get("description")),ruleDescription.toUpperCase()));
459        }
460        if (ruleTemplateId != null) {
461            predicates.add(cb.equal(root.get("ruleTemplateId"),ruleTemplateId));
462        }
463        if (delegateRule != null) {
464            predicates.add(cb.equal(root.get("delegateRule"),delegateRule));
465        }
466        if (extensionValues != null && !extensionValues.isEmpty()) {
467            for (Iterator iter2 = extensionValues.entrySet().iterator(); iter2.hasNext();) {
468                Map.Entry entry = (Map.Entry) iter2.next();
469                if (!StringUtils.isEmpty((String) entry.getValue())) {
470                    Subquery ruleExtSubQuery = query.subquery(RuleExtensionBo.class);
471                    Root<RuleExtensionBo> ruleExtRoot = ruleExtSubQuery.from(RuleExtensionBo.class);
472                    javax.persistence.criteria.Predicate predAnd = cb.and(
473                            cb.equal(ruleExtRoot.get("extensionValues").get("key"),entry.getKey()),
474                            cb.like(ruleExtRoot.get("extensionValues").<String>get("value"),
475                                    ("%" + (String) entry.getValue() + "%").toUpperCase()));
476                    ruleExtSubQuery.where(predAnd);
477                    ruleExtSubQuery.select(ruleExtRoot.get("ruleBaseValuesId"));
478
479                    predicates.add(cb.in(root.get("id")).value(ruleExtSubQuery));
480                }
481            }
482        }
483        return predicates;
484    }
485
486    private Subquery<RuleResponsibilityBo> getRuleResponsibilitySubQuery(String ruleRespName,
487                        CriteriaQuery<RuleBaseValues> query){
488        CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
489        Subquery<RuleResponsibilityBo> subquery = query.subquery(RuleResponsibilityBo.class);
490        Root fromResp = subquery.from(RuleResponsibilityBo.class);
491        subquery.where(cb.equal(fromResp.get("ruleResponsibilityName"),ruleRespName));
492        subquery.select(fromResp.get("ruleBaseValuesId"));
493
494        return subquery;
495    }
496
497
498        @Override
499    public List<RuleBaseValues> findByPreviousRuleId(String previousRuleId) {
500        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
501                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
502        builder.setPredicates(equal("previousRuleId",previousRuleId));
503                return getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
504        }
505
506        @Override
507    public RuleBaseValues findDefaultRuleByRuleTemplateId(String ruleTemplateId) {
508        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
509                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
510        if(StringUtils.isNotBlank(ruleTemplateId)){
511            builder.setPredicates(equal("ruleTemplateId",ruleTemplateId),
512                    equal("templateRuleInd",Boolean.TRUE));
513
514            List rules = getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
515            if (rules != null && !rules.isEmpty()) {
516                return (RuleBaseValues) rules.get(0);
517            }
518        }
519
520                return null;
521        }
522
523        @Override
524    public void retrieveAllReferences(RuleBaseValues rule) {
525                // getPersistenceBroker().retrieveAllReferences(rule);
526        }
527
528        @Override
529    public RuleBaseValues getParentRule(String ruleBaseValuesId) {
530        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
531                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
532        builder.setPredicates(equal("responsibilities.delegationRules.delegateRuleId",ruleBaseValuesId),
533                equal("currentInd",Boolean.TRUE));
534
535                Collection rules = getDataObjectService().findMatching(RuleBaseValues.class,builder.build()).getResults();
536                RuleBaseValues rule = null;
537                for (Iterator iterator = rules.iterator(); iterator.hasNext();) {
538                        RuleBaseValues currentRule = (RuleBaseValues) iterator.next();
539                        if (rule == null || currentRule.getVersionNbr().intValue() > rule.getVersionNbr().intValue()) {
540                                rule = currentRule;
541                        }
542                }
543                return rule;
544        }
545
546        @Override
547    public List findOldDelegations(final RuleBaseValues oldRule, final RuleBaseValues newRule) {
548
549                Query q = entityManager.createNativeQuery(OLD_DELEGATIONS_SQL);
550                q.setParameter(1, oldRule.getId());
551                q.setParameter(2, newRule.getId());
552                List oldDelegations = new ArrayList();
553                for(Object l:q.getResultList()){
554                        // FIXME: KULRICE-5201 - This used to be a cast by new Long(l) -- assuming that the Object here in result list is actually a string or is castable to string by .toString()
555                        oldDelegations.add(findRuleBaseValuesById(String.valueOf(l)));
556                }
557                return oldDelegations;
558
559        }
560
561        @Override
562    public String findResponsibilityIdForRule(String ruleName, String ruleResponsibilityName, String ruleResponsibilityType) {
563        org.kuali.rice.core.api.criteria.QueryByCriteria.Builder builder =
564                org.kuali.rice.core.api.criteria.QueryByCriteria.Builder.create();
565        builder.setPredicates(equal("ruleResponsibilityName",ruleResponsibilityName),
566                                equal("ruleResponsibilityType",ruleResponsibilityType),
567                                equal("ruleBaseValues.currentInd",Boolean.TRUE),
568                                equal("ruleBaseValues.name",ruleName));
569                Collection responsibilities = getDataObjectService().findMatching(
570                            RuleResponsibilityBo.class,builder.build()).getResults();
571                if (responsibilities != null) {
572                        for (Iterator iter = responsibilities.iterator(); iter.hasNext();) {
573                                RuleResponsibilityBo responsibility = (RuleResponsibilityBo) iter.next();
574                                return responsibility.getResponsibilityId();
575                        }
576                }
577                return null;
578        }
579
580    public EntityManager getEntityManager() {
581        return this.entityManager;
582    }
583
584    public void setEntityManager(EntityManager entityManager) {
585        this.entityManager = entityManager;
586    }
587
588
589    public DataObjectService getDataObjectService() {
590        return dataObjectService;
591    }
592
593    @Required
594    public void setDataObjectService(DataObjectService dataObjectService) {
595        this.dataObjectService = dataObjectService;
596    }
597
598}