/* * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.apache.wicket.security.hive.authorization.permissions; import org.apache.wicket.security.actions.Inherit; import org.apache.wicket.security.actions.WaspAction; import org.apache.wicket.security.hive.authorization.Permission; import org.apache.wicket.security.hive.config.HiveFactory; /** * Base class for any Permission that uses actions. Each implementation of * ActionPermission should at least expose the ActionPermission(String name, SwarmAction * actions) constructor to the outside world, for it will be used by a {@link HiveFactory} * when constructing permissions. Note if you do not wish to use actions in your * permissions you should build your own permissions. * * @author marrink */ public class ActionPermission extends Permission { private static final long serialVersionUID = 1L; private WaspAction actions; /** * Creates a new ActionPermission with the specified name and actions. * * @param name * non null name of the permission * @param actions * a logical and of all the allowed / required actions for this permission */ protected ActionPermission(String name, WaspAction actions) { super(name); if (name == null) throw new IllegalArgumentException("Name is required."); if (actions == null) throw new IllegalArgumentException("Actions is required."); this.actions = actions; // WaspAction is immutable } /** * Performs a logical and to see if this permission has at least all the actions as * the other permission and thus if this permission implies the other permission. * Inherited actions are considered. * * <pre> * Some basic rules about implies: * <li> * if 2 permissions are equal both should imply the other. * </li> * <li> * if 2 permissions are not equal they might still imply each other, or 1 might implies the other but not vice versa * </li> * <li> * a permission should imply another permission if they are of the same class and the first has at least, * all the actions of the second permission and they have the same name. * </li> * <li> * a permission should imply another permission if there is some kind of hierarchical structure between them * and the other permission is able to inherit the required actions from the first permission. * * To further clarify the part about inheritance. This implementation implies any type of ActionPermission under the following conditions. * <li> * Equal name and actions * </li> * <li> * This permission has the inherit action and all or more of the other permissions actions * and the name of the other permission starts with the name of this permission. * </li> * Subclasses like DataPermission that only wish to imply other DataPermissions could simply override implies like this. * <code> * if (permission instanceof DataPermission) * return super.implies(permission); * return false; * </code> * Note that this does not prevent other subclasses from ActionPermission to imply your permission (as stated above). * </pre> * * @see Permission#implies(Permission) */ @Override public boolean implies(Permission permission) { if (permission instanceof ActionPermission) { ActionPermission other = (ActionPermission) permission; if (actions.implies(actions.getActionFactory().getAction(Inherit.class))) return actions.implies(other.actions) && other.getName().startsWith(getName()); return actions.implies(other.actions) && getName().equals(other.getName()); } return false; } /** * ActionPermissions are only equal if they have the same class, name and actions. * * @see Permission#equals(java.lang.Object) * */ @Override public boolean equals(Object obj) { if (obj != null && obj.getClass().equals(getClass())) { ActionPermission other = (ActionPermission) obj; return other.getName().equals(getName()) && other.actions.equals(actions); // both fields are not null } return false; } /** * generates a hashcode including the classname. * * @see Permission#hashCode() */ @Override public int hashCode() { int result = 4679; result = 37 * result + getClass().getName().hashCode(); result = 37 * result + getName().hashCode(); result = 37 * result + actions.hashCode(); return result; } /** * A logically ordered comma separated string containing each action this permission * has. * * @see Permission#getActions() */ @Override public final String getActions() { return actions.getName(); } /** * * @see java.lang.Object#toString() */ @Override public String toString() { return getClass().getName() + " \"" + getName() + "\" \"" + getActions() + "\""; } /** * The internal representation of this action. * * @return the action */ protected final WaspAction getAction() { return actions; } }