001    /**
002     * Copyright 2005-2013 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.rice.kew.api.rule;
017    
018    import java.io.Serializable;
019    import java.lang.reflect.Type;
020    import java.util.ArrayList;
021    import java.util.Collection;
022    import java.util.Collections;
023    import java.util.List;
024    import javax.xml.bind.annotation.XmlAccessType;
025    import javax.xml.bind.annotation.XmlAccessorType;
026    import javax.xml.bind.annotation.XmlAnyElement;
027    import javax.xml.bind.annotation.XmlElement;
028    import javax.xml.bind.annotation.XmlElementWrapper;
029    import javax.xml.bind.annotation.XmlRootElement;
030    import javax.xml.bind.annotation.XmlType;
031    
032    import org.apache.commons.collections.CollectionUtils;
033    import org.apache.commons.lang.ObjectUtils;
034    import org.apache.commons.lang.StringUtils;
035    import org.apache.commons.lang.math.NumberUtils;
036    import org.kuali.rice.core.api.CoreConstants;
037    import org.kuali.rice.core.api.mo.AbstractDataTransferObject;
038    import org.kuali.rice.core.api.mo.ModelBuilder;
039    import org.kuali.rice.kew.api.KewApiConstants;
040    import org.w3c.dom.Element;
041    
042    @XmlRootElement(name = RuleResponsibility.Constants.ROOT_ELEMENT_NAME)
043    @XmlAccessorType(XmlAccessType.NONE)
044    @XmlType(name = RuleResponsibility.Constants.TYPE_NAME, propOrder = {
045        RuleResponsibility.Elements.ID,
046        RuleResponsibility.Elements.PRIORITY,
047        RuleResponsibility.Elements.RESPONSIBILITY_ID,
048        RuleResponsibility.Elements.ACTION_REQUESTED_CD,
049        RuleResponsibility.Elements.APPROVE_POLICY,
050        RuleResponsibility.Elements.PRINCIPAL_ID,
051        RuleResponsibility.Elements.GROUP_ID,
052        RuleResponsibility.Elements.ROLE_NAME,
053        RuleResponsibility.Elements.DELEGATION_RULES,
054        RuleResponsibility.Elements.USING_ROLE,
055        RuleResponsibility.Elements.USING_GROUP,
056        RuleResponsibility.Elements.USING_PRINCIPAL,
057        CoreConstants.CommonElements.VERSION_NUMBER,
058        CoreConstants.CommonElements.OBJECT_ID,
059        CoreConstants.CommonElements.FUTURE_ELEMENTS
060    })
061    public final class RuleResponsibility
062        extends AbstractDataTransferObject
063        implements RuleResponsibilityContract
064    {
065        @XmlElement(name = Elements.ID, required = false)
066        private final String id;
067    
068        @XmlElement(name = Elements.PRIORITY, required = false)
069        private final Integer priority;
070    
071        @XmlElement(name = Elements.RESPONSIBILITY_ID, required = true)
072        private final String responsibilityId;
073    
074        @XmlElement(name = Elements.ACTION_REQUESTED_CD, required = false)
075        private final String actionRequestedCd;
076    
077        @XmlElement(name = Elements.APPROVE_POLICY, required = false)
078        private final String approvePolicy;
079    
080        @XmlElement(name = Elements.PRINCIPAL_ID, required = false)
081        private final String principalId;
082    
083        @XmlElement(name = Elements.GROUP_ID, required = false)
084        private final String groupId;
085    
086        @XmlElement(name = Elements.ROLE_NAME, required = false)
087        private final String roleName;
088    
089        @XmlElementWrapper(name = Elements.DELEGATION_RULES, required = false)
090        @XmlElement(name = Elements.DELEGATION_RULE, required = false)
091        private final List<RuleDelegation> delegationRules;
092    
093        @XmlElement(name = Elements.USING_ROLE, required = false)
094        private final boolean usingRole;
095    
096        @XmlElement(name = Elements.USING_PRINCIPAL, required = false)
097        private final boolean usingPrincipal;
098    
099        @XmlElement(name = Elements.USING_GROUP, required = false)
100        private final boolean usingGroup;
101    
102        @XmlElement(name = CoreConstants.CommonElements.VERSION_NUMBER, required = false)
103        private final Long versionNumber;
104    
105        @XmlElement(name = CoreConstants.CommonElements.OBJECT_ID, required = false)
106        private final String objectId;
107    
108        @SuppressWarnings("unused")
109        @XmlAnyElement
110        private final Collection<Element> _futureElements = null;
111    
112        /**
113         * Private constructor used only by JAXB.
114         * 
115         */
116        private RuleResponsibility() {
117            this.id = null;
118            this.priority = null;
119            this.responsibilityId = null;
120            this.actionRequestedCd = null;
121            this.approvePolicy = null;
122            this.principalId = null;
123            this.groupId = null;
124            this.roleName = null;
125            this.delegationRules = null;
126            this.usingGroup = false;
127            this.usingPrincipal = false;
128            this.usingRole = false;
129            this.versionNumber = null;
130            this.objectId = null;
131        }
132    
133        private RuleResponsibility(Builder builder) {
134            this.id = builder.getId();
135            this.priority = builder.getPriority();
136            this.responsibilityId = builder.getResponsibilityId();
137            this.actionRequestedCd = builder.getActionRequestedCd();
138            this.approvePolicy = builder.getApprovePolicy();
139            this.principalId = builder.getPrincipalId();
140            this.groupId = builder.getGroupId();
141            this.roleName = builder.getRoleName();
142            if (CollectionUtils.isNotEmpty(builder.getDelegationRules())) {
143                List<RuleDelegation> delegationList = new ArrayList<RuleDelegation>();
144                for (RuleDelegation.Builder b : builder.getDelegationRules()) {
145                    delegationList.add(b.build());
146                }
147                this.delegationRules = delegationList;
148            } else {
149                this.delegationRules = Collections.emptyList();
150            }
151            this.usingGroup = builder.isUsingGroup();
152            this.usingPrincipal = builder.isUsingPrincipal();
153            this.usingRole = builder.isUsingRole();
154            versionNumber = builder.getVersionNumber();
155            objectId = builder.getObjectId();
156        }
157    
158        @Override
159        public String getId() {
160            return this.id;
161        }
162    
163        @Override
164        public Integer getPriority() {
165            return this.priority;
166        }
167    
168        @Override
169        public String getResponsibilityId() {
170            return this.responsibilityId;
171        }
172    
173        @Override
174        public String getActionRequestedCd() {
175            return this.actionRequestedCd;
176        }
177    
178        @Override
179        public String getApprovePolicy() {
180            return this.approvePolicy;
181        }
182    
183        @Override
184        public String getPrincipalId() {
185            return this.principalId;
186        }
187    
188        @Override
189        public String getGroupId() {
190            return this.groupId;
191        }
192    
193        @Override
194        public String getRoleName() {
195            return this.roleName;
196        }
197    
198        @Override
199        public List<RuleDelegation> getDelegationRules() {
200            return this.delegationRules;
201        }
202    
203        @Override
204        public boolean isUsingRole() {
205            return this.usingRole;
206        }
207    
208        @Override
209        public boolean isUsingPrincipal() {
210            return this.usingPrincipal;
211        }
212    
213        @Override
214        public boolean isUsingGroup() {
215            return this.usingGroup;
216        }
217    
218        @Override
219        public Long getVersionNumber() {
220            return versionNumber;
221        }
222    
223        @Override
224        public String getObjectId() {
225            return objectId;
226        }
227    
228        public String getRoleAttributeName() {
229                return getRoleName().substring(0, getRoleName().indexOf("!"));
230        }
231    
232        public String getResolvedRoleName() {
233            if (isUsingRole()) {
234                return getRoleName().substring(getRoleName().indexOf("!") + 1, getRoleName().length());
235            }
236            return null;
237        }
238    
239        /**
240         * A builder which can be used to construct {@link RuleResponsibility} instances.  Enforces the constraints of the {@link RuleResponsibilityContract}.
241         * 
242         */
243        public final static class Builder
244            implements Serializable, ModelBuilder, RuleResponsibilityContract
245        {
246            private String id;
247            private Integer priority;
248            private String responsibilityId;
249            private String actionRequestedCd;
250            private String approvePolicy;
251            private String principalId;
252            private String groupId;
253            private String roleName;
254            private List<RuleDelegation.Builder> delegationRules;
255            private boolean usingRole = false;
256            private boolean usingPrincipal = false;
257            private boolean usingGroup = false;
258            private Long versionNumber;
259            private String objectId;
260    
261            private Builder() {
262            }
263    
264            public static Builder create() {
265                return new Builder();
266            }
267    
268            public static Builder create(RuleResponsibilityContract contract) {
269                if (contract == null) {
270                    throw new IllegalArgumentException("contract was null");
271                }
272                Builder builder = create();
273                builder.setId(contract.getId());
274                builder.setPriority(contract.getPriority());
275                builder.setResponsibilityId(contract.getResponsibilityId());
276                builder.setActionRequestedCd(contract.getActionRequestedCd());
277                builder.setApprovePolicy(contract.getApprovePolicy());
278                builder.setPrincipalId(contract.getPrincipalId());
279                builder.setGroupId(contract.getGroupId());
280                builder.setRoleName(contract.getRoleName());
281                if (CollectionUtils.isNotEmpty(contract.getDelegationRules())) {
282                    List<RuleDelegation.Builder> builders = new ArrayList<RuleDelegation.Builder>();
283                    for (RuleDelegationContract delegationContract : contract.getDelegationRules()) {
284                        builders.add(RuleDelegation.Builder.create(delegationContract));
285                    }
286                    builder.setDelegationRules(builders);
287                } else {
288                    builder.setDelegationRules(Collections.<RuleDelegation.Builder>emptyList());
289                }
290                builder.setUsingGroup(contract.isUsingGroup());
291                builder.setUsingPrincipal(contract.isUsingPrincipal());
292                builder.setUsingRole(contract.isUsingRole());
293                builder.setVersionNumber(contract.getVersionNumber());
294                builder.setObjectId(contract.getObjectId());
295                return builder;
296            }
297    
298            public RuleResponsibility build() {
299                return new RuleResponsibility(this);
300            }
301    
302            @Override
303            public String getId() {
304                return this.id;
305            }
306    
307            @Override
308            public Integer getPriority() {
309                return this.priority;
310            }
311    
312            @Override
313            public String getResponsibilityId() {
314                return this.responsibilityId;
315            }
316    
317            @Override
318            public String getActionRequestedCd() {
319                return this.actionRequestedCd;
320            }
321    
322            @Override
323            public String getApprovePolicy() {
324                return this.approvePolicy;
325            }
326    
327            @Override
328            public String getPrincipalId() {
329                return this.principalId;
330            }
331    
332            @Override
333            public String getGroupId() {
334                return this.groupId;
335            }
336    
337            @Override
338            public String getRoleName() {
339                return this.roleName;
340            }
341    
342            @Override
343            public List<RuleDelegation.Builder> getDelegationRules() {
344                return this.delegationRules;
345            }
346    
347            @Override
348            public boolean isUsingRole() {
349                return this.usingRole;
350            }
351    
352            @Override
353            public boolean isUsingPrincipal() {
354                return this.usingPrincipal;
355            }
356    
357            @Override
358            public boolean isUsingGroup() {
359                return this.usingGroup;
360            }
361    
362            @Override
363            public Long getVersionNumber() {
364                return versionNumber;
365            }
366    
367            @Override
368            public String getObjectId() {
369                return objectId;
370            }
371    
372            public void setId(String id) {
373                if (StringUtils.isWhitespace(id)) {
374                    throw new IllegalArgumentException("id is whitespace");
375                }
376                this.id = id;
377            }
378            public void setPriority(Integer priority) {
379                this.priority = priority;
380            }
381    
382            public void setResponsibilityId(String responsibilityId) {
383                this.responsibilityId = responsibilityId;
384            }
385    
386            public void setActionRequestedCd(String actionRequestedCd) {
387                this.actionRequestedCd = actionRequestedCd;
388            }
389    
390            public void setApprovePolicy(String approvePolicy) {
391                this.approvePolicy = approvePolicy;
392            }
393    
394            public void setPrincipalId(String principalId) {
395                this.principalId = principalId;
396            }
397    
398            public void setGroupId(String groupId) {
399                this.groupId = groupId;
400            }
401    
402            public void setRoleName(String roleName) {
403                this.roleName = roleName;
404            }
405    
406            public void setDelegationRules(List<RuleDelegation.Builder> delegationRules) {
407                this.delegationRules = delegationRules;
408            }
409    
410            public void setUsingRole(boolean usingRole) {
411                this.usingRole = usingRole;
412            }
413    
414            public void setUsingPrincipal(boolean usingPrincipal) {
415                this.usingPrincipal = usingPrincipal;
416            }
417    
418            public void setUsingGroup(boolean usingGroup) {
419                this.usingGroup = usingGroup;
420            }
421    
422            public void setVersionNumber(Long versionNumber) {
423                this.versionNumber = versionNumber;
424            }
425    
426            public void setObjectId(String objectId) {
427                this.objectId = objectId;
428            }
429    
430    
431        }
432    
433        @Override
434        public boolean equals(Object o) {
435            if (o == null) { return false; }
436            if (!(o instanceof RuleResponsibilityContract)) { return false; }
437            RuleResponsibilityContract resp = (RuleResponsibilityContract) o;
438            return StringUtils.equals(getPrincipalId(),  resp.getPrincipalId()) &&
439                   StringUtils.equals(getRoleName(), resp.getRoleName()) &&
440                   StringUtils.equals(getGroupId(), resp.getGroupId()) &&
441                   StringUtils.equals(getActionRequestedCd(), resp.getActionRequestedCd()) &&
442                   ObjectUtils.equals(getPriority(), resp.getPriority()) &&
443                   StringUtils.equals(getApprovePolicy(), resp.getApprovePolicy());
444        }
445    
446        /**
447         * Defines some internal constants used on this class.
448         * 
449         */
450        static class Constants {
451    
452            final static String ROOT_ELEMENT_NAME = "ruleResponsibility";
453            final static String TYPE_NAME = "RuleResponsibilityType";
454    
455        }
456    
457    
458        /**
459         * A private class which exposes constants which define the XML element names to use when this object is marshalled to XML.
460         * 
461         */
462        static class Elements {
463            final static String ID = "id";
464            final static String PRIORITY = "priority";
465            final static String RESPONSIBILITY_ID = "responsibilityId";
466            final static String ACTION_REQUESTED_CD = "actionRequestedCd";
467            final static String APPROVE_POLICY = "approvePolicy";
468            final static String PRINCIPAL_ID = "principalId";
469            final static String GROUP_ID = "groupId";
470            final static String ROLE_NAME = "roleName";
471            final static String DELEGATION_RULES = "delegationRules";
472            final static String DELEGATION_RULE = "delegationRule";
473            final static String USING_ROLE = "usingRole";
474            final static String USING_PRINCIPAL = "usingPrincipal";
475            final static String USING_GROUP = "usingGroup";
476        }
477    
478        public static class Cache {
479            public static final String NAME = KewApiConstants.Namespaces.KEW_NAMESPACE_2_0 + "/" + RuleResponsibility.Constants.TYPE_NAME;
480        }
481    }