001    /*
002     * Licensed to the Apache Software Foundation (ASF) under one
003     * or more contributor license agreements.  See the NOTICE file
004     * distributed with this work for additional information
005     * regarding copyright ownership.  The ASF licenses this file
006     * to you under the Apache License, Version 2.0 (the
007     * "License"); you may not use this file except in compliance
008     * with the License.  You may obtain a copy of the License at
009     *
010     *     http://www.apache.org/licenses/LICENSE-2.0
011     *
012     * Unless required by applicable law or agreed to in writing,
013     * software distributed under the License is distributed on an
014     * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
015     * KIND, either express or implied.  See the License for the
016     * specific language governing permissions and limitations
017     * under the License.
018     */
019    package org.apache.shiro.authz.permission;
020    
021    import org.apache.shiro.util.StringUtils;
022    
023    /**
024     * Provides a base Permission class from which type-safe/domain-specific subclasses may extend.  Can be used
025     * as a base class for JPA/Hibernate persisted permissions that wish to store the parts of the permission string
026     * in separate columns (e.g. 'domain', 'actions' and 'targets' columns), which can be used in querying
027     * strategies.
028     *
029     * @author Les Hazlewood
030     * @since 1.0
031     */
032    public abstract class DomainPermission extends WildcardPermission {
033    
034        private String domain;
035        private String actions;
036        private String targets;
037    
038        /**
039         * Creates a domain permission with *all* actions for *all* targets;
040         */
041        public DomainPermission() {
042            setParts(getDomain(getClass()), null, null);
043        }
044    
045        public DomainPermission(String actions) {
046            setParts(getDomain(getClass()), actions, null);
047        }
048    
049        public DomainPermission(String actions, String targets) {
050            setParts(getDomain(getClass()), actions, targets);
051        }
052    
053        protected void setParts(String domain, String actions, String targets) {
054            if (!StringUtils.hasText(domain)) {
055                throw new IllegalArgumentException("domain argument cannot be null or empty.");
056            }
057            StringBuilder sb = new StringBuilder(domain);
058    
059            if (!StringUtils.hasText(actions)) {
060                if (StringUtils.hasText(targets)) {
061                    sb.append(PART_DIVIDER_TOKEN).append(WILDCARD_TOKEN);
062                }
063            } else {
064                sb.append(PART_DIVIDER_TOKEN).append(actions);
065            }
066            if (targets != null) {
067                sb.append(PART_DIVIDER_TOKEN).append(targets);
068            }
069            setParts(sb.toString());
070        }
071    
072        protected String getDomain(Class<? extends DomainPermission> clazz) {
073            String domain = clazz.getSimpleName().toLowerCase();
074            //strip any trailing 'permission' text from the name (as all subclasses should have been named):
075            int index = domain.lastIndexOf("permission");
076            if (index != -1) {
077                domain = domain.substring(0, index);
078            }
079            return domain;
080        }
081    
082        public String getDomain() {
083            return domain;
084        }
085    
086        protected void setDomain(String domain) {
087            this.domain = domain;
088        }
089    
090        public String getActions() {
091            return actions;
092        }
093    
094        protected void setActions(String actions) {
095            this.actions = actions;
096        }
097    
098        public String getTargets() {
099            return targets;
100        }
101    
102        protected void setTargets(String targets) {
103            this.targets = targets;
104        }
105    }