OpenDJ 3 : config framework
* add admin classes from opendj server, with original package names
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | import org.opends.server.authorization.dseecompat.Aci; |
| | | import org.opends.server.authorization.dseecompat.AciException; |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.ByteString; |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | /** |
| | | * ACI property definition. |
| | | */ |
| | | public class ACIPropertyDefinition extends PropertyDefinition<Aci> { |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing ACI property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<Aci, ACIPropertyDefinition> { |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected ACIPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Aci> defaultBehavior) { |
| | | return new ACIPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior); |
| | | } |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Create a ACI property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new ACI property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | // Private constructor. |
| | | private ACIPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Aci> defaultBehavior) { |
| | | super(d, Aci.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(Aci value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No additional validation required. |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Aci decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | return Aci.decode(ByteString.valueOf(value), DN.NULL_DN); |
| | | } catch (AciException e) { |
| | | // TODO: it would be nice to throw the cause. |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitACI(this, p); |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, Aci value, P p) { |
| | | return v.visitACI(this, value, p); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(Aci o1, Aci o2) { |
| | | return o1.toString().compareTo(o2.toString()); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default behavior provider which retrieves default values from a |
| | | * managed object in an absolute location. It should be used by |
| | | * properties which inherit their default value(s) from properties |
| | | * held in an other managed object. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public final class AbsoluteInheritedDefaultBehaviorProvider<T> extends |
| | | DefaultBehaviorProvider<T> { |
| | | |
| | | // The absolute path to the managed object containing the property. |
| | | private ManagedObjectPath<?, ?> path = null; |
| | | |
| | | // The string representation of the managed object path specifying |
| | | // the absolute location of the managed object. |
| | | private final String pathString; |
| | | |
| | | // The name of the property containing the inherited default values. |
| | | private final String propertyName; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an absolute inherited default behavior provider associated |
| | | * with the managed object at the specified absolute location. |
| | | * |
| | | * @param pathString |
| | | * The string representation of the managed object path |
| | | * specifying the absolute location of the managed object. |
| | | * @param propertyName |
| | | * The name of the property containing the inherited |
| | | * default values. |
| | | */ |
| | | public AbsoluteInheritedDefaultBehaviorProvider(String pathString, |
| | | String propertyName) { |
| | | this.pathString = pathString; |
| | | this.propertyName = propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <R, P> R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p) { |
| | | return v.visitAbsoluteInherited(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the definition of the parent managed object containing the |
| | | * inherited default values. |
| | | * |
| | | * @return Returns the definition of the parent managed object |
| | | * containing the inherited default values. |
| | | */ |
| | | public AbstractManagedObjectDefinition<?, ?> getManagedObjectDefinition() { |
| | | return path.getManagedObjectDefinition(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the absolute path of the managed object containing the |
| | | * property which has the default values. |
| | | * |
| | | * @return Returns the absolute path of the managed object |
| | | * containing the property which has the default values. |
| | | */ |
| | | public ManagedObjectPath<?, ?> getManagedObjectPath() { |
| | | return path; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the name of the property containing the inherited default |
| | | * values. |
| | | * |
| | | * @return Returns the name of the property containing the inherited |
| | | * default values. |
| | | */ |
| | | public String getPropertyName() { |
| | | return propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception { |
| | | // Decode the path. |
| | | path = ManagedObjectPath.valueOf(pathString); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2007-2010 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.ArrayList; |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.EnumSet; |
| | | import java.util.HashMap; |
| | | import java.util.HashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | import java.util.Set; |
| | | |
| | | import java.util.Vector; |
| | | import org.forgerock.i18n.LocalizableMessage; |
| | | import org.opends.server.admin.DefinitionDecodingException.Reason; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Defines the structure of an abstract managed object. Abstract managed objects |
| | | * cannot be instantiated. |
| | | * <p> |
| | | * Applications can query a managed object definition in order to determine the |
| | | * overall configuration model of an application. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this definition |
| | | * represents. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this definition |
| | | * represents. |
| | | */ |
| | | public abstract class AbstractManagedObjectDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> { |
| | | |
| | | // The name of the definition. |
| | | private final String name; |
| | | |
| | | // The parent managed object definition if applicable. |
| | | private final AbstractManagedObjectDefinition<? super C, ? super S> parent; |
| | | |
| | | // The set of constraints associated with this managed object |
| | | // definition. |
| | | private final Collection<Constraint> constraints; |
| | | |
| | | // The set of property definitions applicable to this managed object |
| | | // definition. |
| | | private final Map<String, PropertyDefinition<?>> propertyDefinitions; |
| | | |
| | | // The set of relation definitions applicable to this managed object |
| | | // definition. |
| | | private final Map<String, RelationDefinition<?, ?>> relationDefinitions; |
| | | |
| | | // The set of relation definitions directly referencing this managed |
| | | // object definition. |
| | | private final Set<RelationDefinition<C, S>> reverseRelationDefinitions; |
| | | |
| | | // The set of all property definitions associated with this managed |
| | | // object definition including inherited property definitions. |
| | | private final Map<String, PropertyDefinition<?>> allPropertyDefinitions; |
| | | |
| | | // The set of all relation definitions associated with this managed |
| | | // object definition including inherited relation definitions. |
| | | private final Map<String, RelationDefinition<?, ?>> allRelationDefinitions; |
| | | |
| | | // The set of aggregation property definitions applicable to this |
| | | // managed object definition. |
| | | private final Map<String, AggregationPropertyDefinition<?, ?>> |
| | | aggregationPropertyDefinitions; |
| | | |
| | | // The set of aggregation property definitions directly referencing this |
| | | // managed object definition. |
| | | private final Vector<AggregationPropertyDefinition<?, ?>> |
| | | reverseAggregationPropertyDefinitions; |
| | | |
| | | // The set of all aggregation property definitions associated with this |
| | | // managed object definition including inherited relation definitions. |
| | | private final Map<String, AggregationPropertyDefinition<?, ?>> |
| | | allAggregationPropertyDefinitions; |
| | | |
| | | // The set of tags associated with this managed object. |
| | | private final Set<Tag> allTags; |
| | | |
| | | // Options applicable to this definition. |
| | | private final Set<ManagedObjectOption> options; |
| | | |
| | | // The set of managed object definitions which inherit from this definition. |
| | | private final Map<String, |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S>> children; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new abstract managed object definition. |
| | | * |
| | | * @param name |
| | | * The name of the definition. |
| | | * @param parent |
| | | * The parent definition, or <code>null</code> if there |
| | | * is no parent (only the {@link TopCfgDefn} should have a |
| | | * <code>null</code> parent, unless the definition is |
| | | * being used for testing). |
| | | */ |
| | | protected AbstractManagedObjectDefinition(String name, |
| | | AbstractManagedObjectDefinition<? super C, ? super S> parent) { |
| | | this.name = name; |
| | | this.parent = parent; |
| | | this.constraints = new LinkedList<Constraint>(); |
| | | this.propertyDefinitions = new HashMap<String, PropertyDefinition<?>>(); |
| | | this.relationDefinitions = new HashMap<String, RelationDefinition<?,?>>(); |
| | | this.reverseRelationDefinitions = new HashSet<RelationDefinition<C,S>>(); |
| | | this.allPropertyDefinitions = new HashMap<String, PropertyDefinition<?>>(); |
| | | this.allRelationDefinitions = |
| | | new HashMap<String, RelationDefinition<?, ?>>(); |
| | | this.aggregationPropertyDefinitions = |
| | | new HashMap<String, AggregationPropertyDefinition<?,?>>(); |
| | | this.reverseAggregationPropertyDefinitions = |
| | | new Vector<AggregationPropertyDefinition<?,?>>(); |
| | | this.allAggregationPropertyDefinitions = |
| | | new HashMap<String, AggregationPropertyDefinition<?, ?>>(); |
| | | this.allTags = new HashSet<Tag>(); |
| | | this.options = EnumSet.noneOf(ManagedObjectOption.class); |
| | | |
| | | this.children = new HashMap<String, |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S>>(); |
| | | |
| | | // If we have a parent definition then inherit its features. |
| | | if (parent != null) { |
| | | registerInParent(); |
| | | |
| | | for (PropertyDefinition<?> pd : parent.getAllPropertyDefinitions()) { |
| | | allPropertyDefinitions.put(pd.getName(), pd); |
| | | } |
| | | |
| | | for (RelationDefinition<?, ?> rd : parent.getAllRelationDefinitions()) { |
| | | allRelationDefinitions.put(rd.getName(), rd); |
| | | } |
| | | |
| | | for (AggregationPropertyDefinition<?, ?> apd : |
| | | parent.getAllAggregationPropertyDefinitions()) { |
| | | |
| | | allAggregationPropertyDefinitions.put(apd.getName(), apd); |
| | | } |
| | | |
| | | // Tag inheritance is performed during preprocessing. |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the child managed object definitions which inherit from |
| | | * this managed object definition. |
| | | * |
| | | * @return Returns an unmodifiable collection containing all the |
| | | * subordinate managed object definitions which inherit from |
| | | * this managed object definition. |
| | | */ |
| | | public final Collection<AbstractManagedObjectDefinition |
| | | <? extends C, ? extends S>> getAllChildren() { |
| | | List<AbstractManagedObjectDefinition<? extends C, ? extends S>> list = |
| | | new ArrayList<AbstractManagedObjectDefinition<? extends C, ? extends S>>( |
| | | children.values()); |
| | | |
| | | for (AbstractManagedObjectDefinition<? extends C, ? extends S> child : |
| | | children.values()) { |
| | | list.addAll(child.getAllChildren()); |
| | | } |
| | | |
| | | return Collections.unmodifiableCollection(list); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the constraints associated with this type of managed |
| | | * object. The returned collection will contain inherited |
| | | * constraints. |
| | | * |
| | | * @return Returns a collection containing all the constraints |
| | | * associated with this type of managed object. The caller |
| | | * is free to modify the collection if required. |
| | | */ |
| | | public final Collection<Constraint> getAllConstraints() { |
| | | // This method does not used a cached set of constraints because |
| | | // constraints may be updated after child definitions have been |
| | | // defined. |
| | | List<Constraint> allConstraints = new LinkedList<Constraint>(); |
| | | |
| | | if (parent != null) { |
| | | allConstraints.addAll(parent.getAllConstraints()); |
| | | } |
| | | allConstraints.addAll(constraints); |
| | | |
| | | return allConstraints; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the property definitions associated with this type of |
| | | * managed object. The returned collection will contain inherited |
| | | * property definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing all the |
| | | * property definitions associated with this type of managed |
| | | * object. |
| | | */ |
| | | public final Collection<PropertyDefinition<?>> getAllPropertyDefinitions() { |
| | | return Collections.unmodifiableCollection(allPropertyDefinitions.values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the relation definitions associated with this type of |
| | | * managed object. The returned collection will contain inherited |
| | | * relation definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing all the |
| | | * relation definitions associated with this type of managed |
| | | * object. |
| | | */ |
| | | public final Collection<RelationDefinition<?, ?>> |
| | | getAllRelationDefinitions() { |
| | | return Collections.unmodifiableCollection(allRelationDefinitions.values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the relation definitions which refer to this managed |
| | | * object definition. The returned collection will contain relation |
| | | * definitions which refer to parents of this managed object |
| | | * definition. |
| | | * |
| | | * @return Returns a collection containing all the relation |
| | | * definitions which refer to this managed object |
| | | * definition. The caller is free to modify the collection |
| | | * if required. |
| | | */ |
| | | public final Collection<RelationDefinition<? super C, ? super S>> |
| | | getAllReverseRelationDefinitions() { |
| | | // This method does not used a cached set of relations because |
| | | // relations may be updated after child definitions have been |
| | | // defined. |
| | | List<RelationDefinition<? super C, ? super S>> rdlist = |
| | | new LinkedList<RelationDefinition<? super C, ? super S>>(); |
| | | |
| | | if (parent != null) { |
| | | rdlist.addAll(parent.getAllReverseRelationDefinitions()); |
| | | } |
| | | rdlist.addAll(reverseRelationDefinitions); |
| | | |
| | | return rdlist; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the aggregation property definitions associated with this type of |
| | | * managed object. The returned collection will contain inherited |
| | | * aggregation property definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing all the |
| | | * aggregation property definitions associated with this type of |
| | | * managed object. |
| | | */ |
| | | public final Collection<AggregationPropertyDefinition<?, ?>> |
| | | getAllAggregationPropertyDefinitions() { |
| | | return Collections.unmodifiableCollection( |
| | | allAggregationPropertyDefinitions.values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the aggregation property definitions which refer to this managed |
| | | * object definition. The returned collection will contain aggregation |
| | | * property definitions which refer to parents of this managed object |
| | | * definition. |
| | | * |
| | | * @return Returns a collection containing all the aggregation property |
| | | * definitions which refer to this managed object |
| | | * definition. The caller is free to modify the collection |
| | | * if required. |
| | | */ |
| | | public final Collection<AggregationPropertyDefinition<?, ?>> |
| | | getAllReverseAggregationPropertyDefinitions() { |
| | | // This method does not used a cached set of aggregation properties because |
| | | // aggregation properties may be updated after child definitions have been |
| | | // defined. |
| | | List<AggregationPropertyDefinition<?, ?>> apdlist = |
| | | new LinkedList<AggregationPropertyDefinition<?, ?>>(); |
| | | |
| | | if (parent != null) { |
| | | apdlist.addAll(parent.getAllReverseAggregationPropertyDefinitions()); |
| | | } |
| | | apdlist.addAll(reverseAggregationPropertyDefinitions); |
| | | |
| | | return apdlist; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the tags associated with this type of managed object. The |
| | | * returned collection will contain inherited tags. |
| | | * |
| | | * @return Returns an unmodifiable collection containing all the |
| | | * tags associated with this type of managed object. |
| | | */ |
| | | public final Collection<Tag> getAllTags() { |
| | | return Collections.unmodifiableCollection(allTags); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the named child managed object definition which inherits from |
| | | * this managed object definition. This method will recursively |
| | | * search down through the inheritance hierarchy. |
| | | * |
| | | * @param name |
| | | * The name of the managed object definition sub-type. |
| | | * @return Returns the named child managed object definition which |
| | | * inherits from this managed object definition. |
| | | * @throws IllegalArgumentException |
| | | * If the specified managed object definition name was |
| | | * null or empty or if the requested subordinate managed |
| | | * object definition was not found. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<? extends C, ? extends S> |
| | | getChild(String name) throws IllegalArgumentException { |
| | | if ((name == null) || (name.length() == 0)) { |
| | | throw new IllegalArgumentException("null or empty managed object name"); |
| | | } |
| | | |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> d = children |
| | | .get(name); |
| | | |
| | | if (d == null) { |
| | | // Recursively search. |
| | | for (AbstractManagedObjectDefinition<? extends C, ? extends S> child : |
| | | children.values()) { |
| | | try { |
| | | d = child.getChild(name); |
| | | break; |
| | | } catch (IllegalArgumentException e) { |
| | | // Try the next child. |
| | | } |
| | | } |
| | | } |
| | | |
| | | if (d == null) { |
| | | throw new IllegalArgumentException("child managed object definition \"" |
| | | + name + "\" not found"); |
| | | } |
| | | |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the child managed object definitions which inherit directly |
| | | * from this managed object definition. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * subordinate managed object definitions which inherit |
| | | * directly from this managed object definition. |
| | | */ |
| | | public final Collection<AbstractManagedObjectDefinition |
| | | <? extends C, ? extends S>> getChildren() { |
| | | return Collections.unmodifiableCollection(children.values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the constraints defined by this managed object definition. |
| | | * The returned collection will not contain inherited constraints. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * constraints defined by this managed object definition. |
| | | */ |
| | | public final Collection<Constraint> getConstraints() { |
| | | return Collections.unmodifiableCollection(constraints); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this managed object definition |
| | | * in the default locale. |
| | | * |
| | | * @return Returns the description of this managed object definition |
| | | * in the default locale, or <code>null</code> if there is |
| | | * no description. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getDescription() throws UnsupportedOperationException { |
| | | return getDescription(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this managed object definition |
| | | * in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the description of this managed object definition |
| | | * in the specified locale, or <code>null</code> if there |
| | | * is no description. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getDescription(Locale locale) |
| | | throws UnsupportedOperationException { |
| | | try { |
| | | return ManagedObjectDefinitionI18NResource.getInstance() |
| | | .getMessage(this, "description", locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the definition. |
| | | * |
| | | * @return Returns the name of the definition. |
| | | */ |
| | | public final String getName() { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the parent managed object definition, if applicable. |
| | | * |
| | | * @return Returns the parent of this managed object definition, or |
| | | * <code>null</code> if this definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<? super C, |
| | | ? super S> getParent() { |
| | | return parent; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the specified property definition associated with this type |
| | | * of managed object. The search will include any inherited property |
| | | * definitions. |
| | | * |
| | | * @param name |
| | | * The name of the property definition to be retrieved. |
| | | * @return Returns the specified property definition associated with |
| | | * this type of managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the specified property name was null or empty or if |
| | | * the requested property definition was not found. |
| | | */ |
| | | public final PropertyDefinition<?> getPropertyDefinition(String name) |
| | | throws IllegalArgumentException { |
| | | if ((name == null) || (name.length() == 0)) { |
| | | throw new IllegalArgumentException("null or empty property name"); |
| | | } |
| | | |
| | | PropertyDefinition<?> d = allPropertyDefinitions.get(name); |
| | | if (d == null) { |
| | | throw new IllegalArgumentException("property definition \"" + name |
| | | + "\" not found"); |
| | | } |
| | | |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the property definitions defined by this managed object |
| | | * definition. The returned collection will not contain inherited |
| | | * property definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * property definitions defined by this managed object |
| | | * definition. |
| | | */ |
| | | public final Collection<PropertyDefinition<?>> getPropertyDefinitions() { |
| | | return Collections.unmodifiableCollection(propertyDefinitions |
| | | .values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the specified relation definition associated with this type |
| | | * of managed object.The search will include any inherited relation |
| | | * definitions. |
| | | * |
| | | * @param name |
| | | * The name of the relation definition to be retrieved. |
| | | * @return Returns the specified relation definition associated with |
| | | * this type of managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the specified relation name was null or empty or if |
| | | * the requested relation definition was not found. |
| | | */ |
| | | public final RelationDefinition<?, ?> getRelationDefinition(String name) |
| | | throws IllegalArgumentException { |
| | | if ((name == null) || (name.length() == 0)) { |
| | | throw new IllegalArgumentException("null or empty relation name"); |
| | | } |
| | | |
| | | RelationDefinition<?, ?> d = allRelationDefinitions.get(name); |
| | | if (d == null) { |
| | | throw new IllegalArgumentException("relation definition \"" + name |
| | | + "\" not found"); |
| | | } |
| | | |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the relation definitions defined by this managed object |
| | | * definition. The returned collection will not contain inherited |
| | | * relation definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * relation definitions defined by this managed object |
| | | * definition. |
| | | */ |
| | | public final Collection<RelationDefinition<?,?>> getRelationDefinitions() { |
| | | return Collections.unmodifiableCollection(relationDefinitions.values()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the relation definitions which refer directly to this managed |
| | | * object definition. The returned collection will not contain |
| | | * relation definitions which refer to parents of this managed |
| | | * object definition. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * relation definitions which refer directly to this managed |
| | | * object definition. |
| | | */ |
| | | public final Collection<RelationDefinition<C, S>> |
| | | getReverseRelationDefinitions() { |
| | | return Collections.unmodifiableCollection(reverseRelationDefinitions); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the specified aggregation property definition associated with this type |
| | | * of managed object.The search will include any inherited aggregation |
| | | * property definitions. |
| | | * |
| | | * @param name |
| | | * The name of the aggregation property definition to be retrieved. |
| | | * @return Returns the specified aggregation property definition associated |
| | | * with this type of managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the specified aggregation property name was null or empty or |
| | | * if the requested aggregation property definition was not found. |
| | | */ |
| | | public final AggregationPropertyDefinition<?, ?> |
| | | getAggregationPropertyDefinition(String name) |
| | | throws IllegalArgumentException { |
| | | if ((name == null) || (name.length() == 0)) { |
| | | throw new IllegalArgumentException( |
| | | "null or empty aggregation property name"); |
| | | } |
| | | |
| | | AggregationPropertyDefinition<?, ?> d = |
| | | allAggregationPropertyDefinitions.get(name); |
| | | if (d == null) { |
| | | throw new IllegalArgumentException("aggregation property definition \"" |
| | | + name + "\" not found"); |
| | | } |
| | | |
| | | return d; |
| | | } |
| | | |
| | | /** |
| | | * Get the aggregation property definitions defined by this managed object |
| | | * definition. The returned collection will not contain inherited |
| | | * aggregation property definitions. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * aggregation property definitions defined by this managed object |
| | | * definition. |
| | | */ |
| | | public final Collection<AggregationPropertyDefinition<?, ?>> |
| | | getAggregationPropertyDefinitions() { |
| | | return Collections.unmodifiableCollection( |
| | | aggregationPropertyDefinitions.values()); |
| | | } |
| | | |
| | | /** |
| | | * Get the aggregation property definitions which refer directly to this |
| | | * managed object definition. The returned collection will not contain |
| | | * aggregation property definitions which refer to parents of this managed |
| | | * object definition. |
| | | * |
| | | * @return Returns an unmodifiable collection containing the |
| | | * aggregation property definitions which refer directly to this |
| | | * managed object definition. |
| | | */ |
| | | public final Collection<AggregationPropertyDefinition<?, ?>> |
| | | getReverseAggregationPropertyDefinitions() { |
| | | return Collections.unmodifiableCollection( |
| | | reverseAggregationPropertyDefinitions); |
| | | } |
| | | |
| | | /** |
| | | * Gets the synopsis of this managed object definition in the |
| | | * default locale. |
| | | * |
| | | * @return Returns the synopsis of this managed object definition in |
| | | * the default locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getSynopsis() throws UnsupportedOperationException { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this managed object definition in the |
| | | * specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this managed object definition in |
| | | * the specified locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) |
| | | throws UnsupportedOperationException { |
| | | return ManagedObjectDefinitionI18NResource.getInstance() |
| | | .getMessage(this, "synopsis", locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly name of this managed object definition in |
| | | * the default locale. |
| | | * |
| | | * @return Returns the user friendly name of this managed object |
| | | * definition in the default locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getUserFriendlyName() |
| | | throws UnsupportedOperationException { |
| | | return getUserFriendlyName(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly name of this managed object definition in |
| | | * the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the user friendly name of this managed object |
| | | * definition in the specified locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getUserFriendlyName(Locale locale) |
| | | throws UnsupportedOperationException { |
| | | // TODO: have admin framework getMessage return a Message |
| | | return Message.raw(ManagedObjectDefinitionI18NResource.getInstance() |
| | | .getMessage(this, "user-friendly-name", locale)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this managed object |
| | | * definition in the default locale. |
| | | * |
| | | * @return Returns the user friendly plural name of this managed |
| | | * object definition in the default locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getUserFriendlyPluralName() |
| | | throws UnsupportedOperationException { |
| | | return getUserFriendlyPluralName(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this managed object |
| | | * definition in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the user friendly plural name of this managed |
| | | * object definition in the specified locale. |
| | | * @throws UnsupportedOperationException |
| | | * If this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final Message getUserFriendlyPluralName(Locale locale) |
| | | throws UnsupportedOperationException { |
| | | return ManagedObjectDefinitionI18NResource.getInstance() |
| | | .getMessage(this, "user-friendly-plural-name", locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether there are any child managed object definitions which |
| | | * inherit from this managed object definition. |
| | | * |
| | | * @return Returns <code>true</code> if this type of managed object has any |
| | | * child managed object definitions, <code>false</code> otherwise. |
| | | */ |
| | | public final boolean hasChildren() { |
| | | return !children.isEmpty(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object definition has the |
| | | * specified option. |
| | | * |
| | | * @param option |
| | | * The option to test. |
| | | * @return Returns <code>true</code> if the option is set, or |
| | | * <code>false</code> otherwise. |
| | | */ |
| | | public final boolean hasOption(ManagedObjectOption option) { |
| | | return options.contains(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object definition has the |
| | | * specified tag. |
| | | * |
| | | * @param t |
| | | * The tag definition. |
| | | * @return Returns <code>true</code> if this managed object |
| | | * definition has the specified tag. |
| | | */ |
| | | public final boolean hasTag(Tag t) { |
| | | return allTags.contains(t); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object definition is a |
| | | * sub-type of the provided managed object definition. This managed |
| | | * object definition is a sub-type of the provided managed object |
| | | * definition if they are both the same or if the provided managed |
| | | * object definition can be obtained by recursive invocations of the |
| | | * {@link #getParent()} method. |
| | | * |
| | | * @param d |
| | | * The managed object definition to be checked. |
| | | * @return Returns <code>true</code> if this managed object |
| | | * definition is a sub-type of the provided managed object |
| | | * definition. |
| | | */ |
| | | public final boolean isChildOf(AbstractManagedObjectDefinition<?, ?> d) { |
| | | AbstractManagedObjectDefinition<?, ?> i; |
| | | for (i = this; i != null; i = i.parent) { |
| | | if (i == d) { |
| | | return true; |
| | | } |
| | | } |
| | | return false; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object definition is a |
| | | * super-type of the provided managed object definition. This |
| | | * managed object definition is a super-type of the provided managed |
| | | * object definition if they are both the same or if the provided |
| | | * managed object definition is a member of the set of children |
| | | * returned from {@link #getAllChildren()}. |
| | | * |
| | | * @param d |
| | | * The managed object definition to be checked. |
| | | * @return Returns <code>true</code> if this managed object |
| | | * definition is a super-type of the provided managed object |
| | | * definition. |
| | | */ |
| | | public final boolean isParentOf(AbstractManagedObjectDefinition<?, ?> d) { |
| | | return d.isChildOf(this); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object definition is the |
| | | * {@link TopCfgDefn}. |
| | | * |
| | | * @return Returns <code>true</code> if this managed object |
| | | * definition is the {@link TopCfgDefn}. |
| | | */ |
| | | public final boolean isTop() { |
| | | return (this instanceof TopCfgDefn); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Finds a sub-type of this managed object definition which most closely |
| | | * corresponds to the matching criteria of the provided definition resolver. |
| | | * |
| | | * @param r |
| | | * The definition resolver. |
| | | * @return Returns the sub-type of this managed object definition which most |
| | | * closely corresponds to the matching criteria of the provided |
| | | * definition resolver. |
| | | * @throws DefinitionDecodingException |
| | | * If no matching sub-type could be found or if the resolved |
| | | * definition was abstract. |
| | | * @see DefinitionResolver |
| | | */ |
| | | @SuppressWarnings("unchecked") |
| | | public final ManagedObjectDefinition<? extends C, ? extends S> |
| | | resolveManagedObjectDefinition( |
| | | DefinitionResolver r) throws DefinitionDecodingException { |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> rd; |
| | | rd = resolveManagedObjectDefinitionAux(this, r); |
| | | if (rd == null) { |
| | | // Unable to resolve the definition. |
| | | throw new DefinitionDecodingException(this, |
| | | Reason.WRONG_TYPE_INFORMATION); |
| | | } else if (rd instanceof ManagedObjectDefinition) { |
| | | return (ManagedObjectDefinition<? extends C, ? extends S>) rd; |
| | | } else { |
| | | // Resolved definition was abstract. |
| | | throw new DefinitionDecodingException(this, |
| | | Reason.ABSTRACT_TYPE_INFORMATION); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public final String toString() { |
| | | StringBuilder builder = new StringBuilder(); |
| | | toString(builder); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a string representation of the managed object definition to the |
| | | * provided string builder. |
| | | * |
| | | * @param builder |
| | | * The string builder where the string representation should be |
| | | * appended. |
| | | */ |
| | | public final void toString(StringBuilder builder) { |
| | | builder.append(getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Initializes all of the components associated with this managed |
| | | * object definition. |
| | | * |
| | | * @throws Exception |
| | | * If this managed object definition could not be |
| | | * initialized. |
| | | */ |
| | | protected final void initialize() throws Exception { |
| | | for (PropertyDefinition<?> pd : getAllPropertyDefinitions()) { |
| | | pd.initialize(); |
| | | pd.getDefaultBehaviorProvider().initialize(); |
| | | } |
| | | |
| | | for (RelationDefinition<?, ?> rd : getAllRelationDefinitions()) { |
| | | rd.initialize(); |
| | | } |
| | | |
| | | for (AggregationPropertyDefinition<?, ?> apd : |
| | | getAllAggregationPropertyDefinitions()) { |
| | | |
| | | apd.initialize(); |
| | | // Now register the aggregation property in the referenced managed object |
| | | // definition for reverse lookups. |
| | | registerReverseAggregationPropertyDefinition(apd); |
| | | } |
| | | |
| | | for (Constraint constraint : getAllConstraints()) { |
| | | constraint.initialize(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register a constraint with this managed object definition. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications. |
| | | * |
| | | * @param constraint |
| | | * The constraint to be registered. |
| | | */ |
| | | protected final void registerConstraint(Constraint constraint) { |
| | | constraints.add(constraint); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register a property definition with this managed object definition, |
| | | * overriding any existing property definition with the same name. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications. |
| | | * |
| | | * @param d |
| | | * The property definition to be registered. |
| | | */ |
| | | protected final void registerPropertyDefinition(PropertyDefinition<?> d) { |
| | | String propName = d.getName(); |
| | | |
| | | propertyDefinitions.put(propName, d); |
| | | allPropertyDefinitions.put(propName, d); |
| | | |
| | | if (d instanceof AggregationPropertyDefinition<?,?>) { |
| | | AggregationPropertyDefinition<?, ?> apd = |
| | | (AggregationPropertyDefinition<?, ?>) d; |
| | | aggregationPropertyDefinitions.put(propName, apd); |
| | | // The key must also contain the managed object name, since several MOs |
| | | // in an inheritance tree may aggregate the same aggregation property name |
| | | allAggregationPropertyDefinitions.put( |
| | | apd.getManagedObjectDefinition().getName() + ":" + propName, apd); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register a relation definition with this managed object definition, |
| | | * overriding any existing relation definition with the same name. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications. |
| | | * |
| | | * @param d |
| | | * The relation definition to be registered. |
| | | */ |
| | | protected final void registerRelationDefinition(RelationDefinition<?, ?> d) { |
| | | // Register the relation in this managed object definition. |
| | | String relName = d.getName(); |
| | | |
| | | relationDefinitions.put(relName, d); |
| | | allRelationDefinitions.put(relName, d); |
| | | |
| | | // Now register the relation in the referenced managed object |
| | | // definition for reverse lookups. |
| | | registerReverseRelationDefinition(d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register an option with this managed object definition. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications. |
| | | * |
| | | * @param option |
| | | * The option to be registered. |
| | | */ |
| | | protected final void registerOption(ManagedObjectOption option) { |
| | | options.add(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register a tag with this managed object definition. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications. |
| | | * |
| | | * @param tag |
| | | * The tag to be registered. |
| | | */ |
| | | protected final void registerTag(Tag tag) { |
| | | allTags.add(tag); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Deregister a constraint from the managed object definition. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications and is |
| | | * only intended for internal testing. |
| | | * |
| | | * @param constraint |
| | | * The constraint to be deregistered. |
| | | */ |
| | | final void deregisterConstraint(Constraint constraint) { |
| | | if (!constraints.remove(constraint)) { |
| | | throw new RuntimeException("Failed to deregister a constraint"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Deregister a relation definition from the managed object |
| | | * definition. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications and is |
| | | * only intended for internal testing. |
| | | * |
| | | * @param d |
| | | * The relation definition to be deregistered. |
| | | */ |
| | | final void deregisterRelationDefinition( |
| | | RelationDefinition<?, ?> d) { |
| | | // Deregister the relation from this managed object definition. |
| | | String relName = d.getName(); |
| | | relationDefinitions.remove(relName); |
| | | allRelationDefinitions.remove(relName); |
| | | |
| | | // Now deregister the relation from the referenced managed object |
| | | // definition for reverse lookups. |
| | | d.getChildDefinition().reverseRelationDefinitions.remove(d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Register this managed object definition in its parent. |
| | | * <p> |
| | | * This method <b>must not</b> be called by applications and is |
| | | * only intended for internal testing. |
| | | */ |
| | | final void registerInParent() { |
| | | if (parent != null) { |
| | | parent.children.put(name, this); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | // Register a relation definition in the referenced managed object |
| | | // definition's reverse lookup table. |
| | | private <CC extends ConfigurationClient, SS extends Configuration> |
| | | void registerReverseRelationDefinition(RelationDefinition<CC, SS> rd) { |
| | | rd.getChildDefinition().reverseRelationDefinitions.add(rd); |
| | | } |
| | | |
| | | |
| | | |
| | | // Register a aggregation property definition in the referenced managed object |
| | | // definition's reverse lookup table. |
| | | private void registerReverseAggregationPropertyDefinition( |
| | | AggregationPropertyDefinition<?, ?> apd) { |
| | | |
| | | apd.getRelationDefinition().getChildDefinition(). |
| | | reverseAggregationPropertyDefinitions.add(apd); |
| | | } |
| | | |
| | | |
| | | |
| | | // Recursively descend definition hierarchy to find the best match definition. |
| | | private AbstractManagedObjectDefinition<? extends C, ? extends S> |
| | | resolveManagedObjectDefinitionAux( |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> d, |
| | | DefinitionResolver r) { |
| | | if (!r.matches(d)) { |
| | | return null; |
| | | } |
| | | |
| | | for (AbstractManagedObjectDefinition<? extends C, ? extends S> child : d |
| | | .getChildren()) { |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> rd = |
| | | resolveManagedObjectDefinitionAux(child, r); |
| | | if (rd != null) { |
| | | return rd; |
| | | } |
| | | } |
| | | |
| | | return d; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | import org.opends.server.types.OpenDsException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Exceptions thrown when interacting with administration framework. |
| | | */ |
| | | public abstract class AdminException extends OpenDsException { |
| | | |
| | | /** |
| | | * Fake serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 1L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an admin exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected AdminException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an admin exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected AdminException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Exceptions thrown when interacting with administration framework |
| | | * that applications are not expected to catch. |
| | | */ |
| | | public abstract class AdminRuntimeException extends RuntimeException { |
| | | |
| | | /** |
| | | * Fake serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 1L; |
| | | |
| | | |
| | | |
| | | // Message that explains the problem. |
| | | private final Message message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an admin runtime exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected AdminRuntimeException(Message message, Throwable cause) { |
| | | super(message.toString(), cause); |
| | | this.message = message; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an admin runtime exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected AdminRuntimeException(Message message) { |
| | | super(message.toString()); |
| | | this.message = message; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns the message that explains the problem that occurred. |
| | | * |
| | | * @return Returns the message describing the problem that occurred |
| | | * (never <code>null</code>). |
| | | */ |
| | | public Message getMessageObject() { |
| | | return this.message; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2006-2010 Sun Microsystems, Inc. |
| | | * Portions copyright 2011-2013 ForgeRock AS |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | import static org.opends.server.loggers.ErrorLogger.logError; |
| | | import static org.opends.server.loggers.debug.DebugLogger.*; |
| | | import static org.opends.messages.AdminMessages.*; |
| | | import java.io.File; |
| | | import java.io.FileWriter; |
| | | import java.io.PrintWriter; |
| | | import java.net.InetAddress; |
| | | import java.util.ArrayList; |
| | | import java.util.List; |
| | | import java.util.SortedSet; |
| | | import java.util.TreeSet; |
| | | import javax.naming.ldap.Rdn; |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.server.ConfigurationChangeListener; |
| | | import org.opends.server.admin.server.ServerManagementContext; |
| | | import org.opends.server.admin.std.meta.LDAPConnectionHandlerCfgDefn. |
| | | SSLClientAuthPolicy; |
| | | import org.opends.server.admin.std.server.AdministrationConnectorCfg; |
| | | import org.opends.server.admin.std.server.ConnectionHandlerCfg; |
| | | import org.opends.server.admin.std.server.KeyManagerProviderCfg; |
| | | import org.opends.server.admin.std.server.FileBasedKeyManagerProviderCfg; |
| | | import org.opends.server.admin.std.server.FileBasedTrustManagerProviderCfg; |
| | | import org.opends.server.admin.std.server.LDAPConnectionHandlerCfg; |
| | | import org.opends.server.admin.std.server.RootCfg; |
| | | import org.opends.server.config.ConfigException; |
| | | import org.opends.server.core.SynchronousStrategy; |
| | | import org.opends.server.protocols.ldap.LDAPConnectionHandler; |
| | | import org.opends.server.types.AddressMask; |
| | | import org.opends.server.types.ConfigChangeResult; |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.InitializationException; |
| | | import org.opends.server.types.ResultCode; |
| | | import org.opends.server.util.CertificateManager; |
| | | import org.opends.server.util.SetupUtils; |
| | | import org.opends.server.admin.std.server.TrustManagerProviderCfg; |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.loggers.ErrorLogger; |
| | | import org.opends.server.loggers.debug.DebugTracer; |
| | | import org.opends.server.types.DebugLogLevel; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.FilePermission; |
| | | |
| | | /** |
| | | * This class is a wrapper on top of LDAPConnectionHandler to manage |
| | | * the administration connector, which is an LDAPConnectionHandler |
| | | * with specific (limited) configuration properties. |
| | | */ |
| | | public final class AdministrationConnector implements |
| | | ConfigurationChangeListener<AdministrationConnectorCfg> |
| | | { |
| | | |
| | | /** |
| | | * Default Administration Connector port. |
| | | */ |
| | | public static final int DEFAULT_ADMINISTRATION_CONNECTOR_PORT = 4444; |
| | | |
| | | /** |
| | | * Validity (in days) of the generated certificate. |
| | | */ |
| | | public static final int ADMIN_CERT_VALIDITY = 20 * 365; |
| | | |
| | | // Friendly name of the administration connector |
| | | private static final String FRIENDLY_NAME = "Administration Connector"; |
| | | |
| | | // The tracer object for the debug logger. |
| | | private static final DebugTracer TRACER = getTracer(); |
| | | |
| | | private LDAPConnectionHandler adminConnectionHandler; |
| | | |
| | | private AdministrationConnectorCfg config; // |
| | | |
| | | // Predefined values for Administration Connector configuration |
| | | // |
| | | private static final String ADMIN_CLASS_NAME = |
| | | "org.opends.server.protocols.ldap.LDAPConnectionHandler"; |
| | | |
| | | private static final boolean ADMIN_ALLOW_LDAP_V2 = false; |
| | | |
| | | private static final boolean ADMIN_ALLOW_START_TLS = false; |
| | | |
| | | private static final SortedSet<AddressMask> ADMIN_ALLOWED_CLIENT = |
| | | new TreeSet<AddressMask>(); |
| | | |
| | | private static final SortedSet<AddressMask> ADMIN_DENIED_CLIENT = |
| | | new TreeSet<AddressMask>(); |
| | | |
| | | private static final boolean ADMIN_ENABLED = true; |
| | | |
| | | private static final boolean ADMIN_KEEP_STATS = true; |
| | | |
| | | private static final boolean ADMIN_USE_SSL = true; |
| | | |
| | | private static final int ADMIN_ACCEPT_BACKLOG = 128; |
| | | |
| | | private static final boolean ADMIN_ALLOW_TCP_REUSE_ADDRESS = true; |
| | | |
| | | private static final long ADMIN_MAX_BLOCKED_WRITE_TIME_LIMIT = 120000; // 2mn |
| | | |
| | | private static final int ADMIN_MAX_REQUEST_SIZE = 5000000; // 5 Mb |
| | | |
| | | private static final int ADMIN_WRITE_BUFFER_SIZE = 4096; |
| | | |
| | | private static final int ADMIN_NUM_REQUEST_HANDLERS = 1; |
| | | |
| | | private static final boolean ADMIN_SEND_REJECTION_NOTICE = true; |
| | | |
| | | private static final boolean ADMIN_USE_TCP_KEEP_ALIVE = true; |
| | | |
| | | private static final boolean ADMIN_USE_TCP_NO_DELAY = true; |
| | | |
| | | private static final SSLClientAuthPolicy ADMIN_SSL_CLIENT_AUTH_POLICY = |
| | | SSLClientAuthPolicy.DISABLED; |
| | | |
| | | private static final SortedSet<String> ADMIN_SSL_CIPHER_SUITE = |
| | | new TreeSet<String>(); |
| | | |
| | | private static final SortedSet<String> ADMIN_SSL_PROTOCOL = |
| | | new TreeSet<String>(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Initializes this administration connector provider based on the |
| | | * information in the provided administration connector |
| | | * configuration. |
| | | * |
| | | * @param configuration |
| | | * The connection handler configuration that contains the |
| | | * information to use to initialize this connection |
| | | * handler. |
| | | * @throws ConfigException |
| | | * If an unrecoverable problem arises in the process of |
| | | * performing the initialization as a result of the server |
| | | * configuration. |
| | | * @throws InitializationException |
| | | * If a problem occurs during initialization that is not |
| | | * related to the server configuration. |
| | | */ |
| | | public void initializeAdministrationConnector( |
| | | AdministrationConnectorCfg configuration) throws ConfigException, |
| | | InitializationException |
| | | { |
| | | this.config = configuration; |
| | | |
| | | // Create a fake LDAP connection handler configuration |
| | | LDAPConnectionHandlerCfg ldapConnectionHandlerCfg = |
| | | new FakeLDAPConnectionHandlerCfg(config); |
| | | |
| | | // Administration Connector uses the LDAP connection handler |
| | | // implementation |
| | | adminConnectionHandler = new LDAPConnectionHandler( |
| | | new SynchronousStrategy(), FRIENDLY_NAME); |
| | | adminConnectionHandler |
| | | .initializeConnectionHandler(ldapConnectionHandlerCfg); |
| | | adminConnectionHandler.setAdminConnectionHandler(); |
| | | |
| | | // Register this as a change listener. |
| | | config.addChangeListener(this); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an instance of the administration connector. |
| | | */ |
| | | public AdministrationConnector() |
| | | { |
| | | // Do nothing. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the connection handler linked to this administration |
| | | * connector. |
| | | * |
| | | * @return The connection handler linked to this administration |
| | | * connector. |
| | | */ |
| | | public LDAPConnectionHandler getConnectionHandler() |
| | | { |
| | | return adminConnectionHandler; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isConfigurationChangeAcceptable( |
| | | AdministrationConnectorCfg configuration, |
| | | List<Message> unacceptableReasons) |
| | | { |
| | | LDAPConnectionHandlerCfg cfg = new FakeLDAPConnectionHandlerCfg( |
| | | configuration); |
| | | return adminConnectionHandler.isConfigurationAcceptable(cfg, |
| | | unacceptableReasons); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public ConfigChangeResult applyConfigurationChange( |
| | | AdministrationConnectorCfg configuration) |
| | | { |
| | | return new ConfigChangeResult(ResultCode.SUCCESS, true, |
| | | new ArrayList<Message>()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * This private class implements a fake LDAP connection Handler |
| | | * configuration. This allows to re-use the LDAPConnectionHandler as |
| | | * it is. |
| | | */ |
| | | private static class FakeLDAPConnectionHandlerCfg implements |
| | | LDAPConnectionHandlerCfg |
| | | { |
| | | |
| | | private final AdministrationConnectorCfg config; |
| | | |
| | | |
| | | |
| | | public FakeLDAPConnectionHandlerCfg(AdministrationConnectorCfg config) |
| | | { |
| | | this.config = config; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Class<? extends LDAPConnectionHandlerCfg> configurationClass() |
| | | { |
| | | return LDAPConnectionHandlerCfg.class; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public void addLDAPChangeListener( |
| | | ConfigurationChangeListener<LDAPConnectionHandlerCfg> listener) |
| | | { |
| | | // do nothing. change listener already added. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public void removeLDAPChangeListener( |
| | | ConfigurationChangeListener<LDAPConnectionHandlerCfg> listener) |
| | | { |
| | | // do nothing. change listener already added. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public int getAcceptBacklog() |
| | | { |
| | | return ADMIN_ACCEPT_BACKLOG; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isAllowLDAPV2() |
| | | { |
| | | return ADMIN_ALLOW_LDAP_V2; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isAllowStartTLS() |
| | | { |
| | | return ADMIN_ALLOW_START_TLS; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isAllowTCPReuseAddress() |
| | | { |
| | | return ADMIN_ALLOW_TCP_REUSE_ADDRESS; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public String getJavaClass() |
| | | { |
| | | return ADMIN_CLASS_NAME; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isKeepStats() |
| | | { |
| | | return ADMIN_KEEP_STATS; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public String getKeyManagerProvider() |
| | | { |
| | | return config.getKeyManagerProvider(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public DN getKeyManagerProviderDN() |
| | | { |
| | | return config.getKeyManagerProviderDN(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SortedSet<InetAddress> getListenAddress() |
| | | { |
| | | return config.getListenAddress(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public int getListenPort() |
| | | { |
| | | return config.getListenPort(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public long getMaxBlockedWriteTimeLimit() |
| | | { |
| | | return ADMIN_MAX_BLOCKED_WRITE_TIME_LIMIT; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public long getMaxRequestSize() |
| | | { |
| | | return ADMIN_MAX_REQUEST_SIZE; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public long getBufferSize() |
| | | { |
| | | return ADMIN_WRITE_BUFFER_SIZE; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Integer getNumRequestHandlers() |
| | | { |
| | | return ADMIN_NUM_REQUEST_HANDLERS; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isSendRejectionNotice() |
| | | { |
| | | return ADMIN_SEND_REJECTION_NOTICE; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public String getSSLCertNickname() |
| | | { |
| | | return config.getSSLCertNickname(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SortedSet<String> getSSLCipherSuite() |
| | | { |
| | | return config.getSSLCipherSuite(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SSLClientAuthPolicy getSSLClientAuthPolicy() |
| | | { |
| | | return ADMIN_SSL_CLIENT_AUTH_POLICY; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SortedSet<String> getSSLProtocol() |
| | | { |
| | | return config.getSSLProtocol(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public String getTrustManagerProvider() |
| | | { |
| | | return config.getTrustManagerProvider(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public DN getTrustManagerProviderDN() |
| | | { |
| | | return config.getTrustManagerProviderDN(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isUseSSL() |
| | | { |
| | | return ADMIN_USE_SSL; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isUseTCPKeepAlive() |
| | | { |
| | | return ADMIN_USE_TCP_KEEP_ALIVE; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isUseTCPNoDelay() |
| | | { |
| | | return ADMIN_USE_TCP_NO_DELAY; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public void addChangeListener( |
| | | ConfigurationChangeListener<ConnectionHandlerCfg> listener) |
| | | { |
| | | // do nothing. change listener already added. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public void removeChangeListener( |
| | | ConfigurationChangeListener<ConnectionHandlerCfg> listener) |
| | | { |
| | | // do nothing. change listener already added. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SortedSet<AddressMask> getAllowedClient() |
| | | { |
| | | return ADMIN_ALLOWED_CLIENT; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public SortedSet<AddressMask> getDeniedClient() |
| | | { |
| | | return ADMIN_DENIED_CLIENT; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isEnabled() |
| | | { |
| | | return ADMIN_ENABLED; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public DN dn() |
| | | { |
| | | return config.dn(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a self-signed JKS certificate if needed. |
| | | * |
| | | * @throws InitializationException |
| | | * If an unexpected error occurred whilst trying to create the |
| | | * certificate. |
| | | */ |
| | | public static void createSelfSignedCertificateIfNeeded() |
| | | throws InitializationException |
| | | { |
| | | try |
| | | { |
| | | RootCfg root = ServerManagementContext.getInstance() |
| | | .getRootConfiguration(); |
| | | AdministrationConnectorCfg config = root.getAdministrationConnector(); |
| | | |
| | | // Check if certificate generation is needed |
| | | String certAlias = config.getSSLCertNickname(); |
| | | KeyManagerProviderCfg keyMgrConfig = root.getKeyManagerProvider(config |
| | | .getKeyManagerProvider()); |
| | | TrustManagerProviderCfg trustMgrConfig = root |
| | | .getTrustManagerProvider(config.getTrustManagerProvider()); |
| | | |
| | | if (hasDefaultConfigChanged(keyMgrConfig, trustMgrConfig)) |
| | | { |
| | | // nothing to do |
| | | return; |
| | | } |
| | | |
| | | FileBasedKeyManagerProviderCfg fbKeyManagerConfig = |
| | | (FileBasedKeyManagerProviderCfg) keyMgrConfig; |
| | | String keystorePath = getFullPath(fbKeyManagerConfig.getKeyStoreFile()); |
| | | FileBasedTrustManagerProviderCfg fbTrustManagerConfig = |
| | | (FileBasedTrustManagerProviderCfg) trustMgrConfig; |
| | | String truststorePath = getFullPath(fbTrustManagerConfig |
| | | .getTrustStoreFile()); |
| | | String pinFilePath = getFullPath(fbKeyManagerConfig.getKeyStorePinFile()); |
| | | |
| | | // Check that either we do not have any file, |
| | | // or we have the 3 required files (keystore, truststore, pin |
| | | // file) |
| | | boolean keystore = false; |
| | | boolean truststore = false; |
| | | boolean pinFile = false; |
| | | int nbFiles = 0; |
| | | if (new File(keystorePath).exists()) |
| | | { |
| | | keystore = true; |
| | | nbFiles++; |
| | | } |
| | | if (new File(truststorePath).exists()) |
| | | { |
| | | truststore = true; |
| | | nbFiles++; |
| | | } |
| | | if (new File(pinFilePath).exists()) |
| | | { |
| | | pinFile = true; |
| | | nbFiles++; |
| | | } |
| | | if (nbFiles == 3) |
| | | { |
| | | // nothing to do |
| | | return; |
| | | } |
| | | if (nbFiles != 0) |
| | | { |
| | | // 1 or 2 files are missing : error |
| | | String err = ""; |
| | | if (!keystore) |
| | | { |
| | | err += keystorePath + " "; |
| | | } |
| | | if (!truststore) |
| | | { |
| | | err += truststorePath + " "; |
| | | } |
| | | if (!pinFile) |
| | | { |
| | | err += pinFilePath + " "; |
| | | } |
| | | Message message = ERR_ADMIN_CERTIFICATE_GENERATION_MISSING_FILES |
| | | .get(err); |
| | | logError(message); |
| | | throw new InitializationException(message); |
| | | } |
| | | |
| | | // Generate a password |
| | | String pwd = new String(SetupUtils.createSelfSignedCertificatePwd()); |
| | | |
| | | // Generate a self-signed certificate |
| | | CertificateManager certManager = new CertificateManager( |
| | | getFullPath(fbKeyManagerConfig.getKeyStoreFile()), fbKeyManagerConfig |
| | | .getKeyStoreType(), pwd); |
| | | String hostName = |
| | | SetupUtils.getHostNameForCertificate(DirectoryServer.getServerRoot()); |
| | | String subjectDN = "cn=" |
| | | + Rdn.escapeValue(hostName) + ",O=" |
| | | + FRIENDLY_NAME + " Self-Signed Certificate"; |
| | | certManager.generateSelfSignedCertificate(certAlias, subjectDN, |
| | | ADMIN_CERT_VALIDITY); |
| | | |
| | | // Export the certificate |
| | | String tempCertPath = getFullPath("config" + File.separator |
| | | + "admin-cert.txt"); |
| | | SetupUtils.exportCertificate(certManager, certAlias, tempCertPath); |
| | | |
| | | // Create a new trust store and import the server certificate |
| | | // into it |
| | | CertificateManager trustManager = new CertificateManager(truststorePath, |
| | | CertificateManager.KEY_STORE_TYPE_JKS, pwd); |
| | | trustManager.addCertificate(certAlias, new File(tempCertPath)); |
| | | |
| | | // Generate a password file |
| | | if (!new File(pinFilePath).exists()) |
| | | { |
| | | FileWriter file = new FileWriter(pinFilePath); |
| | | PrintWriter out = new PrintWriter(file); |
| | | out.println(pwd); |
| | | out.flush(); |
| | | out.close(); |
| | | file.close(); |
| | | } |
| | | |
| | | // Change the password file permission if possible |
| | | if (FilePermission.canSetPermissions()) |
| | | { |
| | | try |
| | | { |
| | | if (!FilePermission.setPermissions(new File(pinFilePath), |
| | | new FilePermission(0600))) |
| | | { |
| | | // Log a warning that the permissions were not set. |
| | | Message message = WARN_ADMIN_SET_PERMISSIONS_FAILED |
| | | .get(pinFilePath); |
| | | ErrorLogger.logError(message); |
| | | } |
| | | } |
| | | catch (DirectoryException e) |
| | | { |
| | | // Log a warning that the permissions were not set. |
| | | Message message = WARN_ADMIN_SET_PERMISSIONS_FAILED.get(pinFilePath); |
| | | ErrorLogger.logError(message); |
| | | } |
| | | } |
| | | |
| | | // Delete the exported certificate |
| | | File f = new File(tempCertPath); |
| | | f.delete(); |
| | | } |
| | | catch (InitializationException e) |
| | | { |
| | | throw e; |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | if (debugEnabled()) |
| | | { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | Message message = ERR_ADMIN_CERTIFICATE_GENERATION.get(e.getMessage()); |
| | | logError(message); |
| | | throw new InitializationException(message); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Check if default configuration for administrator's key manager and trust |
| | | * manager provider has changed. |
| | | * |
| | | * @param keyConfig |
| | | * key manager provider configuration |
| | | * @param trustConfig |
| | | * trust manager provider configuration |
| | | * @return true if default configuration has changed, false otherwise |
| | | */ |
| | | private static boolean hasDefaultConfigChanged( |
| | | KeyManagerProviderCfg keyConfig, TrustManagerProviderCfg trustConfig) |
| | | { |
| | | if (keyConfig.isEnabled() |
| | | && (keyConfig instanceof FileBasedKeyManagerProviderCfg) |
| | | && trustConfig.isEnabled() |
| | | && (trustConfig instanceof FileBasedTrustManagerProviderCfg)) |
| | | { |
| | | FileBasedKeyManagerProviderCfg fileKeyConfig = |
| | | (FileBasedKeyManagerProviderCfg) keyConfig; |
| | | boolean pinIsProvidedByFileOnly = |
| | | (fileKeyConfig.getKeyStorePinFile() != null) |
| | | && (fileKeyConfig.getKeyStorePin() == null) |
| | | && (fileKeyConfig.getKeyStorePinEnvironmentVariable() == null) |
| | | && (fileKeyConfig.getKeyStorePinProperty() == null); |
| | | return !pinIsProvidedByFileOnly; |
| | | } |
| | | return true; |
| | | } |
| | | |
| | | private static String getFullPath(String path) |
| | | { |
| | | File file = new File(path); |
| | | if (!file.isAbsolute()) |
| | | { |
| | | path = DirectoryServer.getInstanceRoot() + File.separator + path; |
| | | } |
| | | |
| | | return path; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2006-2008 Sun Microsystems, Inc. |
| | | * Portions Copyright 2012 ForgeRock AS |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.protocols.internal.InternalClientConnection; |
| | | import org.opends.server.protocols.internal.InternalSearchOperation; |
| | | import org.opends.server.protocols.ldap.LDAPFilter; |
| | | import org.opends.server.schema.DirectoryStringSyntax; |
| | | import org.opends.server.types.Attribute; |
| | | import org.opends.server.types.AttributeType; |
| | | import org.opends.server.types.Attributes; |
| | | import org.opends.server.types.ByteString; |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.DereferencePolicy; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.Entry; |
| | | import org.opends.server.types.LDAPException; |
| | | import org.opends.server.types.Modification; |
| | | import org.opends.server.types.ModificationType; |
| | | import org.opends.server.types.ResultCode; |
| | | import org.opends.server.types.SearchResultEntry; |
| | | import org.opends.server.types.SearchScope; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check if information found in "cn=admin data" is coherent with |
| | | * cn=config. If and inconsistency is detected, we log a warning |
| | | * message and update "cn=admin data" |
| | | */ |
| | | public final class AdministrationDataSync |
| | | { |
| | | |
| | | /** |
| | | * The root connection. |
| | | */ |
| | | private InternalClientConnection internalConnection; |
| | | |
| | | /** |
| | | * The attribute name used to store the port. TODO Use the default |
| | | * one. |
| | | */ |
| | | private static final String LDAP_PORT = "ds-cfg-listen-port"; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an object that will syncrhonize configuration and the |
| | | * admin data. |
| | | * |
| | | * @param internalConnection |
| | | * The root connection. |
| | | */ |
| | | public AdministrationDataSync(InternalClientConnection internalConnection) |
| | | { |
| | | this.internalConnection = internalConnection; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check if information found in "cn=admin data" is coherent with |
| | | * cn=config. If and inconsistancy is detected, we log a warning |
| | | * message and update "cn=admin data" |
| | | */ |
| | | public void synchronize() |
| | | { |
| | | // Check if the admin connector is in sync |
| | | checkAdminConnector(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check if the admin connector is in sync. The desynchronization |
| | | * could occurs after the upgrade from 1.0. |
| | | */ |
| | | private void checkAdminConnector() |
| | | { |
| | | // Look for the server registration in "cn=admin data" |
| | | DN serverEntryDN = searchServerEntry(); |
| | | if (serverEntryDN == null) |
| | | { |
| | | // Nothing to do |
| | | return; |
| | | } |
| | | |
| | | // Get the admin port |
| | | String adminPort = getAttr("cn=Administration Connector,cn=config", |
| | | LDAP_PORT); |
| | | if (adminPort == null) |
| | | { |
| | | // best effort. |
| | | return; |
| | | } |
| | | |
| | | LinkedList<Modification> mods = new LinkedList<Modification>(); |
| | | // adminport |
| | | String attName = "adminport"; |
| | | AttributeType attrType = DirectoryServer.getAttributeType(attName |
| | | .toLowerCase()); |
| | | if (attrType == null) |
| | | { |
| | | attrType = DirectoryServer.getDefaultAttributeType(attName.toLowerCase()); |
| | | } |
| | | mods.add(new Modification(ModificationType.REPLACE, Attributes.create( |
| | | attrType, adminPort))); |
| | | |
| | | // adminEnabled |
| | | attName = "adminEnabled"; |
| | | attrType = DirectoryServer.getAttributeType(attName.toLowerCase()); |
| | | if (attrType == null) |
| | | { |
| | | attrType = DirectoryServer.getDefaultAttributeType(attName.toLowerCase()); |
| | | } |
| | | mods.add(new Modification(ModificationType.REPLACE, Attributes.create( |
| | | attrType, "true"))); |
| | | |
| | | // Process modification |
| | | internalConnection.processModify(serverEntryDN, mods); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Look for the DN of the local register server. Assumption: default |
| | | * Connection Handler naming is used. |
| | | * |
| | | * @return The DN of the local register server or null. |
| | | */ |
| | | private DN searchServerEntry() |
| | | { |
| | | DN returnDN = null; |
| | | |
| | | // Get the LDAP and LDAPS port |
| | | String ldapPort = getAttr( |
| | | "cn=LDAP Connection Handler,cn=Connection Handlers,cn=config", |
| | | LDAP_PORT); |
| | | String ldapsPort = getAttr( |
| | | "cn=LDAPS Connection Handler,cn=Connection Handlers,cn=config", |
| | | LDAP_PORT); |
| | | boolean ldapsPortEnable = false; |
| | | String val = getAttr( |
| | | "cn=LDAPS Connection Handler,cn=Connection Handlers,cn=config", |
| | | "ds-cfg-enabled"); |
| | | if (val != null) |
| | | { |
| | | ldapsPortEnable = val.toLowerCase().equals("true"); |
| | | } |
| | | if ((ldapPort == null) && (ldapsPort == null)) |
| | | { |
| | | // best effort (see assumption) |
| | | return null; |
| | | } |
| | | |
| | | // Get the IP address of the local host. |
| | | String hostName; |
| | | try |
| | | { |
| | | hostName = java.net.InetAddress.getLocalHost().getCanonicalHostName(); |
| | | } |
| | | catch (Throwable t) |
| | | { |
| | | // best effort. |
| | | return null; |
| | | } |
| | | |
| | | // Look for a local server with the Ldap Port. |
| | | String attrName = "hostname"; |
| | | AttributeType hostnameType = DirectoryServer.getAttributeType(attrName); |
| | | if (hostnameType == null) |
| | | { |
| | | hostnameType = DirectoryServer.getDefaultAttributeType(attrName); |
| | | } |
| | | try |
| | | { |
| | | InternalSearchOperation op = internalConnection.processSearch( |
| | | "cn=Servers,cn=admin data", |
| | | SearchScope.SINGLE_LEVEL, "objectclass=*"); |
| | | if (op.getResultCode() == ResultCode.SUCCESS) |
| | | { |
| | | Entry entry = null; |
| | | for (Entry currentEntry : op.getSearchEntries()) |
| | | { |
| | | String currentHostname = currentEntry.getAttributeValue(hostnameType, |
| | | DirectoryStringSyntax.DECODER); |
| | | try |
| | | { |
| | | String currentIPAddress = java.net.InetAddress.getByName( |
| | | currentHostname).getCanonicalHostName(); |
| | | if (currentIPAddress.equals(hostName)) |
| | | { |
| | | // Check if one of the port match |
| | | attrName = "ldapport"; |
| | | AttributeType portType = DirectoryServer |
| | | .getAttributeType(attrName); |
| | | if (portType == null) |
| | | { |
| | | portType = DirectoryServer.getDefaultAttributeType(attrName); |
| | | } |
| | | String currentport = currentEntry.getAttributeValue(portType, |
| | | DirectoryStringSyntax.DECODER); |
| | | if (currentport.equals(ldapPort)) |
| | | { |
| | | entry = currentEntry; |
| | | break; |
| | | } |
| | | if (ldapsPortEnable) |
| | | { |
| | | attrName = "ldapsport"; |
| | | portType = DirectoryServer.getAttributeType(attrName); |
| | | if (portType == null) |
| | | { |
| | | portType = DirectoryServer.getDefaultAttributeType(attrName); |
| | | } |
| | | currentport = currentEntry.getAttributeValue(portType, |
| | | DirectoryStringSyntax.DECODER); |
| | | if (currentport.equals(ldapsPort)) |
| | | { |
| | | entry = currentEntry; |
| | | break; |
| | | } |
| | | } |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | // best effort. |
| | | continue; |
| | | } |
| | | } |
| | | |
| | | if (entry != null) |
| | | { |
| | | returnDN = entry.getDN(); |
| | | } |
| | | } |
| | | |
| | | } |
| | | catch (DirectoryException e) |
| | | { |
| | | // never happens because the filter is always valid. |
| | | return null; |
| | | } |
| | | return returnDN; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets an attribute value from an entry. |
| | | * |
| | | * @param DN |
| | | * The DN of the entry. |
| | | * @param attrName |
| | | * The attribute name. |
| | | * @return The attribute value or {@code null} if the value could |
| | | * not be retrieved. |
| | | */ |
| | | private String getAttr(String baseDN, String attrName) |
| | | { |
| | | // Prepare the ldap search |
| | | LDAPFilter filter; |
| | | try |
| | | { |
| | | filter = LDAPFilter.decode("objectclass=*"); |
| | | } |
| | | catch (LDAPException e) |
| | | { |
| | | // can not happen |
| | | // best effort. |
| | | // TODO Log an Error. |
| | | return null; |
| | | } |
| | | |
| | | LinkedHashSet<String> attributes = new LinkedHashSet<String>(1); |
| | | attributes.add(attrName); |
| | | InternalSearchOperation search = internalConnection.processSearch( |
| | | ByteString.valueOf(baseDN), SearchScope.BASE_OBJECT, |
| | | DereferencePolicy.DEREF_ALWAYS, 0, 0, false, filter, attributes); |
| | | |
| | | if ((search.getResultCode() != ResultCode.SUCCESS)) |
| | | { |
| | | // can not happen |
| | | // best effort. |
| | | // TODO Log an Error. |
| | | return null; |
| | | } |
| | | |
| | | SearchResultEntry adminConnectorEntry = null; |
| | | |
| | | /* |
| | | * Read the port from the PORT attribute |
| | | */ |
| | | LinkedList<SearchResultEntry> result = search.getSearchEntries(); |
| | | if (!result.isEmpty()) |
| | | { |
| | | adminConnectorEntry = result.getFirst(); |
| | | } |
| | | |
| | | AttributeType attrType = DirectoryServer.getAttributeType(attrName); |
| | | if (attrType == null) |
| | | { |
| | | attrType = DirectoryServer.getDefaultAttributeType(attrName); |
| | | } |
| | | |
| | | List<Attribute> attrs = adminConnectorEntry.getAttribute(attrType); |
| | | |
| | | if (attrs == null) |
| | | { |
| | | // can not happen |
| | | // best effort. |
| | | // TODO Log an Error. |
| | | return null; |
| | | } |
| | | |
| | | // Get the attribute value |
| | | return attrs.get(0).iterator().next().toString(); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import java.util.Locale; |
| | | import java.util.MissingResourceException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Defines an optional action which administators must perform after |
| | | * they have modified a property. By default modifications to |
| | | * properties are assumed to take effect immediately and require no |
| | | * additional administrative action. Developers should be aware that, |
| | | * where feasible, they should implement components such that property |
| | | * modifications require no additional administrative action. This is |
| | | * required in order to minimize server downtime during administration |
| | | * and provide a more user-friendly experience. |
| | | */ |
| | | public final class AdministratorAction { |
| | | |
| | | /** |
| | | * Specifies the type of administrator action which must be |
| | | * performed in order for pending changes to take effect. |
| | | */ |
| | | public static enum Type { |
| | | /** |
| | | * Used when modifications to a property require a component |
| | | * restart in order to take effect (usually by disabling and |
| | | * re-enabling the component). May have a description describing |
| | | * any additional administrator action that is required when the |
| | | * component is restarted. |
| | | */ |
| | | COMPONENT_RESTART("component-restart"), |
| | | |
| | | /** |
| | | * Used when modifications to a property take effect immediately, |
| | | * and no additional administrator action is required. May have a |
| | | * description describing how changes to the modified property |
| | | * will take effect. |
| | | */ |
| | | NONE("none"), |
| | | |
| | | /** |
| | | * Used when modifications to a property require an additional |
| | | * administrative action in order to take effect. This should be |
| | | * used when neither a server restart nor a component restart are |
| | | * applicable. Always has a description which describes the |
| | | * additional administrator action which is required when the |
| | | * property is modified. |
| | | */ |
| | | OTHER("other"), |
| | | |
| | | /** |
| | | * Used when modifications to a property require a server restart |
| | | * in order to take effect. May have a description describing any |
| | | * additional administrator action that is required when the |
| | | * component is restarted. |
| | | */ |
| | | SERVER_RESTART("server-restart"); |
| | | |
| | | // The user-friendly name of the type. |
| | | private final String name; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private Type(String name) { |
| | | this.name = name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String toString() { |
| | | return name; |
| | | } |
| | | |
| | | } |
| | | |
| | | // The managed object definition associated with this administrator |
| | | // action. |
| | | private final AbstractManagedObjectDefinition<?, ?> definition; |
| | | |
| | | // The name of the property definition associated with this |
| | | // administrator action. |
| | | private final String propertyName; |
| | | |
| | | // The type of administration action. |
| | | private final Type type; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new administrator action. |
| | | * |
| | | * @param type |
| | | * The type of this administration action. |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * administrator action. |
| | | * @param propertyName |
| | | * The name of the property definition associated with this |
| | | * administrator action. |
| | | */ |
| | | public AdministratorAction(Type type, |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | this.type = type; |
| | | this.definition = d; |
| | | this.propertyName = propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this administrator action in the default |
| | | * locale. |
| | | * |
| | | * @return Returns the synopsis of this administrator action in the |
| | | * default locale, or <code>null</code> if there is no |
| | | * synopsis defined. |
| | | */ |
| | | public final Message getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this administrator action in the specified |
| | | * locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this administrator action in the |
| | | * specified locale, or <code>null</code> if there is no |
| | | * synopsis defined. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + propertyName |
| | | + ".requires-admin-action.synopsis"; |
| | | try { |
| | | return resource.getMessage(definition, property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the type of this administrator action. |
| | | * |
| | | * @return Returns the type of this administrator action. |
| | | */ |
| | | public final Type getType() { |
| | | return type; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2007-2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | import static org.opends.server.loggers.debug.DebugLogger.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.EnumSet; |
| | | import java.util.HashMap; |
| | | import java.util.Iterator; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | import java.util.SortedSet; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.client.AuthorizationException; |
| | | import org.opends.server.admin.client.ClientConstraintHandler; |
| | | import org.opends.server.admin.client.CommunicationException; |
| | | import org.opends.server.admin.client.ManagedObject; |
| | | import org.opends.server.admin.client.ManagedObjectDecodingException; |
| | | import org.opends.server.admin.client.ManagementContext; |
| | | import org.opends.server.admin.condition.Condition; |
| | | import org.opends.server.admin.condition.Conditions; |
| | | import org.opends.server.admin.server.ConfigurationDeleteListener; |
| | | import org.opends.server.admin.server.ServerConstraintHandler; |
| | | import org.opends.server.admin.server.ServerManagedObject; |
| | | import org.opends.server.admin.server.ServerManagedObjectChangeListener; |
| | | import org.opends.server.admin.server.ServerManagementContext; |
| | | import org.opends.server.admin.std.meta.RootCfgDefn; |
| | | import org.opends.server.config.ConfigException; |
| | | import org.opends.server.loggers.ErrorLogger; |
| | | import org.opends.server.loggers.debug.DebugTracer; |
| | | import org.opends.server.types.ConfigChangeResult; |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.DebugLogLevel; |
| | | import org.opends.server.types.ResultCode; |
| | | import org.opends.server.util.StaticUtils; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Aggregation property definition. |
| | | * <p> |
| | | * An aggregation property names one or more managed objects which are |
| | | * required by the managed object associated with this property. An |
| | | * aggregation property definition takes care to perform referential |
| | | * integrity checks: referenced managed objects cannot be deleted. Nor |
| | | * can an aggregation reference non-existent managed objects. |
| | | * Referential integrity checks are <b>not</b> performed during value |
| | | * validation. Instead they are performed when changes to the managed |
| | | * object are committed. |
| | | * <p> |
| | | * An aggregation property definition can optionally identify two |
| | | * properties: |
| | | * <ul> |
| | | * <li>an <code>enabled</code> property in the aggregated managed |
| | | * object - the property must be a {@link BooleanPropertyDefinition} |
| | | * and indicate whether the aggregated managed object is enabled or |
| | | * not. If specified, the administration framework will prevent the |
| | | * aggregated managed object from being disabled while it is |
| | | * referenced |
| | | * <li>an <code>enabled</code> property in this property's managed |
| | | * object - the property must be a {@link BooleanPropertyDefinition} |
| | | * and indicate whether this property's managed object is enabled or |
| | | * not. If specified, and as long as there is an equivalent |
| | | * <code>enabled</code> property defined for the aggregated managed |
| | | * object, the <code>enabled</code> property in the aggregated |
| | | * managed object will only be checked when this property is true. |
| | | * </ul> |
| | | * In other words, these properties can be used to make sure that |
| | | * referenced managed objects are not disabled while they are |
| | | * referenced. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * aggregation property definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * aggregation property definition refers to. |
| | | */ |
| | | public final class AggregationPropertyDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends PropertyDefinition<String> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing aggregation property |
| | | * definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | */ |
| | | public static class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractBuilder<String, AggregationPropertyDefinition<C, S>> { |
| | | |
| | | // The string representation of the managed object path specifying |
| | | // the parent of the aggregated managed objects. |
| | | private String parentPathString = null; |
| | | |
| | | // The name of a relation in the parent managed object which |
| | | // contains the aggregated managed objects. |
| | | private String rdName = null; |
| | | |
| | | // The condition which is used to determine if a referenced |
| | | // managed object is enabled. |
| | | private Condition targetIsEnabledCondition = Conditions.TRUE; |
| | | |
| | | // The condition which is used to determine whether or not |
| | | // referenced managed objects need to be enabled. |
| | | private Condition targetNeedsEnablingCondition = Conditions.TRUE; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the name of the managed object which is the parent of the |
| | | * aggregated managed objects. |
| | | * <p> |
| | | * This must be defined before the property definition can be |
| | | * built. |
| | | * |
| | | * @param pathString |
| | | * The string representation of the managed object path |
| | | * specifying the parent of the aggregated managed |
| | | * objects. |
| | | */ |
| | | public final void setParentPath(String pathString) { |
| | | this.parentPathString = pathString; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the relation in the parent managed object which contains |
| | | * the aggregated managed objects. |
| | | * <p> |
| | | * This must be defined before the property definition can be |
| | | * built. |
| | | * |
| | | * @param rdName |
| | | * The name of a relation in the parent managed object |
| | | * which contains the aggregated managed objects. |
| | | */ |
| | | public final void setRelationDefinition(String rdName) { |
| | | this.rdName = rdName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the condition which is used to determine if a referenced |
| | | * managed object is enabled. By default referenced managed |
| | | * objects are assumed to always be enabled. |
| | | * |
| | | * @param condition |
| | | * The condition which is used to determine if a |
| | | * referenced managed object is enabled. |
| | | */ |
| | | public final void setTargetIsEnabledCondition(Condition condition) { |
| | | this.targetIsEnabledCondition = condition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the condition which is used to determine whether or not |
| | | * referenced managed objects need to be enabled. By default |
| | | * referenced managed objects must always be enabled. |
| | | * |
| | | * @param condition |
| | | * The condition which is used to determine whether or |
| | | * not referenced managed objects need to be enabled. |
| | | */ |
| | | public final void setTargetNeedsEnablingCondition(Condition condition) { |
| | | this.targetNeedsEnablingCondition = condition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected AggregationPropertyDefinition<C, S> buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior) { |
| | | // Make sure that the parent path has been defined. |
| | | if (parentPathString == null) { |
| | | throw new IllegalStateException("Parent path undefined"); |
| | | } |
| | | |
| | | // Make sure that the relation definition has been defined. |
| | | if (rdName == null) { |
| | | throw new IllegalStateException("Relation definition undefined"); |
| | | } |
| | | |
| | | return new AggregationPropertyDefinition<C, S>(d, propertyName, options, |
| | | adminAction, defaultBehavior, parentPathString, rdName, |
| | | targetNeedsEnablingCondition, targetIsEnabledCondition); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A change listener which prevents the named component from being |
| | | * disabled. |
| | | */ |
| | | private class ReferentialIntegrityChangeListener implements |
| | | ServerManagedObjectChangeListener<S> { |
| | | |
| | | // The error message which should be returned if an attempt is |
| | | // made to disable the referenced component. |
| | | private final Message message; |
| | | |
| | | // The path of the referenced component. |
| | | private final ManagedObjectPath<C, S> path; |
| | | |
| | | |
| | | |
| | | // Creates a new referential integrity delete listener. |
| | | private ReferentialIntegrityChangeListener(ManagedObjectPath<C, S> path, |
| | | Message message) { |
| | | this.path = path; |
| | | this.message = message; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public ConfigChangeResult applyConfigurationChange( |
| | | ServerManagedObject<? extends S> mo) { |
| | | try { |
| | | if (targetIsEnabledCondition.evaluate(mo)) { |
| | | return new ConfigChangeResult(ResultCode.SUCCESS, false); |
| | | } |
| | | } catch (ConfigException e) { |
| | | // This should not happen - ignore it and throw an exception |
| | | // anyway below. |
| | | } |
| | | |
| | | // This should not happen - the previous call-back should have |
| | | // trapped this. |
| | | throw new IllegalStateException("Attempting to disable a referenced " |
| | | + relationDefinition.getChildDefinition().getUserFriendlyName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isConfigurationChangeAcceptable( |
| | | ServerManagedObject<? extends S> mo, |
| | | List<Message> unacceptableReasons) { |
| | | // Always prevent the referenced component from being |
| | | // disabled. |
| | | try { |
| | | if (!targetIsEnabledCondition.evaluate(mo)) { |
| | | unacceptableReasons.add(message); |
| | | return false; |
| | | } else { |
| | | return true; |
| | | } |
| | | } catch (ConfigException e) { |
| | | // The condition could not be evaluated. |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_REFINT_UNABLE_TO_EVALUATE_TARGET_CONDITION.get(mo |
| | | .getManagedObjectDefinition().getUserFriendlyName(), String |
| | | .valueOf(mo.getDN()), StaticUtils.getExceptionMessage(e)); |
| | | ErrorLogger.logError(message); |
| | | unacceptableReasons.add(message); |
| | | return false; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | // Gets the path associated with this listener. |
| | | private ManagedObjectPath<C, S> getManagedObjectPath() { |
| | | return path; |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A delete listener which prevents the named component from being |
| | | * deleted. |
| | | */ |
| | | private class ReferentialIntegrityDeleteListener implements |
| | | ConfigurationDeleteListener<S> { |
| | | |
| | | // The DN of the referenced configuration entry. |
| | | private final DN dn; |
| | | |
| | | // The error message which should be returned if an attempt is |
| | | // made to delete the referenced component. |
| | | private final Message message; |
| | | |
| | | |
| | | |
| | | // Creates a new referential integrity delete listener. |
| | | private ReferentialIntegrityDeleteListener(DN dn, Message message) { |
| | | this.dn = dn; |
| | | this.message = message; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public ConfigChangeResult applyConfigurationDelete(S configuration) { |
| | | // This should not happen - the |
| | | // isConfigurationDeleteAcceptable() call-back should have |
| | | // trapped this. |
| | | if (configuration.dn().equals(dn)) { |
| | | // This should not happen - the |
| | | // isConfigurationDeleteAcceptable() call-back should have |
| | | // trapped this. |
| | | throw new IllegalStateException("Attempting to delete a referenced " |
| | | + relationDefinition.getChildDefinition().getUserFriendlyName()); |
| | | } else { |
| | | return new ConfigChangeResult(ResultCode.SUCCESS, false); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public boolean isConfigurationDeleteAcceptable(S configuration, |
| | | List<Message> unacceptableReasons) { |
| | | if (configuration.dn().equals(dn)) { |
| | | // Always prevent deletion of the referenced component. |
| | | unacceptableReasons.add(message); |
| | | return false; |
| | | } |
| | | |
| | | return true; |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * The server-side constraint handler implementation. |
| | | */ |
| | | private class ServerHandler extends ServerConstraintHandler { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isUsable(ServerManagedObject<?> managedObject, |
| | | Collection<Message> unacceptableReasons) throws ConfigException { |
| | | SortedSet<String> names = managedObject |
| | | .getPropertyValues(AggregationPropertyDefinition.this); |
| | | ServerManagementContext context = ServerManagementContext.getInstance(); |
| | | Message thisUFN = managedObject.getManagedObjectDefinition() |
| | | .getUserFriendlyName(); |
| | | String thisDN = managedObject.getDN().toString(); |
| | | Message thatUFN = getRelationDefinition().getUserFriendlyName(); |
| | | |
| | | boolean isUsable = true; |
| | | boolean needsEnabling = targetNeedsEnablingCondition |
| | | .evaluate(managedObject); |
| | | for (String name : names) { |
| | | ManagedObjectPath<C, S> path = getChildPath(name); |
| | | String thatDN = path.toDN().toString(); |
| | | |
| | | if (!context.managedObjectExists(path)) { |
| | | Message msg = ERR_SERVER_REFINT_DANGLING_REFERENCE.get(name, |
| | | getName(), thisUFN, thisDN, thatUFN, thatDN); |
| | | unacceptableReasons.add(msg); |
| | | isUsable = false; |
| | | } else if (needsEnabling) { |
| | | // Check that the referenced component is enabled if |
| | | // required. |
| | | ServerManagedObject<? extends S> ref = context.getManagedObject(path); |
| | | if (!targetIsEnabledCondition.evaluate(ref)) { |
| | | Message msg = ERR_SERVER_REFINT_TARGET_DISABLED.get(name, |
| | | getName(), thisUFN, thisDN, thatUFN, thatDN); |
| | | unacceptableReasons.add(msg); |
| | | isUsable = false; |
| | | } |
| | | } |
| | | } |
| | | |
| | | return isUsable; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void performPostAdd(ServerManagedObject<?> managedObject) |
| | | throws ConfigException { |
| | | // First make sure existing listeners associated with this |
| | | // managed object are removed. This is required in order to |
| | | // prevent multiple change listener registrations from |
| | | // occurring, for example if this call-back is invoked multiple |
| | | // times after the same add event. |
| | | performPostDelete(managedObject); |
| | | |
| | | // Add change and delete listeners against all referenced |
| | | // components. |
| | | Message thisUFN = managedObject.getManagedObjectDefinition() |
| | | .getUserFriendlyName(); |
| | | String thisDN = managedObject.getDN().toString(); |
| | | Message thatUFN = getRelationDefinition().getUserFriendlyName(); |
| | | |
| | | // Referenced managed objects will only need a change listener |
| | | // if they have can be disabled. |
| | | boolean needsChangeListeners = targetNeedsEnablingCondition |
| | | .evaluate(managedObject); |
| | | |
| | | // Delete listeners need to be registered against the parent |
| | | // entry of the referenced components. |
| | | ServerManagementContext context = ServerManagementContext.getInstance(); |
| | | ManagedObjectPath<?, ?> parentPath = getParentPath(); |
| | | ServerManagedObject<?> parent = context.getManagedObject(parentPath); |
| | | |
| | | // Create entries in the listener tables. |
| | | List<ReferentialIntegrityDeleteListener> dlist = |
| | | new LinkedList<ReferentialIntegrityDeleteListener>(); |
| | | deleteListeners.put(managedObject.getDN(), dlist); |
| | | |
| | | List<ReferentialIntegrityChangeListener> clist = |
| | | new LinkedList<ReferentialIntegrityChangeListener>(); |
| | | changeListeners.put(managedObject.getDN(), clist); |
| | | |
| | | for (String name : managedObject |
| | | .getPropertyValues(AggregationPropertyDefinition.this)) { |
| | | ManagedObjectPath<C, S> path = getChildPath(name); |
| | | DN dn = path.toDN(); |
| | | String thatDN = dn.toString(); |
| | | |
| | | // Register the delete listener. |
| | | Message msg = ERR_SERVER_REFINT_CANNOT_DELETE.get(thatUFN, thatDN, |
| | | getName(), thisUFN, thisDN); |
| | | ReferentialIntegrityDeleteListener dl = |
| | | new ReferentialIntegrityDeleteListener(dn, msg); |
| | | parent.registerDeleteListener(getRelationDefinition(), dl); |
| | | dlist.add(dl); |
| | | |
| | | // Register the change listener if required. |
| | | if (needsChangeListeners) { |
| | | ServerManagedObject<? extends S> ref = context.getManagedObject(path); |
| | | msg = ERR_SERVER_REFINT_CANNOT_DISABLE.get(thatUFN, thatDN, |
| | | getName(), thisUFN, thisDN); |
| | | ReferentialIntegrityChangeListener cl = |
| | | new ReferentialIntegrityChangeListener(path, msg); |
| | | ref.registerChangeListener(cl); |
| | | clist.add(cl); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void performPostDelete(ServerManagedObject<?> managedObject) |
| | | throws ConfigException { |
| | | // Remove any registered delete and change listeners. |
| | | ServerManagementContext context = ServerManagementContext.getInstance(); |
| | | DN dn = managedObject.getDN(); |
| | | |
| | | // Delete listeners need to be deregistered against the parent |
| | | // entry of the referenced components. |
| | | ManagedObjectPath<?, ?> parentPath = getParentPath(); |
| | | ServerManagedObject<?> parent = context.getManagedObject(parentPath); |
| | | if (deleteListeners.containsKey(dn)) { |
| | | for (ReferentialIntegrityDeleteListener dl : deleteListeners.get(dn)) { |
| | | parent.deregisterDeleteListener(getRelationDefinition(), dl); |
| | | } |
| | | deleteListeners.remove(dn); |
| | | } |
| | | |
| | | // Change listeners need to be deregistered from their |
| | | // associated referenced component. |
| | | if (changeListeners.containsKey(dn)) { |
| | | for (ReferentialIntegrityChangeListener cl : changeListeners.get(dn)) { |
| | | ManagedObjectPath<C, S> path = cl.getManagedObjectPath(); |
| | | ServerManagedObject<? extends S> ref = context.getManagedObject(path); |
| | | ref.deregisterChangeListener(cl); |
| | | } |
| | | changeListeners.remove(dn); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void performPostModify(ServerManagedObject<?> managedObject) |
| | | throws ConfigException { |
| | | // Remove all the constraints associated with this managed |
| | | // object and then re-register them. |
| | | performPostDelete(managedObject); |
| | | performPostAdd(managedObject); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * The client-side constraint handler implementation which enforces |
| | | * referential integrity when aggregating managed objects are added |
| | | * or modified. |
| | | */ |
| | | private class SourceClientHandler extends ClientConstraintHandler { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isAddAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | // If all of this managed object's "enabled" properties are true |
| | | // then any referenced managed objects must also be enabled. |
| | | boolean needsEnabling = targetNeedsEnablingCondition.evaluate(context, |
| | | managedObject); |
| | | |
| | | // Check the referenced managed objects exist and, if required, |
| | | // are enabled. |
| | | boolean isAcceptable = true; |
| | | Message ufn = getRelationDefinition().getUserFriendlyName(); |
| | | for (String name : managedObject |
| | | .getPropertyValues(AggregationPropertyDefinition.this)) { |
| | | // Retrieve the referenced managed object and make sure it |
| | | // exists. |
| | | ManagedObjectPath<?, ?> path = getChildPath(name); |
| | | ManagedObject<?> ref; |
| | | try { |
| | | ref = context.getManagedObject(path); |
| | | } catch (DefinitionDecodingException e) { |
| | | Message msg = ERR_CLIENT_REFINT_TARGET_INVALID.get(ufn, name, |
| | | getName(), e.getMessageObject()); |
| | | unacceptableReasons.add(msg); |
| | | isAcceptable = false; |
| | | continue; |
| | | } catch (ManagedObjectDecodingException e) { |
| | | Message msg = ERR_CLIENT_REFINT_TARGET_INVALID.get(ufn, name, |
| | | getName(), e.getMessageObject()); |
| | | unacceptableReasons.add(msg); |
| | | isAcceptable = false; |
| | | continue; |
| | | } catch (ManagedObjectNotFoundException e) { |
| | | Message msg = ERR_CLIENT_REFINT_TARGET_DANGLING_REFERENCE.get(ufn, |
| | | name, getName()); |
| | | unacceptableReasons.add(msg); |
| | | isAcceptable = false; |
| | | continue; |
| | | } |
| | | |
| | | // Make sure the reference managed object is enabled. |
| | | if (needsEnabling) { |
| | | if (!targetIsEnabledCondition.evaluate(context, ref)) { |
| | | Message msg = ERR_CLIENT_REFINT_TARGET_DISABLED.get(ufn, name, |
| | | getName()); |
| | | unacceptableReasons.add(msg); |
| | | isAcceptable = false; |
| | | } |
| | | } |
| | | } |
| | | return isAcceptable; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isModifyAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | // The same constraint applies as for adds. |
| | | return isAddAcceptable(context, managedObject, unacceptableReasons); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * The client-side constraint handler implementation which enforces |
| | | * referential integrity when aggregated managed objects are deleted |
| | | * or modified. |
| | | */ |
| | | private class TargetClientHandler extends ClientConstraintHandler { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isDeleteAcceptable(ManagementContext context, |
| | | ManagedObjectPath<?, ?> path, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | // Any references to the deleted managed object should cause a |
| | | // constraint violation. |
| | | boolean isAcceptable = true; |
| | | for (ManagedObject<?> mo : findReferences(context, |
| | | getManagedObjectDefinition(), path.getName())) { |
| | | String name = mo.getManagedObjectPath().getName(); |
| | | if (name == null) { |
| | | Message msg = ERR_CLIENT_REFINT_CANNOT_DELETE_WITHOUT_NAME.get( |
| | | getName(), mo.getManagedObjectDefinition().getUserFriendlyName(), |
| | | getManagedObjectDefinition().getUserFriendlyName()); |
| | | unacceptableReasons.add(msg); |
| | | } else { |
| | | Message msg = ERR_CLIENT_REFINT_CANNOT_DELETE_WITH_NAME.get( |
| | | getName(), mo.getManagedObjectDefinition().getUserFriendlyName(), |
| | | name, getManagedObjectDefinition().getUserFriendlyName()); |
| | | unacceptableReasons.add(msg); |
| | | } |
| | | isAcceptable = false; |
| | | } |
| | | return isAcceptable; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isModifyAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | // If the modified managed object is disabled and there are some |
| | | // active references then refuse the change. |
| | | if (targetIsEnabledCondition.evaluate(context, managedObject)) { |
| | | return true; |
| | | } |
| | | |
| | | // The referenced managed object is disabled. Need to check for |
| | | // active references. |
| | | boolean isAcceptable = true; |
| | | for (ManagedObject<?> mo : findReferences(context, |
| | | getManagedObjectDefinition(), managedObject.getManagedObjectPath() |
| | | .getName())) { |
| | | if (targetNeedsEnablingCondition.evaluate(context, mo)) { |
| | | String name = mo.getManagedObjectPath().getName(); |
| | | if (name == null) { |
| | | Message msg = ERR_CLIENT_REFINT_CANNOT_DISABLE_WITHOUT_NAME.get( |
| | | managedObject.getManagedObjectDefinition() |
| | | .getUserFriendlyName(), getName(), mo |
| | | .getManagedObjectDefinition().getUserFriendlyName()); |
| | | unacceptableReasons.add(msg); |
| | | } else { |
| | | Message msg = ERR_CLIENT_REFINT_CANNOT_DISABLE_WITH_NAME.get( |
| | | managedObject.getManagedObjectDefinition() |
| | | .getUserFriendlyName(), getName(), mo |
| | | .getManagedObjectDefinition().getUserFriendlyName(), name); |
| | | unacceptableReasons.add(msg); |
| | | } |
| | | isAcceptable = false; |
| | | } |
| | | } |
| | | return isAcceptable; |
| | | } |
| | | |
| | | |
| | | |
| | | // Find all managed objects which reference the named managed |
| | | // object using this property. |
| | | private <CC extends ConfigurationClient> |
| | | List<ManagedObject<? extends CC>> findReferences( |
| | | ManagementContext context, AbstractManagedObjectDefinition<CC, ?> mod, |
| | | String name) throws AuthorizationException, CommunicationException { |
| | | List<ManagedObject<? extends CC>> instances = findInstances(context, mod); |
| | | |
| | | Iterator<ManagedObject<? extends CC>> i = instances.iterator(); |
| | | while (i.hasNext()) { |
| | | ManagedObject<? extends CC> mo = i.next(); |
| | | boolean hasReference = false; |
| | | |
| | | for (String value : mo |
| | | .getPropertyValues(AggregationPropertyDefinition.this)) { |
| | | if (compare(value, name) == 0) { |
| | | hasReference = true; |
| | | break; |
| | | } |
| | | } |
| | | |
| | | if (!hasReference) { |
| | | i.remove(); |
| | | } |
| | | } |
| | | |
| | | return instances; |
| | | } |
| | | |
| | | |
| | | |
| | | // Find all instances of a specific type of managed object. |
| | | @SuppressWarnings("unchecked") |
| | | private <CC extends ConfigurationClient> |
| | | List<ManagedObject<? extends CC>> findInstances( |
| | | ManagementContext context, AbstractManagedObjectDefinition<CC, ?> mod) |
| | | throws AuthorizationException, CommunicationException { |
| | | List<ManagedObject<? extends CC>> instances = |
| | | new LinkedList<ManagedObject<? extends CC>>(); |
| | | |
| | | if (mod == RootCfgDefn.getInstance()) { |
| | | instances.add((ManagedObject<? extends CC>) context |
| | | .getRootConfigurationManagedObject()); |
| | | } else { |
| | | for (RelationDefinition<? super CC, ?> rd : mod |
| | | .getAllReverseRelationDefinitions()) { |
| | | for (ManagedObject<?> parent : findInstances(context, rd |
| | | .getParentDefinition())) { |
| | | try { |
| | | if (rd instanceof SingletonRelationDefinition) { |
| | | SingletonRelationDefinition<? super CC, ?> srd = |
| | | (SingletonRelationDefinition<? super CC, ?>) rd; |
| | | ManagedObject<?> mo = parent.getChild(srd); |
| | | if (mo.getManagedObjectDefinition().isChildOf(mod)) { |
| | | instances.add((ManagedObject<? extends CC>) mo); |
| | | } |
| | | } else if (rd instanceof OptionalRelationDefinition) { |
| | | OptionalRelationDefinition<? super CC, ?> ord = |
| | | (OptionalRelationDefinition<? super CC, ?>) rd; |
| | | ManagedObject<?> mo = parent.getChild(ord); |
| | | if (mo.getManagedObjectDefinition().isChildOf(mod)) { |
| | | instances.add((ManagedObject<? extends CC>) mo); |
| | | } |
| | | } else if (rd instanceof InstantiableRelationDefinition) { |
| | | InstantiableRelationDefinition<? super CC, ?> ird = |
| | | (InstantiableRelationDefinition<? super CC, ?>) rd; |
| | | |
| | | for (String name : parent.listChildren(ird)) { |
| | | ManagedObject<?> mo = parent.getChild(ird, name); |
| | | if (mo.getManagedObjectDefinition().isChildOf(mod)) { |
| | | instances.add((ManagedObject<? extends CC>) mo); |
| | | } |
| | | } |
| | | } |
| | | } catch (OperationsException e) { |
| | | // Ignore all operations exceptions. |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | return instances; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * The tracer object for the debug logger. |
| | | */ |
| | | private static final DebugTracer TRACER = getTracer(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates an aggregation property definition builder. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new aggregation property definition builder. |
| | | */ |
| | | public static <C extends ConfigurationClient, S extends Configuration> |
| | | Builder<C, S> createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder<C, S>(d, propertyName); |
| | | } |
| | | |
| | | // The active server-side referential integrity change listeners |
| | | // associated with this property. |
| | | private final Map<DN, List<ReferentialIntegrityChangeListener>> |
| | | changeListeners = new HashMap<DN, |
| | | List<ReferentialIntegrityChangeListener>>(); |
| | | |
| | | // The active server-side referential integrity delete listeners |
| | | // associated with this property. |
| | | private final Map<DN, List<ReferentialIntegrityDeleteListener>> |
| | | deleteListeners = new HashMap<DN, |
| | | List<ReferentialIntegrityDeleteListener>>(); |
| | | |
| | | // The name of the managed object which is the parent of the |
| | | // aggregated managed objects. |
| | | private ManagedObjectPath<?, ?> parentPath; |
| | | |
| | | // The string representation of the managed object path specifying |
| | | // the parent of the aggregated managed objects. |
| | | private final String parentPathString; |
| | | |
| | | // The name of a relation in the parent managed object which |
| | | // contains the aggregated managed objects. |
| | | private final String rdName; |
| | | |
| | | // The relation in the parent managed object which contains the |
| | | // aggregated managed objects. |
| | | private InstantiableRelationDefinition<C, S> relationDefinition; |
| | | |
| | | // The source constraint. |
| | | private final Constraint sourceConstraint; |
| | | |
| | | // The condition which is used to determine if a referenced managed |
| | | // object is enabled. |
| | | private final Condition targetIsEnabledCondition; |
| | | |
| | | // The condition which is used to determine whether or not |
| | | // referenced managed objects need to be enabled. |
| | | private final Condition targetNeedsEnablingCondition; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private AggregationPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior, String parentPathString, |
| | | String rdName, Condition targetNeedsEnablingCondition, |
| | | Condition targetIsEnabledCondition) { |
| | | super(d, String.class, propertyName, options, adminAction, defaultBehavior); |
| | | |
| | | this.parentPathString = parentPathString; |
| | | this.rdName = rdName; |
| | | this.targetNeedsEnablingCondition = targetNeedsEnablingCondition; |
| | | this.targetIsEnabledCondition = targetIsEnabledCondition; |
| | | this.sourceConstraint = new Constraint() { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ClientConstraintHandler> getClientConstraintHandlers() { |
| | | ClientConstraintHandler handler = new SourceClientHandler(); |
| | | return Collections.singleton(handler); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ServerConstraintHandler> getServerConstraintHandlers() { |
| | | ServerConstraintHandler handler = new ServerHandler(); |
| | | return Collections.singleton(handler); |
| | | } |
| | | }; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitAggregation(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, String value, P p) { |
| | | return v.visitAggregation(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | validateValue(value); |
| | | return value; |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Constructs a DN for a referenced managed object having the |
| | | * provided name. This method is implemented by first calling |
| | | * {@link #getChildPath(String)} and then invoking |
| | | * {@code ManagedObjectPath.toDN()} on the returned path. |
| | | * |
| | | * @param name |
| | | * The name of the child managed object. |
| | | * @return Returns a DN for a referenced managed object having the |
| | | * provided name. |
| | | */ |
| | | public final DN getChildDN(String name) { |
| | | return getChildPath(name).toDN(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Constructs a managed object path for a referenced managed object |
| | | * having the provided name. |
| | | * |
| | | * @param name |
| | | * The name of the child managed object. |
| | | * @return Returns a managed object path for a referenced managed |
| | | * object having the provided name. |
| | | */ |
| | | public final ManagedObjectPath<C, S> getChildPath(String name) { |
| | | return parentPath.child(relationDefinition, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the name of the managed object which is the parent of the |
| | | * aggregated managed objects. |
| | | * |
| | | * @return Returns the name of the managed object which is the |
| | | * parent of the aggregated managed objects. |
| | | */ |
| | | public final ManagedObjectPath<?, ?> getParentPath() { |
| | | return parentPath; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the relation in the parent managed object which contains the |
| | | * aggregated managed objects. |
| | | * |
| | | * @return Returns the relation in the parent managed object which |
| | | * contains the aggregated managed objects. |
| | | */ |
| | | public final InstantiableRelationDefinition<C, S> getRelationDefinition() { |
| | | return relationDefinition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the constraint which should be enforced on the aggregating |
| | | * managed object. |
| | | * |
| | | * @return Returns the constraint which should be enforced on the |
| | | * aggregating managed object. |
| | | */ |
| | | public final Constraint getSourceConstraint() { |
| | | return sourceConstraint; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional constraint synopsis of this aggregation |
| | | * property definition in the default locale. The constraint |
| | | * synopsis describes when and how referenced managed objects must |
| | | * be enabled. When there are no constraints between the source |
| | | * managed object and the objects it references through this |
| | | * aggregation, <code>null</code> is returned. |
| | | * |
| | | * @return Returns the optional constraint synopsis of this |
| | | * aggregation property definition in the default locale, or |
| | | * <code>null</code> if there is no constraint synopsis. |
| | | */ |
| | | public final Message getSourceConstraintSynopsis() { |
| | | return getSourceConstraintSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional constraint synopsis of this aggregation |
| | | * property definition in the specified locale.The constraint |
| | | * synopsis describes when and how referenced managed objects must |
| | | * be enabled. When there are no constraints between the source |
| | | * managed object and the objects it references through this |
| | | * aggregation, <code>null</code> is returned. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the optional constraint synopsis of this |
| | | * aggregation property definition in the specified locale, |
| | | * or <code>null</code> if there is no constraint |
| | | * synopsis. |
| | | */ |
| | | public final Message getSourceConstraintSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + getName() |
| | | + ".syntax.aggregation.constraint-synopsis"; |
| | | try { |
| | | return resource |
| | | .getMessage(getManagedObjectDefinition(), property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the condition which is used to determine if a referenced |
| | | * managed object is enabled. |
| | | * |
| | | * @return Returns the condition which is used to determine if a |
| | | * referenced managed object is enabled. |
| | | */ |
| | | public final Condition getTargetIsEnabledCondition() { |
| | | return targetIsEnabledCondition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the condition which is used to determine whether or not |
| | | * referenced managed objects need to be enabled. |
| | | * |
| | | * @return Returns the condition which is used to determine whether |
| | | * or not referenced managed objects need to be enabled. |
| | | */ |
| | | public final Condition getTargetNeedsEnablingCondition() { |
| | | return targetNeedsEnablingCondition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String normalizeValue(String value) |
| | | throws IllegalPropertyValueException { |
| | | try { |
| | | Reference<C, S> reference = Reference.parseName(parentPath, |
| | | relationDefinition, value); |
| | | return reference.getNormalizedName(); |
| | | } catch (IllegalArgumentException e) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | super.toString(builder); |
| | | |
| | | builder.append(" parentPath="); |
| | | builder.append(parentPath); |
| | | |
| | | builder.append(" relationDefinition="); |
| | | builder.append(relationDefinition.getName()); |
| | | |
| | | builder.append(" targetNeedsEnablingCondition="); |
| | | builder.append(String.valueOf(targetNeedsEnablingCondition)); |
| | | |
| | | builder.append(" targetIsEnabledCondition="); |
| | | builder.append(String.valueOf(targetIsEnabledCondition)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(String value) throws IllegalPropertyValueException { |
| | | try { |
| | | Reference.parseName(parentPath, relationDefinition, value); |
| | | } catch (IllegalArgumentException e) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @SuppressWarnings("unchecked") |
| | | @Override |
| | | public void initialize() throws Exception { |
| | | // Decode the path. |
| | | parentPath = ManagedObjectPath.valueOf(parentPathString); |
| | | |
| | | // Decode the relation definition. |
| | | AbstractManagedObjectDefinition<?, ?> parent = parentPath |
| | | .getManagedObjectDefinition(); |
| | | RelationDefinition<?, ?> rd = parent.getRelationDefinition(rdName); |
| | | relationDefinition = (InstantiableRelationDefinition<C, S>) rd; |
| | | |
| | | // Now decode the conditions. |
| | | targetNeedsEnablingCondition.initialize(getManagedObjectDefinition()); |
| | | targetIsEnabledCondition.initialize(rd.getChildDefinition()); |
| | | |
| | | // Register a client-side constraint with the referenced |
| | | // definition. This will be used to enforce referential integrity |
| | | // for actions performed against referenced managed objects. |
| | | Constraint constraint = new Constraint() { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ClientConstraintHandler> getClientConstraintHandlers() { |
| | | ClientConstraintHandler handler = new TargetClientHandler(); |
| | | return Collections.singleton(handler); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ServerConstraintHandler> getServerConstraintHandlers() { |
| | | return Collections.emptyList(); |
| | | } |
| | | }; |
| | | |
| | | rd.getChildDefinition().registerConstraint(constraint); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | import java.util.Locale; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default behavior provider which indicates special behavior. It should be |
| | | * used by properties which have a default behavior which cannot be directly |
| | | * represented using real values of the property. For example, a property |
| | | * containing a set of user names might default to "all users" when no values |
| | | * are provided. This meaning cannot be represented using a finite set of |
| | | * values. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public final class AliasDefaultBehaviorProvider<T> extends |
| | | DefaultBehaviorProvider<T> { |
| | | |
| | | // The managed object definition associated with this default |
| | | // behavior. |
| | | private final AbstractManagedObjectDefinition<?, ?> definition; |
| | | |
| | | // The name of the property definition associated with this default |
| | | // behavior. |
| | | private final String propertyName; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an alias default behavior provider. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * default behavior. |
| | | * @param propertyName |
| | | * The name of the property definition associated with this |
| | | * default behavior. |
| | | */ |
| | | public AliasDefaultBehaviorProvider( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | this.definition = d; |
| | | this.propertyName = propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <R, P> R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p) { |
| | | return v.visitAlias(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this alias default behavior in the |
| | | * default locale. |
| | | * |
| | | * @return Returns the synopsis of this alias default behavior in |
| | | * the default locale. |
| | | */ |
| | | public final Message getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this alias default behavior in the specified |
| | | * locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this alias default behavior in |
| | | * the specified locale. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + propertyName |
| | | + ".default-behavior.alias.synopsis"; |
| | | return resource.getMessage(definition, property, locale); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | import org.forgerock.opendj.ldap.schema.AttributeType; |
| | | import org.opends.server.core.DirectoryServer; |
| | | |
| | | /** |
| | | * Attribute type property definition. |
| | | */ |
| | | public final class AttributeTypePropertyDefinition extends |
| | | PropertyDefinition<AttributeType> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing attribute type |
| | | * property definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<AttributeType, AttributeTypePropertyDefinition> { |
| | | |
| | | // Private constructor |
| | | private Builder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected AttributeTypePropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<AttributeType> defaultBehavior) { |
| | | return new AttributeTypePropertyDefinition(d, propertyName, |
| | | options, adminAction, defaultBehavior); |
| | | } |
| | | } |
| | | |
| | | // Flag indicating whether or not attribute type names should be |
| | | // validated against the schema. |
| | | private static boolean isCheckSchema = true; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a attribute type property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new attribute type property definition |
| | | * builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not attribute type names should be |
| | | * validated against the schema. |
| | | * |
| | | * @return Returns <code>true</code> if attribute type names |
| | | * should be validated against the schema. |
| | | */ |
| | | public static boolean isCheckSchema() { |
| | | return isCheckSchema; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specify whether or not attribute type names should be validated |
| | | * against the schema. |
| | | * <p> |
| | | * By default validation is switched on. |
| | | * |
| | | * @param value |
| | | * <code>true</code> if attribute type names should be |
| | | * validated against the schema. |
| | | */ |
| | | public static void setCheckSchema(boolean value) { |
| | | isCheckSchema = value; |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private AttributeTypePropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<AttributeType> defaultBehavior) { |
| | | super(d, AttributeType.class, propertyName, options, |
| | | adminAction, defaultBehavior); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitAttributeType(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, |
| | | AttributeType value, P p) { |
| | | return v.visitAttributeType(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(AttributeType o1, AttributeType o2) { |
| | | return o1.getNameOrOID().compareToIgnoreCase(o2.getNameOrOID()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public AttributeType decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | String name = value.trim().toLowerCase(); |
| | | AttributeType type = DirectoryServer.getAttributeType(name, |
| | | !isCheckSchema); |
| | | |
| | | if (type == null) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } else { |
| | | try { |
| | | validateValue(type); |
| | | return type; |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String encodeValue(AttributeType value) |
| | | throws IllegalPropertyValueException { |
| | | return value.getNameOrOID(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(AttributeType value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No implementation required. |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | import java.util.HashMap; |
| | | import java.util.Map; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Boolean property definition. |
| | | */ |
| | | public final class BooleanPropertyDefinition extends |
| | | PropertyDefinition<Boolean> { |
| | | |
| | | /** |
| | | * Mapping used for parsing boolean values. This mapping is more flexible than |
| | | * the standard boolean string parser and supports common true/false synonyms |
| | | * used in configuration. |
| | | */ |
| | | private static final Map<String, Boolean> VALUE_MAP; |
| | | static { |
| | | VALUE_MAP = new HashMap<String, Boolean>(); |
| | | |
| | | // We could have more possibilities but decided against in issue 1960. |
| | | VALUE_MAP.put("false", Boolean.FALSE); |
| | | VALUE_MAP.put("true", Boolean.TRUE); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing boolean property definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<Boolean, BooleanPropertyDefinition> { |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected BooleanPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Boolean> defaultBehavior) { |
| | | return new BooleanPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a boolean property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new boolean property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private BooleanPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Boolean> defaultBehavior) { |
| | | super(d, Boolean.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(Boolean value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No additional validation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Boolean decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | String nvalue = value.trim().toLowerCase(); |
| | | Boolean b = VALUE_MAP.get(nvalue); |
| | | |
| | | if (b == null) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } else { |
| | | return b; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitBoolean(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, Boolean value, P p) { |
| | | return v.visitBoolean(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(Boolean o1, Boolean o2) { |
| | | return o1.compareTo(o2); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | * Portions copyright 2012 ForgeRock AS. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | import static org.opends.messages.ExtensionMessages.*; |
| | | import static org.opends.server.loggers.ErrorLogger.*; |
| | | import static org.opends.server.loggers.debug.DebugLogger.*; |
| | | import static org.opends.server.util.StaticUtils.*; |
| | | import static org.opends.server.util.ServerConstants.EOL; |
| | | |
| | | import java.io.ByteArrayOutputStream; |
| | | import java.io.BufferedReader; |
| | | import java.io.File; |
| | | import java.io.FileFilter; |
| | | import java.io.IOException; |
| | | import java.io.InputStream; |
| | | import java.io.InputStreamReader; |
| | | import java.io.PrintStream; |
| | | import java.lang.reflect.Method; |
| | | import java.net.MalformedURLException; |
| | | import java.net.URL; |
| | | import java.net.URLClassLoader; |
| | | import java.util.ArrayList; |
| | | import java.util.HashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Set; |
| | | import java.util.jar.Attributes; |
| | | import java.util.jar.JarEntry; |
| | | import java.util.jar.JarFile; |
| | | import java.util.jar.Manifest; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.std.meta.RootCfgDefn; |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.loggers.debug.DebugTracer; |
| | | import org.opends.server.types.DebugLogLevel; |
| | | import org.opends.server.types.InitializationException; |
| | | import org.opends.server.util.Validator; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Manages the class loader which should be used for loading |
| | | * configuration definition classes and associated extensions. |
| | | * <p> |
| | | * For extensions which define their own extended configuration |
| | | * definitions, the class loader will make sure that the configuration |
| | | * definition classes are loaded and initialized. |
| | | * <p> |
| | | * Initially the class loader provider is disabled, and calls to the |
| | | * {@link #getClassLoader()} will return the system default class |
| | | * loader. |
| | | * <p> |
| | | * Applications <b>MUST NOT</b> maintain persistent references to the |
| | | * class loader as it can change at run-time. |
| | | */ |
| | | public final class ClassLoaderProvider { |
| | | |
| | | /** |
| | | * The tracer object for the debug logger. |
| | | */ |
| | | private static final DebugTracer TRACER = getTracer(); |
| | | |
| | | /** |
| | | * Private URLClassLoader implementation. This is only required so |
| | | * that we can provide access to the addURL method. |
| | | */ |
| | | private static final class MyURLClassLoader extends URLClassLoader { |
| | | |
| | | /** |
| | | * Create a class loader with the default parent class loader. |
| | | */ |
| | | public MyURLClassLoader() { |
| | | super(new URL[0]); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a class loader with the provided parent class loader. |
| | | * |
| | | * @param parent |
| | | * The parent class loader. |
| | | */ |
| | | public MyURLClassLoader(ClassLoader parent) { |
| | | super(new URL[0], parent); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add a Jar file to this class loader. |
| | | * |
| | | * @param jarFile |
| | | * The name of the Jar file. |
| | | * @throws MalformedURLException |
| | | * If a protocol handler for the URL could not be found, |
| | | * or if some other error occurred while constructing |
| | | * the URL. |
| | | * @throws SecurityException |
| | | * If a required system property value cannot be |
| | | * accessed. |
| | | */ |
| | | public void addJarFile(File jarFile) throws SecurityException, |
| | | MalformedURLException { |
| | | addURL(jarFile.toURI().toURL()); |
| | | } |
| | | |
| | | } |
| | | |
| | | // The name of the manifest file listing the core configuration |
| | | // definition classes. |
| | | private static final String CORE_MANIFEST = "core.manifest"; |
| | | |
| | | // The name of the manifest file listing a extension's configuration |
| | | // definition classes. |
| | | private static final String EXTENSION_MANIFEST = "extension.manifest"; |
| | | |
| | | // The name of the lib directory. |
| | | private static final String LIB_DIR = "lib"; |
| | | |
| | | // The name of the extensions directory. |
| | | private static final String EXTENSIONS_DIR = "extensions"; |
| | | |
| | | // The singleton instance. |
| | | private static final ClassLoaderProvider INSTANCE = new ClassLoaderProvider(); |
| | | |
| | | // Attribute name in jar's MANIFEST corresponding to the revision number. |
| | | private static final String REVISION_NUMBER = "Revision-Number"; |
| | | |
| | | // The attribute names for build information is name, version and revision |
| | | // number |
| | | private static final String[] BUILD_INFORMATION_ATTRIBUTE_NAMES = |
| | | new String[]{Attributes.Name.EXTENSION_NAME.toString(), |
| | | Attributes.Name.IMPLEMENTATION_VERSION.toString(), |
| | | REVISION_NUMBER}; |
| | | |
| | | |
| | | /** |
| | | * Get the single application wide class loader provider instance. |
| | | * |
| | | * @return Returns the single application wide class loader provider |
| | | * instance. |
| | | */ |
| | | public static ClassLoaderProvider getInstance() { |
| | | return INSTANCE; |
| | | } |
| | | |
| | | // Set of registered Jar files. |
| | | private Set<File> jarFiles = new HashSet<File>(); |
| | | |
| | | // Underlying class loader used to load classes and resources (null |
| | | // if disabled). |
| | | // |
| | | // We contain a reference to the URLClassLoader rather than |
| | | // sub-class it so that it is possible to replace the loader at |
| | | // run-time. For example, when removing or replacing extension Jar |
| | | // files (the URLClassLoader only supports adding new |
| | | // URLs, not removal). |
| | | private MyURLClassLoader loader = null; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private ClassLoaderProvider() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add the named extensions to this class loader provider. |
| | | * |
| | | * @param extensions |
| | | * The names of the extensions to be loaded. The names |
| | | * should not contain any path elements and must be located |
| | | * within the extensions folder. |
| | | * @throws InitializationException |
| | | * If one of the extensions could not be loaded and |
| | | * initialized. |
| | | * @throws IllegalStateException |
| | | * If this class loader provider is disabled. |
| | | * @throws IllegalArgumentException |
| | | * If one of the extension names was not a single relative |
| | | * path name element or was an absolute path. |
| | | */ |
| | | public synchronized void addExtension(String... extensions) |
| | | throws InitializationException, IllegalStateException, |
| | | IllegalArgumentException { |
| | | Validator.ensureNotNull(extensions); |
| | | |
| | | if (loader == null) { |
| | | throw new IllegalStateException( |
| | | "Class loader provider is disabled."); |
| | | } |
| | | |
| | | File libPath = new File(DirectoryServer.getInstanceRoot(), LIB_DIR); |
| | | File extensionsPath = new File(libPath, EXTENSIONS_DIR); |
| | | |
| | | ArrayList<File> files = new ArrayList<File>(extensions.length); |
| | | for (String extension : extensions) { |
| | | File file = new File(extensionsPath, extension); |
| | | |
| | | // For security reasons we need to make sure that the file name |
| | | // passed in did not contain any path elements and names a file |
| | | // in the extensions folder. |
| | | |
| | | // Can handle potential null parent. |
| | | if (!extensionsPath.equals(file.getParentFile())) { |
| | | throw new IllegalArgumentException("Illegal file name: " |
| | | + extension); |
| | | } |
| | | |
| | | // The file is valid. |
| | | files.add(file); |
| | | } |
| | | |
| | | // Add the extensions. |
| | | addExtension(files.toArray(new File[files.size()])); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Disable this class loader provider and removed any registered |
| | | * extensions. |
| | | * |
| | | * @throws IllegalStateException |
| | | * If this class loader provider is already disabled. |
| | | */ |
| | | public synchronized void disable() throws IllegalStateException { |
| | | if (loader == null) { |
| | | throw new IllegalStateException( |
| | | "Class loader provider already disabled."); |
| | | } |
| | | loader = null; |
| | | jarFiles = new HashSet<File>(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Enable this class loader provider using the application's |
| | | * class loader as the parent class loader. |
| | | * |
| | | * @throws InitializationException |
| | | * If the class loader provider could not initialize |
| | | * successfully. |
| | | * @throws IllegalStateException |
| | | * If this class loader provider is already enabled. |
| | | */ |
| | | public synchronized void enable() throws InitializationException, |
| | | IllegalStateException { |
| | | enable(RootCfgDefn.class.getClassLoader()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Enable this class loader provider using the provided parent class |
| | | * loader. |
| | | * |
| | | * @param parent |
| | | * The parent class loader. |
| | | * @throws InitializationException |
| | | * If the class loader provider could not initialize |
| | | * successfully. |
| | | * @throws IllegalStateException |
| | | * If this class loader provider is already enabled. |
| | | */ |
| | | public synchronized void enable(ClassLoader parent) |
| | | throws InitializationException, IllegalStateException { |
| | | if (loader != null) { |
| | | throw new IllegalStateException( |
| | | "Class loader provider already enabled."); |
| | | } |
| | | |
| | | if (parent != null) { |
| | | loader = new MyURLClassLoader(parent); |
| | | } else { |
| | | loader = new MyURLClassLoader(); |
| | | } |
| | | |
| | | // Forcefully load all configuration definition classes in |
| | | // OpenDS.jar. |
| | | initializeCoreComponents(); |
| | | |
| | | // Put extensions jars into the class loader and load all |
| | | // configuration definition classes in that they contain. |
| | | // First load the extension from the install directory, then |
| | | // from the instance directory. |
| | | File libDir ; |
| | | File installExtensionsPath ; |
| | | File instanceExtensionsPath ; |
| | | |
| | | |
| | | // load install dir extension |
| | | libDir = new File(DirectoryServer.getServerRoot(), LIB_DIR); |
| | | try |
| | | { |
| | | installExtensionsPath = |
| | | new File(libDir, EXTENSIONS_DIR).getCanonicalFile(); |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | installExtensionsPath = new File(libDir, EXTENSIONS_DIR); |
| | | } |
| | | initializeAllExtensions(installExtensionsPath); |
| | | |
| | | // load instance dir extension |
| | | libDir = new File(DirectoryServer.getInstanceRoot(),LIB_DIR); |
| | | try |
| | | { |
| | | instanceExtensionsPath = |
| | | new File(libDir, EXTENSIONS_DIR).getCanonicalFile(); |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | instanceExtensionsPath = new File(libDir, EXTENSIONS_DIR); |
| | | } |
| | | if (! installExtensionsPath.getAbsolutePath().equals( |
| | | instanceExtensionsPath.getAbsolutePath())) |
| | | { |
| | | initializeAllExtensions(instanceExtensionsPath); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the class loader which should be used for loading classes |
| | | * and resources. When this class loader provider is disabled, the |
| | | * system default class loader will be returned by default. |
| | | * <p> |
| | | * Applications <b>MUST NOT</b> maintain persistent references to |
| | | * the class loader as it can change at run-time. |
| | | * |
| | | * @return Returns the class loader which should be used for loading |
| | | * classes and resources. |
| | | */ |
| | | public synchronized ClassLoader getClassLoader() { |
| | | if (loader != null) { |
| | | return loader; |
| | | } else { |
| | | return ClassLoader.getSystemClassLoader(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this class loader provider is enabled. |
| | | * |
| | | * @return Returns <code>true</code> if this class loader provider |
| | | * is enabled. |
| | | */ |
| | | public synchronized boolean isEnabled() { |
| | | return loader != null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add the named extensions to this class loader. |
| | | * |
| | | * @param extensions |
| | | * The names of the extensions to be loaded. |
| | | * @throws InitializationException |
| | | * If one of the extensions could not be loaded and |
| | | * initialized. |
| | | */ |
| | | private synchronized void addExtension(File... extensions) |
| | | throws InitializationException { |
| | | // First add the Jar files to the class loader. |
| | | List<JarFile> jars = new LinkedList<JarFile>(); |
| | | for (File extension : extensions) { |
| | | if (jarFiles.contains(extension)) { |
| | | // Skip this file as it is already loaded. |
| | | continue; |
| | | } |
| | | |
| | | // Attempt to load it. |
| | | jars.add(loadJarFile(extension)); |
| | | |
| | | // Register the Jar file with the class loader. |
| | | try { |
| | | loader.addJarFile(extension); |
| | | } catch (Exception e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_ADMIN_CANNOT_OPEN_JAR_FILE. |
| | | get(extension.getName(), extension.getParent(), |
| | | stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message); |
| | | } |
| | | jarFiles.add(extension); |
| | | } |
| | | |
| | | // Now forcefully load the configuration definition classes. |
| | | for (JarFile jar : jars) { |
| | | initializeExtension(jar); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Prints out all information about extensions. |
| | | * |
| | | * @return a String instance representing all information about extensions; |
| | | * <code>null</code> if there is no information available. |
| | | */ |
| | | public String printExtensionInformation() { |
| | | File extensionsPath = |
| | | new File(new StringBuilder(DirectoryServer.getServerRoot()). |
| | | append(File.separator). |
| | | append(LIB_DIR). |
| | | append(File.separator). |
| | | append(EXTENSIONS_DIR). |
| | | toString()); |
| | | |
| | | if (!extensionsPath.exists() || !extensionsPath.isDirectory()) { |
| | | // no extensions' directory |
| | | return null; |
| | | } |
| | | |
| | | File[] extensions = extensionsPath.listFiles(new FileFilter(){ |
| | | public boolean accept(File pathname) { |
| | | // only files with names ending with ".jar" |
| | | return pathname.isFile() && pathname.getName().endsWith(".jar"); |
| | | } |
| | | }); |
| | | |
| | | if ( extensions.length == 0 ) { |
| | | return null; |
| | | } |
| | | |
| | | ByteArrayOutputStream baos = new ByteArrayOutputStream(); |
| | | PrintStream ps = new PrintStream(baos); |
| | | // prints: |
| | | // -- |
| | | // Name Build number Revision number |
| | | ps.printf("--%s %-20s %-20s %-20s%s", |
| | | EOL, |
| | | "Name", |
| | | "Build number", |
| | | "Revision number", |
| | | EOL); |
| | | |
| | | for(File extension : extensions) { |
| | | // retrieve MANIFEST entry and display name, build number and revision |
| | | // number |
| | | try { |
| | | JarFile jarFile = new JarFile(extension); |
| | | JarEntry entry = jarFile.getJarEntry("admin/" + EXTENSION_MANIFEST); |
| | | if (entry == null) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | String[] information = getBuildInformation(jarFile); |
| | | |
| | | ps.append("Extension: "); |
| | | boolean addBlank = false; |
| | | for(String name : information) { |
| | | if ( addBlank ) { |
| | | ps.append(addBlank ? " " : ""); // add blank if not first append |
| | | } else { |
| | | addBlank = true; |
| | | } |
| | | |
| | | ps.printf("%-20s", name); |
| | | } |
| | | ps.append(EOL); |
| | | } catch(Exception e) { |
| | | // ignore extra information for this extension |
| | | } |
| | | } |
| | | |
| | | return baos.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns a String array with the following information : |
| | | * <br>index 0: the name of the extension. |
| | | * <br>index 1: the build number of the extension. |
| | | * <br>index 2: the revision number of the extension. |
| | | * |
| | | * @param extension the jar file of the extension |
| | | * @return a String array containing the name, the build number and the |
| | | * revision number of the extension given in argument |
| | | * @throws java.io.IOException thrown if the jar file has been closed. |
| | | */ |
| | | private String[] getBuildInformation(JarFile extension) throws IOException { |
| | | String[] result = new String[3]; |
| | | |
| | | // retrieve MANIFEST entry and display name, version and revision |
| | | Manifest manifest = extension.getManifest(); |
| | | |
| | | if ( manifest != null ) { |
| | | Attributes attributes = manifest.getMainAttributes(); |
| | | |
| | | int index = 0; |
| | | for(String name : BUILD_INFORMATION_ATTRIBUTE_NAMES) { |
| | | String value = attributes.getValue(name); |
| | | if ( value == null ) { |
| | | value = "<unknown>"; |
| | | } |
| | | result[index++] = value; |
| | | } |
| | | } |
| | | |
| | | return result; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Put extensions jars into the class loader and load all |
| | | * configuration definition classes in that they contain. |
| | | * @param extensionsPath Indicates where extensions are located. |
| | | * |
| | | * @throws InitializationException |
| | | * If the extensions folder could not be accessed or if a |
| | | * extension jar file could not be accessed or if one of |
| | | * the configuration definition classes could not be |
| | | * initialized. |
| | | */ |
| | | private void initializeAllExtensions(File extensionsPath) |
| | | throws InitializationException { |
| | | |
| | | try { |
| | | if (!extensionsPath.exists()) { |
| | | // The extensions directory does not exist. This is not a |
| | | // critical problem. |
| | | Message message = ERR_ADMIN_NO_EXTENSIONS_DIR.get( |
| | | String.valueOf(extensionsPath)); |
| | | logError(message); |
| | | return; |
| | | } |
| | | |
| | | if (!extensionsPath.isDirectory()) { |
| | | // The extensions directory is not a directory. This is more |
| | | // critical. |
| | | Message message = |
| | | ERR_ADMIN_EXTENSIONS_DIR_NOT_DIRECTORY.get( |
| | | String.valueOf(extensionsPath)); |
| | | throw new InitializationException(message); |
| | | } |
| | | |
| | | // Get each extension file name. |
| | | FileFilter filter = new FileFilter() { |
| | | |
| | | /** |
| | | * Must be a Jar file. |
| | | */ |
| | | public boolean accept(File pathname) { |
| | | if (!pathname.isFile()) { |
| | | return false; |
| | | } |
| | | |
| | | String name = pathname.getName(); |
| | | return name.endsWith(".jar"); |
| | | } |
| | | |
| | | }; |
| | | |
| | | // Add and initialize the extensions. |
| | | addExtension(extensionsPath.listFiles(filter)); |
| | | } catch (InitializationException e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | throw e; |
| | | } catch (Exception e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_ADMIN_EXTENSIONS_CANNOT_LIST_FILES.get( |
| | | String.valueOf(extensionsPath), stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message, e); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Make sure all core configuration definitions are loaded. |
| | | * |
| | | * @throws InitializationException |
| | | * If the core manifest file could not be read or if one |
| | | * of the configuration definition classes could not be |
| | | * initialized. |
| | | */ |
| | | private void initializeCoreComponents() |
| | | throws InitializationException { |
| | | InputStream is = RootCfgDefn.class.getResourceAsStream("/admin/" |
| | | + CORE_MANIFEST); |
| | | |
| | | if (is == null) { |
| | | Message message = ERR_ADMIN_CANNOT_FIND_CORE_MANIFEST.get(CORE_MANIFEST); |
| | | throw new InitializationException(message); |
| | | } |
| | | |
| | | try { |
| | | loadDefinitionClasses(is); |
| | | } catch (InitializationException e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_CLASS_LOADER_CANNOT_LOAD_CORE.get(CORE_MANIFEST, |
| | | stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Make sure all the configuration definition classes in a extension |
| | | * are loaded. |
| | | * |
| | | * @param jarFile |
| | | * The extension's Jar file. |
| | | * @throws InitializationException |
| | | * If the extension jar file could not be accessed or if |
| | | * one of the configuration definition classes could not |
| | | * be initialized. |
| | | */ |
| | | private void initializeExtension(JarFile jarFile) |
| | | throws InitializationException { |
| | | JarEntry entry = jarFile.getJarEntry("admin/" |
| | | + EXTENSION_MANIFEST); |
| | | if (entry != null) { |
| | | InputStream is; |
| | | try { |
| | | is = jarFile.getInputStream(entry); |
| | | } catch (Exception e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_ADMIN_CANNOT_READ_EXTENSION_MANIFEST.get( |
| | | EXTENSION_MANIFEST, jarFile.getName(), |
| | | stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message); |
| | | } |
| | | |
| | | try { |
| | | loadDefinitionClasses(is); |
| | | } catch (InitializationException e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_CLASS_LOADER_CANNOT_LOAD_EXTENSION.get(jarFile |
| | | .getName(), EXTENSION_MANIFEST, stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message); |
| | | } |
| | | try { |
| | | // Log build information of extensions in the error log |
| | | String[] information = getBuildInformation(jarFile); |
| | | logError( |
| | | NOTE_LOG_EXTENSION_INFORMATION. |
| | | get(jarFile.getName(), |
| | | information[1], |
| | | information[2])); |
| | | } catch(Exception e) { |
| | | // Do not log information for that extension |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Forcefully load configuration definition classes named in a |
| | | * manifest file. |
| | | * |
| | | * @param is |
| | | * The manifest file input stream. |
| | | * @throws InitializationException |
| | | * If the definition classes could not be loaded and |
| | | * initialized. |
| | | */ |
| | | private void loadDefinitionClasses(InputStream is) |
| | | throws InitializationException { |
| | | BufferedReader reader = new BufferedReader(new InputStreamReader( |
| | | is)); |
| | | List<AbstractManagedObjectDefinition<?, ?>> definitions = |
| | | new LinkedList<AbstractManagedObjectDefinition<?,?>>(); |
| | | while (true) { |
| | | String className; |
| | | try { |
| | | className = reader.readLine(); |
| | | } catch (IOException e) { |
| | | Message msg = ERR_CLASS_LOADER_CANNOT_READ_MANIFEST_FILE.get(String |
| | | .valueOf(e.getMessage())); |
| | | throw new InitializationException(msg, e); |
| | | } |
| | | |
| | | // Break out when the end of the manifest is reached. |
| | | if (className == null) { |
| | | break; |
| | | } |
| | | |
| | | // Skip blank lines. |
| | | className = className.trim(); |
| | | if (className.length() == 0) { |
| | | continue; |
| | | } |
| | | |
| | | // Skip lines beginning with #. |
| | | if (className.startsWith("#")) { |
| | | continue; |
| | | } |
| | | |
| | | TRACER.debugMessage(DebugLogLevel.INFO, "Loading class " + className); |
| | | |
| | | // Load the class and get an instance of it if it is a definition. |
| | | Class<?> theClass; |
| | | try { |
| | | theClass = Class.forName(className, true, loader); |
| | | } catch (Exception e) { |
| | | Message msg = ERR_CLASS_LOADER_CANNOT_LOAD_CLASS.get(className, String |
| | | .valueOf(e.getMessage())); |
| | | throw new InitializationException(msg, e); |
| | | } |
| | | if (AbstractManagedObjectDefinition.class.isAssignableFrom(theClass)) { |
| | | // We need to instantiate it using its getInstance() static method. |
| | | Method method; |
| | | try { |
| | | method = theClass.getMethod("getInstance"); |
| | | } catch (Exception e) { |
| | | Message msg = ERR_CLASS_LOADER_CANNOT_FIND_GET_INSTANCE_METHOD.get( |
| | | className, String.valueOf(e.getMessage())); |
| | | throw new InitializationException(msg, e); |
| | | } |
| | | |
| | | // Get the definition instance. |
| | | AbstractManagedObjectDefinition<?, ?> d; |
| | | try { |
| | | d = (AbstractManagedObjectDefinition<?, ?>) method.invoke(null); |
| | | } catch (Exception e) { |
| | | Message msg = ERR_CLASS_LOADER_CANNOT_INVOKE_GET_INSTANCE_METHOD.get( |
| | | className, String.valueOf(e.getMessage())); |
| | | throw new InitializationException(msg, e); |
| | | } |
| | | definitions.add(d); |
| | | } |
| | | } |
| | | |
| | | // Initialize any definitions that were loaded. |
| | | for (AbstractManagedObjectDefinition<?, ?> d : definitions) { |
| | | try { |
| | | d.initialize(); |
| | | } catch (Exception e) { |
| | | Message msg = ERR_CLASS_LOADER_CANNOT_INITIALIZE_DEFN.get(d.getName(), |
| | | d.getClass().getName(), String.valueOf(e.getMessage())); |
| | | throw new InitializationException(msg, e); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Load the named Jar file. |
| | | * |
| | | * @param jar |
| | | * The name of the Jar file to load. |
| | | * @return Returns the loaded Jar file. |
| | | * @throws InitializationException |
| | | * If the Jar file could not be loaded. |
| | | */ |
| | | private JarFile loadJarFile(File jar) |
| | | throws InitializationException { |
| | | JarFile jarFile; |
| | | |
| | | try { |
| | | // Load the extension jar file. |
| | | jarFile = new JarFile(jar); |
| | | } catch (Exception e) { |
| | | if (debugEnabled()) { |
| | | TRACER.debugCaught(DebugLogLevel.ERROR, e); |
| | | } |
| | | |
| | | Message message = ERR_ADMIN_CANNOT_OPEN_JAR_FILE.get( |
| | | jar.getName(), jar.getParent(), stackTraceToSingleLineString(e)); |
| | | throw new InitializationException(message); |
| | | } |
| | | return jarFile; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.Collections; |
| | | import java.util.EnumSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Class property definition. |
| | | * <p> |
| | | * A class property definition defines a property whose values |
| | | * represent a Java class. It is possible to restrict the type of java |
| | | * class by specifying "instance of" constraints. |
| | | * <p> |
| | | * Note that in a client/server environment, the client is probably |
| | | * not capable of validating the Java class (e.g. it will not be able |
| | | * to load it nor have access to the interfaces it is supposed to |
| | | * implement). For this reason, it is possible to switch off |
| | | * validation in the client by calling the static method |
| | | * {@link #setAllowClassValidation(boolean)}. |
| | | */ |
| | | public final class ClassPropertyDefinition extends PropertyDefinition<String> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing class property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<String, ClassPropertyDefinition> { |
| | | |
| | | // List of interfaces which property values must implement. |
| | | private List<String> instanceOfInterfaces; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | |
| | | this.instanceOfInterfaces = new LinkedList<String>(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add an class name which property values must implement. |
| | | * |
| | | * @param className |
| | | * The name of a class which property values must |
| | | * implement. |
| | | */ |
| | | public final void addInstanceOf(String className) { |
| | | ensureNotNull(className); |
| | | |
| | | // Do some basic checks to make sure the string representation |
| | | // is valid. |
| | | String value = className.trim(); |
| | | if (!value.matches(CLASS_RE)) { |
| | | throw new IllegalArgumentException("\"" + value |
| | | + "\" is not a valid Java class name"); |
| | | } |
| | | |
| | | // If possible try and load the class in order to perform |
| | | // additional |
| | | // validation. |
| | | if (isAllowClassValidation()) { |
| | | // Check that the class can be loaded so that validation can |
| | | // be |
| | | // performed. |
| | | try { |
| | | loadClass(value); |
| | | } catch (ClassNotFoundException e) { |
| | | // TODO: can we do something better here? |
| | | throw new RuntimeException(e); |
| | | } |
| | | } |
| | | |
| | | instanceOfInterfaces.add(value); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected ClassPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior) { |
| | | return new ClassPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior, instanceOfInterfaces); |
| | | } |
| | | |
| | | } |
| | | |
| | | // Regular expression for validating class names. |
| | | private static final String CLASS_RE = |
| | | "^([A-Za-z][A-Za-z0-9_]*\\.)*[A-Za-z][A-Za-z0-9_]*(\\$[A-Za-z0-9_]+)*$"; |
| | | |
| | | // Flag indicating whether class property values should be |
| | | // validated. |
| | | private static boolean allowClassValidation = true; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a class property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new class property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether or not class property definitions should |
| | | * validate class name property values. Validation involves checking |
| | | * that the class exists and that it implements the required |
| | | * interfaces. |
| | | * |
| | | * @return Returns <code>true</code> if class property definitions |
| | | * should validate class name property values. |
| | | */ |
| | | public static boolean isAllowClassValidation() { |
| | | return allowClassValidation; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specify whether or not class property definitions should validate |
| | | * class name property values. Validation involves checking that the |
| | | * class exists and that it implements the required interfaces. |
| | | * <p> |
| | | * By default validation is switched on. |
| | | * |
| | | * @param value |
| | | * <code>true</code> if class property definitions should |
| | | * validate class name property values. |
| | | */ |
| | | public static void setAllowClassValidation(boolean value) { |
| | | allowClassValidation = value; |
| | | } |
| | | |
| | | |
| | | |
| | | // Load a named class. |
| | | private static Class<?> loadClass(String className) |
| | | throws ClassNotFoundException, LinkageError { |
| | | return Class.forName(className, true, ClassLoaderProvider |
| | | .getInstance().getClassLoader()); |
| | | } |
| | | |
| | | // List of interfaces which property values must implement. |
| | | private final List<String> instanceOfInterfaces; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private ClassPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior, |
| | | List<String> instanceOfInterfaces) { |
| | | super(d, String.class, propertyName, options, adminAction, defaultBehavior); |
| | | |
| | | this.instanceOfInterfaces = Collections |
| | | .unmodifiableList(new LinkedList<String>(instanceOfInterfaces)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitClass(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, String value, P p) { |
| | | return v.visitClass(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | validateValue(value); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | return value; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get an unmodifiable list of classes which values of this property |
| | | * must implement. |
| | | * |
| | | * @return Returns an unmodifiable list of classes which values of |
| | | * this property must implement. |
| | | */ |
| | | public List<String> getInstanceOfInterface() { |
| | | return instanceOfInterfaces; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Validate and load the named class, and cast it to a subclass of |
| | | * the specified class. |
| | | * |
| | | * @param <T> |
| | | * The requested type. |
| | | * @param className |
| | | * The name of the class to validate and load. |
| | | * @param instanceOf |
| | | * The class representing the requested type. |
| | | * @return Returns the named class cast to a subclass of the |
| | | * specified class. |
| | | * @throws IllegalPropertyValueException |
| | | * If the named class was invalid, could not be loaded, or |
| | | * did not implement the required interfaces. |
| | | * @throws ClassCastException |
| | | * If the referenced class does not implement the |
| | | * requested type. |
| | | */ |
| | | public <T> Class<? extends T> loadClass(String className, |
| | | Class<T> instanceOf) throws IllegalPropertyValueException, |
| | | ClassCastException { |
| | | ensureNotNull(className, instanceOf); |
| | | |
| | | // Make sure that the named class is valid. |
| | | validateClassName(className); |
| | | Class<?> theClass = validateClassInterfaces(className); |
| | | |
| | | // Cast it to the required type. |
| | | return theClass.asSubclass(instanceOf); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String normalizeValue(String value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | return value.trim(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(String value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // Always make sure the name is a valid class name. |
| | | validateClassName(value); |
| | | |
| | | // If additional validation is enabled then attempt to load the |
| | | // class and |
| | | // check the interfaces that it implements/extends. |
| | | if (allowClassValidation) { |
| | | validateClassInterfaces(value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | // Make sure that named class implements the interfaces named by |
| | | // this |
| | | // definition. |
| | | private Class<?> validateClassInterfaces(String className) |
| | | throws IllegalPropertyValueException { |
| | | String nvalue = className.trim(); |
| | | |
| | | Class<?> theClass; |
| | | try { |
| | | theClass = loadClass(nvalue); |
| | | } catch (Exception e) { |
| | | // If the class cannot be loaded then it is an invalid value. |
| | | throw new IllegalPropertyValueException(this, className); |
| | | } |
| | | |
| | | for (String i : instanceOfInterfaces) { |
| | | try { |
| | | Class<?> instanceOfClass = loadClass(i); |
| | | |
| | | if (!instanceOfClass.isAssignableFrom(theClass)) { |
| | | throw new IllegalPropertyValueException(this, className); |
| | | } |
| | | } catch (Exception e) { |
| | | // Should not happen because the class was validated when the |
| | | // property |
| | | // definition was constructed. |
| | | throw new IllegalPropertyValueException(this, className); |
| | | } |
| | | } |
| | | |
| | | return theClass; |
| | | } |
| | | |
| | | |
| | | |
| | | // Do some basic checks to make sure the string representation is |
| | | // valid. |
| | | private void validateClassName(String className) |
| | | throws IllegalPropertyValueException { |
| | | String nvalue = className.trim(); |
| | | if (!nvalue.matches(CLASS_RE)) { |
| | | throw new IllegalPropertyValueException(this, className); |
| | | } |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2007-2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | import org.forgerock.opendj.ldap.DN; |
| | | |
| | | /** |
| | | * A common base interface for all server managed object |
| | | * configurations. |
| | | */ |
| | | public interface Configuration { |
| | | |
| | | /** |
| | | * Gets the DN of the LDAP entry associated with this configuration. |
| | | * |
| | | * @return Returns the DN of the LDAP entry associated with this |
| | | * configuration. |
| | | */ |
| | | DN dn(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the configuration class associated with this configuration. |
| | | * |
| | | * @return Returns the configuration class associated with this |
| | | * configuration. |
| | | */ |
| | | Class<? extends Configuration> configurationClass(); |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.server.admin.client.AuthorizationException; |
| | | import org.opends.server.admin.client.CommunicationException; |
| | | import org.opends.server.admin.client.ConcurrentModificationException; |
| | | import org.opends.server.admin.client.MissingMandatoryPropertiesException; |
| | | import org.opends.server.admin.client.OperationRejectedException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A common base interface for all managed object configuration |
| | | * clients. |
| | | */ |
| | | public interface ConfigurationClient { |
| | | |
| | | /** |
| | | * Get the configuration definition associated with this |
| | | * configuration. |
| | | * |
| | | * @return Returns the configuration definition associated with this |
| | | * configuration. |
| | | */ |
| | | ManagedObjectDefinition<? extends ConfigurationClient, |
| | | ? extends Configuration> definition(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get a property provider view of this configuration. |
| | | * |
| | | * @return Returns a property provider view of this configuration. |
| | | */ |
| | | PropertyProvider properties(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * If this is a new configuration this method will attempt to add it |
| | | * to the server, otherwise it will commit any changes made to this |
| | | * configuration. |
| | | * |
| | | * @throws ManagedObjectAlreadyExistsException |
| | | * If this is a new configuration but it could not be |
| | | * added to the server because it already exists. |
| | | * @throws MissingMandatoryPropertiesException |
| | | * If this configuration contains some mandatory |
| | | * properties which have been left undefined. |
| | | * @throws ConcurrentModificationException |
| | | * If this is a new configuration which is being added to |
| | | * the server but its parent has been removed by another |
| | | * client, or if this configuration is being modified but |
| | | * it has been removed from the server by another client. |
| | | * @throws OperationRejectedException |
| | | * If the server refuses to add or modify this |
| | | * configuration due to some server-side constraint which |
| | | * cannot be satisfied. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to add or modify this |
| | | * configuration because the client does not have the |
| | | * correct privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | void commit() throws ManagedObjectAlreadyExistsException, |
| | | MissingMandatoryPropertiesException, ConcurrentModificationException, |
| | | OperationRejectedException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | |
| | | import org.opends.server.admin.client.ClientConstraintHandler; |
| | | import org.opends.server.admin.server.ServerConstraintHandler; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for enforcing constraints and dependencies between |
| | | * managed objects and their properties. Constraints express |
| | | * relationships between managed objects and their properties, for |
| | | * example: |
| | | * <ul> |
| | | * <li>referential integrity: where one managed object references |
| | | * another a constraint can enforce referential integrity. The |
| | | * constraint can prevent creation of references to non-existent |
| | | * managed objects, and also prevent deletion of referenced managed |
| | | * objects |
| | | * <li>property dependencies: for example, when a boolean property is |
| | | * <code>true</code>, one or more additional properties must be |
| | | * specified. This is useful for features like SSL, which when |
| | | * enabled, requires that various SSL related configuration options |
| | | * are specified |
| | | * <li>property constraints: for example, when an upper limit |
| | | * property must not have a value which is less than the lower limit |
| | | * property. |
| | | * </ul> |
| | | * On the client-side constraints are enforced immediately before a |
| | | * write operation is performed. That is to say, immediately before a |
| | | * new managed object is created, changes to a managed object are |
| | | * applied, or an existing managed object is deleted. |
| | | */ |
| | | public abstract class Constraint { |
| | | |
| | | /** |
| | | * Creates a new constraint. |
| | | */ |
| | | protected Constraint() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the client-side constraint handlers which will be used to |
| | | * enforce this constraint in client applications. The default |
| | | * implementation is to return an empty set of client constraint |
| | | * handlers. |
| | | * |
| | | * @return Returns the client-side constraint handlers which will be |
| | | * used to enforce this constraint in client applications. |
| | | * The returned collection must not be <code>null</code> |
| | | * but maybe empty (indicating that the constraint can only |
| | | * be enforced on the server-side). |
| | | */ |
| | | public Collection<ClientConstraintHandler> getClientConstraintHandlers() { |
| | | return Collections.emptySet(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the server-side constraint handlers which will be used to |
| | | * enforce this constraint within the server. The default |
| | | * implementation is to return an empty set of server constraint |
| | | * handlers. |
| | | * |
| | | * @return Returns the server-side constraint handlers which will be |
| | | * used to enforce this constraint within the server. The |
| | | * returned collection must not be <code>null</code> and |
| | | * must not be empty, since constraints must always be |
| | | * enforced on the server. |
| | | */ |
| | | public Collection<ServerConstraintHandler> getServerConstraintHandlers() { |
| | | return Collections.emptySet(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Initializes this constraint. The default implementation is to do |
| | | * nothing. |
| | | * |
| | | * @throws Exception |
| | | * If this constraint could not be initialized. |
| | | */ |
| | | protected void initialize() throws Exception { |
| | | // Default implementation is to do nothing. |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.DirectoryException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * DN property definition. |
| | | */ |
| | | public final class DNPropertyDefinition extends PropertyDefinition<DN> { |
| | | |
| | | // Optional base DN which all valid values must be immediately |
| | | // subordinate to. |
| | | private final DN baseDN; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing DN property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<DN, DNPropertyDefinition> { |
| | | |
| | | // Optional base DN which all valid values must be immediately |
| | | // subordinate to. |
| | | private DN baseDN = null; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the base DN which all valid values must be immediately |
| | | * subordinate to. By default there is no based DN. |
| | | * |
| | | * @param baseDN |
| | | * The string representation of the base DN. |
| | | * @throws IllegalArgumentException |
| | | * If the provided string is not a valid DN string |
| | | * representation. |
| | | */ |
| | | public void setBaseDN(String baseDN) |
| | | throws IllegalArgumentException { |
| | | if (baseDN == null) { |
| | | setBaseDN((DN) null); |
| | | } else { |
| | | try { |
| | | setBaseDN(DN.decode(baseDN)); |
| | | } catch (DirectoryException e) { |
| | | throw new IllegalArgumentException(e); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the base DN which all valid values must be immediately |
| | | * subordinate to. By default there is no based DN. |
| | | * |
| | | * @param baseDN |
| | | * The base DN. |
| | | */ |
| | | public void setBaseDN(DN baseDN) { |
| | | this.baseDN = baseDN; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected DNPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<DN> defaultBehavior) { |
| | | return new DNPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior, baseDN); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a DN property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new boolean property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private DNPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<DN> defaultBehavior, DN baseDN) { |
| | | super(d, DN.class, propertyName, options, adminAction, defaultBehavior); |
| | | this.baseDN = baseDN; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the base DN which all valid values must be immediately |
| | | * subordinate to, or <code>null</code> if there is no based DN. |
| | | * |
| | | * @return Returns the base DN which all valid values must be |
| | | * immediately subordinate to. |
| | | */ |
| | | public DN getBaseDN() { |
| | | return baseDN; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(DN value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | if (baseDN != null) { |
| | | DN parent = value.getParent(); |
| | | |
| | | if (parent == null) { |
| | | parent = DN.nullDN(); |
| | | } |
| | | |
| | | if (!parent.equals(baseDN)) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public DN decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | DN dn = DN.decode(value); |
| | | validateValue(dn); |
| | | return dn; |
| | | } catch (DirectoryException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitDN(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, DN value, P p) { |
| | | return v.visitDN(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(DN o1, DN o2) { |
| | | return o1.compareTo(o2); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The requested managed object was found but it could not be decoded. |
| | | */ |
| | | public abstract class DecodingException extends OperationsException { |
| | | |
| | | /** |
| | | * Fake serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 1L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a decoding exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected DecodingException(Message message) { |
| | | super(message); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when a property's default values cannot be |
| | | * determined. This can occur in the following situations: |
| | | * <ul> |
| | | * <li>the property has a well-defined set of default values but they |
| | | * are invalid according to the property's syntax |
| | | * <li>the property inherits its default values from another managed |
| | | * object but they could not be retrieved, perhaps because of a |
| | | * communication problem. |
| | | * </ul> |
| | | */ |
| | | public class DefaultBehaviorException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -2542117466747573053L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new default behavior exception with a cause. |
| | | * |
| | | * @param pd |
| | | * The property definition whose default values could not |
| | | * be determined. |
| | | * @param cause |
| | | * The exception that prevented the default values from |
| | | * being determined. |
| | | */ |
| | | public DefaultBehaviorException(PropertyDefinition<?> pd, Throwable cause) { |
| | | super(pd, ERR_DEFAULT_BEHAVIOR_PROPERTY_EXCEPTION.get(pd.getName()), cause); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for determining the default behavior of a property. A |
| | | * property exhibits default behavior when it has no values defined. |
| | | * There are four different types of default behavior: |
| | | * <ol> |
| | | * <li>there is no default behavior - e.g. leaving a "description" |
| | | * unset has no side-effects. This default behavior is represented |
| | | * using the {@link UndefinedDefaultBehaviorProvider} implementation |
| | | * <li>the property defaults to one or more real values of the |
| | | * property. This default behavior is represented using the |
| | | * {@link DefinedDefaultBehaviorProvider} implementation |
| | | * <li>the property defaults to some special behavior that cannot be |
| | | * represented using real property values. This default behavior is |
| | | * represented using the {@link AliasDefaultBehaviorProvider} |
| | | * implementation |
| | | * <li>the property inherits its values from property held in another |
| | | * managed object (e.g. the parent managed object). This default |
| | | * behavior is represented using the |
| | | * {@link AbsoluteInheritedDefaultBehaviorProvider} and |
| | | * {@link RelativeInheritedDefaultBehaviorProvider} implementations. |
| | | * </ol> |
| | | * An application can perform actions based on the type of the default |
| | | * behavior by implementing the {@link DefaultBehaviorProviderVisitor} |
| | | * interface. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public abstract class DefaultBehaviorProvider<T> { |
| | | |
| | | /** |
| | | * Creates a new default behavior provider. |
| | | */ |
| | | protected DefaultBehaviorProvider() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Apply a visitor to this default behavior provider. |
| | | * |
| | | * @param <R> |
| | | * The return type of the visitor's methods. |
| | | * @param <P> |
| | | * The type of the additional parameters to the visitor's |
| | | * methods. |
| | | * @param v |
| | | * The default behavior visitor. |
| | | * @param p |
| | | * Optional additional visitor parameter. |
| | | * @return Returns a result as specified by the visitor. |
| | | */ |
| | | public abstract <R, P> |
| | | R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Performs any run-time initialization required by this default |
| | | * behavior provider. This may include resolving managed object |
| | | * paths and property names. |
| | | * <p> |
| | | * The default implementation is to do nothing. |
| | | * |
| | | * @throws Exception |
| | | * If this default behavior provider could not be |
| | | * initialized. |
| | | */ |
| | | protected void initialize() throws Exception { |
| | | // Default implementation is to do nothing. |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A visitor of default behavior providers, in the style of the visitor design |
| | | * pattern. Classes implementing this interface can query default behavior |
| | | * providers in a type-safe manner when the kind of default behavior provider |
| | | * is unknown at compile time. When a visitor is passed to a default behavior |
| | | * provider's accept method, the corresponding visit method most applicable to |
| | | * that default behavior provider is invoked. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by the default value provider. |
| | | * @param <R> |
| | | * The return type of this visitor's methods. Use |
| | | * {@link java.lang.Void} for visitors that do not need to return |
| | | * results. |
| | | * @param <P> |
| | | * The type of the additional parameter to this visitor's methods. Use |
| | | * {@link java.lang.Void} for visitors that do not need an additional |
| | | * parameter. |
| | | */ |
| | | public interface DefaultBehaviorProviderVisitor<T, R, P> { |
| | | |
| | | /** |
| | | * Visit an absolute inherited default behavior provider. |
| | | * |
| | | * @param d |
| | | * The absolute inherited default behavior provider to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | R visitAbsoluteInherited(AbsoluteInheritedDefaultBehaviorProvider<T> d, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an alias default behavior provider. |
| | | * |
| | | * @param d |
| | | * The alias default behavior provider to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | R visitAlias(AliasDefaultBehaviorProvider<T> d, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an defined default behavior provider. |
| | | * |
| | | * @param d |
| | | * The defined default behavior provider to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | R visitDefined(DefinedDefaultBehaviorProvider<T> d, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a relative inherited default behavior provider. |
| | | * |
| | | * @param d |
| | | * The relative inherited default behavior provider to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | R visitRelativeInherited(RelativeInheritedDefaultBehaviorProvider<T> d, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an undefined default behavior provider. |
| | | * |
| | | * @param d |
| | | * The undefined default behavior provider to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | R visitUndefined(UndefinedDefaultBehaviorProvider<T> d, P p); |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Arrays; |
| | | import java.util.HashMap; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.SortedSet; |
| | | import java.util.TreeSet; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default managed object which should be created when a parent |
| | | * managed object is created. Default managed objects are associated |
| | | * with a {@link RelationDefinition}. |
| | | * |
| | | * @param <C> |
| | | * The type of client default managed object configuration. |
| | | * @param <S> |
| | | * The type of server default managed object configuration. |
| | | */ |
| | | public final class DefaultManagedObject |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | implements PropertyProvider { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing default managed |
| | | * objects. |
| | | * |
| | | * @param <C> |
| | | * The type of client default managed object configuration. |
| | | * @param <S> |
| | | * The type of server default managed object configuration. |
| | | */ |
| | | public static final class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> { |
| | | |
| | | // The default managed object's definition. |
| | | private final ManagedObjectDefinition<C, S> definition; |
| | | |
| | | // The string encoded default managed object's properties. |
| | | private final Map<String, List<String>> propertyStringValues = |
| | | new HashMap<String, List<String>>(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new default managed object builder. |
| | | * |
| | | * @param definition |
| | | * The default managed object's definition. |
| | | */ |
| | | public Builder(ManagedObjectDefinition<C, S> definition) { |
| | | this.definition = definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Construct a default managed object based on the properties of |
| | | * this builder. |
| | | * |
| | | * @return Returns the new default managed object. |
| | | */ |
| | | public DefaultManagedObject<C, S> getInstance() { |
| | | return new DefaultManagedObject<C, S>(definition, propertyStringValues); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Defines a property's values for the default managed object. |
| | | * |
| | | * @param name |
| | | * The name of the property. |
| | | * @param values |
| | | * One or more property values in the string |
| | | * representation. |
| | | */ |
| | | public void setPropertyValues(String name, String... values) { |
| | | if (values == null || values.length == 0) { |
| | | throw new IllegalArgumentException( |
| | | "null or empty values specified for property " + name); |
| | | } |
| | | |
| | | propertyStringValues.put(name, Arrays.asList(values)); |
| | | } |
| | | } |
| | | |
| | | // The default managed object's definition. |
| | | private final ManagedObjectDefinition<C, S> definition; |
| | | |
| | | // The string encoded default managed object's properties. |
| | | private final Map<String, List<String>> propertyStringValues; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private DefaultManagedObject(ManagedObjectDefinition<C, S> definition, |
| | | Map<String, List<String>> propertyStringValues) { |
| | | this.definition = definition; |
| | | this.propertyStringValues = propertyStringValues; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the managed object definition associated with this default |
| | | * managed object. |
| | | * |
| | | * @return Returns the managed object definition associated with |
| | | * this default managed object. |
| | | */ |
| | | public ManagedObjectDefinition<C, S> getManagedObjectDefinition() { |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets a mutable copy of the set of property values for the |
| | | * specified property. |
| | | * |
| | | * @param <T> |
| | | * The type of the property to be retrieved. |
| | | * @param pd |
| | | * The property to be retrieved. |
| | | * @return Returns a newly allocated set containing a copy of the |
| | | * property's values. An empty set indicates that the |
| | | * property has no values defined and any default behavior |
| | | * is applicable. |
| | | * @throws IllegalArgumentException |
| | | * If the property definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | public <T> SortedSet<T> getPropertyValues(PropertyDefinition<T> pd) |
| | | throws IllegalArgumentException { |
| | | // Validate the property definition. |
| | | definition.getPropertyDefinition(pd.getName()); |
| | | |
| | | // Do a defensive copy. |
| | | SortedSet<T> values = new TreeSet<T>(pd); |
| | | List<String> stringValues = propertyStringValues.get(pd.getName()); |
| | | if (stringValues != null) { |
| | | for (String stringValue : stringValues) { |
| | | values.add(pd.decodeValue(stringValue)); |
| | | } |
| | | } |
| | | return values; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Performs run-time initialization of properties. |
| | | * |
| | | * @throws Exception |
| | | * If this default managed object could not be |
| | | * initialized. |
| | | */ |
| | | void initialize() throws Exception { |
| | | // FIXME: it would be nice if we could decode all property values |
| | | // at this point. However this is not possible on the server side |
| | | // since some properties will be determined to be invalid since |
| | | // the schema is not loaded. |
| | | |
| | | // Validate provided property names. |
| | | for (String name : propertyStringValues.keySet()) { |
| | | definition.getPropertyDefinition(name); |
| | | } |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.ArrayList; |
| | | import java.util.Arrays; |
| | | import java.util.Collection; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default behavior provider which represents a well-defined set of default |
| | | * values. It should be used by properties which have default value(s) which are |
| | | * valid value(s) according to the constraints of the property's definition. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public final class DefinedDefaultBehaviorProvider<T> extends |
| | | DefaultBehaviorProvider<T> { |
| | | |
| | | // The collection of default values. |
| | | private final Collection<String> values; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new defined default behavior provider associated with the |
| | | * specified list of values. |
| | | * |
| | | * @param values |
| | | * The list of values (must be non-<code>null</code> and not |
| | | * empty) in their string representation. |
| | | * @throws IllegalArgumentException |
| | | * If the list of values was <code>null</code> or empty. |
| | | */ |
| | | public DefinedDefaultBehaviorProvider(String... values) |
| | | throws IllegalArgumentException { |
| | | if (values == null || values.length == 0) { |
| | | throw new IllegalArgumentException( |
| | | "Null or empty list of default values"); |
| | | } |
| | | this.values = Arrays.asList(values); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <R, P> R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p) { |
| | | return v.visitDefined(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get a copy of the default values. |
| | | * |
| | | * @return Returns a newly allocated collection containing a copy of the |
| | | * default values. |
| | | */ |
| | | public Collection<String> getDefaultValues() { |
| | | return new ArrayList<String>(values); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The requested managed object was found but its type could not be |
| | | * determined. |
| | | */ |
| | | public class DefinitionDecodingException extends DecodingException { |
| | | |
| | | /** |
| | | * An enumeration defining the reasons why the definition could not |
| | | * be resolved. |
| | | */ |
| | | public static enum Reason { |
| | | /** |
| | | * The managed object could be found but its type resolved to an |
| | | * abstract managed object definition. |
| | | */ |
| | | ABSTRACT_TYPE_INFORMATION(), |
| | | |
| | | /** |
| | | * The managed object could be found but did not contain any type |
| | | * information (eg missing object classes in LDAP). |
| | | */ |
| | | NO_TYPE_INFORMATION(), |
| | | |
| | | /** |
| | | * The managed object could be found but did not contain the |
| | | * expected type information (eg incorrect object classes in |
| | | * LDAP). |
| | | */ |
| | | WRONG_TYPE_INFORMATION(); |
| | | |
| | | } |
| | | |
| | | /** |
| | | * Version ID required by serializable classes. |
| | | */ |
| | | private static final long serialVersionUID = 3459033551415663416L; |
| | | |
| | | |
| | | |
| | | // Create the message. |
| | | private static Message createMessage(AbstractManagedObjectDefinition<?, ?> d, |
| | | Reason reason) { |
| | | Message ufn = d.getUserFriendlyName(); |
| | | switch (reason) { |
| | | case NO_TYPE_INFORMATION: |
| | | return ERR_DECODING_EXCEPTION_NO_TYPE_INFO.get(ufn); |
| | | case WRONG_TYPE_INFORMATION: |
| | | return ERR_DECODING_EXCEPTION_WRONG_TYPE_INFO.get(ufn); |
| | | default: |
| | | return ERR_DECODING_EXCEPTION_ABSTRACT_TYPE_INFO.get(ufn); |
| | | } |
| | | } |
| | | |
| | | // The expected type of managed object. |
| | | private final AbstractManagedObjectDefinition<?, ?> d; |
| | | |
| | | // The reason why the definition could not be determined. |
| | | private final Reason reason; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new definition decoding exception. |
| | | * |
| | | * @param d |
| | | * The expected type of managed object. |
| | | * @param reason |
| | | * The reason why the definition could not be determined. |
| | | */ |
| | | public DefinitionDecodingException(AbstractManagedObjectDefinition<?, ?> d, |
| | | Reason reason) { |
| | | super(createMessage(d, reason)); |
| | | this.d = d; |
| | | this.reason = reason; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the expected managed object definition. |
| | | * |
| | | * @return Returns the expected managed object definition. |
| | | */ |
| | | public AbstractManagedObjectDefinition<?, ?> getManagedObjectDefinition() { |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the reason why the definition could not be determined. |
| | | * |
| | | * @return Returns the reason why the definition could not be |
| | | * determined. |
| | | */ |
| | | public Reason getReason() { |
| | | return reason; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This interface is used to determine the "best match" managed object |
| | | * definition in a definition hierarchy. |
| | | * <p> |
| | | * Managed object definitions, like Java classes, are arranged in an |
| | | * inheritance hierarchy. When managed objects are decoded (e.g. from |
| | | * LDAP entries), the driver implementation is provided with an |
| | | * "expected managed object definition". However, the actual decoded |
| | | * managed object is often an instance of a sub-type of this |
| | | * definition. For example, when decoding a connection handler managed |
| | | * object, the actual type can never be a connection handler because |
| | | * it is an abstract managed object type. Instead, the decoded managed |
| | | * object must be a "concrete" sub-type: an LDAP connection handler or |
| | | * JMX connection handler. |
| | | * <p> |
| | | * This resolution process is coordinated by the |
| | | * <code>resolveManagedObjectDefinition</code> method in managed |
| | | * object definitions, where it is passed a |
| | | * <code>DefinitionResolver</code> implementation. The |
| | | * <code>resolveManagedObjectDefinition</code> method takes care of |
| | | * recursively descending through the definition hierarchy and invokes |
| | | * the {@link #matches(AbstractManagedObjectDefinition)} method |
| | | * against each potential sub-type. It is the job of the resolver to |
| | | * indicate whether the provided managed object definition is a |
| | | * candidate definition. For example, the LDAP driver provides a |
| | | * definition resolver which uses the decoded LDAP entry's object |
| | | * classes to determine the final appropriate managed object |
| | | * definition. |
| | | */ |
| | | public interface DefinitionResolver { |
| | | |
| | | /** |
| | | * Determines whether or not the provided managed object definition matches |
| | | * this resolver's criteria. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns <code>true</code> if the the provided managed object |
| | | * definition matches this resolver's criteria. |
| | | */ |
| | | boolean matches(AbstractManagedObjectDefinition<?, ?> d); |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Duration property definition. |
| | | * <p> |
| | | * A duration property definition comprises of: |
| | | * <ul> |
| | | * <li>a <i>base unit</i> - specifies the minimum granularity which |
| | | * can be used to specify duration property values. For example, if |
| | | * the base unit is in seconds then values represented in milliseconds |
| | | * will not be permitted. The default base unit is seconds |
| | | * <li>an optional <i>maximum unit</i> - specifies the biggest |
| | | * duration unit which can be used to specify duration property |
| | | * values. Values presented in units greater than this unit will not |
| | | * be permitted. There is no default maximum unit |
| | | * <li><i>lower limit</i> - specifies the smallest duration |
| | | * permitted by the property. The default lower limit is 0 and can |
| | | * never be less than 0 |
| | | * <li>an optional <i>upper limit</i> - specifies the biggest |
| | | * duration permitted by the property. By default, there is no upper |
| | | * limit |
| | | * <li>support for <i>unlimited</i> durations - when permitted users |
| | | * can specify "unlimited" durations. These are represented using the |
| | | * decoded value, -1, or the encoded string value "unlimited". By |
| | | * default, unlimited durations are not permitted. In addition, it is |
| | | * not possible to define an upper limit and support unlimited values. |
| | | * </ul> |
| | | * Decoded values are represented using <code>long</code> values in |
| | | * the base unit defined for the duration property definition. |
| | | */ |
| | | public final class DurationPropertyDefinition extends PropertyDefinition<Long> { |
| | | |
| | | // String used to represent unlimited durations. |
| | | private static final String UNLIMITED = "unlimited"; |
| | | |
| | | // The base unit for this property definition. |
| | | private final DurationUnit baseUnit; |
| | | |
| | | // The optional maximum unit for this property definition. |
| | | private final DurationUnit maximumUnit; |
| | | |
| | | // The lower limit of the property value in milli-seconds. |
| | | private final long lowerLimit; |
| | | |
| | | // The optional upper limit of the property value in milli-seconds. |
| | | private final Long upperLimit; |
| | | |
| | | // Indicates whether this property allows the use of the "unlimited" |
| | | // duration value (represented using a -1L or the string |
| | | // "unlimited"). |
| | | private final boolean allowUnlimited; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing duration property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<Long, DurationPropertyDefinition> { |
| | | |
| | | // The base unit for this property definition. |
| | | private DurationUnit baseUnit = DurationUnit.SECONDS; |
| | | |
| | | // The optional maximum unit for this property definition. |
| | | private DurationUnit maximumUnit = null; |
| | | |
| | | // The lower limit of the property value in milli-seconds. |
| | | private long lowerLimit = 0L; |
| | | |
| | | // The optional upper limit of the property value in |
| | | // milli-seconds. |
| | | private Long upperLimit = null; |
| | | |
| | | // Indicates whether this property allows the use of the |
| | | // "unlimited" duration value (represented using a -1L or the |
| | | // string "unlimited"). |
| | | private boolean allowUnlimited = false; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the base unit for this property definition (values |
| | | * including limits are specified in this unit). By default a |
| | | * duration property definition uses seconds. |
| | | * |
| | | * @param unit |
| | | * The string representation of the base unit (must not |
| | | * be <code>null</code>). |
| | | * @throws IllegalArgumentException |
| | | * If the provided unit name did not correspond to a |
| | | * known duration unit, or if the base unit is bigger |
| | | * than the maximum unit. |
| | | */ |
| | | public final void setBaseUnit(String unit) throws IllegalArgumentException { |
| | | ensureNotNull(unit); |
| | | |
| | | setBaseUnit(DurationUnit.getUnit(unit)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the base unit for this property definition (values |
| | | * including limits are specified in this unit). By default a |
| | | * duration property definition uses seconds. |
| | | * |
| | | * @param unit |
| | | * The base unit (must not be <code>null</code>). |
| | | * @throws IllegalArgumentException |
| | | * If the provided base unit is bigger than the maximum |
| | | * unit. |
| | | */ |
| | | public final void setBaseUnit(DurationUnit unit) |
| | | throws IllegalArgumentException { |
| | | ensureNotNull(unit); |
| | | |
| | | // Make sure that the base unit is not bigger than the maximum |
| | | // unit. |
| | | if (maximumUnit != null) { |
| | | if (unit.getDuration() > maximumUnit.getDuration()) { |
| | | throw new IllegalArgumentException( |
| | | "Base unit greater than maximum unit"); |
| | | } |
| | | } |
| | | |
| | | this.baseUnit = unit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the maximum unit for this property definition. By default |
| | | * there is no maximum unit. |
| | | * |
| | | * @param unit |
| | | * The string representation of the maximum unit, or |
| | | * <code>null</code> if there should not be a maximum |
| | | * unit. |
| | | * @throws IllegalArgumentException |
| | | * If the provided unit name did not correspond to a |
| | | * known duration unit, or if the maximum unit is |
| | | * smaller than the base unit. |
| | | */ |
| | | public final void setMaximumUnit(String unit) |
| | | throws IllegalArgumentException { |
| | | if (unit == null) { |
| | | setMaximumUnit((DurationUnit) null); |
| | | } else { |
| | | setMaximumUnit(DurationUnit.getUnit(unit)); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the maximum unit for this property definition. By default |
| | | * there is no maximum unit. |
| | | * |
| | | * @param unit |
| | | * The maximum unit, or <code>null</code> if there |
| | | * should not be a maximum unit. |
| | | * @throws IllegalArgumentException |
| | | * If the provided maximum unit is smaller than the base |
| | | * unit. |
| | | */ |
| | | public final void setMaximumUnit(DurationUnit unit) |
| | | throws IllegalArgumentException { |
| | | if (unit != null) { |
| | | // Make sure that the maximum unit is not smaller than the |
| | | // base unit. |
| | | if (unit.getDuration() < baseUnit.getDuration()) { |
| | | throw new IllegalArgumentException( |
| | | "Maximum unit smaller than base unit"); |
| | | } |
| | | } |
| | | |
| | | this.maximumUnit = unit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the lower limit in milli-seconds. |
| | | * |
| | | * @param lowerLimit |
| | | * The new lower limit (must be >= 0) in milli-seconds. |
| | | * @throws IllegalArgumentException |
| | | * If a negative lower limit was specified, or the lower |
| | | * limit is greater than the upper limit. |
| | | */ |
| | | public final void setLowerLimit(long lowerLimit) |
| | | throws IllegalArgumentException { |
| | | if (lowerLimit < 0) { |
| | | throw new IllegalArgumentException("Negative lower limit"); |
| | | } |
| | | |
| | | if (upperLimit != null && lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | |
| | | this.lowerLimit = lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the lower limit using a string representation of the limit. |
| | | * If the string does not specify a unit, the current base unit |
| | | * will be used. |
| | | * |
| | | * @param lowerLimit |
| | | * The string representation of the new lower limit. |
| | | * @throws IllegalArgumentException |
| | | * If the lower limit could not be parsed, or if a |
| | | * negative lower limit was specified, or the lower |
| | | * limit is greater than the upper limit. |
| | | */ |
| | | public final void setLowerLimit(String lowerLimit) |
| | | throws IllegalArgumentException { |
| | | setLowerLimit(DurationUnit.parseValue(lowerLimit, baseUnit)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the upper limit in milli-seconds. |
| | | * |
| | | * @param upperLimit |
| | | * The new upper limit in milli-seconds, or |
| | | * <code>null</code> if there is no upper limit. |
| | | * @throws IllegalArgumentException |
| | | * If a negative upper limit was specified, or the lower |
| | | * limit is greater than the upper limit or unlimited |
| | | * durations are permitted. |
| | | */ |
| | | public final void setUpperLimit(Long upperLimit) |
| | | throws IllegalArgumentException { |
| | | if (upperLimit != null) { |
| | | if (upperLimit < 0) { |
| | | throw new IllegalArgumentException("Negative upper limit"); |
| | | } |
| | | |
| | | if (lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | |
| | | if (allowUnlimited) { |
| | | throw new IllegalArgumentException( |
| | | "Upper limit specified when unlimited durations are permitted"); |
| | | } |
| | | } |
| | | |
| | | this.upperLimit = upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the upper limit using a string representation of the limit. |
| | | * If the string does not specify a unit, the current base unit |
| | | * will be used. |
| | | * |
| | | * @param upperLimit |
| | | * The string representation of the new upper limit, or |
| | | * <code>null</code> if there is no upper limit. |
| | | * @throws IllegalArgumentException |
| | | * If the upper limit could not be parsed, or if the |
| | | * lower limit is greater than the upper limit. |
| | | */ |
| | | public final void setUpperLimit(String upperLimit) |
| | | throws IllegalArgumentException { |
| | | if (upperLimit == null) { |
| | | setUpperLimit((Long) null); |
| | | } else { |
| | | setUpperLimit(DurationUnit.parseValue(upperLimit, baseUnit)); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specify whether or not this property definition will allow |
| | | * unlimited values (default is false). |
| | | * |
| | | * @param allowUnlimited |
| | | * <code>true</code> if the property will allow |
| | | * unlimited values, or <code>false</code> otherwise. |
| | | * @throws IllegalArgumentException |
| | | * If unlimited values are to be permitted but there is |
| | | * an upper limit specified. |
| | | */ |
| | | public final void setAllowUnlimited(boolean allowUnlimited) |
| | | throws IllegalArgumentException { |
| | | if (allowUnlimited && upperLimit != null) { |
| | | throw new IllegalArgumentException( |
| | | "Upper limit specified when unlimited durations are permitted"); |
| | | } |
| | | |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected DurationPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Long> defaultBehavior) { |
| | | return new DurationPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior, baseUnit, maximumUnit, lowerLimit, |
| | | upperLimit, allowUnlimited); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a duration property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new integer property definition builder. |
| | | */ |
| | | public static Builder createBuilder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private DurationPropertyDefinition(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Long> defaultBehavior, DurationUnit baseUnit, |
| | | DurationUnit maximumUnit, Long lowerLimit, Long upperLimit, |
| | | boolean allowUnlimited) { |
| | | super(d, Long.class, propertyName, options, adminAction, defaultBehavior); |
| | | this.baseUnit = baseUnit; |
| | | this.maximumUnit = maximumUnit; |
| | | this.lowerLimit = lowerLimit; |
| | | this.upperLimit = upperLimit; |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the base unit for this property definition (values including |
| | | * limits are specified in this unit). |
| | | * |
| | | * @return Returns the base unit for this property definition |
| | | * (values including limits are specified in this unit). |
| | | */ |
| | | public DurationUnit getBaseUnit() { |
| | | return baseUnit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the maximum unit for this property definition if specified. |
| | | * |
| | | * @return Returns the maximum unit for this property definition, or |
| | | * <code>null</code> if there is no maximum unit. |
| | | */ |
| | | public DurationUnit getMaximumUnit() { |
| | | return maximumUnit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the lower limit in milli-seconds. |
| | | * |
| | | * @return Returns the lower limit in milli-seconds. |
| | | */ |
| | | public long getLowerLimit() { |
| | | return lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the upper limit in milli-seconds. |
| | | * |
| | | * @return Returns the upper limit in milli-seconds, or |
| | | * <code>null</code> if there is no upper limit. |
| | | */ |
| | | public Long getUpperLimit() { |
| | | return upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether this property allows unlimited durations. |
| | | * |
| | | * @return Returns <code>true</code> if this this property allows |
| | | * unlimited durations. |
| | | */ |
| | | public boolean isAllowUnlimited() { |
| | | return allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(Long value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | long nvalue = baseUnit.toMilliSeconds(value); |
| | | if (!allowUnlimited && nvalue < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | |
| | | // unlimited allowed |
| | | } else if (nvalue >= 0 && nvalue < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | |
| | | if ((upperLimit != null) && (nvalue > upperLimit)) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String encodeValue(Long value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // Make sure that we correctly encode negative values as |
| | | // "unlimited". |
| | | if (allowUnlimited) { |
| | | if (value < 0) { |
| | | return UNLIMITED; |
| | | } |
| | | } |
| | | |
| | | // Encode the size value using the base unit. |
| | | StringBuilder builder = new StringBuilder(); |
| | | builder.append(value); |
| | | builder.append(' '); |
| | | builder.append(baseUnit.toString()); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Long decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | // First check for the special "unlimited" value when necessary. |
| | | if (allowUnlimited) { |
| | | if (value.trim().equalsIgnoreCase(UNLIMITED)) { |
| | | return -1L; |
| | | } |
| | | } |
| | | |
| | | // Parse the string representation. |
| | | long ms; |
| | | try { |
| | | ms = DurationUnit.parseValue(value); |
| | | } catch (NumberFormatException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | // Check the unit is in range - values must not be more granular |
| | | // than the base unit. |
| | | if ((ms % baseUnit.getDuration()) != 0) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | // Convert the value a long in the property's required unit. |
| | | Long i = (long) baseUnit.fromMilliSeconds(ms); |
| | | try { |
| | | validateValue(i); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | return i; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitDuration(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, Long value, P p) { |
| | | return v.visitDuration(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | super.toString(builder); |
| | | |
| | | builder.append(" baseUnit="); |
| | | builder.append(baseUnit); |
| | | |
| | | if (maximumUnit != null) { |
| | | builder.append(" maximumUnit="); |
| | | builder.append(maximumUnit); |
| | | } |
| | | |
| | | builder.append(" lowerLimit="); |
| | | builder.append(lowerLimit); |
| | | builder.append("ms"); |
| | | |
| | | if (upperLimit != null) { |
| | | builder.append(" upperLimit="); |
| | | builder.append(upperLimit); |
| | | builder.append("ms"); |
| | | } |
| | | |
| | | builder.append(" allowUnlimited="); |
| | | builder.append(allowUnlimited); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(Long o1, Long o2) { |
| | | return o1.compareTo(o2); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.HashMap; |
| | | import java.util.Map; |
| | | import java.util.regex.Matcher; |
| | | import java.util.regex.Pattern; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This enumeration defines various duration units. |
| | | */ |
| | | public enum DurationUnit { |
| | | |
| | | /** |
| | | * A day unit. |
| | | */ |
| | | DAYS((long) 24 * 60 * 60 * 1000, "d", "days"), |
| | | |
| | | /** |
| | | * An hour unit. |
| | | */ |
| | | HOURS((long) 60 * 60 * 1000, "h", "hours"), |
| | | |
| | | /** |
| | | * A millisecond unit. |
| | | */ |
| | | MILLI_SECONDS(1L, "ms", "milliseconds"), |
| | | |
| | | /** |
| | | * A minute unit. |
| | | */ |
| | | MINUTES((long) 60 * 1000, "m", "minutes"), |
| | | |
| | | /** |
| | | * A second unit. |
| | | */ |
| | | SECONDS(1000L, "s", "seconds"), |
| | | |
| | | /** |
| | | * A week unit. |
| | | */ |
| | | WEEKS((long) 7 * 24 * 60 * 60 * 1000, "w", "weeks"); |
| | | |
| | | // A lookup table for resolving a unit from its name. |
| | | private static final Map<String, DurationUnit> nameToUnit; |
| | | static { |
| | | nameToUnit = new HashMap<String, DurationUnit>(); |
| | | |
| | | for (DurationUnit unit : DurationUnit.values()) { |
| | | nameToUnit.put(unit.shortName, unit); |
| | | nameToUnit.put(unit.longName, unit); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the unit corresponding to the provided unit name. |
| | | * |
| | | * @param s |
| | | * The name of the unit. Can be the abbreviated or long |
| | | * name and can contain white space and mixed case |
| | | * characters. |
| | | * @return Returns the unit corresponding to the provided unit name. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name did not correspond to a known |
| | | * duration unit. |
| | | */ |
| | | public static DurationUnit getUnit(String s) throws IllegalArgumentException { |
| | | DurationUnit unit = nameToUnit.get(s.trim().toLowerCase()); |
| | | if (unit == null) { |
| | | throw new IllegalArgumentException("Illegal duration unit \"" + s + "\""); |
| | | } |
| | | return unit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parse the provided duration string and return its equivalent |
| | | * duration in milliseconds. The duration string must specify the |
| | | * unit e.g. "10s". This method will parse duration string |
| | | * representations produced from the {@link #toString(long)} method. |
| | | * Therefore, a duration can comprise of multiple duration |
| | | * specifiers, for example <code>1d15m25s</code>. |
| | | * |
| | | * @param s |
| | | * The duration string to be parsed. |
| | | * @return Returns the parsed duration in milliseconds. |
| | | * @throws NumberFormatException |
| | | * If the provided duration string could not be parsed. |
| | | * @see #toString(long) |
| | | */ |
| | | public static long parseValue(String s) throws NumberFormatException { |
| | | return parseValue(s, null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parse the provided duration string and return its equivalent |
| | | * duration in milliseconds. This method will parse duration string |
| | | * representations produced from the {@link #toString(long)} method. |
| | | * Therefore, a duration can comprise of multiple duration |
| | | * specifiers, for example <code>1d15m25s</code>. |
| | | * |
| | | * @param s |
| | | * The duration string to be parsed. |
| | | * @param defaultUnit |
| | | * The default unit to use if there is no unit specified in |
| | | * the duration string, or <code>null</code> if the |
| | | * string must always contain a unit. |
| | | * @return Returns the parsed duration in milliseconds. |
| | | * @throws NumberFormatException |
| | | * If the provided duration string could not be parsed. |
| | | * @see #toString(long) |
| | | */ |
| | | public static long parseValue(String s, DurationUnit defaultUnit) |
| | | throws NumberFormatException { |
| | | String ns = s.trim(); |
| | | if (ns.length() == 0) { |
| | | throw new NumberFormatException("Empty duration value \"" + s + "\""); |
| | | } |
| | | |
| | | Pattern p1 = Pattern.compile("^\\s*((\\d+)\\s*w)?" + "\\s*((\\d+)\\s*d)?" |
| | | + "\\s*((\\d+)\\s*h)?" + "\\s*((\\d+)\\s*m)?" + "\\s*((\\d+)\\s*s)?" |
| | | + "\\s*((\\d+)\\s*ms)?\\s*$", Pattern.CASE_INSENSITIVE); |
| | | Matcher m1 = p1.matcher(ns); |
| | | if (m1.matches()) { |
| | | // Value must be of the form produced by toString(long). |
| | | String weeks = m1.group(2); |
| | | String days = m1.group(4); |
| | | String hours = m1.group(6); |
| | | String minutes = m1.group(8); |
| | | String seconds = m1.group(10); |
| | | String ms = m1.group(12); |
| | | |
| | | long duration = 0; |
| | | |
| | | try { |
| | | if (weeks != null) { |
| | | duration += Long.valueOf(weeks) * WEEKS.getDuration(); |
| | | } |
| | | |
| | | if (days != null) { |
| | | duration += Long.valueOf(days) * DAYS.getDuration(); |
| | | } |
| | | |
| | | if (hours != null) { |
| | | duration += Long.valueOf(hours) * HOURS.getDuration(); |
| | | } |
| | | |
| | | if (minutes != null) { |
| | | duration += Long.valueOf(minutes) * MINUTES.getDuration(); |
| | | } |
| | | |
| | | if (seconds != null) { |
| | | duration += Long.valueOf(seconds) * SECONDS.getDuration(); |
| | | } |
| | | |
| | | if (ms != null) { |
| | | duration += Long.valueOf(ms) * MILLI_SECONDS.getDuration(); |
| | | } |
| | | } catch (NumberFormatException e) { |
| | | throw new NumberFormatException("Invalid duration value \"" + s + "\""); |
| | | } |
| | | |
| | | return duration; |
| | | } else { |
| | | // Value must be a floating point number followed by a unit. |
| | | Pattern p2 = Pattern.compile("^\\s*(\\d+(\\.\\d+)?)\\s*(\\w+)?\\s*$"); |
| | | Matcher m2 = p2.matcher(ns); |
| | | |
| | | if (!m2.matches()) { |
| | | throw new NumberFormatException("Invalid duration value \"" + s + "\""); |
| | | } |
| | | |
| | | // Group 1 is the float. |
| | | double d; |
| | | try { |
| | | d = Double.valueOf(m2.group(1)); |
| | | } catch (NumberFormatException e) { |
| | | throw new NumberFormatException("Invalid duration value \"" + s + "\""); |
| | | } |
| | | |
| | | // Group 3 is the unit. |
| | | String unitString = m2.group(3); |
| | | DurationUnit unit; |
| | | if (unitString == null) { |
| | | if (defaultUnit == null) { |
| | | throw new NumberFormatException("Invalid duration value \"" + s |
| | | + "\""); |
| | | } else { |
| | | unit = defaultUnit; |
| | | } |
| | | } else { |
| | | try { |
| | | unit = getUnit(unitString); |
| | | } catch (IllegalArgumentException e) { |
| | | throw new NumberFormatException("Invalid duration value \"" + s |
| | | + "\""); |
| | | } |
| | | } |
| | | |
| | | return unit.toMilliSeconds(d); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns a string representation of the provided duration. The |
| | | * string representation can be parsed using the |
| | | * {@link #parseValue(String)} method. The string representation is |
| | | * comprised of one or more of the number of weeks, days, hours, |
| | | * minutes, seconds, and milliseconds. Here are some examples: |
| | | * |
| | | * <pre> |
| | | * toString(0) // 0 ms |
| | | * toString(999) // 999 ms |
| | | * toString(1000) // 1 s |
| | | * toString(1500) // 1 s 500 ms |
| | | * toString(3650000) // 1 h 50 s |
| | | * toString(3700000) // 1 h 1 m 40 s |
| | | * </pre> |
| | | * |
| | | * @param duration |
| | | * The duration in milliseconds. |
| | | * @return Returns a string representation of the provided duration. |
| | | * @throws IllegalArgumentException |
| | | * If the provided duration is negative. |
| | | * @see #parseValue(String) |
| | | * @see #parseValue(String, DurationUnit) |
| | | */ |
| | | public static String toString(long duration) throws IllegalArgumentException { |
| | | if (duration < 0) { |
| | | throw new IllegalArgumentException("Negative duration " + duration); |
| | | } |
| | | |
| | | if (duration == 0) { |
| | | return "0 ms"; |
| | | } |
| | | |
| | | DurationUnit[] units = new DurationUnit[] { WEEKS, DAYS, HOURS, MINUTES, |
| | | SECONDS, MILLI_SECONDS }; |
| | | long remainder = duration; |
| | | StringBuilder builder = new StringBuilder(); |
| | | boolean isFirst = true; |
| | | for (DurationUnit unit : units) { |
| | | long count = remainder / unit.getDuration(); |
| | | if (count > 0) { |
| | | if (!isFirst) { |
| | | builder.append(' '); |
| | | } |
| | | builder.append(count); |
| | | builder.append(' '); |
| | | builder.append(unit.getShortName()); |
| | | remainder = remainder - (count * unit.getDuration()); |
| | | isFirst = false; |
| | | } |
| | | } |
| | | return builder.toString(); |
| | | } |
| | | |
| | | // The long name of the unit. |
| | | private final String longName; |
| | | |
| | | // The abbreviation of the unit. |
| | | private final String shortName; |
| | | |
| | | // The size of the unit in milliseconds. |
| | | private final long sz; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private DurationUnit(long sz, String shortName, String longName) { |
| | | this.sz = sz; |
| | | this.shortName = shortName; |
| | | this.longName = longName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Converts the specified duration in milliseconds to this unit. |
| | | * |
| | | * @param duration |
| | | * The duration in milliseconds. |
| | | * @return Returns milliseconds in this unit. |
| | | */ |
| | | public double fromMilliSeconds(long duration) { |
| | | return ((double) duration / sz); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the number of milliseconds that this unit represents. |
| | | * |
| | | * @return Returns the number of milliseconds that this unit |
| | | * represents. |
| | | */ |
| | | public long getDuration() { |
| | | return sz; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the long name of this unit. |
| | | * |
| | | * @return Returns the long name of this unit. |
| | | */ |
| | | public String getLongName() { |
| | | return longName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the abbreviated name of this unit. |
| | | * |
| | | * @return Returns the abbreviated name of this unit. |
| | | */ |
| | | public String getShortName() { |
| | | return shortName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Converts the specified duration in this unit to milliseconds. |
| | | * |
| | | * @param duration |
| | | * The duration as a quantity of this unit. |
| | | * @return Returns the number of milliseconds that the duration |
| | | * represents. |
| | | */ |
| | | public long toMilliSeconds(double duration) { |
| | | return (long) (sz * duration); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | * <p> |
| | | * This implementation returns the abbreviated name of this duration |
| | | * unit. |
| | | */ |
| | | @Override |
| | | public String toString() { |
| | | return shortName; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | import java.util.HashMap; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Enumeration property definition. |
| | | * |
| | | * @param <E> |
| | | * The enumeration that should be used for values of this |
| | | * property definition. |
| | | */ |
| | | public final class EnumPropertyDefinition<E extends Enum<E>> extends |
| | | PropertyDefinition<E> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing enumeration property |
| | | * definitions. |
| | | * |
| | | * @param <E> |
| | | * The enumeration that should be used for values of this |
| | | * property definition. |
| | | */ |
| | | public static class Builder<E extends Enum<E>> extends |
| | | AbstractBuilder<E, EnumPropertyDefinition<E>> { |
| | | |
| | | // The enumeration class. |
| | | private Class<E> enumClass; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | this.enumClass = null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the enumeration class which should be used for values of |
| | | * this property definition. |
| | | * |
| | | * @param enumClass |
| | | * The enumeration class which should be used for values |
| | | * of this property definition. |
| | | */ |
| | | public final void setEnumClass(Class<E> enumClass) { |
| | | this.enumClass = enumClass; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected EnumPropertyDefinition<E> buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<E> defaultBehavior) { |
| | | // Make sure that the enumeration class has been defined. |
| | | if (enumClass == null) { |
| | | throw new IllegalStateException("Enumeration class undefined"); |
| | | } |
| | | |
| | | return new EnumPropertyDefinition<E>(d, propertyName, options, |
| | | adminAction, defaultBehavior, enumClass); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an enumeration property definition builder. |
| | | * |
| | | * @param <E> |
| | | * The enumeration that should be used for values of this |
| | | * property definition. |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new enumeration property definition builder. |
| | | */ |
| | | public static <E extends Enum<E>> Builder<E> createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder<E>(d, propertyName); |
| | | } |
| | | |
| | | // The enumeration class. |
| | | private final Class<E> enumClass; |
| | | |
| | | // Map used for decoding values. |
| | | private final Map<String, E> decodeMap; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private EnumPropertyDefinition(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<E> defaultBehavior, Class<E> enumClass) { |
| | | super(d, enumClass, propertyName, options, adminAction, defaultBehavior); |
| | | this.enumClass = enumClass; |
| | | |
| | | // Initialize the decoding map. |
| | | this.decodeMap = new HashMap<String, E>(); |
| | | for (E value : EnumSet.<E> allOf(enumClass)) { |
| | | String s = value.toString().trim().toLowerCase(); |
| | | this.decodeMap.put(s, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitEnum(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, E value, P p) { |
| | | return v.visitEnum(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public E decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | String nvalue = value.trim().toLowerCase(); |
| | | E eValue = decodeMap.get(nvalue); |
| | | if (eValue == null) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } else { |
| | | return eValue; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the enumeration class used for values of this property. |
| | | * |
| | | * @return Returns the enumeration class used for values of this |
| | | * property. |
| | | */ |
| | | public Class<E> getEnumClass() { |
| | | return enumClass; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of the specified enumeration value of this |
| | | * enumeration property definition in the default locale. |
| | | * |
| | | * @param value |
| | | * The enumeration value. |
| | | * @return Returns the synopsis of the specified enumeration value |
| | | * of this enumeration property definition in the default |
| | | * locale. |
| | | */ |
| | | public final Message getValueSynopsis(E value) { |
| | | return getValueSynopsis(Locale.getDefault(), value); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of the specified enumeration value of this |
| | | * enumeration property definition in the specified locale. |
| | | * |
| | | * @param value |
| | | * The enumeration value. |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of the specified enumeration value |
| | | * of this enumeration property definition in the specified |
| | | * locale. |
| | | */ |
| | | public final Message getValueSynopsis(Locale locale, E value) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + getName() |
| | | + ".syntax.enumeration.value." + value.toString() |
| | | + ".synopsis"; |
| | | try { |
| | | return resource.getMessage(getManagedObjectDefinition(), |
| | | property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String normalizeValue(E value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | return value.toString().trim().toLowerCase(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(E value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No additional validation required. |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.Locale; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.client.AuthorizationException; |
| | | import org.opends.server.admin.client.ClientConstraintHandler; |
| | | import org.opends.server.admin.client.CommunicationException; |
| | | import org.opends.server.admin.client.ManagedObject; |
| | | import org.opends.server.admin.client.ManagementContext; |
| | | import org.opends.server.admin.condition.Condition; |
| | | import org.opends.server.admin.server.ServerConstraintHandler; |
| | | import org.opends.server.admin.server.ServerManagedObject; |
| | | import org.opends.server.config.ConfigException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A generic constraint which comprises of an underlying condition and |
| | | * a description. The condition must evaluate to <code>true</code> |
| | | * in order for a new managed object to be created or modified. |
| | | */ |
| | | public class GenericConstraint extends Constraint { |
| | | |
| | | /** |
| | | * The client-side constraint handler. |
| | | */ |
| | | private class ClientHandler extends ClientConstraintHandler { |
| | | |
| | | // Private constructor. |
| | | private ClientHandler() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isAddAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | if (!condition.evaluate(context, managedObject)) { |
| | | unacceptableReasons.add(getSynopsis()); |
| | | return false; |
| | | } else { |
| | | return true; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isModifyAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | if (!condition.evaluate(context, managedObject)) { |
| | | unacceptableReasons.add(getSynopsis()); |
| | | return false; |
| | | } else { |
| | | return true; |
| | | } |
| | | } |
| | | |
| | | }; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The server-side constraint handler. |
| | | */ |
| | | private class ServerHandler extends ServerConstraintHandler { |
| | | |
| | | // Private constructor. |
| | | private ServerHandler() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean isUsable(ServerManagedObject<?> managedObject, |
| | | Collection<Message> unacceptableReasons) throws ConfigException { |
| | | if (!condition.evaluate(managedObject)) { |
| | | unacceptableReasons.add(getSynopsis()); |
| | | return false; |
| | | } else { |
| | | return true; |
| | | } |
| | | } |
| | | |
| | | }; |
| | | |
| | | // The client-side constraint handler. |
| | | private final ClientConstraintHandler clientHandler = new ClientHandler(); |
| | | |
| | | // The condition associated with this constraint. |
| | | private final Condition condition; |
| | | |
| | | // The managed object definition associated with this constraint. |
| | | private final AbstractManagedObjectDefinition<?, ?> definition; |
| | | |
| | | // The constraint ID. |
| | | private final int id; |
| | | |
| | | // The server-side constraint handler. |
| | | private final ServerConstraintHandler serverHandler = new ServerHandler(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new generic constraint. |
| | | * |
| | | * @param definition |
| | | * The managed object definition associated with this |
| | | * constraint. |
| | | * @param id |
| | | * The constraint ID. |
| | | * @param condition |
| | | * The condition associated with this constraint. |
| | | */ |
| | | public GenericConstraint(AbstractManagedObjectDefinition<?, ?> definition, |
| | | int id, Condition condition) { |
| | | this.definition = definition; |
| | | this.id = id; |
| | | this.condition = condition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ClientConstraintHandler> getClientConstraintHandlers() { |
| | | return Collections.singleton(clientHandler); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public Collection<ServerConstraintHandler> getServerConstraintHandlers() { |
| | | return Collections.singleton(serverHandler); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this constraint in the default locale. |
| | | * |
| | | * @return Returns the synopsis of this constraint in the default |
| | | * locale. |
| | | */ |
| | | public final Message getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this constraint in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this constraint in the specified |
| | | * locale. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "constraint." + id + ".synopsis"; |
| | | return resource.getMessage(definition, property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception { |
| | | condition.initialize(definition); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | import org.opends.server.config.ConfigException; |
| | | import org.opends.server.types.AddressMask; |
| | | |
| | | |
| | | |
| | | /** |
| | | * IP address mask property definition. |
| | | */ |
| | | public final class IPAddressMaskPropertyDefinition extends |
| | | PropertyDefinition<AddressMask> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing IP address mask property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<AddressMask, IPAddressMaskPropertyDefinition> { |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected IPAddressMaskPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<AddressMask> defaultBehavior) { |
| | | return new IPAddressMaskPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a IP address mask property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new IP address mask property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private IPAddressMaskPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<AddressMask> defaultBehavior) { |
| | | super(d, AddressMask.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(AddressMask value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No additional validation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public AddressMask decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | return AddressMask.decode(value); |
| | | } catch (ConfigException e) { |
| | | // TODO: it would be nice to throw the cause. |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitIPAddressMask(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, AddressMask value, P p) { |
| | | return v.visitIPAddressMask(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(AddressMask o1, AddressMask o2) { |
| | | return o1.toString().compareTo(o2.toString()); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.net.InetAddress; |
| | | import java.net.UnknownHostException; |
| | | import java.util.EnumSet; |
| | | |
| | | |
| | | |
| | | /** |
| | | * IP address property definition. |
| | | */ |
| | | public final class IPAddressPropertyDefinition extends |
| | | PropertyDefinition<InetAddress> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing IP address property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<InetAddress, IPAddressPropertyDefinition> { |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected IPAddressPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<InetAddress> defaultBehavior) { |
| | | return new IPAddressPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a IP address property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new IP address property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private IPAddressPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<InetAddress> defaultBehavior) { |
| | | super(d, InetAddress.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(InetAddress value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // No additional validation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public InetAddress decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | return InetAddress.getByName(value); |
| | | } catch (UnknownHostException e) { |
| | | // TODO: it would be nice to throw the cause. |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String encodeValue(InetAddress value) |
| | | throws IllegalPropertyValueException { |
| | | // We should return the host name if it is available, or the IP |
| | | // address if not. |
| | | |
| | | // Unforunately, there is no InetAddress method for doing this, so |
| | | // we have to resort to hacking at the toString() encoding. |
| | | String s = value.toString(); |
| | | int i = s.indexOf('/'); |
| | | if (i > 0) { |
| | | // Host address is before the forward slash. |
| | | return s.substring(0, i); |
| | | } else { |
| | | return value.getHostAddress(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitIPAddress(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, InetAddress value, P p) { |
| | | return v.visitIPAddress(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(InetAddress o1, InetAddress o2) { |
| | | return o1.getHostAddress().compareTo(o2.getHostAddress()); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown to indicate that a property value was invalid according to |
| | | * its associated property definition. |
| | | */ |
| | | public class IllegalPropertyValueException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -3145632074909281823L; |
| | | |
| | | // The illegal property value. |
| | | private final Object value; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new illegal property value exception. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | * @param value |
| | | * The illegal property value. |
| | | */ |
| | | public IllegalPropertyValueException(PropertyDefinition<?> pd, Object value) { |
| | | super(pd, createMessage(pd, value)); |
| | | this.value = value; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the illegal property value that caused the exception. |
| | | * |
| | | * @return Returns the illegal property value. |
| | | */ |
| | | public final Object getIllegalValue() { |
| | | return value; |
| | | } |
| | | |
| | | |
| | | |
| | | // Create the message. |
| | | private static Message createMessage(PropertyDefinition<?> pd, Object value) { |
| | | PropertyDefinitionUsageBuilder builder = new PropertyDefinitionUsageBuilder( |
| | | true); |
| | | return ERR_ILLEGAL_PROPERTY_VALUE_EXCEPTION.get(String.valueOf(value), pd |
| | | .getName(), builder.getUsage(pd)); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown to indicate that a property value string was invalid |
| | | * according to its associated property definition. |
| | | */ |
| | | public class IllegalPropertyValueStringException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -3145632074909281823L; |
| | | |
| | | // The illegal property value string. |
| | | private final String value; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new illegal property value string exception. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | * @param value |
| | | * The illegal property value string. |
| | | */ |
| | | public IllegalPropertyValueStringException(PropertyDefinition<?> pd, |
| | | String value) { |
| | | super(pd, createMessage(pd, value)); |
| | | this.value = value; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the illegal property value string that caused the exception. |
| | | * |
| | | * @return Returns the illegal property value string. |
| | | */ |
| | | public final String getIllegalValueString() { |
| | | return value; |
| | | } |
| | | |
| | | |
| | | |
| | | // Create the message. |
| | | private static Message createMessage(PropertyDefinition<?> pd, String value) { |
| | | PropertyDefinitionUsageBuilder builder = new PropertyDefinitionUsageBuilder( |
| | | true); |
| | | return ERR_ILLEGAL_PROPERTY_VALUE_STRING_EXCEPTION.get(value, pd.getName(), |
| | | builder.getUsage(pd)); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | import java.util.Collections; |
| | | import java.util.HashMap; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A managed object composite relationship definition which represents |
| | | * a composition of zero or more managed objects. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public final class InstantiableRelationDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends RelationDefinition<C, S> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing instantiable relation |
| | | * definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this relation definition refers to. |
| | | */ |
| | | public static final class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractBuilder<C, S, InstantiableRelationDefinition<C, S>> { |
| | | |
| | | // The optional naming property definition. |
| | | private PropertyDefinition<?> namingPropertyDefinition = null; |
| | | |
| | | // The plural name of the relation. |
| | | private final String pluralName; |
| | | |
| | | // The optional default managed objects associated with this |
| | | // instantiable relation definition. |
| | | private final Map<String, DefaultManagedObject<? extends C, ? extends S>> |
| | | defaultManagedObjects = new HashMap<String, |
| | | DefaultManagedObject<? extends C, ? extends S>>(); |
| | | |
| | | |
| | | /** |
| | | * Creates a new builder which can be used to incrementally build |
| | | * an instantiable relation definition. |
| | | * |
| | | * @param pd |
| | | * The parent managed object definition. |
| | | * @param name |
| | | * The name of the relation. |
| | | * @param pluralName |
| | | * The plural name of the relation. |
| | | * @param cd |
| | | * The child managed object definition. |
| | | */ |
| | | public Builder(AbstractManagedObjectDefinition<?, ?> pd, String name, |
| | | String pluralName, AbstractManagedObjectDefinition<C, S> cd) { |
| | | super(pd, name, cd); |
| | | this.pluralName = pluralName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the named default managed object to this instantiable |
| | | * relation definition. |
| | | * |
| | | * @param name |
| | | * The name of the default managed object. |
| | | * @param defaultManagedObject |
| | | * The default managed object. |
| | | */ |
| | | public void setDefaultManagedObject(String name, |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) { |
| | | this.defaultManagedObjects.put(name, defaultManagedObject); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the naming property for the instantiable relation |
| | | * definition. |
| | | * |
| | | * @param namingPropertyDefinition |
| | | * The property of the child managed object definition |
| | | * which should be used for naming, or <code>null</code> |
| | | * if this relation does not use a property for naming. |
| | | */ |
| | | public void setNamingProperty( |
| | | PropertyDefinition<?> namingPropertyDefinition) { |
| | | ensureNotNull(namingPropertyDefinition); |
| | | this.namingPropertyDefinition = namingPropertyDefinition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected InstantiableRelationDefinition<C, S> buildInstance( |
| | | Common<C, S> common) { |
| | | return new InstantiableRelationDefinition<C, S>(common, pluralName, |
| | | namingPropertyDefinition, defaultManagedObjects); |
| | | } |
| | | |
| | | } |
| | | |
| | | // The optional naming property definition. |
| | | private final PropertyDefinition<?> namingPropertyDefinition; |
| | | |
| | | // The plural name of the relation. |
| | | private final String pluralName; |
| | | |
| | | // The optional default managed objects associated with this |
| | | // instantiable relation definition. |
| | | private final Map<String, DefaultManagedObject<? extends C, ? extends S>> |
| | | defaultManagedObjects; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private InstantiableRelationDefinition(Common<C, S> common, |
| | | String pluralName, |
| | | PropertyDefinition<?> namingPropertyDefinition, |
| | | Map<String, DefaultManagedObject<? extends C, ? extends S>> |
| | | defaultManagedObjects) { |
| | | super(common); |
| | | this.pluralName = pluralName; |
| | | this.namingPropertyDefinition = namingPropertyDefinition; |
| | | this.defaultManagedObjects = defaultManagedObjects; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(RelationDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitInstantiable(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the named default managed object associated with this |
| | | * instantiable relation definition. |
| | | * |
| | | * @param name |
| | | * The name of the default managed object. |
| | | * @return Returns the named default managed object. |
| | | * @throws IllegalArgumentException |
| | | * If there is no default managed object associated with |
| | | * the provided name. |
| | | */ |
| | | public DefaultManagedObject<? extends C, ? extends S> getDefaultManagedObject( |
| | | String name) throws IllegalArgumentException { |
| | | if (!defaultManagedObjects.containsKey(name)) { |
| | | throw new IllegalArgumentException( |
| | | "unrecognized default managed object \"" + name + "\""); |
| | | } |
| | | return defaultManagedObjects.get(name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the names of the default managed objects associated with |
| | | * this instantiable relation definition. |
| | | * |
| | | * @return Returns an unmodifiable set containing the names of the |
| | | * default managed object. |
| | | */ |
| | | public Set<String> getDefaultManagedObjectNames() { |
| | | return Collections.unmodifiableSet(defaultManagedObjects.keySet()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the property of the child managed object definition which |
| | | * should be used for naming children. |
| | | * |
| | | * @return Returns the property of the child managed object |
| | | * definition which should be used for naming, or |
| | | * <code>null</code> if this relation does not use a |
| | | * property for naming. |
| | | */ |
| | | public PropertyDefinition<?> getNamingPropertyDefinition() { |
| | | return namingPropertyDefinition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the plural name of the relation. |
| | | * |
| | | * @return Returns the plural name of the relation. |
| | | */ |
| | | public String getPluralName() { |
| | | return pluralName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this relation definition in |
| | | * the default locale. |
| | | * |
| | | * @return Returns the user friendly plural name of this relation |
| | | * definition in the default locale. |
| | | */ |
| | | public Message getUserFriendlyPluralName() { |
| | | return getUserFriendlyPluralName(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this relation definition in |
| | | * the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the user friendly plural name of this relation |
| | | * definition in the specified locale. |
| | | */ |
| | | public Message getUserFriendlyPluralName(Locale locale) { |
| | | String property = "relation." + getName() + ".user-friendly-plural-name"; |
| | | return ManagedObjectDefinitionI18NResource.getInstance().getMessage( |
| | | getParentDefinition(), property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | builder.append("name="); |
| | | builder.append(getName()); |
| | | builder.append(" type=collection parent="); |
| | | builder.append(getParentDefinition().getName()); |
| | | builder.append(" child="); |
| | | builder.append(getChildDefinition().getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception { |
| | | for (DefaultManagedObject<?, ?> dmo : defaultManagedObjects.values()) { |
| | | dmo.initialize(); |
| | | } |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | import java.util.Locale; |
| | | import java.util.MissingResourceException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Integer property definition. |
| | | * <p> |
| | | * All values must be zero or positive and within the lower/upper limit |
| | | * constraints. Support is provided for "unlimited" values. These are |
| | | * represented using a negative value or using the string "unlimited". |
| | | */ |
| | | public final class IntegerPropertyDefinition extends |
| | | PropertyDefinition<Integer> { |
| | | |
| | | // String used to represent unlimited. |
| | | private static final String UNLIMITED = "unlimited"; |
| | | |
| | | // The lower limit of the property value. |
| | | private final int lowerLimit; |
| | | |
| | | // The optional upper limit of the property value. |
| | | private final Integer upperLimit; |
| | | |
| | | // Indicates whether this property allows the use of the "unlimited" value |
| | | // (represented using a -1 or the string "unlimited"). |
| | | private final boolean allowUnlimited; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing integer property definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<Integer, IntegerPropertyDefinition> { |
| | | |
| | | // The lower limit of the property value. |
| | | private int lowerLimit = 0; |
| | | |
| | | // The optional upper limit of the property value. |
| | | private Integer upperLimit = null; |
| | | |
| | | // Indicates whether this property allows the use of the "unlimited" value |
| | | // (represented using a -1 or the string "unlimited"). |
| | | private boolean allowUnlimited = false; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the lower limit. |
| | | * |
| | | * @param lowerLimit |
| | | * The new lower limit (must be >= 0). |
| | | * @throws IllegalArgumentException |
| | | * If a negative lower limit was specified or the lower limit is |
| | | * greater than the upper limit. |
| | | */ |
| | | public final void setLowerLimit(int lowerLimit) |
| | | throws IllegalArgumentException { |
| | | if (lowerLimit < 0) { |
| | | throw new IllegalArgumentException("Negative lower limit"); |
| | | } |
| | | if (upperLimit != null && lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | this.lowerLimit = lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the upper limit. |
| | | * |
| | | * @param upperLimit |
| | | * The new upper limit or <code>null</code> if there is no upper |
| | | * limit. |
| | | */ |
| | | public final void setUpperLimit(Integer upperLimit) { |
| | | if (upperLimit != null) { |
| | | if (upperLimit < 0) { |
| | | throw new IllegalArgumentException("Negative lower limit"); |
| | | } |
| | | if (lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | } |
| | | this.upperLimit = upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specify whether or not this property definition will allow unlimited |
| | | * values (default is false). |
| | | * |
| | | * @param allowUnlimited |
| | | * <code>true</code> if the property will allow unlimited values, |
| | | * or <code>false</code> otherwise. |
| | | */ |
| | | public final void setAllowUnlimited(boolean allowUnlimited) { |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected IntegerPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Integer> defaultBehavior) { |
| | | return new IntegerPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior, lowerLimit, upperLimit, allowUnlimited); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an integer property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new integer property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private IntegerPropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Integer> defaultBehavior, int lowerLimit, |
| | | Integer upperLimit, boolean allowUnlimited) { |
| | | super(d, Integer.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | this.lowerLimit = lowerLimit; |
| | | this.upperLimit = upperLimit; |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the lower limit. |
| | | * |
| | | * @return Returns the lower limit. |
| | | */ |
| | | public int getLowerLimit() { |
| | | return lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the upper limit. |
| | | * |
| | | * @return Returns the upper limit or <code>null</code> if there is no upper |
| | | * limit. |
| | | */ |
| | | public Integer getUpperLimit() { |
| | | return upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional unit synopsis of this integer property |
| | | * definition in the default locale. |
| | | * |
| | | * @return Returns the unit synopsis of this integer property |
| | | * definition in the default locale, or <code>null</code> |
| | | * if there is no unit synopsis. |
| | | */ |
| | | public Message getUnitSynopsis() { |
| | | return getUnitSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional unit synopsis of this integer property |
| | | * definition in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the unit synopsis of this integer property |
| | | * definition in the specified locale, or <code>null</code> |
| | | * if there is no unit synopsis. |
| | | */ |
| | | public Message getUnitSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + getName() + ".syntax.integer.unit-synopsis"; |
| | | try { |
| | | return resource.getMessage(getManagedObjectDefinition(), |
| | | property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether this property allows unlimited values. |
| | | * |
| | | * @return Returns <code>true</code> if this this property allows unlimited |
| | | * values. |
| | | */ |
| | | public boolean isAllowUnlimited() { |
| | | return allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(Integer value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | if (!allowUnlimited && value < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | |
| | | // unlimited allowed |
| | | } else if (value >= 0 && value < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | |
| | | if ((upperLimit != null) && (value > upperLimit)) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String encodeValue(Integer value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // Make sure that we correctly encode negative values as "unlimited". |
| | | if (allowUnlimited) { |
| | | if (value < 0) { |
| | | return UNLIMITED; |
| | | } |
| | | } |
| | | |
| | | return value.toString(); |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Integer decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | if (allowUnlimited) { |
| | | if (value.trim().equalsIgnoreCase(UNLIMITED)) { |
| | | return -1; |
| | | } |
| | | } |
| | | |
| | | Integer i; |
| | | try { |
| | | i = Integer.valueOf(value); |
| | | } catch (NumberFormatException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | try { |
| | | validateValue(i); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | return i; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitInteger(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, Integer value, P p) { |
| | | return v.visitInteger(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | super.toString(builder); |
| | | |
| | | builder.append(" lowerLimit="); |
| | | builder.append(lowerLimit); |
| | | |
| | | if (upperLimit != null) { |
| | | builder.append(" upperLimit="); |
| | | builder.append(upperLimit); |
| | | } |
| | | |
| | | builder.append(" allowUnlimited="); |
| | | builder.append(allowUnlimited); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(Integer o1, Integer o2) { |
| | | return o1.compareTo(o2); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Arrays; |
| | | import java.util.HashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.MissingResourceException; |
| | | import java.util.NoSuchElementException; |
| | | import java.util.Set; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This class is used to map configuration elements to their LDAP |
| | | * schema names. |
| | | * <p> |
| | | * It is possible to augment the core LDAP profile with additional |
| | | * profile mappings at run-time using instances of {@link Wrapper}. |
| | | * This is useful for unit tests which need to add and remove mock |
| | | * components. |
| | | */ |
| | | public final class LDAPProfile { |
| | | |
| | | /** |
| | | * LDAP profile wrappers can be used to provide temporary LDAP |
| | | * profile information for components which do not have LDAP profile |
| | | * property files. These components are typically "mock" components |
| | | * used in unit-tests. |
| | | */ |
| | | public static abstract class Wrapper { |
| | | |
| | | /** |
| | | * Default constructor. |
| | | */ |
| | | protected Wrapper() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the LDAP attribute associated with the |
| | | * specified property definition. |
| | | * <p> |
| | | * The default implementation of this method is to return |
| | | * <code>null</code>. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param pd |
| | | * The property definition. |
| | | * @return Returns the name of the LDAP attribute associated with |
| | | * the specified property definition, or <code>null</code> |
| | | * if the property definition is not handled by this LDAP |
| | | * profile wrapper. |
| | | */ |
| | | public String getAttributeName(AbstractManagedObjectDefinition<?, ?> d, |
| | | PropertyDefinition<?> pd) { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the LDAP RDN attribute type for child entries of an |
| | | * instantiable relation. |
| | | * <p> |
| | | * The default implementation of this method is to return |
| | | * <code>null</code>. |
| | | * |
| | | * @param r |
| | | * The instantiable relation. |
| | | * @return Returns the LDAP RDN attribute type for child entries |
| | | * of an instantiable relation, or <code>null</code> if |
| | | * the instantiable relation is not handled by this LDAP |
| | | * profile wrapper. |
| | | */ |
| | | public String getRelationChildRDNType( |
| | | InstantiableRelationDefinition<?, ?> r) { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the LDAP RDN attribute type for child entries of an set |
| | | * relation. |
| | | * <p> |
| | | * The default implementation of this method is to return |
| | | * <code>null</code>. |
| | | * |
| | | * @param r |
| | | * The set relation. |
| | | * @return Returns the LDAP RDN attribute type for child entries of |
| | | * an set relation, or <code>null</code> if the set relation |
| | | * is not handled by this LDAP profile wrapper. |
| | | */ |
| | | public String getRelationChildRDNType(SetRelationDefinition<?, ?> r) |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the principle object class associated with the specified |
| | | * definition. |
| | | * <p> |
| | | * The default implementation of this method is to return |
| | | * <code>null</code>. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns the principle object class associated with the |
| | | * specified definition, or <code>null</code> if the |
| | | * managed object definition is not handled by this LDAP |
| | | * profile wrapper. |
| | | */ |
| | | public String getObjectClass(AbstractManagedObjectDefinition<?, ?> d) { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get an LDAP RDN sequence associatied with a relation. |
| | | * <p> |
| | | * The default implementation of this method is to return |
| | | * <code>null</code>. |
| | | * |
| | | * @param r |
| | | * The relation. |
| | | * @return Returns the LDAP RDN sequence associatied with a |
| | | * relation, or <code>null</code> if the relation is not |
| | | * handled by this LDAP profile wrapper. |
| | | */ |
| | | public String getRelationRDNSequence(RelationDefinition<?, ?> r) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | // The singleton instance. |
| | | private static final LDAPProfile INSTANCE = new LDAPProfile(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the global LDAP profile instance. |
| | | * |
| | | * @return Returns the global LDAP profile instance. |
| | | */ |
| | | public static LDAPProfile getInstance() { |
| | | return INSTANCE; |
| | | } |
| | | |
| | | // The list of profile wrappers. |
| | | private final LinkedList<Wrapper> profiles = new LinkedList<Wrapper>();; |
| | | |
| | | // The LDAP profile property table. |
| | | private final ManagedObjectDefinitionResource resource = |
| | | ManagedObjectDefinitionResource.createForProfile("ldap"); |
| | | |
| | | |
| | | |
| | | // Prevent construction. |
| | | private LDAPProfile() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the LDAP attribute associated with the specified |
| | | * property definition. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param pd |
| | | * The property definition. |
| | | * @return Returns the name of the LDAP attribute associated with |
| | | * the specified property definition. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public String getAttributeName(AbstractManagedObjectDefinition<?, ?> d, |
| | | PropertyDefinition<?> pd) throws MissingResourceException { |
| | | for (Wrapper profile : profiles) { |
| | | String attributeName = profile.getAttributeName(d, pd); |
| | | if (attributeName != null) { |
| | | return attributeName; |
| | | } |
| | | } |
| | | return resource.getString(d, "attribute." + pd.getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the LDAP RDN attribute type for child entries of an |
| | | * instantiable relation. |
| | | * |
| | | * @param r |
| | | * The instantiable relation. |
| | | * @return Returns the LDAP RDN attribute type for child entries of |
| | | * an instantiable relation. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public String getRelationChildRDNType( |
| | | InstantiableRelationDefinition<?, ?> r) throws MissingResourceException { |
| | | if (r.getNamingPropertyDefinition() != null) { |
| | | // Use the attribute associated with the naming property. |
| | | return getAttributeName(r.getChildDefinition(), r |
| | | .getNamingPropertyDefinition()); |
| | | } else { |
| | | for (Wrapper profile : profiles) { |
| | | String rdnType = profile.getRelationChildRDNType(r); |
| | | if (rdnType != null) { |
| | | return rdnType; |
| | | } |
| | | } |
| | | return resource.getString(r.getParentDefinition(), "naming-attribute." |
| | | + r.getName()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the LDAP object classes associated with an instantiable or set |
| | | * relation branch. The branch is the parent entry of child managed |
| | | * objects. |
| | | * |
| | | * @param r |
| | | * The instantiable or set relation. |
| | | * @return Returns the LDAP object classes associated with an |
| | | * instantiable or set relation branch. |
| | | */ |
| | | public List<String> getRelationObjectClasses( |
| | | RelationDefinition<?, ?> r) { |
| | | return Arrays.asList(new String[] { "top", "ds-cfg-branch" }); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the LDAP RDN attribute type for child entries of an set |
| | | * relation. |
| | | * |
| | | * @param r |
| | | * The set relation. |
| | | * @return Returns the LDAP RDN attribute type for child entries of an |
| | | * set relation. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public String getRelationChildRDNType(SetRelationDefinition<?, ?> r) |
| | | throws MissingResourceException |
| | | { |
| | | for (Wrapper profile : profiles) |
| | | { |
| | | String rdnType = profile.getRelationChildRDNType(r); |
| | | if (rdnType != null) |
| | | { |
| | | return rdnType; |
| | | } |
| | | } |
| | | return resource.getString(r.getParentDefinition(), |
| | | "naming-attribute." + r.getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the principle object class associated with the specified |
| | | * definition. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns the principle object class associated with the |
| | | * specified definition. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public String getObjectClass(AbstractManagedObjectDefinition<?, ?> d) |
| | | throws MissingResourceException { |
| | | if (d.isTop()) { |
| | | return "top"; |
| | | } |
| | | |
| | | for (Wrapper profile : profiles) { |
| | | String objectClass = profile.getObjectClass(d); |
| | | if (objectClass != null) { |
| | | return objectClass; |
| | | } |
| | | } |
| | | return resource.getString(d, "objectclass"); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get all the object classes associated with the specified |
| | | * definition. |
| | | * <p> |
| | | * The returned list is ordered such that the uppermost object |
| | | * classes appear first (e.g. top). |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns all the object classes associated with the |
| | | * specified definition. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public List<String> getObjectClasses(AbstractManagedObjectDefinition<?, ?> d) |
| | | throws MissingResourceException { |
| | | LinkedList<String> objectClasses = new LinkedList<String>(); |
| | | Set<String> s = new HashSet<String>(); |
| | | |
| | | // Add the object classes from the parent hierarchy. |
| | | while (d != null) { |
| | | String oc = getObjectClass(d); |
| | | if (!s.contains(oc)) { |
| | | objectClasses.addFirst(oc); |
| | | s.add(oc); |
| | | } |
| | | d = d.getParent(); |
| | | } |
| | | |
| | | if (!s.contains("top")) { |
| | | objectClasses.addFirst("top"); |
| | | } |
| | | |
| | | return objectClasses; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get an LDAP RDN sequence associatied with a relation. |
| | | * |
| | | * @param r |
| | | * The relation. |
| | | * @return Returns the LDAP RDN sequence associatied with a |
| | | * relation. |
| | | * @throws MissingResourceException |
| | | * If the LDAP profile properties file associated with the |
| | | * provided managed object definition could not be loaded. |
| | | */ |
| | | public String getRelationRDNSequence(RelationDefinition<?, ?> r) |
| | | throws MissingResourceException { |
| | | for (Wrapper profile : profiles) { |
| | | String rdnSequence = profile.getRelationRDNSequence(r); |
| | | if (rdnSequence != null) { |
| | | return rdnSequence; |
| | | } |
| | | } |
| | | return resource.getString(r.getParentDefinition(), "rdn." + r.getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the last LDAP profile wrapper added using |
| | | * {@link #pushWrapper(org.opends.server.admin.LDAPProfile.Wrapper)}. |
| | | * |
| | | * @throws NoSuchElementException |
| | | * If there are no LDAP profile wrappers. |
| | | */ |
| | | public void popWrapper() throws NoSuchElementException { |
| | | profiles.removeFirst(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Decorates the core LDAP profile with the provided LDAP profile |
| | | * wrapper. All profile requests will be directed to the provided |
| | | * wrapper before being forwarded onto the core profile if the |
| | | * request could not be satisfied. |
| | | * |
| | | * @param wrapper |
| | | * The LDAP profile wrapper. |
| | | */ |
| | | public void pushWrapper(Wrapper wrapper) { |
| | | profiles.addFirst(wrapper); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A managed object could not be created because there is an existing |
| | | * managed object with the same name. |
| | | */ |
| | | public final class ManagedObjectAlreadyExistsException extends |
| | | OperationsException { |
| | | |
| | | /** |
| | | * Version ID required by serializable classes. |
| | | */ |
| | | private static final long serialVersionUID = -2344653674171609366L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a managed object already exists exception. |
| | | */ |
| | | public ManagedObjectAlreadyExistsException() { |
| | | super(ERR_MANAGED_OBJECT_ALREADY_EXISTS_EXCEPTION.get()); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.server.admin.client.ManagedObject; |
| | | import org.opends.server.admin.server.ServerManagedObject; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Defines the structure of a managed object which can be |
| | | * instantiated. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * definition represents. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * definition represents. |
| | | */ |
| | | public abstract class ManagedObjectDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractManagedObjectDefinition<C, S> { |
| | | |
| | | /** |
| | | * Create a new managed object definition. |
| | | * |
| | | * @param name |
| | | * The name of the definition. |
| | | * @param parent |
| | | * The parent definition, or <code>null</code> if there |
| | | * is no parent. |
| | | */ |
| | | protected ManagedObjectDefinition(String name, |
| | | AbstractManagedObjectDefinition<? super C, ? super S> parent) { |
| | | super(name, parent); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a client configuration view of the provided managed |
| | | * object. Modifications made to the underlying managed object will |
| | | * be reflected in the client configuration view and vice versa. |
| | | * |
| | | * @param managedObject |
| | | * The managed object. |
| | | * @return Returns a client configuration view of the provided |
| | | * managed object. |
| | | */ |
| | | public abstract C createClientConfiguration( |
| | | ManagedObject<? extends C> managedObject); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a server configuration view of the provided server |
| | | * managed object. |
| | | * |
| | | * @param managedObject |
| | | * The server managed object. |
| | | * @return Returns a server configuration view of the provided |
| | | * server managed object. |
| | | */ |
| | | public abstract S createServerConfiguration( |
| | | ServerManagedObject<? extends S> managedObject); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the server configuration class instance associated with this |
| | | * managed object definition. |
| | | * |
| | | * @return Returns the server configuration class instance |
| | | * associated with this managed object definition. |
| | | */ |
| | | public abstract Class<S> getServerConfigurationClass(); |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import java.util.HashMap; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | import java.util.ResourceBundle; |
| | | |
| | | import org.forgerock.i18n.LocalizableMessage; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A class for retrieving internationalized resource properties |
| | | * associated with a managed object definition. |
| | | * <p> |
| | | * I18N resource properties are not available for the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public final class ManagedObjectDefinitionI18NResource { |
| | | |
| | | // Application-wide set of instances. |
| | | private static final Map<String, ManagedObjectDefinitionI18NResource> |
| | | INSTANCES = new HashMap<String, ManagedObjectDefinitionI18NResource>(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the internationalized resource instance which can be used to |
| | | * retrieve the localized descriptions for the managed objects and |
| | | * their associated properties and relations. |
| | | * |
| | | * @return Returns the I18N resource instance. |
| | | */ |
| | | public static ManagedObjectDefinitionI18NResource getInstance() { |
| | | return getInstance("admin.messages"); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the internationalized resource instance for the named |
| | | * profile. |
| | | * |
| | | * @param profile |
| | | * The name of the profile. |
| | | * @return Returns the I18N resource instance for the named profile. |
| | | */ |
| | | public static ManagedObjectDefinitionI18NResource getInstanceForProfile( |
| | | String profile) { |
| | | return getInstance("admin.profiles." + profile); |
| | | } |
| | | |
| | | |
| | | |
| | | // Get a resource instance creating it if necessary. |
| | | private synchronized static ManagedObjectDefinitionI18NResource getInstance( |
| | | String prefix) { |
| | | ManagedObjectDefinitionI18NResource instance = INSTANCES |
| | | .get(prefix); |
| | | |
| | | if (instance == null) { |
| | | instance = new ManagedObjectDefinitionI18NResource(prefix); |
| | | INSTANCES.put(prefix, instance); |
| | | } |
| | | |
| | | return instance; |
| | | } |
| | | |
| | | |
| | | |
| | | // Mapping from definition to locale-based resource bundle. |
| | | private final Map<AbstractManagedObjectDefinition<?, ?>, |
| | | Map<Locale, ResourceBundle>> resources; |
| | | |
| | | |
| | | |
| | | // The resource name prefix. |
| | | private final String prefix; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private ManagedObjectDefinitionI18NResource(String prefix) { |
| | | this.resources = new HashMap<AbstractManagedObjectDefinition<?, ?>, |
| | | Map<Locale, ResourceBundle>>(); |
| | | this.prefix = prefix; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the internationalized message associated with the specified |
| | | * key in the default locale. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param key |
| | | * The resource key. |
| | | * @return Returns the internationalized message associated with the |
| | | * specified key in the default locale. |
| | | * @throws MissingResourceException |
| | | * If the key was not found. |
| | | * @throws UnsupportedOperationException |
| | | * If the provided managed object definition was the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public LocalizableMessage getLocalizableMessage(AbstractManagedObjectDefinition<?, ?> d, String key) |
| | | throws MissingResourceException, UnsupportedOperationException { |
| | | return getLocalizableMessage(d, key, Locale.getDefault(), (String[]) null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the internationalized message associated with the specified |
| | | * key and locale. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param key |
| | | * The resource key. |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the internationalized message associated with the |
| | | * specified key and locale. |
| | | * @throws MissingResourceException |
| | | * If the key was not found. |
| | | * @throws UnsupportedOperationException |
| | | * If the provided managed object definition was the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public LocalizableMessage getLocalizableMessage(AbstractManagedObjectDefinition<?, ?> d, |
| | | String key, Locale locale) throws MissingResourceException, |
| | | UnsupportedOperationException { |
| | | return getLocalizableMessage(d, key, locale, (String[]) null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the parameterized internationalized message associated with |
| | | * the specified key and locale. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param key |
| | | * The resource key. |
| | | * @param locale |
| | | * The locale. |
| | | * @param args |
| | | * Arguments that should be inserted into the retrieved |
| | | * message. |
| | | * @return Returns the internationalized message associated with the |
| | | * specified key and locale. |
| | | * @throws MissingResourceException |
| | | * If the key was not found. |
| | | * @throws UnsupportedOperationException |
| | | * If the provided managed object definition was the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public LocalizableMessage getLocalizableMessage(AbstractManagedObjectDefinition<?, ?> d, |
| | | String key, Locale locale, String... args) |
| | | throws MissingResourceException, UnsupportedOperationException { |
| | | ResourceBundle resource = getResourceBundle(d, locale); |
| | | |
| | | // TODO: use message framework directly |
| | | if (args == null) { |
| | | return LocalizableMessage.raw(resource.getString(key)); |
| | | } else { |
| | | return LocalizableMessage.raw(resource.getString(key), (Object[]) args); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the parameterized internationalized message associated with |
| | | * the specified key in the default locale. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param key |
| | | * The resource key. |
| | | * @param args |
| | | * Arguments that should be inserted into the retrieved |
| | | * message. |
| | | * @return Returns the internationalized message associated with the |
| | | * specified key in the default locale. |
| | | * @throws MissingResourceException |
| | | * If the key was not found. |
| | | * @throws UnsupportedOperationException |
| | | * If the provided managed object definition was the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public LocalizableMessage getLocalizableMessage(AbstractManagedObjectDefinition<?, ?> d, |
| | | String key, String... args) throws MissingResourceException, |
| | | UnsupportedOperationException { |
| | | return getLocalizableMessage(d, key, Locale.getDefault(), args); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Forcefully removes any resource bundles associated with the |
| | | * provided definition and using the default locale. |
| | | * <p> |
| | | * This method is intended for internal testing only. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | */ |
| | | synchronized void removeResourceBundle( |
| | | AbstractManagedObjectDefinition<?, ?> d) { |
| | | removeResourceBundle(d, Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Forcefully removes any resource bundles associated with the |
| | | * provided definition and locale. |
| | | * <p> |
| | | * This method is intended for internal testing only. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param locale |
| | | * The locale. |
| | | */ |
| | | synchronized void removeResourceBundle( |
| | | AbstractManagedObjectDefinition<?, ?> d, Locale locale) { |
| | | // Get the locale resource mapping. |
| | | Map<Locale, ResourceBundle> map = resources.get(d); |
| | | if (map != null) { |
| | | map.remove(locale); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Forcefully adds the provided resource bundle to this I18N |
| | | * resource for the default locale. |
| | | * <p> |
| | | * This method is intended for internal testing only. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param resoureBundle |
| | | * The resource bundle to be used. |
| | | */ |
| | | synchronized void setResourceBundle(AbstractManagedObjectDefinition<?, ?> d, |
| | | ResourceBundle resoureBundle) { |
| | | setResourceBundle(d, Locale.getDefault(), resoureBundle); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Forcefully adds the provided resource bundle to this I18N |
| | | * resource. |
| | | * <p> |
| | | * This method is intended for internal testing only. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param locale |
| | | * The locale. |
| | | * @param resoureBundle |
| | | * The resource bundle to be used. |
| | | */ |
| | | synchronized void setResourceBundle(AbstractManagedObjectDefinition<?, ?> d, |
| | | Locale locale, ResourceBundle resoureBundle) { |
| | | // First get the locale-resource mapping, creating it if |
| | | // necessary. |
| | | Map<Locale, ResourceBundle> map = resources.get(d); |
| | | if (map == null) { |
| | | map = new HashMap<Locale, ResourceBundle>(); |
| | | resources.put(d, map); |
| | | } |
| | | |
| | | // Add the resource bundle. |
| | | map.put(locale, resoureBundle); |
| | | } |
| | | |
| | | |
| | | |
| | | // Retrieve the resource bundle associated with a managed object and |
| | | // locale, lazily loading it if necessary. |
| | | private synchronized ResourceBundle getResourceBundle( |
| | | AbstractManagedObjectDefinition<?, ?> d, Locale locale) |
| | | throws MissingResourceException, UnsupportedOperationException { |
| | | if (d.isTop()) { |
| | | throw new UnsupportedOperationException( |
| | | "I18n resources are not available for the " |
| | | + "Top configuration definition"); |
| | | } |
| | | |
| | | // First get the locale-resource mapping, creating it if |
| | | // necessary. |
| | | Map<Locale, ResourceBundle> map = resources.get(d); |
| | | if (map == null) { |
| | | map = new HashMap<Locale, ResourceBundle>(); |
| | | resources.put(d, map); |
| | | } |
| | | |
| | | // Now get the resource based on the locale, loading it if |
| | | // necessary. |
| | | ResourceBundle resourceBundle = map.get(locale); |
| | | if (resourceBundle == null) { |
| | | String baseName = prefix + "." + d.getClass().getName(); |
| | | resourceBundle = ResourceBundle.getBundle(baseName, locale, |
| | | ClassLoaderProvider.getInstance().getClassLoader()); |
| | | map.put(locale, resourceBundle); |
| | | } |
| | | |
| | | return resourceBundle; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.io.BufferedInputStream; |
| | | import java.io.IOException; |
| | | import java.io.InputStream; |
| | | import java.util.HashMap; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | import java.util.Properties; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A class for retrieving non-internationalized resource properties |
| | | * associated with a managed object definition. |
| | | * <p> |
| | | * Resource properties are not available for the {@link TopCfgDefn}. |
| | | */ |
| | | public final class ManagedObjectDefinitionResource { |
| | | |
| | | // Mapping from definition to property tables. |
| | | private final Map<AbstractManagedObjectDefinition<?, ?>, |
| | | Properties> properties; |
| | | |
| | | // The resource name prefix. |
| | | private final String prefix; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new resource instance for the named profile. |
| | | * |
| | | * @param profile |
| | | * The name of the profile. |
| | | * @return Returns the resource instance for the named profile. |
| | | */ |
| | | public static ManagedObjectDefinitionResource createForProfile( |
| | | String profile) { |
| | | return new ManagedObjectDefinitionResource("admin.profiles." |
| | | + profile); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private ManagedObjectDefinitionResource(String prefix) { |
| | | this.properties = |
| | | new HashMap<AbstractManagedObjectDefinition<?, ?>, Properties>(); |
| | | this.prefix = prefix; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the resource value associated with the specified key. |
| | | * |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param key |
| | | * The resource key. |
| | | * @return Returns the resource value associated with the specified |
| | | * key. |
| | | * @throws MissingResourceException |
| | | * If the key was not found. |
| | | * @throws UnsupportedOperationException |
| | | * If the provided managed object definition was the |
| | | * {@link TopCfgDefn}. |
| | | */ |
| | | public String getString(AbstractManagedObjectDefinition<?, ?> d, String key) |
| | | throws MissingResourceException, UnsupportedOperationException { |
| | | if (d.isTop()) { |
| | | throw new UnsupportedOperationException( |
| | | "Profile resources are not available for the " |
| | | + "Top configuration definition"); |
| | | } |
| | | |
| | | Properties p = getProperties(d); |
| | | String result = p.getProperty(key); |
| | | |
| | | if (result == null) { |
| | | String baseName = prefix + "." + d.getClass().getName(); |
| | | String path = baseName.replace('.', '/') + ".properties"; |
| | | |
| | | throw new MissingResourceException("Can't find resource " |
| | | + path + ", key " + key, baseName, key); |
| | | } |
| | | |
| | | return result; |
| | | } |
| | | |
| | | |
| | | |
| | | // Retrieve the properties table associated with a managed object, |
| | | // lazily loading it if necessary. |
| | | private synchronized Properties getProperties( |
| | | AbstractManagedObjectDefinition<?, ?> d) |
| | | throws MissingResourceException { |
| | | Properties p = properties.get(d); |
| | | |
| | | if (p == null) { |
| | | // Load the resource file. |
| | | String baseName = prefix + "." + d.getClass().getName(); |
| | | String path = baseName.replace('.', '/') + ".properties"; |
| | | InputStream stream = ClassLoaderProvider.getInstance() |
| | | .getClassLoader().getResourceAsStream(path); |
| | | |
| | | if (stream == null) { |
| | | throw new MissingResourceException("Can't find resource " |
| | | + path, baseName, ""); |
| | | } |
| | | |
| | | p = new Properties(); |
| | | try { |
| | | p.load(new BufferedInputStream(stream)); |
| | | } catch (IOException e) { |
| | | throw new MissingResourceException("Can't load resource " |
| | | + path + " due to IO exception: " + e.getMessage(), |
| | | baseName, ""); |
| | | } |
| | | |
| | | // Cache the resource. |
| | | properties.put(d, p); |
| | | } |
| | | |
| | | return p; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The requested managed object could not be located. |
| | | */ |
| | | public class ManagedObjectNotFoundException extends OperationsException { |
| | | |
| | | /** |
| | | * Version ID required by serializable classes. |
| | | */ |
| | | private static final long serialVersionUID = -477551786551892978L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a managed object not found exception. |
| | | */ |
| | | public ManagedObjectNotFoundException() { |
| | | super(ERR_MANAGED_OBJECT_NOT_FOUND_EXCEPTION.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a managed object not found exception with the specified |
| | | * cause. |
| | | * |
| | | * @param cause |
| | | * The cause of this exception. |
| | | */ |
| | | public ManagedObjectNotFoundException(Throwable cause) { |
| | | super(ERR_MANAGED_OBJECT_NOT_FOUND_EXCEPTION.get(), cause); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This enumeration contains various options that can be associated |
| | | * with managed object definitions. |
| | | */ |
| | | public enum ManagedObjectOption { |
| | | /** |
| | | * Use this option to identify managed object types which should be |
| | | * considered as advanced and should not be exposed by default in |
| | | * client applications. |
| | | */ |
| | | ADVANCED, |
| | | |
| | | /** |
| | | * Use this option to identify managed object types which must not |
| | | * be directly exposed in client applications. |
| | | */ |
| | | HIDDEN; |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | * Portions Copyright 2011 ForgeRock AS |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Collections; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.regex.Matcher; |
| | | import java.util.regex.Pattern; |
| | | |
| | | import org.opends.server.admin.std.client.RootCfgClient; |
| | | import org.opends.server.admin.std.meta.RootCfgDefn; |
| | | import org.opends.server.admin.std.server.RootCfg; |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.types.*; |
| | | |
| | | |
| | | /** |
| | | * A path which can be used to determine the location of a managed |
| | | * object instance. |
| | | * <p> |
| | | * A path is made up of zero or more elements each of which represents |
| | | * a managed object. Managed objects are arranged hierarchically with |
| | | * the root configuration being the top-most managed object. Elements |
| | | * are ordered such that the root configuration managed object is the |
| | | * first element and subsequent elements representing managed objects |
| | | * further down the hierarchy. |
| | | * <p> |
| | | * A path can be encoded into a string representation using the |
| | | * {@link #toString()} and {@link #toString(StringBuilder)} methods. |
| | | * Conversely, this string representation can be parsed using the |
| | | * {@link #valueOf(String)} method. |
| | | * <p> |
| | | * The string representation of a managed object path is similar in |
| | | * principle to a UNIX file-system path and is defined as follows: |
| | | * <ul> |
| | | * <li>the root element is represented by the string <code>/</code> |
| | | * <li>subordinate elements are arranged in big-endian order |
| | | * separated by a forward slash <code>/</code> character |
| | | * <li>an element representing a managed object associated with a |
| | | * one-to-one (singleton) or one-to-zero-or-one (optional) relation |
| | | * has the form <code>relation=</code><i>relation</i> |
| | | * <code>[+type=</code><i>definition</i><code>]</code>, where |
| | | * <i>relation</i> is the name of the relation and <i>definition</i> |
| | | * is the name of the referenced managed object's definition if |
| | | * required (usually this is implied by the relation itself) |
| | | * <li>an element representing a managed object associated with a |
| | | * one-to-many (instantiable) relation has the form |
| | | * <code>relation=</code><i>relation</i><code>[+type=</code> |
| | | * <i>definition</i><code>]</code><code>+name=</code><i>name</i>, |
| | | * where <i>relation</i> is the name of the relation and |
| | | * <i>definition</i> is the name of the referenced managed object's |
| | | * definition if required (usually this is implied by the relation |
| | | * itself), and <i>name</i> is the name of the managed object |
| | | * instance |
| | | * <li>an element representing a managed object associated with a |
| | | * one-to-many (set) relation has the form |
| | | * <code>relation=</code><i>relation</i><code>[+type=</code> |
| | | * <i>definition</i><code>]</code>, |
| | | * where <i>relation</i> is the name of the relation and |
| | | * <i>definition</i> is the name of the referenced managed object's |
| | | * definition. |
| | | * </ul> |
| | | * The following path string representation identifies a connection |
| | | * handler instance (note that the <code>type</code> is not |
| | | * specified indicating that the path identifies a connection handler |
| | | * called <i>my handler</i> which can be any type of connection |
| | | * handler): |
| | | * |
| | | * <pre> |
| | | * /relation=connection-handler+name=my handler |
| | | * </pre> |
| | | * |
| | | * If the identified connection handler must be an LDAP connection |
| | | * handler then the above path should include the <code>type</code>: |
| | | * |
| | | * <pre> |
| | | * /relation=connection-handler+type=ldap-connection-handler+name=my handler |
| | | * </pre> |
| | | * |
| | | * The final example identifies the global configuration: |
| | | * |
| | | * <pre> |
| | | * /relation=global-configuration |
| | | * </pre> |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * path references. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * path references. |
| | | */ |
| | | public final class ManagedObjectPath<C extends ConfigurationClient, |
| | | S extends Configuration> { |
| | | |
| | | /** |
| | | * A serialize which is used to generate the toDN representation. |
| | | */ |
| | | private static final class DNSerializer implements |
| | | ManagedObjectPathSerializer { |
| | | |
| | | // The current DN. |
| | | private DN dn; |
| | | |
| | | // The LDAP profile. |
| | | private final LDAPProfile profile; |
| | | |
| | | |
| | | |
| | | // Create a new DN builder. |
| | | private DNSerializer() { |
| | | this.dn = DN.nullDN(); |
| | | this.profile = LDAPProfile.getInstance(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | InstantiableRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d, String name) { |
| | | // Add the RDN sequence representing the relation. |
| | | appendManagedObjectPathElement(r); |
| | | |
| | | // Now add the single RDN representing the named instance. |
| | | String type = profile.getRelationChildRDNType(r); |
| | | AttributeType atype = DirectoryServer.getAttributeType( |
| | | type.toLowerCase(), true); |
| | | AttributeValue avalue = AttributeValues.create(atype, name); |
| | | dn = dn.concat(RDN.create(atype, avalue)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SetRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | // Add the RDN sequence representing the relation. |
| | | appendManagedObjectPathElement(r); |
| | | |
| | | // Now add the single RDN representing the instance. |
| | | String type = profile.getRelationChildRDNType(r); |
| | | AttributeType atype = DirectoryServer.getAttributeType( |
| | | type.toLowerCase(), true); |
| | | AttributeValue avalue = AttributeValues.create(atype, d.getName()); |
| | | dn = dn.concat(RDN.create(atype, avalue)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | OptionalRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | // Add the RDN sequence representing the relation. |
| | | appendManagedObjectPathElement(r); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SingletonRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | // Add the RDN sequence representing the relation. |
| | | appendManagedObjectPathElement(r); |
| | | } |
| | | |
| | | |
| | | |
| | | // Appends the RDN sequence representing the provided relation. |
| | | private void appendManagedObjectPathElement(RelationDefinition<?, ?> r) { |
| | | // Add the RDN sequence representing the relation. |
| | | try { |
| | | DN localName = DN.decode(profile.getRelationRDNSequence(r)); |
| | | dn = dn.concat(localName); |
| | | } catch (DirectoryException e) { |
| | | throw new RuntimeException(e); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | // Gets the serialized DN value. |
| | | private DN toDN() { |
| | | return dn; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Abstract path element. |
| | | */ |
| | | private static abstract class Element<C extends ConfigurationClient, |
| | | S extends Configuration> { |
| | | |
| | | // The type of managed object referenced by this element. |
| | | private final AbstractManagedObjectDefinition<C, S> definition; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Protected constructor. |
| | | * |
| | | * @param definition |
| | | * The type of managed object referenced by this element. |
| | | */ |
| | | protected Element(AbstractManagedObjectDefinition<C, S> definition) { |
| | | this.definition = definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the managed object definition associated with this element. |
| | | * |
| | | * @return Returns the managed object definition associated with |
| | | * this element. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<C, S> |
| | | getManagedObjectDefinition() { |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name associated with this element if applicable. |
| | | * |
| | | * @return Returns the name associated with this element if |
| | | * applicable. |
| | | */ |
| | | public String getName() { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the relation definition associated with this element. |
| | | * |
| | | * @return Returns the relation definition associated with this |
| | | * element. |
| | | */ |
| | | public abstract RelationDefinition<? super C, ? super S> |
| | | getRelationDefinition(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Serialize this path element using the provided serialization |
| | | * strategy. |
| | | * |
| | | * @param serializer |
| | | * The managed object path serialization strategy. |
| | | */ |
| | | public abstract void serialize(ManagedObjectPathSerializer serializer); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A path element representing an instantiable managed object. |
| | | */ |
| | | private static final class InstantiableElement |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends Element<C, S> { |
| | | |
| | | // Factory method. |
| | | private static final <C extends ConfigurationClient, |
| | | S extends Configuration> |
| | | InstantiableElement<C, S> create( |
| | | InstantiableRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d, String name) { |
| | | return new InstantiableElement<C, S>(r, d, name); |
| | | } |
| | | |
| | | // The name of the managed object. |
| | | private final String name; |
| | | |
| | | // The instantiable relation. |
| | | private final InstantiableRelationDefinition<? super C, ? super S> r; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private InstantiableElement( |
| | | InstantiableRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d, String name) { |
| | | super(d); |
| | | this.r = r; |
| | | this.name = name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String getName() { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public InstantiableRelationDefinition<? super C, ? super S> |
| | | getRelationDefinition() { |
| | | return r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void serialize(ManagedObjectPathSerializer serializer) { |
| | | serializer.appendManagedObjectPathElement(r, |
| | | getManagedObjectDefinition(), name); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A path element representing an optional managed object. |
| | | */ |
| | | private static final class OptionalElement |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends Element<C, S> { |
| | | |
| | | // Factory method. |
| | | private static final <C extends ConfigurationClient, |
| | | S extends Configuration> OptionalElement<C, S> create( |
| | | OptionalRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | return new OptionalElement<C, S>(r, d); |
| | | } |
| | | |
| | | // The optional relation. |
| | | private final OptionalRelationDefinition<? super C, ? super S> r; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private OptionalElement(OptionalRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | super(d); |
| | | this.r = r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public OptionalRelationDefinition<? super C, ? super S> |
| | | getRelationDefinition() { |
| | | return r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void serialize(ManagedObjectPathSerializer serializer) { |
| | | serializer |
| | | .appendManagedObjectPathElement(r, getManagedObjectDefinition()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A path element representing an set managed object. |
| | | */ |
| | | private static final class SetElement |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends Element<C, S> { |
| | | |
| | | // Factory method. |
| | | private static final <C extends ConfigurationClient, |
| | | S extends Configuration> |
| | | SetElement<C, S> create( |
| | | SetRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | return new SetElement<C, S>(r, d); |
| | | } |
| | | |
| | | // The set relation. |
| | | private final SetRelationDefinition<? super C, ? super S> r; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SetElement( |
| | | SetRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | super(d); |
| | | this.r = r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public SetRelationDefinition<? super C, ? super S> |
| | | getRelationDefinition() { |
| | | return r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void serialize(ManagedObjectPathSerializer serializer) { |
| | | serializer.appendManagedObjectPathElement(r, |
| | | getManagedObjectDefinition()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A path element representing a singleton managed object. |
| | | */ |
| | | private static final class SingletonElement |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends Element<C, S> { |
| | | |
| | | // Factory method. |
| | | private static final <C extends ConfigurationClient, |
| | | S extends Configuration> SingletonElement<C, S> create( |
| | | SingletonRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | return new SingletonElement<C, S>(r, d); |
| | | } |
| | | |
| | | // The singleton relation. |
| | | private final SingletonRelationDefinition<? super C, ? super S> r; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SingletonElement( |
| | | SingletonRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | super(d); |
| | | this.r = r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public SingletonRelationDefinition<? super C, ? super S> |
| | | getRelationDefinition() { |
| | | return r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void serialize(ManagedObjectPathSerializer serializer) { |
| | | serializer |
| | | .appendManagedObjectPathElement(r, getManagedObjectDefinition()); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * A serialize which is used to generate the toString |
| | | * representation. |
| | | */ |
| | | private static final class StringSerializer implements |
| | | ManagedObjectPathSerializer { |
| | | |
| | | // Serialize to this string builder. |
| | | private final StringBuilder builder; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private StringSerializer(StringBuilder builder) { |
| | | this.builder = builder; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | InstantiableRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d, String name) { |
| | | serializeElement(r, d); |
| | | |
| | | // Be careful to escape any forward slashes in the name. |
| | | builder.append("+name="); |
| | | builder.append(name.replace("/", "//")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | OptionalRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) { |
| | | serializeElement(r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SingletonRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) { |
| | | serializeElement(r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SetRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) { |
| | | serializeElement(r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | // Common element serialization. |
| | | private <M, N> void serializeElement(RelationDefinition<?, ?> r, |
| | | AbstractManagedObjectDefinition<?, ?> d) { |
| | | // Always specify the relation name. |
| | | builder.append("/relation="); |
| | | builder.append(r.getName()); |
| | | |
| | | // Only specify the type if it is a sub-type of the relation's |
| | | // type. |
| | | if (r.getChildDefinition() != d) { |
| | | builder.append("+type="); |
| | | builder.append(d.getName()); |
| | | } |
| | | } |
| | | } |
| | | |
| | | // Single instance of a root path. |
| | | private static final ManagedObjectPath<RootCfgClient, RootCfg> EMPTY_PATH = |
| | | new ManagedObjectPath<RootCfgClient, RootCfg>( |
| | | new LinkedList<Element<?, ?>>(), null, RootCfgDefn.getInstance()); |
| | | |
| | | // A regular expression used to parse path elements. |
| | | private static final Pattern PE_REGEXP = Pattern |
| | | .compile("^\\s*relation=\\s*([^+]+)\\s*" |
| | | + "(\\+\\s*type=\\s*([^+]+)\\s*)?" |
| | | + "(\\+\\s*name=\\s*([^+]+)\\s*)?$"); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new managed object path representing the configuration |
| | | * root. |
| | | * |
| | | * @return Returns a new managed object path representing the |
| | | * configuration root. |
| | | */ |
| | | public static ManagedObjectPath<RootCfgClient, RootCfg> emptyPath() { |
| | | return EMPTY_PATH; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns a managed object path holding the value of the specified |
| | | * string. |
| | | * |
| | | * @param s |
| | | * The string to be parsed. |
| | | * @return Returns a managed object path holding the value of the |
| | | * specified string. |
| | | * @throws IllegalArgumentException |
| | | * If the string could not be parsed. |
| | | */ |
| | | public static ManagedObjectPath<?, ?> valueOf(String s) |
| | | throws IllegalArgumentException { |
| | | String ns = s.trim(); |
| | | |
| | | // Check for root special case. |
| | | if (ns.equals("/")) { |
| | | return EMPTY_PATH; |
| | | } |
| | | |
| | | // Parse the elements. |
| | | LinkedList<Element<?, ?>> elements = new LinkedList<Element<?, ?>>(); |
| | | Element<?, ?> lastElement = null; |
| | | AbstractManagedObjectDefinition<?, ?> definition = RootCfgDefn |
| | | .getInstance(); |
| | | |
| | | if (!ns.startsWith("/")) { |
| | | throw new IllegalArgumentException("Invalid path \"" + ns |
| | | + "\": must begin with a \"/\""); |
| | | } |
| | | |
| | | int start = 1; |
| | | while (true) { |
| | | // Get the next path element. |
| | | int end; |
| | | for (end = start; end < ns.length(); end++) { |
| | | char c = ns.charAt(end); |
| | | if (c == '/') { |
| | | if (end == (ns.length() - 1)) { |
| | | throw new IllegalArgumentException("Invalid path \"" + ns |
| | | + "\": must not end with a trailing \"/\""); |
| | | } |
| | | |
| | | if (ns.charAt(end + 1) == '/') { |
| | | // Found an escaped forward slash. |
| | | end++; |
| | | } else { |
| | | // Found the end of this path element. |
| | | break; |
| | | } |
| | | } |
| | | } |
| | | |
| | | // Get the next element. |
| | | String es = ns.substring(start, end); |
| | | |
| | | Matcher m = PE_REGEXP.matcher(es); |
| | | if (!m.matches()) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + es |
| | | + "\" in path \"" + ns + "\""); |
| | | } |
| | | |
| | | // Mandatory. |
| | | String relation = m.group(1); |
| | | |
| | | // Optional. |
| | | String type = m.group(3); |
| | | |
| | | // Mandatory if relation is instantiable. |
| | | String name = m.group(5); |
| | | |
| | | // Get the relation definition. |
| | | RelationDefinition<?, ?> r; |
| | | try { |
| | | r = definition.getRelationDefinition(relation); |
| | | } catch (IllegalArgumentException e) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + es |
| | | + "\" in path \"" + ns + "\": unknown relation \"" + relation |
| | | + "\""); |
| | | } |
| | | |
| | | // Append the next element. |
| | | lastElement = createElement(r, ns, es, type, name); |
| | | elements.add(lastElement); |
| | | definition = lastElement.getManagedObjectDefinition(); |
| | | |
| | | // Update start to point to the beginning of the next element. |
| | | if (end < ns.length()) { |
| | | // Skip to the beginning of the next element |
| | | start = end + 1; |
| | | } else { |
| | | // We reached the end of the string. |
| | | break; |
| | | } |
| | | } |
| | | |
| | | // Construct the new path. |
| | | return create(elements, lastElement); |
| | | } |
| | | |
| | | |
| | | |
| | | // Factory method required in order to allow generic wild-card |
| | | // construction of new paths. |
| | | private static <C extends ConfigurationClient, S extends Configuration> |
| | | ManagedObjectPath<C, S> create( |
| | | LinkedList<Element<?, ?>> elements, Element<C, S> lastElement) { |
| | | return new ManagedObjectPath<C, S>(elements, lastElement |
| | | .getRelationDefinition(), lastElement.getManagedObjectDefinition()); |
| | | } |
| | | |
| | | |
| | | |
| | | // Decode an element. |
| | | private static <C extends ConfigurationClient, S extends Configuration> |
| | | Element<? extends C, ? extends S> createElement( |
| | | RelationDefinition<C, S> r, String path, String element, String type, |
| | | String name) { |
| | | // First determine the managed object definition. |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> d = null; |
| | | |
| | | if (type != null) { |
| | | for (AbstractManagedObjectDefinition<? extends C, ? extends S> child : r |
| | | .getChildDefinition().getAllChildren()) { |
| | | if (child.getName().equals(type)) { |
| | | d = child; |
| | | break; |
| | | } |
| | | } |
| | | |
| | | if (d == null) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path + "\": unknown sub-type \"" + type + "\""); |
| | | } |
| | | } else { |
| | | d = r.getChildDefinition(); |
| | | } |
| | | |
| | | if (r instanceof InstantiableRelationDefinition) { |
| | | InstantiableRelationDefinition<C, S> ir = |
| | | (InstantiableRelationDefinition<C, S>) r; |
| | | |
| | | if (name == null) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path |
| | | + "\": no instance name for instantiable relation"); |
| | | } |
| | | |
| | | return InstantiableElement.create(ir, d, name); |
| | | } else if (r instanceof SetRelationDefinition) { |
| | | SetRelationDefinition<C, S> ir = (SetRelationDefinition<C, S>) r; |
| | | |
| | | if (name != null) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path |
| | | + "\": instance name specified for set relation"); |
| | | } |
| | | |
| | | return SetElement.create(ir, d); |
| | | } else if (r instanceof OptionalRelationDefinition) { |
| | | OptionalRelationDefinition<C, S> or = |
| | | (OptionalRelationDefinition<C, S>) r; |
| | | |
| | | if (name != null) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path |
| | | + "\": instance name specified for optional relation"); |
| | | } |
| | | |
| | | return OptionalElement.create(or, d); |
| | | } else if (r instanceof SingletonRelationDefinition) { |
| | | SingletonRelationDefinition<C, S> sr = |
| | | (SingletonRelationDefinition<C, S>) r; |
| | | |
| | | if (name != null) { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path |
| | | + "\": instance name specified for singleton relation"); |
| | | } |
| | | |
| | | return SingletonElement.create(sr, d); |
| | | } else { |
| | | throw new IllegalArgumentException("Invalid path element \"" + element |
| | | + "\" in path \"" + path + "\": unsupported relation type"); |
| | | } |
| | | } |
| | | |
| | | // The managed object definition in this path. |
| | | private final AbstractManagedObjectDefinition<C, S> d; |
| | | |
| | | // The list of path elements in this path. |
| | | private final List<Element<?, ?>> elements; |
| | | |
| | | // The last relation definition in this path. |
| | | private final RelationDefinition<? super C, ? super S> r; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private ManagedObjectPath(LinkedList<Element<?, ?>> elements, |
| | | RelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d) { |
| | | this.elements = Collections.unmodifiableList(elements); |
| | | this.r = r; |
| | | this.d = d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new managed object path which has the same structure as |
| | | * this path except that the final path element is associated with |
| | | * the specified managed object definition. |
| | | * |
| | | * @param <CC> |
| | | * The type of client managed object configuration that |
| | | * this path will reference. |
| | | * @param <SS> |
| | | * The type of server managed object configuration that |
| | | * this path will reference. |
| | | * @param nd |
| | | * The new managed object definition. |
| | | * @return Returns a new managed object path which has the same |
| | | * structure as this path except that the final path element |
| | | * is associated with the specified managed object |
| | | * definition. |
| | | */ |
| | | @SuppressWarnings("unchecked") |
| | | public <CC extends C, SS extends S> ManagedObjectPath<CC, SS> asSubType( |
| | | AbstractManagedObjectDefinition<CC, SS> nd) { |
| | | if (r instanceof InstantiableRelationDefinition) { |
| | | InstantiableRelationDefinition<? super C, ? super S> ir = |
| | | (InstantiableRelationDefinition<? super C, ? super S>) r; |
| | | if (elements.size() == 0) { |
| | | return parent().child(ir, nd, "null"); |
| | | } else { |
| | | return parent().child(ir, nd, |
| | | elements.get(elements.size() - 1).getName()); |
| | | } |
| | | } else if (r instanceof SetRelationDefinition) { |
| | | SetRelationDefinition<? super C, ? super S> sr = |
| | | (SetRelationDefinition<? super C, ? super S>) r; |
| | | return parent().child(sr, nd); |
| | | } else if (r instanceof OptionalRelationDefinition) { |
| | | OptionalRelationDefinition<? super C, ? super S> or = |
| | | (OptionalRelationDefinition<? super C, ? super S>) r; |
| | | return parent().child(or, nd); |
| | | } else { |
| | | SingletonRelationDefinition<? super C, ? super S> sr = |
| | | (SingletonRelationDefinition<? super C, ? super S>) r; |
| | | return parent().child(sr, nd); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path having the specified managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The instantiable relation referencing the child. |
| | | * @param d |
| | | * The managed object definition associated with the child |
| | | * (must be a sub-type of the relation). |
| | | * @param name |
| | | * The relative name of the child managed object. |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name is empty or blank. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | InstantiableRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d, String name) |
| | | throws IllegalArgumentException { |
| | | if (name.trim().length() == 0) { |
| | | throw new IllegalArgumentException( |
| | | "Empty or blank managed object names are not allowed"); |
| | | } |
| | | LinkedList<Element<?, ?>> celements = new LinkedList<Element<?, ?>>( |
| | | elements); |
| | | celements.add(new InstantiableElement<M, N>(r, d, name)); |
| | | return new ManagedObjectPath<M, N>(celements, r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path using the relation's child managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The instantiable relation referencing the child. |
| | | * @param name |
| | | * The relative name of the child managed object. |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name is empty or blank. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | InstantiableRelationDefinition<M, N> r, String name) |
| | | throws IllegalArgumentException { |
| | | return child(r, r.getChildDefinition(), name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path having the specified managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The optional relation referencing the child. |
| | | * @param d |
| | | * The managed object definition associated with the child |
| | | * (must be a sub-type of the relation). |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | OptionalRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) { |
| | | LinkedList<Element<?, ?>> celements = new LinkedList<Element<?, ?>>( |
| | | elements); |
| | | celements.add(new OptionalElement<M, N>(r, d)); |
| | | return new ManagedObjectPath<M, N>(celements, r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path using the relation's child managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The optional relation referencing the child. |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child(OptionalRelationDefinition<M, N> r) { |
| | | return child(r, r.getChildDefinition()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path having the specified managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The singleton relation referencing the child. |
| | | * @param d |
| | | * The managed object definition associated with the child |
| | | * (must be a sub-type of the relation). |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | SingletonRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) { |
| | | LinkedList<Element<?, ?>> celements = new LinkedList<Element<?, ?>>( |
| | | elements); |
| | | celements.add(new SingletonElement<M, N>(r, d)); |
| | | return new ManagedObjectPath<M, N>(celements, r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path using the relation's child managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The singleton relation referencing the child. |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child(SingletonRelationDefinition<M, N> r) { |
| | | return child(r, r.getChildDefinition()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path having the specified managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The set relation referencing the child. |
| | | * @param d |
| | | * The managed object definition associated with the child |
| | | * (must be a sub-type of the relation). |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name is empty or blank. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | SetRelationDefinition<? super M, ? super N> r, |
| | | AbstractManagedObjectDefinition<M, N> d) |
| | | throws IllegalArgumentException { |
| | | LinkedList<Element<?, ?>> celements = new LinkedList<Element<?, ?>>( |
| | | elements); |
| | | celements.add(new SetElement<M, N>(r, d)); |
| | | return new ManagedObjectPath<M, N>(celements, r, d); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided parent |
| | | * path having the managed object definition indicated by |
| | | * <code>name</code>. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * path references. |
| | | * @param r |
| | | * The set relation referencing the child. |
| | | * @param name |
| | | * The name of the managed object definition associated with |
| | | * the child (must be a sub-type of the relation). |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name is empty or blank or specifies a |
| | | * managed object definition which is not a sub-type of the |
| | | * relation's child definition. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<? extends M, ? extends N> child( |
| | | SetRelationDefinition<M, N> r, |
| | | String name) |
| | | throws IllegalArgumentException { |
| | | AbstractManagedObjectDefinition<M, N> d = r.getChildDefinition(); |
| | | return child(r, d.getChild(name)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object path beneath the provided |
| | | * parent path using the relation's child managed object definition. |
| | | * |
| | | * @param <M> |
| | | * The type of client managed object configuration that the |
| | | * child path references. |
| | | * @param <N> |
| | | * The type of server managed object configuration that the |
| | | * child path references. |
| | | * @param r |
| | | * The set relation referencing the child. |
| | | * @return Returns a new child managed object path beneath the |
| | | * provided parent path. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name is empty or blank. |
| | | */ |
| | | public <M extends ConfigurationClient, N extends Configuration> |
| | | ManagedObjectPath<M, N> child( |
| | | SetRelationDefinition<M, N> r) |
| | | throws IllegalArgumentException { |
| | | return child(r, r.getChildDefinition()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public boolean equals(Object obj) { |
| | | if (obj == this) { |
| | | return true; |
| | | } else if (obj instanceof ManagedObjectPath) { |
| | | ManagedObjectPath<?, ?> other = (ManagedObjectPath<?, ?>) obj; |
| | | return toString().equals(other.toString()); |
| | | } else { |
| | | return false; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the definition of the managed object referred to by this |
| | | * path. |
| | | * <p> |
| | | * When the path is empty, the {@link RootCfgDefn} is returned. |
| | | * |
| | | * @return Returns the definition of the managed object referred to |
| | | * by this path, or the {@link RootCfgDefn} if the path is |
| | | * empty. |
| | | */ |
| | | public AbstractManagedObjectDefinition<C, S> getManagedObjectDefinition() { |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the managed object referred to by this path if |
| | | * applicable. |
| | | * <p> |
| | | * If there path does not refer to an instantiable managed object |
| | | * <code>null</code> is returned. |
| | | * |
| | | * @return Returns the name of the managed object referred to by |
| | | * this path, or <code>null</code> if the managed object |
| | | * does not have a name. |
| | | */ |
| | | public String getName() { |
| | | if (elements.isEmpty()) { |
| | | return null; |
| | | } else { |
| | | return elements.get(elements.size() - 1).getName(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the relation definition of the managed object referred to by |
| | | * this path. |
| | | * <p> |
| | | * When the path is empty, the <code>null</code> is returned. |
| | | * |
| | | * @return Returns the relation definition of the managed object |
| | | * referred to by this path, or the <code>null</code> if |
| | | * the path is empty. |
| | | */ |
| | | public RelationDefinition<? super C, ? super S> getRelationDefinition() { |
| | | return r; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int hashCode() { |
| | | return toString().hashCode(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether or not this path contains any path elements. |
| | | * |
| | | * @return Returns <code>true</code> if this path does not contain |
| | | * any path elements. |
| | | */ |
| | | public boolean isEmpty() { |
| | | return elements.isEmpty(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether this managed object path references the same |
| | | * location as the provided managed object path. |
| | | * <p> |
| | | * This method differs from <code>equals</code> in that it ignores |
| | | * sub-type definitions. |
| | | * |
| | | * @param other |
| | | * The managed object path to be compared. |
| | | * @return Returns <code>true</code> if this managed object path |
| | | * references the same location as the provided managed |
| | | * object path. |
| | | */ |
| | | public boolean matches(ManagedObjectPath<?, ?> other) { |
| | | DN thisDN = toDN(); |
| | | DN otherDN = other.toDN(); |
| | | return thisDN.equals(otherDN); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new parent managed object path representing the |
| | | * immediate parent of this path. This method is a short-hand for |
| | | * <code>parent(1)</code>. |
| | | * |
| | | * @return Returns a new parent managed object path representing the |
| | | * immediate parent of this path. |
| | | * @throws IllegalArgumentException |
| | | * If this path does not have a parent (i.e. it is the |
| | | * empty path). |
| | | */ |
| | | public ManagedObjectPath<?, ?> parent() throws IllegalArgumentException { |
| | | return parent(1); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new parent managed object path the specified number of |
| | | * path elements above this path. |
| | | * |
| | | * @param offset |
| | | * The number of path elements (0 - means no offset, 1 |
| | | * means the parent, and 2 means the grand-parent). |
| | | * @return Returns a new parent managed object path the specified |
| | | * number of path elements above this path. |
| | | * @throws IllegalArgumentException |
| | | * If the offset is less than 0, or greater than the |
| | | * number of path elements in this path. |
| | | */ |
| | | public ManagedObjectPath<?, ?> parent(int offset) |
| | | throws IllegalArgumentException { |
| | | if (offset < 0) { |
| | | throw new IllegalArgumentException("Negative offset"); |
| | | } |
| | | |
| | | if (offset > elements.size()) { |
| | | throw new IllegalArgumentException( |
| | | "Offset is greater than the number of path elements"); |
| | | } |
| | | |
| | | // An offset of 0 leaves the path unchanged. |
| | | if (offset == 0) { |
| | | return this; |
| | | } |
| | | |
| | | // Return the empty path if the parent has zero elements. |
| | | if (elements.size() == offset) { |
| | | return emptyPath(); |
| | | } |
| | | |
| | | LinkedList<Element<?, ?>> celements = new LinkedList<Element<?, ?>>( |
| | | elements.subList(0, elements.size() - offset)); |
| | | return create(celements, celements.getLast()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new managed object path which has the same structure as |
| | | * this path except that the final path element is renamed. The |
| | | * final path element must comprise of an instantiable relation. |
| | | * |
| | | * @param newName |
| | | * The new name of the final path element. |
| | | * @return Returns a new managed object path which has the same |
| | | * structure as this path except that the final path element |
| | | * is renamed. |
| | | * @throws IllegalStateException |
| | | * If this managed object path is empty or if its final |
| | | * path element does not comprise of an instantiable |
| | | * relation. |
| | | */ |
| | | @SuppressWarnings("unchecked") |
| | | public ManagedObjectPath<C, S> rename(String newName) |
| | | throws IllegalStateException { |
| | | if (elements.size() == 0) { |
| | | throw new IllegalStateException("Cannot rename an empty path"); |
| | | } |
| | | |
| | | if (r instanceof InstantiableRelationDefinition) { |
| | | InstantiableRelationDefinition<? super C, ? super S> ir = |
| | | (InstantiableRelationDefinition<? super C, ? super S>) r; |
| | | return parent().child(ir, d, newName); |
| | | } else { |
| | | throw new IllegalStateException("Not an instantiable relation"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Serialize this managed object path using the provided |
| | | * serialization strategy. |
| | | * <p> |
| | | * The path elements will be passed to the serializer in big-endian |
| | | * order: starting from the root element and proceeding down to the |
| | | * leaf. |
| | | * |
| | | * @param serializer |
| | | * The managed object path serialization strategy. |
| | | */ |
| | | public void serialize(ManagedObjectPathSerializer serializer) { |
| | | for (Element<?, ?> element : elements) { |
| | | element.serialize(serializer); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the number of path elements in this managed object path. |
| | | * |
| | | * @return Returns the number of path elements (0 - means no offset, |
| | | * 1 means the parent, and 2 means the grand-parent). |
| | | */ |
| | | public int size() { |
| | | return elements.size(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a DN representation of this managed object path. |
| | | * |
| | | * @return Returns a DN representation of this managed object path. |
| | | */ |
| | | public DN toDN() { |
| | | // Use a simple serializer to create the contents. |
| | | DNSerializer serializer = new DNSerializer(); |
| | | serialize(serializer); |
| | | return serializer.toDN(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String toString() { |
| | | StringBuilder builder = new StringBuilder(); |
| | | toString(builder); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Appends a string representation of this managed object path to |
| | | * the provided string builder. |
| | | * |
| | | * @param builder |
| | | * Append the string representation to this builder. |
| | | * @see #toString() |
| | | */ |
| | | public void toString(final StringBuilder builder) { |
| | | if (isEmpty()) { |
| | | // Special treatment of root configuration paths. |
| | | builder.append('/'); |
| | | } else { |
| | | // Use a simple serializer to create the contents. |
| | | ManagedObjectPathSerializer serializer = new StringSerializer(builder); |
| | | serialize(serializer); |
| | | } |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A strategy for serializing managed object paths. |
| | | * <p> |
| | | * This interface provides a generic means for serializing managed |
| | | * object paths into application specific forms. For example, a JNDI |
| | | * client would use this interface to construct <code>LdapName</code> |
| | | * objects from a path. Similarly, on the server side, a serialization |
| | | * strategy is used to construct <code>DN</code> instances from a |
| | | * path. |
| | | * <p> |
| | | * During serialization the serializer is invoked for each element in |
| | | * the managed object path in big-endian order, starting from the root |
| | | * and proceeding down to the leaf element. |
| | | */ |
| | | public interface ManagedObjectPathSerializer { |
| | | |
| | | /** |
| | | * Append a managed object path element identified by an |
| | | * instantiable relation and an instance name. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this path element references. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this path element references. |
| | | * @param r |
| | | * The instantiable relation. |
| | | * @param d |
| | | * The managed object definition. |
| | | * @param name |
| | | * The instance name. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | InstantiableRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d, String name); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a managed object path element identified by an optional |
| | | * relation. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this path element references. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this path element references. |
| | | * @param r |
| | | * The optional relation. |
| | | * @param d |
| | | * The managed object definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | OptionalRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a managed object path element identified by a singleton |
| | | * relation. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this path element references. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this path element references. |
| | | * @param r |
| | | * The singleton relation. |
| | | * @param d |
| | | * The managed object definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SingletonRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a managed object path element identified by a |
| | | * set relation. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this path element references. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this path element references. |
| | | * @param r |
| | | * The set relation. |
| | | * @param d |
| | | * The managed object definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void appendManagedObjectPathElement( |
| | | SetRelationDefinition<? super C, ? super S> r, |
| | | AbstractManagedObjectDefinition<C, S> d); |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Exceptions thrown as a result of errors that occurred when reading, |
| | | * listing, and modifying managed objects. |
| | | */ |
| | | public abstract class OperationsException extends AdminException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 6329910102360262187L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an operations exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected OperationsException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an operations exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected OperationsException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A managed object composite relationship definition which represents |
| | | * a composition of an optional single managed object (i.e. the |
| | | * referenced managed object may or may not be present). |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public final class OptionalRelationDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends RelationDefinition<C, S> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing optional relation |
| | | * definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this relation definition refers to. |
| | | */ |
| | | public static final class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractBuilder<C, S, OptionalRelationDefinition<C, S>> { |
| | | |
| | | // The optional default managed object associated with this |
| | | // optional relation. |
| | | private DefaultManagedObject<? extends C, ? extends S> |
| | | defaultManagedObject = null; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new builder which can be used to incrementally build |
| | | * an optional relation definition. |
| | | * |
| | | * @param pd |
| | | * The parent managed object definition. |
| | | * @param name |
| | | * The name of the relation. |
| | | * @param cd |
| | | * The child managed object definition. |
| | | */ |
| | | public Builder(AbstractManagedObjectDefinition<?, ?> pd, String name, |
| | | AbstractManagedObjectDefinition<C, S> cd) { |
| | | super(pd, name, cd); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the optional default managed object associated with this |
| | | * optional relation definition. |
| | | * |
| | | * @param defaultManagedObject |
| | | * The default managed object or <code>null</code> if |
| | | * there is no default managed object defined for this |
| | | * relation definition. |
| | | */ |
| | | public void setDefaultManagedObject( |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) { |
| | | this.defaultManagedObject = defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected OptionalRelationDefinition<C, S> buildInstance( |
| | | Common<C, S> common) { |
| | | return new OptionalRelationDefinition<C, S>(common, defaultManagedObject); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | // The optional default managed object associated with this |
| | | // optional relation. |
| | | private final DefaultManagedObject<? extends C, ? extends S> |
| | | defaultManagedObject; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private OptionalRelationDefinition(Common<C, S> common, |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) { |
| | | super(common); |
| | | this.defaultManagedObject = defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(RelationDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitOptional(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional default managed object associated with this |
| | | * optional relation definition. |
| | | * |
| | | * @return Returns the default managed object or <code>null</code> |
| | | * if there is no default managed object defined for this |
| | | * relation definition. |
| | | */ |
| | | public DefaultManagedObject<? extends C, ? extends S> |
| | | getDefaultManagedObject() { |
| | | return defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | builder.append("name="); |
| | | builder.append(getName()); |
| | | builder.append(" type=optional parent="); |
| | | builder.append(getParentDefinition().getName()); |
| | | builder.append(" child="); |
| | | builder.append(getChildDefinition().getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception { |
| | | if (defaultManagedObject != null) { |
| | | defaultManagedObject.initialize(); |
| | | } |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static com.forgerock.opendj.util.Validator.*; |
| | | |
| | | import java.util.Comparator; |
| | | import java.util.EnumSet; |
| | | import java.util.Locale; |
| | | import java.util.MissingResourceException; |
| | | import java.util.Set; |
| | | |
| | | import org.forgerock.i18n.LocalizableMessage; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for querying generic property definition features. |
| | | * <p> |
| | | * Property definitions are analogous to ConfigAttributes in the |
| | | * current model and will play a similar role. Eventually these will |
| | | * replace them. |
| | | * <p> |
| | | * Implementations <b>must</b> take care to implement the various |
| | | * comparison methods. |
| | | * |
| | | * @param <T> |
| | | * The data-type of values of the property. |
| | | */ |
| | | public abstract class PropertyDefinition<T> implements Comparator<T>, |
| | | Comparable<PropertyDefinition<?>> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing property definitions. |
| | | * |
| | | * @param <T> |
| | | * The data-type of values of the property. |
| | | * @param <D> |
| | | * The type of property definition constructed by this |
| | | * builder. |
| | | */ |
| | | protected abstract static class AbstractBuilder |
| | | <T, D extends PropertyDefinition<T>> { |
| | | |
| | | // The administrator action. |
| | | private AdministratorAction adminAction; |
| | | |
| | | // The default behavior provider. |
| | | private DefaultBehaviorProvider<T> defaultBehavior; |
| | | |
| | | // The abstract managed object |
| | | private final AbstractManagedObjectDefinition<?, ?> definition; |
| | | |
| | | // The options applicable to this definition. |
| | | private final EnumSet<PropertyOption> options; |
| | | |
| | | // The name of this property definition. |
| | | private final String propertyName; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | */ |
| | | protected AbstractBuilder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | this.definition = d; |
| | | this.propertyName = propertyName; |
| | | this.options = EnumSet.noneOf(PropertyOption.class); |
| | | this.adminAction = new AdministratorAction(AdministratorAction.Type.NONE, |
| | | d, propertyName); |
| | | this.defaultBehavior = new UndefinedDefaultBehaviorProvider<T>(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Construct a property definition based on the properties of this |
| | | * builder. |
| | | * |
| | | * @return The new property definition. |
| | | */ |
| | | public final D getInstance() { |
| | | return buildInstance(definition, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the administrator action. |
| | | * |
| | | * @param adminAction |
| | | * The administrator action. |
| | | */ |
| | | public final void setAdministratorAction(AdministratorAction adminAction) { |
| | | ensureNotNull(adminAction); |
| | | this.adminAction = adminAction; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the default behavior provider. |
| | | * |
| | | * @param defaultBehavior |
| | | * The default behavior provider. |
| | | */ |
| | | public final void setDefaultBehaviorProvider( |
| | | DefaultBehaviorProvider<T> defaultBehavior) { |
| | | ensureNotNull(defaultBehavior); |
| | | this.defaultBehavior = defaultBehavior; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add a property definition option. |
| | | * |
| | | * @param option |
| | | * The property option. |
| | | */ |
| | | public final void setOption(PropertyOption option) { |
| | | ensureNotNull(option); |
| | | options.add(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Build a property definition based on the properties of this |
| | | * builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @param options |
| | | * Options applicable to this definition. |
| | | * @param adminAction |
| | | * The administrator action. |
| | | * @param defaultBehavior |
| | | * The default behavior provider. |
| | | * @return The new property definition. |
| | | */ |
| | | protected abstract D buildInstance(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<T> defaultBehavior); |
| | | } |
| | | |
| | | // The administrator action. |
| | | private final AdministratorAction adminAction; |
| | | |
| | | // The default behavior provider. |
| | | private final DefaultBehaviorProvider<T> defaultBehavior; |
| | | |
| | | // The abstract managed object |
| | | private final AbstractManagedObjectDefinition<?, ?> definition; |
| | | |
| | | // Options applicable to this definition. |
| | | private final Set<PropertyOption> options; |
| | | |
| | | // The property name. |
| | | private final String propertyName; |
| | | |
| | | // The property value class. |
| | | private final Class<T> theClass; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a property definition. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param theClass |
| | | * The property value class. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @param options |
| | | * Options applicable to this definition. |
| | | * @param adminAction |
| | | * The administrator action. |
| | | * @param defaultBehavior |
| | | * The default behavior provider. |
| | | */ |
| | | protected PropertyDefinition(AbstractManagedObjectDefinition<?, ?> d, |
| | | Class<T> theClass, String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<T> defaultBehavior) { |
| | | ensureNotNull(d, theClass, propertyName); |
| | | ensureNotNull(options, adminAction, defaultBehavior); |
| | | |
| | | this.definition = d; |
| | | this.theClass = theClass; |
| | | this.propertyName = propertyName; |
| | | this.options = EnumSet.copyOf(options); |
| | | this.adminAction = adminAction; |
| | | this.defaultBehavior = defaultBehavior; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Apply a visitor to this property definition. |
| | | * |
| | | * @param <R> |
| | | * The return type of the visitor's methods. |
| | | * @param <P> |
| | | * The type of the additional parameters to the visitor's |
| | | * methods. |
| | | * @param v |
| | | * The property definition visitor. |
| | | * @param p |
| | | * Optional additional visitor parameter. |
| | | * @return Returns a result as specified by the visitor. |
| | | */ |
| | | public abstract <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Apply a visitor to a property value associated with this property |
| | | * definition. |
| | | * |
| | | * @param <R> |
| | | * The return type of the visitor's methods. |
| | | * @param <P> |
| | | * The type of the additional parameters to the visitor's |
| | | * methods. |
| | | * @param v |
| | | * The property value visitor. |
| | | * @param value |
| | | * The property value. |
| | | * @param p |
| | | * Optional additional visitor parameter. |
| | | * @return Returns a result as specified by the visitor. |
| | | */ |
| | | public abstract <R, P> R accept(PropertyValueVisitor<R, P> v, T value, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Cast the provided value to the type associated with this property |
| | | * definition. |
| | | * <p> |
| | | * This method only casts the object to the required type; it does |
| | | * not validate the value once it has been cast. Subsequent |
| | | * validation should be performed using the method |
| | | * {@link #validateValue(Object)}. |
| | | * <p> |
| | | * This method guarantees the following expression is always |
| | | * <code>true</code>: |
| | | * |
| | | * <pre> |
| | | * PropertyDefinition d; |
| | | * x == d.cast(x); |
| | | * </pre> |
| | | * |
| | | * @param object |
| | | * The property value to be cast (can be <code>null</code>). |
| | | * @return Returns the property value cast to the correct type. |
| | | * @throws ClassCastException |
| | | * If the provided property value did not have the correct |
| | | * type. |
| | | */ |
| | | public final T castValue(Object object) throws ClassCastException { |
| | | return theClass.cast(object); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Compares two property values for order. Returns a negative |
| | | * integer, zero, or a positive integer as the first argument is |
| | | * less than, equal to, or greater than the second. |
| | | * <p> |
| | | * This default implementation normalizes both values using |
| | | * {@link #normalizeValue(Object)} and then performs a |
| | | * case-sensitive string comparison. |
| | | * |
| | | * @param o1 |
| | | * the first object to be compared. |
| | | * @param o2 |
| | | * the second object to be compared. |
| | | * @return a negative integer, zero, or a positive integer as the |
| | | * first argument is less than, equal to, or greater than |
| | | * the second. |
| | | */ |
| | | public int compare(T o1, T o2) { |
| | | ensureNotNull(o1, o2); |
| | | |
| | | String s1 = normalizeValue(o1); |
| | | String s2 = normalizeValue(o2); |
| | | |
| | | return s1.compareTo(s2); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Compares this property definition with the specified property |
| | | * definition for order. Returns a negative integer, zero, or a |
| | | * positive integer if this property definition is less than, equal |
| | | * to, or greater than the specified property definition. |
| | | * <p> |
| | | * The ordering must be determined first from the property name and |
| | | * then base on the underlying value type. |
| | | * |
| | | * @param o |
| | | * The reference property definition with which to compare. |
| | | * @return Returns a negative integer, zero, or a positive integer |
| | | * if this property definition is less than, equal to, or |
| | | * greater than the specified property definition. |
| | | */ |
| | | public final int compareTo(PropertyDefinition<?> o) { |
| | | int rc = propertyName.compareTo(o.propertyName); |
| | | if (rc == 0) { |
| | | rc = theClass.getName().compareTo(o.theClass.getName()); |
| | | } |
| | | return rc; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parse and validate a string representation of a property value. |
| | | * |
| | | * @param value |
| | | * The property string value (must not be <code>null</code>). |
| | | * @return Returns the decoded property value. |
| | | * @throws IllegalPropertyValueStringException |
| | | * If the property value string is invalid. |
| | | */ |
| | | public abstract T decodeValue(String value) |
| | | throws IllegalPropertyValueStringException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Encode the provided property value into its string |
| | | * representation. |
| | | * <p> |
| | | * This default implementation simply returns invokes the |
| | | * {@link Object#toString()} method on the provided value. |
| | | * |
| | | * @param value |
| | | * The property value (must not be <code>null</code>). |
| | | * @return Returns the encoded property string value. |
| | | * @throws IllegalPropertyValueException |
| | | * If the property value is invalid. |
| | | */ |
| | | public String encodeValue(T value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | return value.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether some other object is "equal to" this |
| | | * property definition. This method must obey the general contract |
| | | * of <tt>Object.equals(Object)</tt>. Additionally, this method |
| | | * can return <tt>true</tt> <i>only</i> if the specified Object |
| | | * is also a property definition and it has the same name, as |
| | | * returned by {@link #getName()}, and also is deemed to be |
| | | * "compatible" with this property definition. |
| | | * Compatibility means that the two property definitions share the |
| | | * same underlying value type and provide similar comparator |
| | | * implementations. |
| | | * |
| | | * @param o |
| | | * The reference object with which to compare. |
| | | * @return Returns <code>true</code> only if the specified object |
| | | * is also a property definition and it has the same name |
| | | * and is compatible with this property definition. |
| | | * @see java.lang.Object#equals(java.lang.Object) |
| | | * @see java.lang.Object#hashCode() |
| | | */ |
| | | @Override |
| | | public final boolean equals(Object o) { |
| | | if (this == o) { |
| | | return true; |
| | | } else if (o instanceof PropertyDefinition) { |
| | | PropertyDefinition<?> other = (PropertyDefinition<?>) o; |
| | | if (propertyName.equals(other.propertyName)) { |
| | | if (theClass.equals(other.theClass)) { |
| | | return true; |
| | | } |
| | | } |
| | | return false; |
| | | } else { |
| | | return false; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the administrator action associated with this property |
| | | * definition. The administrator action describes any action which |
| | | * the administrator must perform in order for changes to this |
| | | * property to take effect. |
| | | * |
| | | * @return Returns the administrator action associated with this |
| | | * property definition. |
| | | */ |
| | | public final AdministratorAction getAdministratorAction() { |
| | | return adminAction; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the default behavior provider associated with this property |
| | | * definition. |
| | | * |
| | | * @return Returns the default behavior provider associated with |
| | | * this property definition. |
| | | */ |
| | | public final DefaultBehaviorProvider<T> getDefaultBehaviorProvider() { |
| | | return defaultBehavior; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this property definition in the |
| | | * default locale. |
| | | * |
| | | * @return Returns the description of this property definition in |
| | | * the default locale, or <code>null</code> if there is no |
| | | * description. |
| | | */ |
| | | public final LocalizableMessage getDescription() { |
| | | return getDescription(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this property definition in the |
| | | * specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the description of this property definition in |
| | | * the specified locale, or <code>null</code> if there is |
| | | * no description. |
| | | */ |
| | | public final LocalizableMessage getDescription(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + propertyName + ".description"; |
| | | try { |
| | | return resource.getLocalizableMessage(definition, property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the managed object definition associated with this property |
| | | * definition. |
| | | * |
| | | * @return Returns the managed object definition associated with |
| | | * this property definition. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<?, ?> |
| | | getManagedObjectDefinition() { |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the property. |
| | | * |
| | | * @return Returns the name of the property. |
| | | */ |
| | | public final String getName() { |
| | | return propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this property definition in the default |
| | | * locale. |
| | | * |
| | | * @return Returns the synopsis of this property definition in the |
| | | * default locale. |
| | | */ |
| | | public final LocalizableMessage getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this property definition in the specified |
| | | * locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this property definition in the |
| | | * specified locale. |
| | | */ |
| | | public final LocalizableMessage getSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + propertyName + ".synopsis"; |
| | | return resource.getLocalizableMessage(definition, property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns a hash code value for this property definition. The hash |
| | | * code should be derived from the property name and the type of |
| | | * values handled by this property definition. |
| | | * |
| | | * @return Returns the hash code value for this property definition. |
| | | */ |
| | | @Override |
| | | public final int hashCode() { |
| | | int rc = 17 + propertyName.hashCode(); |
| | | return 37 * rc + theClass.hashCode(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check if the specified option is set for this property |
| | | * definition. |
| | | * |
| | | * @param option |
| | | * The option to test. |
| | | * @return Returns <code>true</code> if the option is set, or |
| | | * <code>false</code> otherwise. |
| | | */ |
| | | public final boolean hasOption(PropertyOption option) { |
| | | return options.contains(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get a normalized string representation of a property value. This |
| | | * can then be used for comparisons and for generating hash-codes. |
| | | * <p> |
| | | * This method may throw an exception if the provided value is |
| | | * invalid. However, applications should not assume that |
| | | * implementations of this method will always validate a value. This |
| | | * task is the responsibility of {@link #validateValue(Object)}. |
| | | * <p> |
| | | * This default implementation simply returns the string |
| | | * representation of the provided value. Sub-classes might want to |
| | | * override this method if this behavior is insufficient (for |
| | | * example, a string property definition might strip white-space and |
| | | * convert characters to lower-case). |
| | | * |
| | | * @param value |
| | | * The property value to be normalized. |
| | | * @return Returns the normalized property value. |
| | | * @throws IllegalPropertyValueException |
| | | * If the property value is invalid. |
| | | */ |
| | | public String normalizeValue(T value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | return encodeValue(value); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns a string representation of this property definition. |
| | | * |
| | | * @return Returns a string representation of this property |
| | | * definition. |
| | | * @see Object#toString() |
| | | */ |
| | | @Override |
| | | public final String toString() { |
| | | StringBuilder builder = new StringBuilder(); |
| | | toString(builder); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a string representation of the property definition to the |
| | | * provided string builder. |
| | | * <p> |
| | | * This simple implementation just outputs the propertyName of the |
| | | * property definition. Sub-classes should override this method to |
| | | * provide more complete string representations. |
| | | * |
| | | * @param builder |
| | | * The string builder where the string representation |
| | | * should be appended. |
| | | */ |
| | | public void toString(StringBuilder builder) { |
| | | builder.append(propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine if the provided property value is valid according to |
| | | * this property definition. |
| | | * |
| | | * @param value |
| | | * The property value (must not be <code>null</code>). |
| | | * @throws IllegalPropertyValueException |
| | | * If the property value is invalid. |
| | | */ |
| | | public abstract void validateValue(T value) |
| | | throws IllegalPropertyValueException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Performs any run-time initialization required by this property |
| | | * definition. This may include resolving managed object paths and |
| | | * property names. |
| | | * |
| | | * @throws Exception |
| | | * If this property definition could not be initialized. |
| | | */ |
| | | protected void initialize() throws Exception { |
| | | // No implementation required. |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | import org.opends.messages.MessageBuilder; |
| | | |
| | | |
| | | import java.text.NumberFormat; |
| | | import java.util.EnumSet; |
| | | import java.util.Set; |
| | | import java.util.TreeSet; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A property definition visitor which can be used to generate syntax |
| | | * usage information. |
| | | */ |
| | | public final class PropertyDefinitionUsageBuilder { |
| | | |
| | | /** |
| | | * Underlying implementation. |
| | | */ |
| | | private class MyPropertyDefinitionVisitor extends |
| | | PropertyDefinitionVisitor<Message, Void> { |
| | | |
| | | // Flag indicating whether detailed syntax information will be |
| | | // generated. |
| | | private final boolean isDetailed; |
| | | |
| | | // The formatter to use for numeric values. |
| | | private final NumberFormat numberFormat; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private MyPropertyDefinitionVisitor(boolean isDetailed) { |
| | | this.isDetailed = isDetailed; |
| | | |
| | | this.numberFormat = NumberFormat.getNumberInstance(); |
| | | this.numberFormat.setGroupingUsed(true); |
| | | this.numberFormat.setMaximumFractionDigits(2); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | Message visitAggregation(AggregationPropertyDefinition<C, S> d, Void p) { |
| | | return Message.raw("NAME"); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitAttributeType(AttributeTypePropertyDefinition d, |
| | | Void p) { |
| | | return Message.raw("OID"); |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitACI(ACIPropertyDefinition d, |
| | | Void p) { |
| | | return Message.raw("ACI"); |
| | | } |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitBoolean(BooleanPropertyDefinition d, Void p) { |
| | | if (isDetailed) { |
| | | return Message.raw("false | true"); |
| | | } else { |
| | | return Message.raw("BOOLEAN"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitClass(ClassPropertyDefinition d, Void p) { |
| | | if (isDetailed && !d.getInstanceOfInterface().isEmpty()) { |
| | | return Message.raw("CLASS <= " + d.getInstanceOfInterface().get(0)); |
| | | } else { |
| | | return Message.raw("CLASS"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitDN(DNPropertyDefinition d, Void p) { |
| | | if (isDetailed && d.getBaseDN() != null) { |
| | | return Message.raw("DN <= " + d.getBaseDN()); |
| | | } else { |
| | | return Message.raw("DN"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitDuration(DurationPropertyDefinition d, Void p) { |
| | | MessageBuilder builder = new MessageBuilder(); |
| | | DurationUnit unit = d.getBaseUnit(); |
| | | |
| | | if (isDetailed && d.getLowerLimit() > 0) { |
| | | builder.append(DurationUnit.toString(d.getLowerLimit())); |
| | | builder.append(" <= "); |
| | | } |
| | | |
| | | builder.append("DURATION ("); |
| | | builder.append(unit.getShortName()); |
| | | builder.append(")"); |
| | | |
| | | if (isDetailed) { |
| | | if (d.getUpperLimit() != null) { |
| | | builder.append(" <= "); |
| | | builder.append(DurationUnit.toString(d.getUpperLimit())); |
| | | } |
| | | |
| | | if (d.isAllowUnlimited()) { |
| | | builder.append(" | unlimited"); |
| | | } |
| | | } |
| | | |
| | | return builder.toMessage(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <E extends Enum<E>> Message visitEnum(EnumPropertyDefinition<E> d, |
| | | Void p) { |
| | | if (!isDetailed) { |
| | | // Use the last word in the property name. |
| | | String name = d.getName(); |
| | | int i = name.lastIndexOf('-'); |
| | | if (i == -1 || i == (name.length() - 1)) { |
| | | return Message.raw(name.toUpperCase()); |
| | | } else { |
| | | return Message.raw(name.substring(i + 1).toUpperCase()); |
| | | } |
| | | } else { |
| | | Set<String> values = new TreeSet<String>(); |
| | | |
| | | for (Object value : EnumSet.allOf(d.getEnumClass())) { |
| | | values.add(value.toString().trim().toLowerCase()); |
| | | } |
| | | |
| | | boolean isFirst = true; |
| | | MessageBuilder builder = new MessageBuilder(); |
| | | for (String s : values) { |
| | | if (!isFirst) { |
| | | builder.append(" | "); |
| | | } |
| | | builder.append(s); |
| | | isFirst = false; |
| | | } |
| | | |
| | | return builder.toMessage(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitInteger(IntegerPropertyDefinition d, Void p) { |
| | | MessageBuilder builder = new MessageBuilder(); |
| | | |
| | | if (isDetailed) { |
| | | builder.append(String.valueOf(d.getLowerLimit())); |
| | | builder.append(" <= "); |
| | | } |
| | | |
| | | builder.append("INTEGER"); |
| | | |
| | | if (isDetailed) { |
| | | if (d.getUpperLimit() != null) { |
| | | builder.append(" <= "); |
| | | builder.append(String.valueOf(d.getUpperLimit())); |
| | | } else if (d.isAllowUnlimited()) { |
| | | builder.append(" | unlimited"); |
| | | } |
| | | } |
| | | |
| | | return builder.toMessage(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitIPAddress(IPAddressPropertyDefinition d, Void p) { |
| | | return Message.raw("HOST_NAME"); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitIPAddressMask(IPAddressMaskPropertyDefinition d, |
| | | Void p) { |
| | | return Message.raw("IP_ADDRESS_MASK"); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitSize(SizePropertyDefinition d, Void p) { |
| | | MessageBuilder builder = new MessageBuilder(); |
| | | |
| | | if (isDetailed && d.getLowerLimit() > 0) { |
| | | SizeUnit unit = SizeUnit.getBestFitUnitExact(d.getLowerLimit()); |
| | | builder.append(numberFormat.format(unit.fromBytes(d.getLowerLimit()))); |
| | | builder.append(' '); |
| | | builder.append(unit.getShortName()); |
| | | builder.append(" <= "); |
| | | } |
| | | |
| | | builder.append("SIZE"); |
| | | |
| | | if (isDetailed) { |
| | | if (d.getUpperLimit() != null) { |
| | | long upperLimit = d.getUpperLimit(); |
| | | SizeUnit unit = SizeUnit.getBestFitUnitExact(upperLimit); |
| | | |
| | | // Quite often an upper limit is some power of 2 minus 1. In those |
| | | // cases lets use a "less than" relation rather than a "less than |
| | | // or equal to" relation. This will result in a much more readable |
| | | // quantity. |
| | | if (unit == SizeUnit.BYTES && upperLimit < Long.MAX_VALUE) { |
| | | unit = SizeUnit.getBestFitUnitExact(upperLimit + 1); |
| | | if (unit != SizeUnit.BYTES) { |
| | | upperLimit += 1; |
| | | builder.append(" < "); |
| | | } else { |
| | | builder.append(" <= "); |
| | | } |
| | | } else { |
| | | builder.append(" <= "); |
| | | } |
| | | |
| | | builder.append(numberFormat.format(unit.fromBytes(upperLimit))); |
| | | builder.append(' '); |
| | | builder.append(unit.getShortName()); |
| | | } |
| | | |
| | | if (d.isAllowUnlimited()) { |
| | | builder.append(" | unlimited"); |
| | | } |
| | | } |
| | | |
| | | return builder.toMessage(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Message visitString(StringPropertyDefinition d, Void p) { |
| | | if (d.getPattern() != null) { |
| | | if (isDetailed) { |
| | | MessageBuilder builder = new MessageBuilder(); |
| | | builder.append(d.getPatternUsage()); |
| | | builder.append(" - "); |
| | | builder.append(d.getPatternSynopsis()); |
| | | return builder.toMessage(); |
| | | } else { |
| | | return Message.raw(d.getPatternUsage()); |
| | | } |
| | | } else { |
| | | return Message.raw("STRING"); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <T> Message visitUnknown(PropertyDefinition<T> d, Void p) |
| | | throws UnknownPropertyDefinitionException { |
| | | return Message.raw("?"); |
| | | } |
| | | } |
| | | |
| | | // Underlying implementation. |
| | | private final MyPropertyDefinitionVisitor pimpl; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new property usage builder. |
| | | * |
| | | * @param isDetailed |
| | | * Indicates whether or not the generated usage should |
| | | * contain detailed information such as constraints. |
| | | */ |
| | | public PropertyDefinitionUsageBuilder(boolean isDetailed) { |
| | | this.pimpl = new MyPropertyDefinitionVisitor(isDetailed); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Generates the usage information for the provided property |
| | | * definition. |
| | | * |
| | | * @param pd |
| | | * The property definitions. |
| | | * @return Returns the usage information for the provided property |
| | | * definition. |
| | | */ |
| | | public Message getUsage(PropertyDefinition<?> pd) { |
| | | return pd.accept(pimpl, null); |
| | | }; |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A visitor of property definitions, in the style of the visitor |
| | | * design pattern. Classes implementing this interface can query |
| | | * property definitions in a type-safe manner when the kind of |
| | | * property definition is unknown at compile time. When a visitor is |
| | | * passed to a property definition's accept method, the corresponding |
| | | * visit method most applicable to that property definition is |
| | | * invoked. |
| | | * <p> |
| | | * Each <code>visitXXX</code> method is provided with a default |
| | | * implementation which calls |
| | | * {@link #visitUnknown(PropertyDefinition, Object)}. Sub-classes can |
| | | * override any or all of the methods to provide their own |
| | | * type-specific behavior. |
| | | * |
| | | * @param <R> |
| | | * The return type of this visitor's methods. Use |
| | | * {@link java.lang.Void} for visitors that do not need to |
| | | * return results. |
| | | * @param <P> |
| | | * The type of the additional parameter to this visitor's |
| | | * methods. Use {@link java.lang.Void} for visitors that do |
| | | * not need an additional parameter. |
| | | */ |
| | | public abstract class PropertyDefinitionVisitor<R, P> { |
| | | |
| | | /** |
| | | * Default constructor. |
| | | */ |
| | | protected PropertyDefinitionVisitor() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a dseecompat Global ACI property definition. |
| | | * |
| | | * @param pd |
| | | * The Global ACI property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitACI(ACIPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an aggregation property definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param pd |
| | | * The aggregation property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | R visitAggregation(AggregationPropertyDefinition<C, S> pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an attribute type property definition. |
| | | * |
| | | * @param pd |
| | | * The attribute type property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitAttributeType(AttributeTypePropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a boolean property definition. |
| | | * |
| | | * @param pd |
| | | * The boolean property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitBoolean(BooleanPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a class property definition. |
| | | * |
| | | * @param pd |
| | | * The class property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitClass(ClassPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a DN property definition. |
| | | * |
| | | * @param pd |
| | | * The DN property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitDN(DNPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a duration property definition. |
| | | * |
| | | * @param pd |
| | | * The duration property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitDuration(DurationPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an enumeration property definition. |
| | | * |
| | | * @param <E> |
| | | * The enumeration that should be used for values of the |
| | | * property definition. |
| | | * @param pd |
| | | * The enumeration property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public <E extends Enum<E>> R visitEnum(EnumPropertyDefinition<E> pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an integer property definition. |
| | | * |
| | | * @param pd |
| | | * The integer property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitInteger(IntegerPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a IP address property definition. |
| | | * |
| | | * @param pd |
| | | * The IP address property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitIPAddress(IPAddressPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a IP address mask property definition. |
| | | * |
| | | * @param pd |
| | | * The IP address mask property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitIPAddressMask(IPAddressMaskPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Visit a size property definition. |
| | | * |
| | | * @param pd |
| | | * The size property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitSize(SizePropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a string property definition. |
| | | * |
| | | * @param pd |
| | | * The string property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitString(StringPropertyDefinition pd, P p) { |
| | | return visitUnknown(pd, p); |
| | | } |
| | | |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an unknown type of property definition. Implementations of |
| | | * this method can provide default behavior for unknown property |
| | | * definition types. |
| | | * <p> |
| | | * The default implementation of this method throws an |
| | | * {@link UnknownPropertyDefinitionException}. Sub-classes can |
| | | * override this method with their own default behavior. |
| | | * |
| | | * @param <T> |
| | | * The type of the underlying property. |
| | | * @param pd |
| | | * The property definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | * @throws UnknownPropertyDefinitionException |
| | | * Visitor implementations may optionally throw this |
| | | * exception. |
| | | */ |
| | | public <T> R visitUnknown(PropertyDefinition<T> pd, P p) |
| | | throws UnknownPropertyDefinitionException { |
| | | throw new UnknownPropertyDefinitionException(pd, p); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Exceptions thrown as a result of errors that occurred when decoding |
| | | * and modifying property values. |
| | | */ |
| | | public abstract class PropertyException extends AdminRuntimeException { |
| | | |
| | | /** |
| | | * Version ID required by serializable classes. |
| | | */ |
| | | private static final long serialVersionUID = -8465109598081914482L; |
| | | |
| | | // The property definition associated with the property that caused |
| | | // the exception. |
| | | private final PropertyDefinition<?> pd; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates property exception without a cause. |
| | | * |
| | | * @param pd |
| | | * The property definition associated with the property |
| | | * that caused the exception. |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected PropertyException(PropertyDefinition<?> pd, Message message) { |
| | | super(message); |
| | | this.pd = pd; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates property exception with a cause. |
| | | * |
| | | * @param pd |
| | | * The property definition associated with the property |
| | | * that caused the exception. |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected PropertyException(PropertyDefinition<?> pd, Message message, |
| | | Throwable cause) { |
| | | super(message, cause); |
| | | this.pd = pd; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the property definition associated with the property that |
| | | * caused the exception. |
| | | * |
| | | * @return Returns the property definition associated with the |
| | | * property that caused the exception. |
| | | */ |
| | | public final PropertyDefinition<?> getPropertyDefinition() { |
| | | return pd; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown when an attempt is made to remove a mandatory property. |
| | | */ |
| | | public class PropertyIsMandatoryException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 5328211711156565625L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new property is mandatory exception. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | */ |
| | | public PropertyIsMandatoryException(PropertyDefinition<?> pd) { |
| | | super(pd, ERR_PROPERTY_IS_MANDATORY_EXCEPTION.get(pd.getName())); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown when an attempt is made to modify a read-only property. |
| | | */ |
| | | public class PropertyIsReadOnlyException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 5315348044141024459L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new property is read-only exception. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | */ |
| | | public PropertyIsReadOnlyException(PropertyDefinition<?> pd) { |
| | | super(pd, ERR_PROPERTY_IS_READ_ONLY_EXCEPTION.get(pd.getName())); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown when an attempt is made to add more than value to a |
| | | * single-valued property. |
| | | */ |
| | | public class PropertyIsSingleValuedException extends PropertyException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -8056602690887917027L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new property is single valued exception. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | */ |
| | | public PropertyIsSingleValuedException(PropertyDefinition<?> pd) { |
| | | super(pd, ERR_PROPERTY_IS_SINGLE_VALUED_EXCEPTION.get(pd.getName())); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | /** |
| | | * Thrown when an attempt is made to retrieve a property using its name but the |
| | | * name was not recognized. |
| | | * <p> |
| | | * This exception can occur when attempt is made to retrieve inherited default |
| | | * values from a managed object. |
| | | */ |
| | | public class PropertyNotFoundException extends OperationsException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -895548482881819610L; |
| | | |
| | | // The name of the property that could not be found. |
| | | private final String propertyName; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new property not found exception. |
| | | * |
| | | * @param propertyName |
| | | * The name of the property that could not be found. |
| | | */ |
| | | public PropertyNotFoundException(String propertyName) { |
| | | super(ERR_PROPERTY_NOT_FOUND_EXCEPTION.get(propertyName)); |
| | | |
| | | this.propertyName = propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the property that could not be found. |
| | | * |
| | | * @return Returns the name of the property that could not be found. |
| | | */ |
| | | public String getPropertyName() { |
| | | return propertyName; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This enumeration contains various options that can be associated |
| | | * with property definitions. |
| | | */ |
| | | public enum PropertyOption { |
| | | /** |
| | | * Use this option to identify properties which should be considered |
| | | * as advanced and should not be exposed by default in client |
| | | * applications. |
| | | */ |
| | | ADVANCED, |
| | | |
| | | /** |
| | | * Use this option to identify properties which must not be directly |
| | | * exposed in client applications. |
| | | */ |
| | | HIDDEN, |
| | | |
| | | /** |
| | | * Use this option to identify properties which must have a value. |
| | | */ |
| | | MANDATORY, |
| | | |
| | | /** |
| | | * Use this option to identify properties which are multi-valued. |
| | | */ |
| | | MULTI_VALUED, |
| | | |
| | | /** |
| | | * Use this option to identify properties which can be initialized |
| | | * once only and are read-only thereafter. |
| | | */ |
| | | READ_ONLY, |
| | | |
| | | /** |
| | | * Use this option to identify properties which are for monitoring |
| | | * purposes only and are generated automatically by the server.. |
| | | */ |
| | | MONITORING; |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface which can be used to initialize the contents of a managed |
| | | * object. |
| | | */ |
| | | public interface PropertyProvider { |
| | | |
| | | /** |
| | | * A property provider which always returns empty property values, indicating |
| | | * default behavior. |
| | | */ |
| | | public static final PropertyProvider DEFAULT_PROVIDER = |
| | | new PropertyProvider() { |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <T> Collection<T> getPropertyValues(PropertyDefinition<T> d) |
| | | throws IllegalArgumentException { |
| | | return Collections.<T> emptySet(); |
| | | } |
| | | |
| | | }; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the property values associated with the specified property definition. |
| | | * <p> |
| | | * Implementations are not required to validate the values that they provide. |
| | | * Specifically: |
| | | * <ul> |
| | | * <li>they do not need to guarantee that the provided values are valid |
| | | * according to the property's syntax |
| | | * <li>they do not need to provide values for mandatory properties |
| | | * <li>they do not need to ensure that single-valued properties do contain at |
| | | * most one value. |
| | | * </ul> |
| | | * The returned set of values is allowed to contain duplicates. |
| | | * |
| | | * @param <T> |
| | | * The underlying type of the property. |
| | | * @param d |
| | | * The Property definition. |
| | | * @return Returns a newly allocated set containing a copy of the property's |
| | | * values. An empty set indicates that the property has no values |
| | | * defined and any default behavior is applicable. |
| | | * @throws IllegalArgumentException |
| | | * If this property provider does not recognise the requested |
| | | * property definition. |
| | | */ |
| | | <T> Collection<T> getPropertyValues(PropertyDefinition<T> d) |
| | | throws IllegalArgumentException; |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.net.InetAddress; |
| | | |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.forgerock.opendj.ldap.schema.AttributeType; |
| | | import org.opends.server.authorization.dseecompat.Aci; |
| | | import org.opends.server.types.AddressMask; |
| | | |
| | | |
| | | /** |
| | | * A visitor of property values, in the style of the visitor design |
| | | * pattern. Classes implementing this interface can query a property a |
| | | * value and its associated property definition in a type-safe manner |
| | | * when the kind of property value is unknown at compile time. When a |
| | | * visitor is passed to a property definition's accept method, the |
| | | * corresponding visit method most applicable to that property |
| | | * definition is invoked. |
| | | * <p> |
| | | * Each <code>visitXXX</code> method is provided with a default |
| | | * implementation which calls |
| | | * {@link #visitUnknown(PropertyDefinition, Object, Object)}. |
| | | * Sub-classes can override any or all of the methods to provide their |
| | | * own type-specific behavior. |
| | | * |
| | | * @param <R> |
| | | * The return type of this visitor's methods. Use |
| | | * {@link java.lang.Void} for visitors that do not need to |
| | | * return results. |
| | | * @param <P> |
| | | * The type of the additional parameter to this visitor's |
| | | * methods. Use {@link java.lang.Void} for visitors that do |
| | | * not need an additional parameter. |
| | | */ |
| | | public abstract class PropertyValueVisitor<R, P> { |
| | | |
| | | /** |
| | | * Default constructor. |
| | | */ |
| | | protected PropertyValueVisitor() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a dseecompat ACI. |
| | | * |
| | | * @param pd |
| | | * The dseecompat ACI property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitACI(ACIPropertyDefinition pd, Aci v, |
| | | P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an aggregation property value. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this aggregation property definition refers to. |
| | | * @param pd |
| | | * The aggregation property definition to visit. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public <C extends ConfigurationClient, S extends Configuration> |
| | | R visitAggregation( |
| | | AggregationPropertyDefinition<C, S> pd, String v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an attribute type. |
| | | * |
| | | * @param pd |
| | | * The attribute type property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitAttributeType(AttributeTypePropertyDefinition pd, |
| | | AttributeType v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a boolean. |
| | | * |
| | | * @param pd |
| | | * The boolean property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitBoolean(BooleanPropertyDefinition pd, Boolean v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a class. |
| | | * |
| | | * @param pd |
| | | * The class property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitClass(ClassPropertyDefinition pd, String v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a DN. |
| | | * |
| | | * @param pd |
| | | * The DN property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitDN(DNPropertyDefinition pd, DN v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a duration. |
| | | * |
| | | * @param pd |
| | | * The duration property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitDuration(DurationPropertyDefinition pd, Long v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an enumeration. |
| | | * |
| | | * @param <E> |
| | | * The enumeration that should be used for values of the |
| | | * property definition. |
| | | * @param pd |
| | | * The enumeration property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public <E extends Enum<E>> |
| | | R visitEnum(EnumPropertyDefinition<E> pd, E v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an integer. |
| | | * |
| | | * @param pd |
| | | * The integer property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitInteger(IntegerPropertyDefinition pd, Integer v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a IP address. |
| | | * |
| | | * @param pd |
| | | * The IP address property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitIPAddress(IPAddressPropertyDefinition pd, InetAddress v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a IP address mask. |
| | | * |
| | | * @param pd |
| | | * The IP address mask property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitIPAddressMask(IPAddressMaskPropertyDefinition pd, AddressMask v, |
| | | P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Visit a size. |
| | | * |
| | | * @param pd |
| | | * The size property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitSize(SizePropertyDefinition pd, Long v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a string. |
| | | * |
| | | * @param pd |
| | | * The string property definition. |
| | | * @param v |
| | | * The property value to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | public R visitString(StringPropertyDefinition pd, String v, P p) { |
| | | return visitUnknown(pd, v, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an unknown type of property value. Implementations of this |
| | | * method can provide default behavior for unknown types of |
| | | * property. |
| | | * <p> |
| | | * The default implementation of this method throws an |
| | | * {@link UnknownPropertyDefinitionException}. Sub-classes can |
| | | * override this method with their own default behavior. |
| | | * |
| | | * @param <T> |
| | | * The type of property value to visit. |
| | | * @param pd |
| | | * The property definition. |
| | | * @param v |
| | | * The property value. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | * @throws UnknownPropertyDefinitionException |
| | | * Visitor implementations may optionally throw this |
| | | * exception. |
| | | */ |
| | | public <T> R visitUnknown(PropertyDefinition<T> pd, T v, P p) |
| | | throws UnknownPropertyDefinitionException { |
| | | throw new UnknownPropertyDefinitionException(pd, p); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import org.opends.server.types.AttributeValue; |
| | | import org.forgerock.opendj.ldap.DN; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.RDN; |
| | | import org.opends.server.util.StaticUtils; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A reference to another managed object. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * reference refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * reference refers to. |
| | | */ |
| | | public final class Reference<C extends ConfigurationClient, |
| | | S extends Configuration> { |
| | | |
| | | /** |
| | | * Parses a DN string value as a reference using the provided |
| | | * managed object path and relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this reference refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this reference refers to. |
| | | * @param p |
| | | * The path of the referenced managed object's parent. |
| | | * @param rd |
| | | * The instantiable relation in the parent which contains |
| | | * the referenced managed object. |
| | | * @param s |
| | | * The DN string value. |
| | | * @return Returns the new reference based on the provided DN string |
| | | * value. |
| | | * @throws IllegalArgumentException |
| | | * If the DN string value could not be decoded as a DN or |
| | | * if the provided DN did not correspond to the provided |
| | | * path and relation. |
| | | */ |
| | | public static <C extends ConfigurationClient, S extends Configuration> |
| | | Reference<C, S> parseDN( |
| | | ManagedObjectPath<?, ?> p, InstantiableRelationDefinition<C, S> rd, |
| | | String s) throws IllegalArgumentException { |
| | | AbstractManagedObjectDefinition<?, ?> d = p.getManagedObjectDefinition(); |
| | | RelationDefinition<?, ?> tmp = d.getRelationDefinition(rd.getName()); |
| | | if (tmp != rd) { |
| | | throw new IllegalArgumentException("The relation \"" + rd.getName() |
| | | + "\" is not associated with the definition \"" + d.getName() + "\""); |
| | | } |
| | | |
| | | DN dn; |
| | | try { |
| | | dn = DN.decode(s); |
| | | } catch (DirectoryException e) { |
| | | throw new IllegalArgumentException("Unabled to decode the DN string: \"" |
| | | + s + "\""); |
| | | } |
| | | |
| | | RDN rdn = dn.getRDN(); |
| | | if (rdn == null) { |
| | | throw new IllegalArgumentException("Unabled to decode the DN string: \"" |
| | | + s + "\""); |
| | | } |
| | | |
| | | AttributeValue av = rdn.getAttributeValue(0); |
| | | if (av == null) { |
| | | throw new IllegalArgumentException("Unabled to decode the DN string: \"" |
| | | + s + "\""); |
| | | } |
| | | |
| | | String name = av.getValue().toString(); |
| | | |
| | | // Check that the DN was valid. |
| | | DN expected = p.child(rd, name).toDN(); |
| | | if (!dn.equals(expected)) { |
| | | throw new IllegalArgumentException("Unabled to decode the DN string: \"" |
| | | + s + "\""); |
| | | } |
| | | |
| | | return new Reference<C, S>(p, rd, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parses a name as a reference using the provided managed object |
| | | * path and relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this reference refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this reference refers to. |
| | | * @param p |
| | | * The path of the referenced managed object's parent. |
| | | * @param rd |
| | | * The instantiable relation in the parent which contains |
| | | * the referenced managed object. |
| | | * @param s |
| | | * The name of the referenced managed object. |
| | | * @return Returns the new reference based on the provided name. |
| | | * @throws IllegalArgumentException |
| | | * If the relation is not associated with the provided |
| | | * parent's definition, or if the provided name is empty. |
| | | */ |
| | | public static <C extends ConfigurationClient, S extends Configuration> |
| | | Reference<C, S> parseName( |
| | | ManagedObjectPath<?, ?> p, InstantiableRelationDefinition<C, S> rd, |
| | | String s) throws IllegalArgumentException { |
| | | // Sanity checks. |
| | | AbstractManagedObjectDefinition<?, ?> d = p.getManagedObjectDefinition(); |
| | | RelationDefinition<?, ?> tmp = d.getRelationDefinition(rd.getName()); |
| | | if (tmp != rd) { |
| | | throw new IllegalArgumentException("The relation \"" + rd.getName() |
| | | + "\" is not associated with the definition \"" + d.getName() + "\""); |
| | | } |
| | | |
| | | if (s.trim().length() == 0) { |
| | | throw new IllegalArgumentException("Empty names are not allowed"); |
| | | } |
| | | |
| | | return new Reference<C, S>(p, rd, s); |
| | | } |
| | | |
| | | // The name of the referenced managed object. |
| | | private final String name; |
| | | |
| | | // The path of the referenced managed object. |
| | | private final ManagedObjectPath<C, S> path; |
| | | |
| | | // The instantiable relation in the parent which contains the |
| | | // referenced managed object. |
| | | private final InstantiableRelationDefinition<C, S> relation; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private Reference(ManagedObjectPath<?, ?> parent, |
| | | InstantiableRelationDefinition<C, S> relation, String name) |
| | | throws IllegalArgumentException { |
| | | this.relation = relation; |
| | | this.name = name; |
| | | this.path = parent.child(relation, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the name of the referenced managed object. |
| | | * |
| | | * @return Returns the name of the referenced managed object. |
| | | */ |
| | | public String getName() { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the normalized name of the referenced managed object. |
| | | * |
| | | * @return Returns the normalized name of the referenced managed |
| | | * object. |
| | | */ |
| | | public String getNormalizedName() { |
| | | PropertyDefinition<?> pd = relation.getNamingPropertyDefinition(); |
| | | return normalizeName(pd); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the DN of the referenced managed object. |
| | | * |
| | | * @return Returns the DN of the referenced managed object. |
| | | */ |
| | | public DN toDN() { |
| | | return path.toDN(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public String toString() { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | // Normalize a value using the specified naming property definition |
| | | // if defined. |
| | | private <T> String normalizeName(PropertyDefinition<T> pd) { |
| | | if (pd != null) { |
| | | try { |
| | | T tvalue = pd.decodeValue(name); |
| | | return pd.normalizeValue(tvalue); |
| | | } catch (IllegalPropertyValueStringException e) { |
| | | // Fall through to default normalization. |
| | | } |
| | | } |
| | | |
| | | // FIXME: should really use directory string normalizer. |
| | | String s = name.trim().replaceAll(" +", " "); |
| | | return StaticUtils.toLowerCase(s); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | import java.util.EnumSet; |
| | | import java.util.Locale; |
| | | import java.util.MissingResourceException; |
| | | import java.util.Set; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Relation definitions define relationships between types of managed |
| | | * objects. In addition they define the ownership model: |
| | | * <ul> |
| | | * <li>composition - referenced managed objects are owned by the |
| | | * parent managed object and are deleted when the parent is deleted |
| | | * <li>aggregation - referenced managed objects are not owned by the |
| | | * parent managed object. Instead they are shared by other managed |
| | | * objects. |
| | | * </ul> |
| | | * Relations define how clients interact with the configuration. For |
| | | * example, clients manage aggregated managed objects in a shared |
| | | * location and attach them to parent managed objects. Composed |
| | | * managed objects, on the other hand, would be created directly |
| | | * beneath the parent managed object and destroyed with it too. |
| | | * <p> |
| | | * Within the server, listeners can choose to request notification of |
| | | * managed objects being added or removed from relations. |
| | | * <p> |
| | | * In LDAP, compositions are represented as follows: |
| | | * <ul> |
| | | * <li>singleton relations (one to one): a referenced managed object |
| | | * is represented using a child entry directly beneath the parent |
| | | * <li>optional relations (one to zero or one): a referenced managed |
| | | * object is represented using a child entry directly beneath the |
| | | * parent |
| | | * <li>instantiable relations (one to many): the relation is |
| | | * represented using a child entry directly beneath the parent. |
| | | * Referenced managed objects are represented using child entries of |
| | | * this "relation entry" and are named by the user |
| | | * <li>set relations (one to many): the relation is |
| | | * represented using a child entry directly beneath the parent. |
| | | * Referenced managed objects are represented using child entries of |
| | | * this "relation entry" whose name is the type of the managed object. |
| | | * </ul> |
| | | * Whereas, aggregations are represented by storing the DNs of the |
| | | * referenced managed objects in an attribute of the aggregating |
| | | * managed object. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public abstract class RelationDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing relation definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <D> |
| | | * The type of relation definition constructed by this |
| | | * builder. |
| | | */ |
| | | protected abstract static class AbstractBuilder |
| | | <C extends ConfigurationClient, S extends Configuration, |
| | | D extends RelationDefinition<C, S>> { |
| | | |
| | | // Common fields. |
| | | private final Common<C, S> common; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a property definition builder. |
| | | * |
| | | * @param pd |
| | | * The parent managed object definition. |
| | | * @param name |
| | | * The name of the relation. |
| | | * @param cd |
| | | * The child managed object definition. |
| | | */ |
| | | protected AbstractBuilder(AbstractManagedObjectDefinition<?, ?> pd, |
| | | String name, AbstractManagedObjectDefinition<C, S> cd) { |
| | | this.common = new Common<C, S>(pd, name, cd); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Construct a relation definition based on the properties of this |
| | | * builder. |
| | | * |
| | | * @return The new relation definition. |
| | | */ |
| | | public final D getInstance() { |
| | | return buildInstance(common); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Add a relation definition option. |
| | | * |
| | | * @param option |
| | | * The relation option. |
| | | */ |
| | | public final void setOption(RelationOption option) { |
| | | ensureNotNull(option); |
| | | common.options.add(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Build a relation definition based on the properties of this |
| | | * builder. |
| | | * |
| | | * @param common |
| | | * The common fields of the new relation definition. |
| | | * @return The new relation definition. |
| | | */ |
| | | protected abstract D buildInstance(Common<C, S> common); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Opaque structure containing fields common to all relation |
| | | * definition types. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this relation definition refers to. |
| | | */ |
| | | protected static final class Common |
| | | <C extends ConfigurationClient, S extends Configuration> { |
| | | |
| | | // The definition of the child managed object. |
| | | private final AbstractManagedObjectDefinition<C, S> cd; |
| | | |
| | | // The name of the relation. |
| | | private final String name; |
| | | |
| | | // Options applicable to this definition. |
| | | private final Set<RelationOption> options; |
| | | |
| | | // The definition of the parent managed object. |
| | | private final AbstractManagedObjectDefinition<?, ?> pd; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private Common(AbstractManagedObjectDefinition<?, ?> pd, String name, |
| | | AbstractManagedObjectDefinition<C, S> cd) { |
| | | this.name = name; |
| | | this.pd = pd; |
| | | this.cd = cd; |
| | | this.options = EnumSet.noneOf(RelationOption.class); |
| | | } |
| | | } |
| | | |
| | | // Common fields. |
| | | private final Common<C, S> common; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new managed object relation definition with the |
| | | * specified common fields. |
| | | * |
| | | * @param common |
| | | * The common fields of the new relation definition. |
| | | */ |
| | | protected RelationDefinition(Common<C, S> common) { |
| | | this.common = common; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Apply a visitor to this relation definition. |
| | | * |
| | | * @param <R> |
| | | * The return type of the visitor's methods. |
| | | * @param <P> |
| | | * The type of the additional parameters to the visitor's |
| | | * methods. |
| | | * @param v |
| | | * The relation definition visitor. |
| | | * @param p |
| | | * Optional additional visitor parameter. |
| | | * @return Returns a result as specified by the visitor. |
| | | */ |
| | | public abstract <R, P> R accept(RelationDefinitionVisitor<R, P> v, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the definition of the child managed object. |
| | | * |
| | | * @return Returns the definition of the child managed object. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<C, S> getChildDefinition() { |
| | | return common.cd; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this relation definition in the |
| | | * default locale. |
| | | * |
| | | * @return Returns the description of this relation definition in |
| | | * the default locale, or <code>null</code> if there is no |
| | | * description. |
| | | */ |
| | | public final Message getDescription() { |
| | | return getDescription(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional description of this relation definition in the |
| | | * specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the description of this relation definition in |
| | | * the specified locale, or <code>null</code> if there is |
| | | * no description. |
| | | */ |
| | | public final Message getDescription(Locale locale) { |
| | | try { |
| | | String property = "relation." + common.name + ".description"; |
| | | return ManagedObjectDefinitionI18NResource.getInstance().getMessage( |
| | | getParentDefinition(), property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the name of the relation. |
| | | * |
| | | * @return Returns the name of the relation. |
| | | */ |
| | | public final String getName() { |
| | | return common.name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the definition of the parent managed object. |
| | | * |
| | | * @return Returns the definition of the parent managed object. |
| | | */ |
| | | public final AbstractManagedObjectDefinition<?, ?> getParentDefinition() { |
| | | return common.pd; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this relation definition in the default |
| | | * locale. |
| | | * |
| | | * @return Returns the synopsis of this relation definition in the |
| | | * default locale. |
| | | */ |
| | | public final Message getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this relation definition in the specified |
| | | * locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this relation definition in the |
| | | * specified locale. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) { |
| | | String property = "relation." + common.name + ".synopsis"; |
| | | return ManagedObjectDefinitionI18NResource.getInstance().getMessage( |
| | | getParentDefinition(), property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly name of this relation definition in the |
| | | * default locale. |
| | | * |
| | | * @return Returns the user friendly name of this relation |
| | | * definition in the default locale. |
| | | */ |
| | | public final Message getUserFriendlyName() { |
| | | return getUserFriendlyName(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly name of this relation definition in the |
| | | * specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the user friendly name of this relation |
| | | * definition in the specified locale. |
| | | */ |
| | | public final Message getUserFriendlyName(Locale locale) { |
| | | String property = "relation." + common.name + ".user-friendly-name"; |
| | | return ManagedObjectDefinitionI18NResource.getInstance().getMessage( |
| | | getParentDefinition(), property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Check if the specified option is set for this relation |
| | | * definition. |
| | | * |
| | | * @param option |
| | | * The option to test. |
| | | * @return Returns <code>true</code> if the option is set, or |
| | | * <code>false</code> otherwise. |
| | | */ |
| | | public final boolean hasOption(RelationOption option) { |
| | | return common.options.contains(option); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public final String toString() { |
| | | StringBuilder builder = new StringBuilder(); |
| | | toString(builder); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Append a string representation of the managed object relation to |
| | | * the provided string builder. |
| | | * |
| | | * @param builder |
| | | * The string builder where the string representation |
| | | * should be appended. |
| | | */ |
| | | public abstract void toString(StringBuilder builder); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Performs any run-time initialization required by this relation |
| | | * definition. This may include resolving managed object paths and |
| | | * property names. |
| | | * |
| | | * @throws Exception |
| | | * If this relation definition could not be initialized. |
| | | */ |
| | | protected void initialize() throws Exception { |
| | | // No implementation required. |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A visitor of relation definitions, in the style of the visitor |
| | | * design pattern. Classes implementing this interface can query |
| | | * relation definitions in a type-safe manner when the kind of |
| | | * relation definition is unknown at compile time. When a visitor is |
| | | * passed to a relation definition's accept method, the corresponding |
| | | * visit method most applicable to that relation definition is |
| | | * invoked. |
| | | * |
| | | * @param <R> |
| | | * The return type of this visitor's methods. Use |
| | | * {@link java.lang.Void} for visitors that do not need to |
| | | * return results. |
| | | * @param <P> |
| | | * The type of the additional parameter to this visitor's |
| | | * methods. Use {@link java.lang.Void} for visitors that do |
| | | * not need an additional parameter. |
| | | */ |
| | | public interface RelationDefinitionVisitor<R, P> { |
| | | |
| | | /** |
| | | * Visit an instantiable relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param rd |
| | | * The instantiable relation definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> R visitInstantiable( |
| | | InstantiableRelationDefinition<C, S> rd, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a set relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param rd |
| | | * The set relation definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> R visitSet( |
| | | SetRelationDefinition<C, S> rd, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit an optional relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param rd |
| | | * The optional relation definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> R visitOptional( |
| | | OptionalRelationDefinition<C, S> rd, P p); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Visit a singleton relation definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param rd |
| | | * The singleton relation definition to visit. |
| | | * @param p |
| | | * A visitor specified parameter. |
| | | * @return Returns a visitor specified result. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> R visitSingleton( |
| | | SingletonRelationDefinition<C, S> rd, P p); |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This enumeration contains various options that can be associated |
| | | * with relation definitions. |
| | | */ |
| | | public enum RelationOption { |
| | | /** |
| | | * Use this option to identify relations which should be considered |
| | | * as advanced and should not be exposed by default in client |
| | | * applications. |
| | | */ |
| | | ADVANCED, |
| | | |
| | | /** |
| | | * Use this option to identify relations which must not be directly |
| | | * exposed in client applications. |
| | | */ |
| | | HIDDEN; |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default behavior provider which retrieves default values from a |
| | | * parent managed object. It should be used by properties which |
| | | * inherit their default value(s) from properties held in an other |
| | | * managed object. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public final class RelativeInheritedDefaultBehaviorProvider<T> extends |
| | | DefaultBehaviorProvider<T> { |
| | | |
| | | // The type of managed object expected at the relative offset. |
| | | private final AbstractManagedObjectDefinition<?, ?> d; |
| | | |
| | | // The relative offset (where 1 = parent, 2 = grandparent) of the |
| | | // managed object containing the property. |
| | | private final int offset; |
| | | |
| | | // The name of the property containing the inherited default values. |
| | | private final String propertyName; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a relative inherited default behavior provider associated |
| | | * with a parent managed object. |
| | | * |
| | | * @param d |
| | | * The type of parent managed object expected at the |
| | | * relative location. |
| | | * @param propertyName |
| | | * The name of the property containing the inherited |
| | | * default values. |
| | | * @param offset |
| | | * The relative location of the parent managed object |
| | | * (where 0 is the managed object itself, 1 is the parent, |
| | | * and 2 is the grand-parent). |
| | | * @throws IllegalArgumentException |
| | | * If the offset is less than 0. |
| | | */ |
| | | public RelativeInheritedDefaultBehaviorProvider( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, int offset) |
| | | throws IllegalArgumentException { |
| | | // We do not decode the property name now because the property |
| | | // might not have been constructed at this point (e.g. when the |
| | | // offset is 0). |
| | | if (offset < 0) { |
| | | throw new IllegalArgumentException("Negative offset"); |
| | | } |
| | | this.d = d; |
| | | this.propertyName = propertyName; |
| | | this.offset = offset; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <R, P> R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p) { |
| | | return v.visitRelativeInherited(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the definition of the parent managed object containing the |
| | | * inherited default values. |
| | | * |
| | | * @return Returns the definition of the parent managed object |
| | | * containing the inherited default values. |
| | | */ |
| | | public AbstractManagedObjectDefinition<?, ?> getManagedObjectDefinition() { |
| | | return d; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the absolute path of the managed object containing the |
| | | * property which has the default values. |
| | | * |
| | | * @param path |
| | | * The path of the current managed object from which the |
| | | * relative path should be determined. |
| | | * @return Returns the absolute path of the managed object |
| | | * containing the property which has the default values. |
| | | */ |
| | | public ManagedObjectPath<?, ?> getManagedObjectPath( |
| | | ManagedObjectPath<?, ?> path) { |
| | | return path.parent(offset); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the name of the property containing the inherited default |
| | | * values. |
| | | * |
| | | * @return Returns the name of the property containing the inherited |
| | | * default values. |
| | | */ |
| | | public String getPropertyName() { |
| | | return propertyName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the relative location of the parent managed object. |
| | | * |
| | | * @return Returns the relative location of the parent managed |
| | | * object (where 0 is the managed object itself, 1 is the |
| | | * parent, and 2 is the grand-parent). |
| | | */ |
| | | public int getRelativeOffset() { |
| | | return offset; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.Collections; |
| | | import java.util.HashMap; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A managed object composite relationship definition which represents a |
| | | * composition of zero or more managed objects each of which must have a |
| | | * different type. The manage objects are named using their type name. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public final class SetRelationDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends RelationDefinition<C, S> |
| | | { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing set relation |
| | | * definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public static final class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractBuilder<C, S, SetRelationDefinition<C, S>> |
| | | { |
| | | |
| | | // The plural name of the relation. |
| | | private final String pluralName; |
| | | |
| | | // The optional default managed objects associated with this |
| | | // set relation definition. |
| | | private final Map<String, |
| | | DefaultManagedObject<? extends C, ? extends S>> |
| | | defaultManagedObjects = |
| | | new HashMap<String, DefaultManagedObject<? extends C, ? extends S>>(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new builder which can be used to incrementally build a |
| | | * set relation definition. |
| | | * |
| | | * @param pd |
| | | * The parent managed object definition. |
| | | * @param name |
| | | * The name of the relation. |
| | | * @param pluralName |
| | | * The plural name of the relation. |
| | | * @param cd |
| | | * The child managed object definition. |
| | | */ |
| | | public Builder(AbstractManagedObjectDefinition<?, ?> pd, |
| | | String name, String pluralName, |
| | | AbstractManagedObjectDefinition<C, S> cd) |
| | | { |
| | | super(pd, name, cd); |
| | | this.pluralName = pluralName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the default managed object to this set relation definition. |
| | | * |
| | | * @param defaultManagedObject |
| | | * The default managed object. |
| | | */ |
| | | public void setDefaultManagedObject( |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) |
| | | { |
| | | this.defaultManagedObjects |
| | | .put(defaultManagedObject.getManagedObjectDefinition() |
| | | .getName(), defaultManagedObject); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected SetRelationDefinition<C, S> buildInstance( |
| | | Common<C, S> common) |
| | | { |
| | | return new SetRelationDefinition<C, S>(common, pluralName, |
| | | defaultManagedObjects); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | // The plural name of the relation. |
| | | private final String pluralName; |
| | | |
| | | // The optional default managed objects associated with this |
| | | // set relation definition. |
| | | private final Map<String, |
| | | DefaultManagedObject<? extends C, ? extends S>> |
| | | defaultManagedObjects; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SetRelationDefinition( |
| | | Common<C, S> common, |
| | | String pluralName, |
| | | Map<String, |
| | | DefaultManagedObject<? extends C, ? extends S>> defaultManagedObjects) |
| | | { |
| | | super(common); |
| | | this.pluralName = pluralName; |
| | | this.defaultManagedObjects = defaultManagedObjects; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(RelationDefinitionVisitor<R, P> v, P p) |
| | | { |
| | | return v.visitSet(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the named default managed object associated with this set |
| | | * relation definition. |
| | | * |
| | | * @param name |
| | | * The name of the default managed object (for set relations |
| | | * this is the type of the default managed object). |
| | | * @return The named default managed object. |
| | | * @throws IllegalArgumentException |
| | | * If there is no default managed object associated with the |
| | | * provided name. |
| | | */ |
| | | public DefaultManagedObject<? extends C, ? extends S> getDefaultManagedObject( |
| | | String name) throws IllegalArgumentException |
| | | { |
| | | if (!defaultManagedObjects.containsKey(name)) |
| | | { |
| | | throw new IllegalArgumentException( |
| | | "unrecognized default managed object \"" + name + "\""); |
| | | } |
| | | return defaultManagedObjects.get(name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the names of the default managed objects associated with this |
| | | * set relation definition. |
| | | * |
| | | * @return An unmodifiable set containing the names of the default |
| | | * managed object. |
| | | */ |
| | | public Set<String> getDefaultManagedObjectNames() |
| | | { |
| | | return Collections.unmodifiableSet(defaultManagedObjects.keySet()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the plural name of the relation. |
| | | * |
| | | * @return The plural name of the relation. |
| | | */ |
| | | public String getPluralName() |
| | | { |
| | | return pluralName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this relation definition in |
| | | * the default locale. |
| | | * |
| | | * @return Returns the user friendly plural name of this relation |
| | | * definition in the default locale. |
| | | */ |
| | | public Message getUserFriendlyPluralName() |
| | | { |
| | | return getUserFriendlyPluralName(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the user friendly plural name of this relation definition in |
| | | * the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the user friendly plural name of this relation |
| | | * definition in the specified locale. |
| | | */ |
| | | public Message getUserFriendlyPluralName(Locale locale) |
| | | { |
| | | String property = |
| | | "relation." + getName() + ".user-friendly-plural-name"; |
| | | return ManagedObjectDefinitionI18NResource.getInstance() |
| | | .getMessage(getParentDefinition(), property, locale); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) |
| | | { |
| | | builder.append("name="); |
| | | builder.append(getName()); |
| | | builder.append(" type=set parent="); |
| | | builder.append(getParentDefinition().getName()); |
| | | builder.append(" child="); |
| | | builder.append(getChildDefinition().getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception |
| | | { |
| | | for (DefaultManagedObject<?, ?> dmo : defaultManagedObjects |
| | | .values()) |
| | | { |
| | | dmo.initialize(); |
| | | } |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A managed object composite relationship definition which represents |
| | | * a composition of a single managed object (i.e. the managed object |
| | | * must be present). |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that this |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that this |
| | | * relation definition refers to. |
| | | */ |
| | | public final class SingletonRelationDefinition |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends RelationDefinition<C, S> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing singleton relation |
| | | * definitions. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that |
| | | * this relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that |
| | | * this relation definition refers to. |
| | | */ |
| | | public static final class Builder |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | extends AbstractBuilder<C, S, SingletonRelationDefinition<C, S>> { |
| | | |
| | | // The optional default managed object associated with this |
| | | // singleton relation. |
| | | private DefaultManagedObject<? extends C, ? extends S> |
| | | defaultManagedObject = null; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new builder which can be used to incrementally build |
| | | * an singleton relation definition. |
| | | * |
| | | * @param pd |
| | | * The parent managed object definition. |
| | | * @param name |
| | | * The name of the relation. |
| | | * @param cd |
| | | * The child managed object definition. |
| | | */ |
| | | public Builder(AbstractManagedObjectDefinition<?, ?> pd, String name, |
| | | AbstractManagedObjectDefinition<C, S> cd) { |
| | | super(pd, name, cd); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the optional default managed object associated with this |
| | | * singleton relation definition. |
| | | * |
| | | * @param defaultManagedObject |
| | | * The default managed object or <code>null</code> if |
| | | * there is no default managed object defined for this |
| | | * relation definition. |
| | | */ |
| | | public void setDefaultManagedObject( |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) { |
| | | this.defaultManagedObject = defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected SingletonRelationDefinition<C, S> buildInstance( |
| | | Common<C, S> common) { |
| | | return new SingletonRelationDefinition<C, S>(common, |
| | | defaultManagedObject); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | // The optional default managed object associated with this |
| | | // singleton relation. |
| | | private final DefaultManagedObject<? extends C, ? extends S> |
| | | defaultManagedObject; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SingletonRelationDefinition(Common<C, S> common, |
| | | DefaultManagedObject<? extends C, ? extends S> defaultManagedObject) { |
| | | super(common); |
| | | this.defaultManagedObject = defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(RelationDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitSingleton(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional default managed object associated with this |
| | | * singleton relation definition. |
| | | * |
| | | * @return Returns the default managed object or <code>null</code> |
| | | * if there is no default managed object defined for this |
| | | * relation definition. |
| | | */ |
| | | public DefaultManagedObject<? extends C, ? extends S> |
| | | getDefaultManagedObject() { |
| | | return defaultManagedObject; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | builder.append("name="); |
| | | builder.append(getName()); |
| | | builder.append(" type=singleton parent="); |
| | | builder.append(getParentDefinition().getName()); |
| | | builder.append(" child="); |
| | | builder.append(getChildDefinition().getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected void initialize() throws Exception { |
| | | if (defaultManagedObject != null) { |
| | | defaultManagedObject.initialize(); |
| | | } |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Memory size property definition. |
| | | * <p> |
| | | * All memory size property values are represented in bytes using longs. |
| | | * <p> |
| | | * All values must be zero or positive and within the lower/upper limit |
| | | * constraints. Support is provided for "unlimited" memory sizes. These are |
| | | * represented using a negative memory size value or using the string |
| | | * "unlimited". |
| | | */ |
| | | public final class SizePropertyDefinition extends PropertyDefinition<Long> { |
| | | |
| | | // String used to represent unlimited memory sizes. |
| | | private static final String UNLIMITED = "unlimited"; |
| | | |
| | | // The lower limit of the property value in bytes. |
| | | private final long lowerLimit; |
| | | |
| | | // The optional upper limit of the property value in bytes. |
| | | private final Long upperLimit; |
| | | |
| | | // Indicates whether this property allows the use of the "unlimited" memory |
| | | // size value (represented using a -1L or the string "unlimited"). |
| | | private final boolean allowUnlimited; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for incrementally constructing memory size property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<Long, SizePropertyDefinition> { |
| | | |
| | | // The lower limit of the property value in bytes. |
| | | private long lowerLimit = 0L; |
| | | |
| | | // The optional upper limit of the property value in bytes. |
| | | private Long upperLimit = null; |
| | | |
| | | // Indicates whether this property allows the use of the "unlimited" memory |
| | | // size value (represented using a -1L or the string "unlimited"). |
| | | private boolean allowUnlimited = false; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the lower limit in bytes. |
| | | * |
| | | * @param lowerLimit |
| | | * The new lower limit (must be >= 0) in bytes. |
| | | * @throws IllegalArgumentException |
| | | * If a negative lower limit was specified, or if the lower limit |
| | | * is greater than the upper limit. |
| | | */ |
| | | public final void setLowerLimit(long lowerLimit) |
| | | throws IllegalArgumentException { |
| | | if (lowerLimit < 0) { |
| | | throw new IllegalArgumentException("Negative lower limit"); |
| | | } |
| | | if (upperLimit != null && lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | this.lowerLimit = lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the lower limit using a string representation of the limit. |
| | | * |
| | | * @param lowerLimit |
| | | * The string representation of the new lower limit. |
| | | * @throws IllegalArgumentException |
| | | * If the lower limit could not be parsed, or if a negative lower |
| | | * limit was specified, or the lower limit is greater than the |
| | | * upper limit. |
| | | */ |
| | | public final void setLowerLimit(String lowerLimit) |
| | | throws IllegalArgumentException { |
| | | setLowerLimit(SizeUnit.parseValue(lowerLimit, SizeUnit.BYTES)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the upper limit in bytes. |
| | | * |
| | | * @param upperLimit |
| | | * The new upper limit in bytes or <code>null</code> if there is |
| | | * no upper limit. |
| | | * @throws IllegalArgumentException |
| | | * If the lower limit is greater than the upper limit. |
| | | */ |
| | | public final void setUpperLimit(Long upperLimit) |
| | | throws IllegalArgumentException { |
| | | if (upperLimit != null) { |
| | | if (upperLimit < 0) { |
| | | throw new IllegalArgumentException("Negative upper limit"); |
| | | } |
| | | if (lowerLimit > upperLimit) { |
| | | throw new IllegalArgumentException( |
| | | "Lower limit greater than upper limit"); |
| | | } |
| | | } |
| | | this.upperLimit = upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the upper limit using a string representation of the limit. |
| | | * |
| | | * @param upperLimit |
| | | * The string representation of the new upper limit, or |
| | | * <code>null</code> if there is no upper limit. |
| | | * @throws IllegalArgumentException |
| | | * If the upper limit could not be parsed, or if the lower limit |
| | | * is greater than the upper limit. |
| | | */ |
| | | public final void setUpperLimit(String upperLimit) |
| | | throws IllegalArgumentException { |
| | | if (upperLimit == null) { |
| | | setUpperLimit((Long) null); |
| | | } else { |
| | | setUpperLimit(SizeUnit.parseValue(upperLimit, SizeUnit.BYTES)); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specify whether or not this property definition will allow unlimited |
| | | * values (default is false). |
| | | * |
| | | * @param allowUnlimited |
| | | * <code>true</code> if the property will allow unlimited values, |
| | | * or <code>false</code> otherwise. |
| | | */ |
| | | public final void setAllowUnlimited(boolean allowUnlimited) { |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected SizePropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Long> defaultBehavior) { |
| | | return new SizePropertyDefinition(d, propertyName, options, adminAction, |
| | | defaultBehavior, lowerLimit, upperLimit, allowUnlimited); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an memory size property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new integer property definition builder. |
| | | */ |
| | | public static Builder createBuilder( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SizePropertyDefinition( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<Long> defaultBehavior, Long lowerLimit, |
| | | Long upperLimit, boolean allowUnlimited) { |
| | | super(d, Long.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | this.lowerLimit = lowerLimit; |
| | | this.upperLimit = upperLimit; |
| | | this.allowUnlimited = allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the lower limit in bytes. |
| | | * |
| | | * @return Returns the lower limit in bytes. |
| | | */ |
| | | public long getLowerLimit() { |
| | | return lowerLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the upper limit in bytes. |
| | | * |
| | | * @return Returns the upper limit in bytes or <code>null</code> if there is |
| | | * no upper limit. |
| | | */ |
| | | public Long getUpperLimit() { |
| | | return upperLimit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determine whether this property allows unlimited memory sizes. |
| | | * |
| | | * @return Returns <code>true</code> if this this property allows unlimited |
| | | * memory sizes. |
| | | */ |
| | | public boolean isAllowUnlimited() { |
| | | return allowUnlimited; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(Long value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | if (!allowUnlimited && value < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | |
| | | // unlimited allowed |
| | | } else if (value >= 0 && value < lowerLimit) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | |
| | | if ((upperLimit != null) && (value > upperLimit)) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String encodeValue(Long value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | // Make sure that we correctly encode negative values as "unlimited". |
| | | if (allowUnlimited) { |
| | | if (value < 0) { |
| | | return UNLIMITED; |
| | | } |
| | | } |
| | | |
| | | // Encode the size value using the best-fit unit. |
| | | StringBuilder builder = new StringBuilder(); |
| | | SizeUnit unit = SizeUnit.getBestFitUnitExact(value); |
| | | |
| | | // Cast to a long to remove fractional part (which should not be there |
| | | // anyway as the best-fit unit should result in an exact conversion). |
| | | builder.append((long) unit.fromBytes(value)); |
| | | builder.append(' '); |
| | | builder.append(unit.toString()); |
| | | return builder.toString(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public Long decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | // First check for the special "unlimited" value when necessary. |
| | | if (allowUnlimited) { |
| | | if (value.trim().equalsIgnoreCase(UNLIMITED)) { |
| | | return -1L; |
| | | } |
| | | } |
| | | |
| | | // Decode the value. |
| | | Long i; |
| | | try { |
| | | i = SizeUnit.parseValue(value, SizeUnit.BYTES); |
| | | } catch (NumberFormatException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | try { |
| | | validateValue(i); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | return i; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitSize(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, Long value, P p) { |
| | | return v.visitSize(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void toString(StringBuilder builder) { |
| | | super.toString(builder); |
| | | |
| | | builder.append(" lowerLimit="); |
| | | builder.append(lowerLimit); |
| | | |
| | | if (upperLimit != null) { |
| | | builder.append(" upperLimit="); |
| | | builder.append(upperLimit); |
| | | } |
| | | |
| | | builder.append(" allowUnlimited="); |
| | | builder.append(allowUnlimited); |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public int compare(Long o1, Long o2) { |
| | | return o1.compareTo(o2); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import java.util.HashMap; |
| | | import java.util.Map; |
| | | import java.util.regex.Matcher; |
| | | import java.util.regex.Pattern; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This enumeration defines various memory size units. |
| | | */ |
| | | public enum SizeUnit { |
| | | |
| | | /** |
| | | * A byte unit. |
| | | */ |
| | | BYTES(1L, "b", "bytes"), |
| | | |
| | | /** |
| | | * A gibi-byte unit. |
| | | */ |
| | | GIBI_BYTES((long) 1024 * 1024 * 1024, "gib", "gibibytes"), |
| | | |
| | | /** |
| | | * A giga-byte unit. |
| | | */ |
| | | GIGA_BYTES((long) 1000 * 1000 * 1000, "gb", "gigabytes"), |
| | | |
| | | /** |
| | | * A kibi-byte unit. |
| | | */ |
| | | KIBI_BYTES(1024L, "kib", "kibibytes"), |
| | | |
| | | /** |
| | | * A kilo-byte unit. |
| | | */ |
| | | KILO_BYTES(1000L, "kb", "kilobytes"), |
| | | |
| | | /** |
| | | * A mebi-byte unit. |
| | | */ |
| | | MEBI_BYTES((long) 1024 * 1024, "mib", "mebibytes"), |
| | | |
| | | /** |
| | | * A mega-byte unit. |
| | | */ |
| | | MEGA_BYTES((long) 1000 * 1000, "mb", "megabytes"), |
| | | |
| | | /** |
| | | * A tebi-byte unit. |
| | | */ |
| | | TEBI_BYTES((long) 1024 * 1024 * 1024 * 1024, "tib", "tebibytes"), |
| | | |
| | | /** |
| | | * A tera-byte unit. |
| | | */ |
| | | TERA_BYTES((long) 1000 * 1000 * 1000 * 1000, "tb", "terabytes"); |
| | | |
| | | // A lookup table for resolving a unit from its name. |
| | | private static final Map<String, SizeUnit> nameToUnit; |
| | | static { |
| | | nameToUnit = new HashMap<String, SizeUnit>(); |
| | | |
| | | for (SizeUnit unit : SizeUnit.values()) { |
| | | nameToUnit.put(unit.shortName, unit); |
| | | nameToUnit.put(unit.longName, unit); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the best-fit unit for the specified number of bytes. The |
| | | * returned unit will be able to represent the number of bytes using |
| | | * a decimal number comprising of an integer part which is greater |
| | | * than zero. Bigger units are chosen in preference to smaller units |
| | | * and binary units are only returned if they are an exact fit. If |
| | | * the number of bytes is zero then the {@link #BYTES} unit is |
| | | * always returned. For example: |
| | | * |
| | | * <pre> |
| | | * getBestFitUnit(0) // BYTES |
| | | * getBestFitUnit(999) // BYTES |
| | | * getBestFitUnit(1000) // KILO_BYTES |
| | | * getBestFitUnit(1024) // KIBI_BYTES |
| | | * getBestFitUnit(1025) // KILO_BYTES |
| | | * getBestFitUnit(999999) // KILO_BYTES |
| | | * getBestFitUnit(1000000) // MEGA_BYTES |
| | | * </pre> |
| | | * |
| | | * @param bytes |
| | | * The number of bytes. |
| | | * @return Returns the best fit unit. |
| | | * @throws IllegalArgumentException |
| | | * If <code>bytes</code> is negative. |
| | | * @see #getBestFitUnitExact(long) |
| | | */ |
| | | public static SizeUnit getBestFitUnit(long bytes) |
| | | throws IllegalArgumentException { |
| | | if (bytes < 0) { |
| | | throw new IllegalArgumentException("negative number of bytes: " + bytes); |
| | | } else if (bytes == 0) { |
| | | // Always use bytes for zero values. |
| | | return BYTES; |
| | | } else { |
| | | // Determine best fit: prefer non-binary units unless binary |
| | | // fits exactly. |
| | | SizeUnit[] nonBinary = new SizeUnit[] { TERA_BYTES, GIGA_BYTES, |
| | | MEGA_BYTES, KILO_BYTES }; |
| | | SizeUnit[] binary = new SizeUnit[] { TEBI_BYTES, GIBI_BYTES, MEBI_BYTES, |
| | | KIBI_BYTES }; |
| | | |
| | | for (int i = 0; i < nonBinary.length; i++) { |
| | | if ((bytes % binary[i].getSize()) == 0) { |
| | | return binary[i]; |
| | | } else if ((bytes / nonBinary[i].getSize()) > 0) { |
| | | return nonBinary[i]; |
| | | } |
| | | } |
| | | |
| | | return BYTES; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the best-fit unit for the specified number of bytes which |
| | | * can represent the provided value using an integral value. Bigger |
| | | * units are chosen in preference to smaller units. If the number of |
| | | * bytes is zero then the {@link #BYTES} unit is always returned. |
| | | * For example: |
| | | * |
| | | * <pre> |
| | | * getBestFitUnitExact(0) // BYTES |
| | | * getBestFitUnitExact(999) // BYTES |
| | | * getBestFitUnitExact(1000) // KILO_BYTES |
| | | * getBestFitUnitExact(1024) // KIBI_BYTES |
| | | * getBestFitUnitExact(1025) // BYTES |
| | | * getBestFitUnitExact(999999) // BYTES |
| | | * getBestFitUnitExact(1000000) // MEGA_BYTES |
| | | * </pre> |
| | | * |
| | | * @param bytes |
| | | * The number of bytes. |
| | | * @return Returns the best fit unit can represent the provided |
| | | * value using an integral value. |
| | | * @throws IllegalArgumentException |
| | | * If <code>bytes</code> is negative. |
| | | * @see #getBestFitUnit(long) |
| | | */ |
| | | public static SizeUnit getBestFitUnitExact(long bytes) |
| | | throws IllegalArgumentException { |
| | | if (bytes < 0) { |
| | | throw new IllegalArgumentException("negative number of bytes: " + bytes); |
| | | } else if (bytes == 0) { |
| | | // Always use bytes for zero values. |
| | | return BYTES; |
| | | } else { |
| | | // Determine best fit. |
| | | SizeUnit[] units = new SizeUnit[] { TEBI_BYTES, TERA_BYTES, GIBI_BYTES, |
| | | GIGA_BYTES, MEBI_BYTES, MEGA_BYTES, KIBI_BYTES, KILO_BYTES }; |
| | | |
| | | for (SizeUnit unit : units) { |
| | | if ((bytes % unit.getSize()) == 0) { |
| | | return unit; |
| | | } |
| | | } |
| | | |
| | | return BYTES; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the unit corresponding to the provided unit name. |
| | | * |
| | | * @param s |
| | | * The name of the unit. Can be the abbreviated or long |
| | | * name and can contain white space and mixed case |
| | | * characters. |
| | | * @return Returns the unit corresponding to the provided unit name. |
| | | * @throws IllegalArgumentException |
| | | * If the provided name did not correspond to a known |
| | | * memory size unit. |
| | | */ |
| | | public static SizeUnit getUnit(String s) throws IllegalArgumentException { |
| | | SizeUnit unit = nameToUnit.get(s.trim().toLowerCase()); |
| | | if (unit == null) { |
| | | throw new IllegalArgumentException("Illegal memory size unit \"" + s |
| | | + "\""); |
| | | } |
| | | return unit; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parse the provided size string and return its equivalent size in |
| | | * bytes. The size string must specify the unit e.g. "10kb". |
| | | * |
| | | * @param s |
| | | * The size string to be parsed. |
| | | * @return Returns the parsed duration in bytes. |
| | | * @throws NumberFormatException |
| | | * If the provided size string could not be parsed. |
| | | */ |
| | | public static long parseValue(String s) throws NumberFormatException { |
| | | return parseValue(s, null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Parse the provided size string and return its equivalent size in |
| | | * bytes. |
| | | * |
| | | * @param s |
| | | * The size string to be parsed. |
| | | * @param defaultUnit |
| | | * The default unit to use if there is no unit specified in |
| | | * the size string, or <code>null</code> if the string |
| | | * must always contain a unit. |
| | | * @return Returns the parsed size in bytes. |
| | | * @throws NumberFormatException |
| | | * If the provided size string could not be parsed. |
| | | */ |
| | | public static long parseValue(String s, SizeUnit defaultUnit) |
| | | throws NumberFormatException { |
| | | // Value must be a floating point number followed by a unit. |
| | | Pattern p = Pattern.compile("^\\s*(\\d+(\\.\\d+)?)\\s*(\\w+)?\\s*$"); |
| | | Matcher m = p.matcher(s); |
| | | |
| | | if (!m.matches()) { |
| | | throw new NumberFormatException("Invalid size value \"" + s + "\""); |
| | | } |
| | | |
| | | // Group 1 is the float. |
| | | double d; |
| | | try { |
| | | d = Double.valueOf(m.group(1)); |
| | | } catch (NumberFormatException e) { |
| | | throw new NumberFormatException("Invalid size value \"" + s + "\""); |
| | | } |
| | | |
| | | // Group 3 is the unit. |
| | | String unitString = m.group(3); |
| | | SizeUnit unit; |
| | | if (unitString == null) { |
| | | if (defaultUnit == null) { |
| | | throw new NumberFormatException("Invalid size value \"" + s + "\""); |
| | | } else { |
| | | unit = defaultUnit; |
| | | } |
| | | } else { |
| | | try { |
| | | unit = getUnit(unitString); |
| | | } catch (IllegalArgumentException e) { |
| | | throw new NumberFormatException("Invalid size value \"" + s + "\""); |
| | | } |
| | | } |
| | | |
| | | return unit.toBytes(d); |
| | | } |
| | | |
| | | // The long name of the unit. |
| | | private final String longName; |
| | | |
| | | // The abbreviation of the unit. |
| | | private final String shortName; |
| | | |
| | | // The size of the unit in bytes. |
| | | private final long sz; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private SizeUnit(long sz, String shortName, String longName) { |
| | | this.sz = sz; |
| | | this.shortName = shortName; |
| | | this.longName = longName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Converts the specified size in bytes to this unit. |
| | | * |
| | | * @param amount |
| | | * The size in bytes. |
| | | * @return Returns size in this unit. |
| | | */ |
| | | public double fromBytes(long amount) { |
| | | return ((double) amount / sz); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the long name of this unit. |
| | | * |
| | | * @return Returns the long name of this unit. |
| | | */ |
| | | public String getLongName() { |
| | | return longName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the abbreviated name of this unit. |
| | | * |
| | | * @return Returns the abbreviated name of this unit. |
| | | */ |
| | | public String getShortName() { |
| | | return shortName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the number of bytes that this unit represents. |
| | | * |
| | | * @return Returns the number of bytes that this unit represents. |
| | | */ |
| | | public long getSize() { |
| | | return sz; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Converts the specified size in this unit to bytes. |
| | | * |
| | | * @param amount |
| | | * The size as a quantity of this unit. |
| | | * @return Returns the number of bytes that the size represents. |
| | | * |
| | | * @throws NumberFormatException |
| | | * If the provided size exceeded long.MAX_VALUE. |
| | | */ |
| | | public long toBytes(double amount) throws NumberFormatException { |
| | | double value = sz * amount; |
| | | if (value > Long.MAX_VALUE) |
| | | { |
| | | throw new NumberFormatException |
| | | ("number too big (exceeded long.MAX_VALUE"); |
| | | } |
| | | return (long) (value); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | * <p> |
| | | * This implementation returns the abbreviated name of this size |
| | | * unit. |
| | | */ |
| | | @Override |
| | | public String toString() { |
| | | return shortName; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.util.Validator.ensureNotNull; |
| | | |
| | | import java.util.EnumSet; |
| | | import java.util.Locale; |
| | | import java.util.MissingResourceException; |
| | | import java.util.regex.Matcher; |
| | | import java.util.regex.Pattern; |
| | | import java.util.regex.PatternSyntaxException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * String property definition. |
| | | */ |
| | | public final class StringPropertyDefinition extends PropertyDefinition<String> { |
| | | |
| | | /** |
| | | * An interface for incrementally constructing string property |
| | | * definitions. |
| | | */ |
| | | public static class Builder extends |
| | | AbstractBuilder<String, StringPropertyDefinition> { |
| | | |
| | | // Flag indicating whether values of this property are |
| | | // case-insensitive. |
| | | private boolean isCaseInsensitive = true; |
| | | |
| | | // Optional pattern which values of this property must match. |
| | | private Pattern pattern = null; |
| | | |
| | | // Pattern usage which provides a user-friendly summary of the |
| | | // pattern if present. |
| | | private String patternUsage = null; |
| | | |
| | | |
| | | |
| | | // Private constructor |
| | | private Builder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | super(d, propertyName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set a flag indicating whether values of this property are |
| | | * case-insensitive. |
| | | * |
| | | * @param value |
| | | * <code>true</code> if values are case-insensitive, or |
| | | * <code>false</code> otherwise. |
| | | */ |
| | | public final void setCaseInsensitive(boolean value) { |
| | | isCaseInsensitive = value; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Set the regular expression pattern which values of this |
| | | * property must match. By default there is no pattern defined. |
| | | * |
| | | * @param pattern |
| | | * The regular expression pattern string, or |
| | | * <code>null</code> if there is no pattern. |
| | | * @param patternUsage |
| | | * A user-friendly usage string representing the pattern |
| | | * which can be used in error messages and help (e.g. for |
| | | * patterns which match a host/port combination, the |
| | | * usage string "HOST:PORT" would be appropriate). |
| | | * @throws PatternSyntaxException |
| | | * If the provided regular expression pattern has an |
| | | * invalid syntax. |
| | | */ |
| | | public final void setPattern(String pattern, String patternUsage) |
| | | throws PatternSyntaxException { |
| | | if (pattern == null) { |
| | | this.pattern = null; |
| | | this.patternUsage = null; |
| | | } else { |
| | | this.pattern = Pattern.compile(pattern); |
| | | this.patternUsage = patternUsage; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | protected StringPropertyDefinition buildInstance( |
| | | AbstractManagedObjectDefinition<?, ?> d, String propertyName, |
| | | EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior) { |
| | | return new StringPropertyDefinition(d, propertyName, options, |
| | | adminAction, defaultBehavior, isCaseInsensitive, pattern, |
| | | patternUsage); |
| | | } |
| | | |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a string property definition builder. |
| | | * |
| | | * @param d |
| | | * The managed object definition associated with this |
| | | * property definition. |
| | | * @param propertyName |
| | | * The property name. |
| | | * @return Returns the new string property definition builder. |
| | | */ |
| | | public static Builder createBuilder(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName) { |
| | | return new Builder(d, propertyName); |
| | | } |
| | | |
| | | // Flag indicating whether values of this property are |
| | | // case-insensitive. |
| | | private final boolean isCaseInsensitive; |
| | | |
| | | // Optional pattern which values of this property must match. |
| | | private final Pattern pattern; |
| | | |
| | | // Pattern usage which provides a user-friendly summary of the |
| | | // pattern if present. |
| | | private final String patternUsage; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private StringPropertyDefinition(AbstractManagedObjectDefinition<?, ?> d, |
| | | String propertyName, EnumSet<PropertyOption> options, |
| | | AdministratorAction adminAction, |
| | | DefaultBehaviorProvider<String> defaultBehavior, |
| | | boolean isCaseInsensitive, Pattern pattern, String patternUsage) { |
| | | super(d, String.class, propertyName, options, adminAction, |
| | | defaultBehavior); |
| | | this.isCaseInsensitive = isCaseInsensitive; |
| | | this.pattern = pattern; |
| | | this.patternUsage = patternUsage; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyDefinitionVisitor<R, P> v, P p) { |
| | | return v.visitString(this, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public <R, P> R accept(PropertyValueVisitor<R, P> v, String value, P p) { |
| | | return v.visitString(this, value, p); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String decodeValue(String value) |
| | | throws IllegalPropertyValueStringException { |
| | | ensureNotNull(value); |
| | | |
| | | try { |
| | | validateValue(value); |
| | | } catch (IllegalPropertyValueException e) { |
| | | throw new IllegalPropertyValueStringException(this, value); |
| | | } |
| | | |
| | | return value; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional regular expression pattern which values of this |
| | | * property must match. |
| | | * |
| | | * @return Returns the optional regular expression pattern which |
| | | * values of this property must match, or <code>null</code> |
| | | * if there is no pattern. |
| | | */ |
| | | public Pattern getPattern() { |
| | | return pattern; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the pattern synopsis of this string property definition in |
| | | * the default locale. |
| | | * |
| | | * @return Returns the pattern synopsis of this string property |
| | | * definition in the default locale, or <code>null</code> |
| | | * if there is no pattern synopsis (which is the case when |
| | | * there is no pattern matching defined for this string |
| | | * property definition). |
| | | */ |
| | | public Message getPatternSynopsis() { |
| | | return getPatternSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the optional pattern synopsis of this string property |
| | | * definition in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the pattern synopsis of this string property |
| | | * definition in the specified locale, or <code>null</code> |
| | | * if there is no pattern synopsis (which is the case when |
| | | * there is no pattern matching defined for this string |
| | | * property definition). |
| | | */ |
| | | public Message getPatternSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "property." + getName() |
| | | + ".syntax.string.pattern.synopsis"; |
| | | try { |
| | | return resource |
| | | .getMessage(getManagedObjectDefinition(), property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets a user-friendly usage string representing the pattern which |
| | | * can be used in error messages and help (e.g. for patterns which |
| | | * match a host/port combination, the usage string "HOST:PORT" would |
| | | * be appropriate). |
| | | * |
| | | * @return Returns the user-friendly pattern usage string, or |
| | | * <code>null</code> if there is no pattern. |
| | | */ |
| | | public String getPatternUsage() { |
| | | return patternUsage; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Query whether values of this property are case-insensitive. |
| | | * |
| | | * @return Returns <code>true</code> if values are |
| | | * case-insensitive, or <code>false</code> otherwise. |
| | | */ |
| | | public boolean isCaseInsensitive() { |
| | | return isCaseInsensitive; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public String normalizeValue(String value) |
| | | throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | if (isCaseInsensitive()) { |
| | | return value.trim().toLowerCase(); |
| | | } else { |
| | | return value.trim(); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public void validateValue(String value) throws IllegalPropertyValueException { |
| | | ensureNotNull(value); |
| | | |
| | | if (pattern != null) { |
| | | Matcher matcher = pattern.matcher(value); |
| | | if (!matcher.matches()) { |
| | | throw new IllegalPropertyValueException(this, value); |
| | | } |
| | | } |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.HashMap; |
| | | import java.util.Locale; |
| | | import java.util.Map; |
| | | import java.util.MissingResourceException; |
| | | |
| | | import org.opends.server.admin.std.meta.RootCfgDefn; |
| | | import org.opends.server.util.Validator; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for querying the properties of a tag. |
| | | * <p> |
| | | * Tags are used to group related managed objects together into |
| | | * categories. |
| | | */ |
| | | public final class Tag implements Comparable<Tag> { |
| | | |
| | | // All the tags. |
| | | private static final Map<String, Tag> tags = new HashMap<String, Tag>(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Defines a new tag with the specified name. |
| | | * |
| | | * @param name |
| | | * The name of the new tag. |
| | | */ |
| | | public static void define(String name) { |
| | | Tag tag = new Tag(name); |
| | | |
| | | // Register the tag. |
| | | tags.put(name, tag); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns the tag associated with the specified name. |
| | | * |
| | | * @param name |
| | | * The name of the tag. |
| | | * @return Returns the tag associated with the specified name. |
| | | * @throws IllegalArgumentException |
| | | * If the tag name was not recognized. |
| | | */ |
| | | public static Tag valueOf(String name) throws IllegalArgumentException { |
| | | Validator.ensureNotNull(name); |
| | | |
| | | // Hack to force initialization of the tag definitions. |
| | | RootCfgDefn.getInstance(); |
| | | |
| | | Tag tag = tags.get(name.toLowerCase()); |
| | | |
| | | if (tag == null) { |
| | | throw new IllegalArgumentException("Unknown tag \"" + name + "\""); |
| | | } |
| | | |
| | | return tag; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Returns an unmodifiable collection view of the set of registered |
| | | * tags. |
| | | * |
| | | * @return Returns an unmodifiable collection view of the set of |
| | | * registered tags. |
| | | */ |
| | | public static Collection<Tag> values() { |
| | | // Hack to force initialization of the tag definitions. |
| | | RootCfgDefn.getInstance(); |
| | | |
| | | return Collections.unmodifiableCollection(tags.values()); |
| | | } |
| | | |
| | | // The name of the tag. |
| | | private final String name; |
| | | |
| | | |
| | | |
| | | // Private constructor. |
| | | private Tag(String name) { |
| | | this.name = name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public final int compareTo(Tag o) { |
| | | return name.compareTo(o.name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public final boolean equals(Object obj) { |
| | | if (this == obj) { |
| | | return true; |
| | | } |
| | | |
| | | if (obj instanceof Tag) { |
| | | Tag other = (Tag) obj; |
| | | return other.name.equals(this.name); |
| | | } |
| | | |
| | | return false; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the name of this tag. |
| | | * |
| | | * @return Returns the name of this tag. |
| | | */ |
| | | public final String getName() { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this tag in the default locale. |
| | | * |
| | | * @return Returns the synopsis of this tag in the default locale. |
| | | */ |
| | | public final Message getSynopsis() { |
| | | return getSynopsis(Locale.getDefault()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the synopsis of this tag in the specified locale. |
| | | * |
| | | * @param locale |
| | | * The locale. |
| | | * @return Returns the synopsis of this tag in the specified locale. |
| | | */ |
| | | public final Message getSynopsis(Locale locale) { |
| | | ManagedObjectDefinitionI18NResource resource = |
| | | ManagedObjectDefinitionI18NResource.getInstance(); |
| | | String property = "tag." + name + ".synopsis"; |
| | | try { |
| | | return resource.getMessage(RootCfgDefn.getInstance(), property, locale); |
| | | } catch (MissingResourceException e) { |
| | | return null; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public final int hashCode() { |
| | | return name.hashCode(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | @Override |
| | | public final String toString() { |
| | | return name; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Configuration definition <code>TopCfgDefn</code> is the root of |
| | | * the configuration definition hierarchy. Every configuration has |
| | | * <code>TopCfgDefn</code> as a superclass. |
| | | * <p> |
| | | * The <code>TopCfgDefn</code> has no properties or relations. |
| | | * However, it can be used to determine all the configuration |
| | | * definitions currently available to the administration framework |
| | | * using the {@link #getAllChildren()}. |
| | | * <p> |
| | | * <b>NOTE:</b> it is not possible to retrieve I18N related |
| | | * information or profile information for this managed object |
| | | * definition. In particular, calls to the methods |
| | | * {@link #getSynopsis()}, {@link #getDescription()}, |
| | | * {@link #getUserFriendlyName()}, and |
| | | * {@link #getUserFriendlyPluralName()} will not work. |
| | | */ |
| | | public final class TopCfgDefn extends |
| | | AbstractManagedObjectDefinition<ConfigurationClient, Configuration> { |
| | | |
| | | // The singleton configuration definition instance. |
| | | private static final TopCfgDefn INSTANCE = new TopCfgDefn(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the Top configuration definition singleton. |
| | | * |
| | | * @return Returns the Top configuration definition singleton. |
| | | */ |
| | | public static TopCfgDefn getInstance() { |
| | | return INSTANCE; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Private constructor. |
| | | */ |
| | | private TopCfgDefn() { |
| | | super("top", null); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A default behavior provider which indicates undefined behavior. It should |
| | | * be used by properties which have no default values or behavior as such. For |
| | | * example, a description property, when left unset, has no default value and no |
| | | * side-effects. |
| | | * |
| | | * @param <T> |
| | | * The type of values represented by this provider. |
| | | */ |
| | | public final class UndefinedDefaultBehaviorProvider<T> extends |
| | | DefaultBehaviorProvider<T> { |
| | | |
| | | /** |
| | | * Create an undefined default behavior provider. |
| | | */ |
| | | public UndefinedDefaultBehaviorProvider() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * {@inheritDoc} |
| | | */ |
| | | public <R, P> R accept(DefaultBehaviorProviderVisitor<T, R, P> v, P p) { |
| | | return v.visitUndefined(this, p); |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates that an unknown type of property definition was |
| | | * encountered. This can occur as the management prototype develops |
| | | * and new kinds of property definitions are added. |
| | | */ |
| | | public final class UnknownPropertyDefinitionException |
| | | extends PropertyException { |
| | | |
| | | // Generated serialization ID. |
| | | private static final long serialVersionUID = 7042646409131322385L; |
| | | |
| | | // The visitor parameter if there was one. |
| | | private Object parameter; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new unknown property definition exception. |
| | | * |
| | | * @param pd |
| | | * The unknown property definition. |
| | | * @param p |
| | | * The visitor parameter if there was one. |
| | | */ |
| | | public UnknownPropertyDefinitionException(PropertyDefinition<?> pd, |
| | | Object p) { |
| | | super(pd, ERR_UNKNOWN_PROPERTY_DEFINITION_EXCEPTION.get(pd.getName(), pd |
| | | .getClass().getName())); |
| | | this.parameter = p; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the visitor parameter if there was one. |
| | | * |
| | | * @return Returns the visitor parameter if there was one. |
| | | */ |
| | | public Object getParameter() { |
| | | return parameter; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | import org.opends.server.admin.AdminException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Administration client exceptions represent non-operational problems |
| | | * which occur whilst interacting with the administration framework. |
| | | * They provide clients with a transport independent interface for |
| | | * handling transport related exceptions. |
| | | * <p> |
| | | * Client exceptions represent communications problems, security |
| | | * problems, and service related problems. |
| | | */ |
| | | public abstract class AdminClientException extends AdminException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 4044747533980824456L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an administration client exception with a message and |
| | | * cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected AdminClientException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an administration client exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected AdminClientException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when a security related problem occurs |
| | | * whilst interacting with the Directory Server. These fall broadly |
| | | * into two categories: authentication problems and authorization |
| | | * problems. |
| | | */ |
| | | public abstract class AdminSecurityException extends AdminClientException { |
| | | |
| | | /** |
| | | * Fake serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 1L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a security exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | protected AdminSecurityException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a security exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | protected AdminSecurityException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when an authentication error occurs while |
| | | * connecting to the Directory Server. An authentication error can |
| | | * happen, for example, when the client credentials are invalid. |
| | | */ |
| | | public class AuthenticationException extends AdminSecurityException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 3544797197747686958L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates an authentication exception with a default message. |
| | | */ |
| | | public AuthenticationException() { |
| | | super(ERR_AUTHENTICATION_EXCEPTION_DEFAULT.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authentication exception with a cause and a default |
| | | * message. |
| | | * |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthenticationException(Throwable cause) { |
| | | super(ERR_AUTHENTICATION_EXCEPTION_DEFAULT.get(), cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authentication exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthenticationException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authentication exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | public AuthenticationException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when the particular flavor of |
| | | * authentication requested is not supported by the Directory Server. |
| | | */ |
| | | public class AuthenticationNotSupportedException |
| | | extends AdminSecurityException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 7387834052676291793L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates an authentication not supported exception with a default |
| | | * message. |
| | | */ |
| | | public AuthenticationNotSupportedException() { |
| | | super(ERR_AUTHENTICATION_NOT_SUPPORTED_EXCEPTION_DEFAULT.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates an authentication not supported exception with a cause |
| | | * and a default message. |
| | | * |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthenticationNotSupportedException(Throwable cause) { |
| | | super(ERR_AUTHENTICATION_NOT_SUPPORTED_EXCEPTION_DEFAULT.get(), cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authentication not supported exception with a message |
| | | * and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthenticationNotSupportedException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authentication not supported exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | public AuthenticationNotSupportedException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when an authorization error occurs while |
| | | * interacting with the Directory Server. Authorization errors can |
| | | * occur when a client attempts to perform an administrative operation |
| | | * which they are not permitted to perform. |
| | | */ |
| | | public class AuthorizationException extends AdminSecurityException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 8414248362572933814L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authorization exception with a default message. |
| | | */ |
| | | public AuthorizationException() { |
| | | super(ERR_AUTHORIZATION_EXCEPTION_DEFAULT.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authorization exception with a cause and a default |
| | | * message. |
| | | * |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthorizationException(Throwable cause) { |
| | | super(ERR_AUTHORIZATION_EXCEPTION_DEFAULT.get(), cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authorization exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public AuthorizationException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create an authorization exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | public AuthorizationException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.ManagedObjectPath; |
| | | |
| | | |
| | | |
| | | /** |
| | | * An interface for performing client-side constraint validation. |
| | | * <p> |
| | | * Constraints are evaluated immediately before the client performs a |
| | | * write operation. If one or more constraints fails, the write |
| | | * operation is refused and fails with an |
| | | * {@link OperationRejectedException}. |
| | | * <p> |
| | | * A client constraint handler must override at least one of the |
| | | * provided methods. |
| | | * |
| | | * @see org.opends.server.admin.Constraint |
| | | */ |
| | | public abstract class ClientConstraintHandler { |
| | | |
| | | /** |
| | | * Creates a new client constraint handler. |
| | | */ |
| | | protected ClientConstraintHandler() { |
| | | // No implementation required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not the newly created managed object which |
| | | * is about to be added to the server configuration satisfies this |
| | | * constraint. |
| | | * <p> |
| | | * If the constraint is not satisfied, the implementation must |
| | | * return <code>false</code> and add a message describing why the |
| | | * constraint was not satisfied. |
| | | * <p> |
| | | * The default implementation is to return <code>true</code>. |
| | | * |
| | | * @param context |
| | | * The management context. |
| | | * @param managedObject |
| | | * The new managed object. |
| | | * @param unacceptableReasons |
| | | * A list of messages to which error messages should be |
| | | * added. |
| | | * @return Returns <code>true</code> if this constraint is |
| | | * satisfied, or <code>false</code> if it is not. |
| | | * @throws AuthorizationException |
| | | * If an authorization failure prevented this constraint |
| | | * from being evaluated. |
| | | * @throws CommunicationException |
| | | * If a communications problem prevented this constraint |
| | | * from being evaluated. |
| | | */ |
| | | public boolean isAddAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | return true; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not the changes to an existing managed |
| | | * object which are about to be committed to the server |
| | | * configuration satisfies this constraint. |
| | | * <p> |
| | | * If the constraint is not satisfied, the implementation must |
| | | * return <code>false</code> and add a message describing why the |
| | | * constraint was not satisfied. |
| | | * <p> |
| | | * The default implementation is to return <code>true</code>. |
| | | * |
| | | * @param context |
| | | * The management context. |
| | | * @param managedObject |
| | | * The modified managed object. |
| | | * @param unacceptableReasons |
| | | * A list of messages to which error messages should be |
| | | * added. |
| | | * @return Returns <code>true</code> if this modify is satisfied, |
| | | * or <code>false</code> if it is not. |
| | | * @throws AuthorizationException |
| | | * If an authorization failure prevented this constraint |
| | | * from being evaluated. |
| | | * @throws CommunicationException |
| | | * If a communications problem prevented this constraint |
| | | * from being evaluated. |
| | | */ |
| | | public boolean isModifyAcceptable(ManagementContext context, |
| | | ManagedObject<?> managedObject, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | return true; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not the existing managed object which is |
| | | * about to be deleted from the server configuration satisfies this |
| | | * constraint. |
| | | * <p> |
| | | * If the constraint is not satisfied, the implementation must |
| | | * return <code>false</code> and add a message describing why the |
| | | * constraint was not satisfied. |
| | | * <p> |
| | | * The default implementation is to return <code>true</code>. |
| | | * |
| | | * @param context |
| | | * The management context. |
| | | * @param path |
| | | * The path of the managed object which is about to be |
| | | * deleted. |
| | | * @param unacceptableReasons |
| | | * A list of messages to which error messages should be |
| | | * added. |
| | | * @return Returns <code>true</code> if this constraint is |
| | | * satisfied, or <code>false</code> if it is not. |
| | | * @throws AuthorizationException |
| | | * If an authorization failure prevented this constraint |
| | | * from being evaluated. |
| | | * @throws CommunicationException |
| | | * If a communications problem prevented this constraint |
| | | * from being evaluated. |
| | | */ |
| | | public boolean isDeleteAcceptable(ManagementContext context, |
| | | ManagedObjectPath<?, ?> path, Collection<Message> unacceptableReasons) |
| | | throws AuthorizationException, CommunicationException { |
| | | return true; |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when a communications related problem |
| | | * occurs whilst interacting with the Directory Server. This may be |
| | | * caused by problems such as network partitioning, the unavailability |
| | | * of the Directory Server, or other failures on the client or server |
| | | * side. |
| | | */ |
| | | public class CommunicationException extends AdminClientException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 9093195928501281027L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a communication exception with a default message. |
| | | */ |
| | | public CommunicationException() { |
| | | super(ERR_COMMUNICATION_EXCEPTION_DEFAULT.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a communication exception with a cause and a default |
| | | * message. |
| | | * |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public CommunicationException(Throwable cause) { |
| | | super(ERR_COMMUNICATION_EXCEPTION_DEFAULT_CAUSE.get(cause.getMessage()), |
| | | cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a communication exception with a message and cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public CommunicationException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a communication exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | public CommunicationException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.OperationsException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This exception is thrown when a critical concurrent modification is |
| | | * detected by the client. This may be caused by another client |
| | | * application removing a managed object whilst it is being managed. |
| | | */ |
| | | public class ConcurrentModificationException extends OperationsException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = -1467024486347612820L; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a concurrent modification exception with a default |
| | | * message. |
| | | */ |
| | | public ConcurrentModificationException() { |
| | | super(ERR_CONCURRENT_MODIFICATION_EXCEPTION_DEFAULT.get()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a concurrent modification exception with a cause and a |
| | | * default message. |
| | | * |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public ConcurrentModificationException(Throwable cause) { |
| | | super(ERR_CONCURRENT_MODIFICATION_EXCEPTION_DEFAULT.get(), cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a concurrent modification exception with a message and |
| | | * cause. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | * @param cause |
| | | * The cause. |
| | | */ |
| | | public ConcurrentModificationException(Message message, Throwable cause) { |
| | | super(message, cause); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a concurrent modification exception with a message. |
| | | * |
| | | * @param message |
| | | * The message. |
| | | */ |
| | | public ConcurrentModificationException(Message message) { |
| | | super(message); |
| | | } |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2008 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import static org.opends.messages.AdminMessages.*; |
| | | |
| | | import org.opends.messages.Message; |
| | | import org.opends.server.admin.IllegalPropertyValueStringException; |
| | | import org.opends.server.admin.OperationsException; |
| | | import org.opends.server.admin.PropertyDefinition; |
| | | import org.opends.server.admin.PropertyDefinitionUsageBuilder; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Thrown when an attempt is made to create a new managed object with |
| | | * an illegal name. |
| | | * <p> |
| | | * This exception can occur when a new managed object is given a name |
| | | * which is either an empty string, a string containing just |
| | | * white-spaces, or a string which is invalid according to the managed |
| | | * object's naming property (if it has one). |
| | | */ |
| | | public class IllegalManagedObjectNameException extends OperationsException { |
| | | |
| | | /** |
| | | * Serialization ID. |
| | | */ |
| | | private static final long serialVersionUID = 7491748228684293291L; |
| | | |
| | | |
| | | |
| | | // Create the message |
| | | private static Message createMessage(String illegalName, |
| | | PropertyDefinition<?> namingPropertyDefinition) { |
| | | if (illegalName.length() == 0) { |
| | | return ERR_ILLEGAL_MANAGED_OBJECT_NAME_EXCEPTION_EMPTY.get(); |
| | | } else if (illegalName.trim().length() == 0) { |
| | | return ERR_ILLEGAL_MANAGED_OBJECT_NAME_EXCEPTION_BLANK.get(); |
| | | } else if (namingPropertyDefinition != null) { |
| | | try { |
| | | namingPropertyDefinition.decodeValue(illegalName); |
| | | } catch (IllegalPropertyValueStringException e) { |
| | | PropertyDefinitionUsageBuilder builder = |
| | | new PropertyDefinitionUsageBuilder(true); |
| | | return ERR_ILLEGAL_MANAGED_OBJECT_NAME_EXCEPTION_SYNTAX.get( |
| | | illegalName, namingPropertyDefinition.getName(), builder |
| | | .getUsage(namingPropertyDefinition)); |
| | | } |
| | | } |
| | | |
| | | return ERR_ILLEGAL_MANAGED_OBJECT_NAME_EXCEPTION_OTHER.get(illegalName); |
| | | } |
| | | |
| | | // The illegal name. |
| | | private final String illegalName; |
| | | |
| | | // The naming property definition if applicable. |
| | | private final PropertyDefinition<?> namingPropertyDefinition; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new illegal name exception and no naming property |
| | | * definition. |
| | | * |
| | | * @param illegalName |
| | | * The illegal managed object name. |
| | | */ |
| | | public IllegalManagedObjectNameException(String illegalName) { |
| | | this(illegalName, null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Create a new illegal name exception and a naming property |
| | | * definition. |
| | | * |
| | | * @param illegalName |
| | | * The illegal managed object name. |
| | | * @param namingPropertyDefinition |
| | | * The naming property definition. |
| | | */ |
| | | public IllegalManagedObjectNameException(String illegalName, |
| | | PropertyDefinition<?> namingPropertyDefinition) { |
| | | super(createMessage(illegalName, namingPropertyDefinition)); |
| | | |
| | | this.illegalName = illegalName; |
| | | this.namingPropertyDefinition = namingPropertyDefinition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the illegal managed object name. |
| | | * |
| | | * @return Returns the illegal managed object name. |
| | | */ |
| | | public String getIllegalName() { |
| | | return illegalName; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Get the naming property definition if applicable. |
| | | * |
| | | * @return Returns naming property definition, or <code>null</code> |
| | | * if none was specified. |
| | | */ |
| | | public PropertyDefinition<?> getNamingPropertyDefinition() { |
| | | return namingPropertyDefinition; |
| | | } |
| | | |
| | | } |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Copyright 2007-2009 Sun Microsystems, Inc. |
| | | */ |
| | | |
| | | package org.opends.server.admin.client; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.SortedSet; |
| | | |
| | | import org.opends.server.admin.AbstractManagedObjectDefinition; |
| | | import org.opends.server.admin.Configuration; |
| | | import org.opends.server.admin.DefaultBehaviorException; |
| | | import org.opends.server.admin.DefinitionDecodingException; |
| | | import org.opends.server.admin.IllegalPropertyValueException; |
| | | import org.opends.server.admin.InstantiableRelationDefinition; |
| | | import org.opends.server.admin.ManagedObjectAlreadyExistsException; |
| | | import org.opends.server.admin.ManagedObjectDefinition; |
| | | import org.opends.server.admin.ConfigurationClient; |
| | | import org.opends.server.admin.ManagedObjectNotFoundException; |
| | | import org.opends.server.admin.ManagedObjectPath; |
| | | import org.opends.server.admin.OptionalRelationDefinition; |
| | | import org.opends.server.admin.PropertyDefinition; |
| | | import org.opends.server.admin.PropertyIsMandatoryException; |
| | | import org.opends.server.admin.PropertyIsReadOnlyException; |
| | | import org.opends.server.admin.PropertyIsSingleValuedException; |
| | | import org.opends.server.admin.PropertyProvider; |
| | | import org.opends.server.admin.SetRelationDefinition; |
| | | import org.opends.server.admin.SingletonRelationDefinition; |
| | | |
| | | |
| | | |
| | | /** |
| | | * A generic interface for accessing client-side managed objects. |
| | | * <p> |
| | | * A managed object comprises of zero or more properties. A property |
| | | * has associated with it three sets of property value(s). These are: |
| | | * <ul> |
| | | * <li><i>default value(s)</i> - these value(s) represent the |
| | | * default behavior for the property when it has no active values. |
| | | * When a property inherits its default value(s) from elsewhere (i.e. |
| | | * a property in another managed object), the default value(s) |
| | | * represent the active value(s) of the inherited property at the time |
| | | * the managed object was retrieved |
| | | * <li><i>active value(s)</i> - these value(s) represent the state |
| | | * of the property at the time the managed object was retrieved |
| | | * <li><i>pending value(s)</i> - these value(s) represent any |
| | | * modifications made to the property's value(s) since the managed |
| | | * object object was retrieved and before the changes have been |
| | | * committed using the {@link #commit()} method, the pending values |
| | | * can be empty indicating that the property should be modified back |
| | | * to its default values. |
| | | * </ul> |
| | | * In addition, a property has an <i>effective state</i> defined by |
| | | * its <i>effective values</i> which are derived by evaluating the |
| | | * following rules in the order presented: |
| | | * <ul> |
| | | * <li>the <i>pending values</i> if defined and non-empty |
| | | * <li>or, the <i>default values</i> if the pending values are |
| | | * defined but are empty |
| | | * <li>or, the <i>active values</i> if defined and non-empty |
| | | * <li>or, the <i>default values</i> if there are no active values |
| | | * <li>or, an empty set of values, if there are no default values. |
| | | * </ul> |
| | | * |
| | | * @param <T> |
| | | * The type of client configuration represented by the client |
| | | * managed object. |
| | | */ |
| | | public interface ManagedObject<T extends ConfigurationClient> extends |
| | | PropertyProvider { |
| | | |
| | | /** |
| | | * Adds this managed object to the server or commits any changes |
| | | * made to it depending on whether or not the managed object already |
| | | * exists on the server. Pending property values will be committed |
| | | * to the managed object. If successful, the pending values will |
| | | * become active values. |
| | | * <p> |
| | | * See the class description for more information regarding pending |
| | | * and active values. |
| | | * |
| | | * @throws ManagedObjectAlreadyExistsException |
| | | * If the managed object cannot be added to the server |
| | | * because it already exists. |
| | | * @throws MissingMandatoryPropertiesException |
| | | * If the managed object contains some mandatory |
| | | * properties which have been left undefined. |
| | | * @throws ConcurrentModificationException |
| | | * If the managed object is being added to the server but |
| | | * its parent has been removed by another client, or if |
| | | * this managed object is being modified but it has been |
| | | * removed from the server by another client. |
| | | * @throws OperationRejectedException |
| | | * If this managed object cannot be added or modified due |
| | | * to some client-side or server-side constraint which |
| | | * cannot be satisfied. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to add or modify this managed |
| | | * object because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | void commit() throws ManagedObjectAlreadyExistsException, |
| | | MissingMandatoryPropertiesException, ConcurrentModificationException, |
| | | OperationRejectedException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not this managed object has been modified since it |
| | | * was constructed. |
| | | * In other words, whether or not the set of pending values differs from |
| | | * the set of active values. |
| | | * |
| | | * @return Returns <code>true</code> if this managed object has been |
| | | * modified since it was constructed. |
| | | */ |
| | | boolean isModified(); |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object bound to the specified |
| | | * instantiable relation. The new managed object will initially not |
| | | * contain any property values (including mandatory properties). |
| | | * Once the managed object has been configured it can be added to |
| | | * the server using the {@link #commit()} method. |
| | | * |
| | | * @param <C> |
| | | * The expected type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The expected type of the child managed object |
| | | * server configuration. |
| | | * @param <CC> |
| | | * The actual type of the added managed object |
| | | * configuration client. |
| | | * @param r |
| | | * The instantiable relation definition. |
| | | * @param d |
| | | * The definition of the managed object to be created. |
| | | * @param name |
| | | * The name of the child managed object. |
| | | * @param exceptions |
| | | * A collection in which to place any |
| | | * {@link DefaultBehaviorException}s that occurred whilst |
| | | * attempting to determine the managed object's default |
| | | * values. |
| | | * @return Returns a new child managed object bound to the specified |
| | | * instantiable relation. |
| | | * @throws IllegalManagedObjectNameException |
| | | * If the name of the child managed object is invalid. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration, CC extends C> |
| | | ManagedObject<CC> createChild(InstantiableRelationDefinition<C, S> r, |
| | | ManagedObjectDefinition<CC, ? extends S> d, String name, |
| | | Collection<DefaultBehaviorException> exceptions) |
| | | throws IllegalManagedObjectNameException, IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object bound to the specified |
| | | * optional relation. The new managed object will initially not |
| | | * contain any property values (including mandatory properties). |
| | | * Once the managed object has been configured it can be added to |
| | | * the server using the {@link #commit()} method. |
| | | * |
| | | * @param <C> |
| | | * The expected type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The expected type of the child managed object |
| | | * server configuration. |
| | | * @param <CC> |
| | | * The actual type of the added managed object |
| | | * configuration client. |
| | | * @param r |
| | | * The optional relation definition. |
| | | * @param d |
| | | * The definition of the managed object to be created. |
| | | * @param exceptions |
| | | * A collection in which to place any |
| | | * {@link DefaultBehaviorException}s that occurred whilst |
| | | * attempting to determine the managed object's default |
| | | * values. |
| | | * @return Returns a new child managed object bound to the specified |
| | | * optional relation. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration, CC extends C> |
| | | ManagedObject<CC> createChild(OptionalRelationDefinition<C, S> r, |
| | | ManagedObjectDefinition<CC, ? extends S> d, |
| | | Collection<DefaultBehaviorException> exceptions) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new child managed object bound to the specified |
| | | * set relation. The new managed object will initially not |
| | | * contain any property values (including mandatory properties). |
| | | * Once the managed object has been configured it can be added to |
| | | * the server using the {@link #commit()} method. |
| | | * |
| | | * @param <C> |
| | | * The expected type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The expected type of the child managed object |
| | | * server configuration. |
| | | * @param <CC> |
| | | * The actual type of the added managed object |
| | | * configuration client. |
| | | * @param r |
| | | * The set relation definition. |
| | | * @param d |
| | | * The definition of the managed object to be created. |
| | | * @param exceptions |
| | | * A collection in which to place any |
| | | * {@link DefaultBehaviorException}s that occurred whilst |
| | | * attempting to determine the managed object's default |
| | | * values. |
| | | * @return Returns a new child managed object bound to the specified |
| | | * set relation. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration, CC extends C> |
| | | ManagedObject<CC> createChild(SetRelationDefinition<C, S> r, |
| | | ManagedObjectDefinition<CC, ? extends S> d, |
| | | Collection<DefaultBehaviorException> exceptions) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves an instantiable child managed object. |
| | | * |
| | | * @param <C> |
| | | * The requested type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The instantiable relation definition. |
| | | * @param name |
| | | * The name of the child managed object. |
| | | * @return Returns the instantiable child managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws DefinitionDecodingException |
| | | * If the managed object was found but its type could not |
| | | * be determined. |
| | | * @throws ManagedObjectDecodingException |
| | | * If the managed object was found but one or more of its |
| | | * properties could not be decoded. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the requested managed object could not be found on |
| | | * the server. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to retrieve the managed object |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | ManagedObject<? extends C> getChild(InstantiableRelationDefinition<C, S> r, |
| | | String name) throws IllegalArgumentException, DefinitionDecodingException, |
| | | ManagedObjectDecodingException, ManagedObjectNotFoundException, |
| | | ConcurrentModificationException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves an optional child managed object. |
| | | * |
| | | * @param <C> |
| | | * The requested type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The optional relation definition. |
| | | * @return Returns the optional child managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws DefinitionDecodingException |
| | | * If the managed object was found but its type could not |
| | | * be determined. |
| | | * @throws ManagedObjectDecodingException |
| | | * If the managed object was found but one or more of its |
| | | * properties could not be decoded. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the requested managed object could not be found on |
| | | * the server. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to retrieve the managed object |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | ManagedObject<? extends C> getChild(OptionalRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, DefinitionDecodingException, |
| | | ManagedObjectDecodingException, ManagedObjectNotFoundException, |
| | | ConcurrentModificationException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a singleton child managed object. |
| | | * |
| | | * @param <C> |
| | | * The requested type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The singleton relation definition. |
| | | * @return Returns the singleton child managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws DefinitionDecodingException |
| | | * If the managed object was found but its type could not |
| | | * be determined. |
| | | * @throws ManagedObjectDecodingException |
| | | * If the managed object was found but one or more of its |
| | | * properties could not be decoded. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the requested managed object could not be found on |
| | | * the server. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to retrieve the managed object |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | ManagedObject<? extends C> getChild(SingletonRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, DefinitionDecodingException, |
| | | ManagedObjectDecodingException, ManagedObjectNotFoundException, |
| | | ConcurrentModificationException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a set child managed object. |
| | | * |
| | | * @param <C> |
| | | * The requested type of the child managed object |
| | | * configuration client. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The set relation definition. |
| | | * @param name |
| | | * The name of the child managed object. |
| | | * @return Returns the set child managed object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws DefinitionDecodingException |
| | | * If the managed object was found but its type could not |
| | | * be determined. |
| | | * @throws ManagedObjectDecodingException |
| | | * If the managed object was found but one or more of its |
| | | * properties could not be decoded. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the requested managed object could not be found on |
| | | * the server. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to retrieve the managed object |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | ManagedObject<? extends C> getChild(SetRelationDefinition<C, S> r, |
| | | String name) throws IllegalArgumentException, DefinitionDecodingException, |
| | | ManagedObjectDecodingException, ManagedObjectNotFoundException, |
| | | ConcurrentModificationException, AuthorizationException, |
| | | CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a client configuration view of this managed object. |
| | | * Modifications made to this managed object will be reflected in |
| | | * the client configuration view and vice versa. |
| | | * |
| | | * @return Returns a client configuration view of this managed |
| | | * object. |
| | | */ |
| | | T getConfiguration(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the definition associated with this managed object. |
| | | * |
| | | * @return Returns the definition associated with this managed |
| | | * object. |
| | | */ |
| | | ManagedObjectDefinition<T, ? extends Configuration> |
| | | getManagedObjectDefinition(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the path of this managed object. |
| | | * |
| | | * @return Returns the path of this managed object. |
| | | */ |
| | | ManagedObjectPath<T, ? extends Configuration> getManagedObjectPath(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets a mutable copy of the set of default values for the |
| | | * specified property. |
| | | * |
| | | * @param <PD> |
| | | * The type of the property to be retrieved. |
| | | * @param pd |
| | | * The property to be retrieved. |
| | | * @return Returns the property's default values, or an empty set if |
| | | * there are no default values defined. |
| | | * @throws IllegalArgumentException |
| | | * If the property definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <PD> SortedSet<PD> getPropertyDefaultValues(PropertyDefinition<PD> pd) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets the effective value of the specified property. |
| | | * <p> |
| | | * See the class description for more information about how the |
| | | * effective property value is derived. |
| | | * |
| | | * @param <PD> |
| | | * The type of the property to be retrieved. |
| | | * @param pd |
| | | * The property to be retrieved. |
| | | * @return Returns the property's effective value, or |
| | | * <code>null</code> if there is no effective value |
| | | * defined. |
| | | * @throws IllegalArgumentException |
| | | * If the property definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <PD> PD getPropertyValue(PropertyDefinition<PD> pd) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Gets a mutable copy of the set of effective values for the |
| | | * specified property. |
| | | * <p> |
| | | * See the class description for more information about how the |
| | | * effective property values are derived. |
| | | * |
| | | * @param <PD> |
| | | * The type of the property to be retrieved. |
| | | * @param pd |
| | | * The property to be retrieved. |
| | | * @return Returns the property's effective values, or an empty set |
| | | * if there are no effective values defined. |
| | | * @throws IllegalArgumentException |
| | | * If the property definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | <PD> SortedSet<PD> getPropertyValues(PropertyDefinition<PD> pd) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not the specified property is set. If the |
| | | * property is unset, then any default behavior associated with the |
| | | * property applies. |
| | | * |
| | | * @param pd |
| | | * The property definition. |
| | | * @return Returns <code>true</code> if the property has been set, |
| | | * or <code>false</code> if it is unset and any default |
| | | * behavior associated with the property applies. |
| | | * @throws IllegalArgumentException |
| | | * If the property definition is not associated with this |
| | | * managed object's definition. |
| | | */ |
| | | boolean isPropertyPresent(PropertyDefinition<?> pd) |
| | | throws IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Determines whether or not the optional managed object associated |
| | | * with the specified optional relations exists. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The optional relation definition. |
| | | * @return Returns <code>true</code> if the optional managed |
| | | * object exists, <code>false</code> otherwise. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to make the determination because |
| | | * the client does not have the correct privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | boolean hasChild(OptionalRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Lists the child managed objects associated with the specified |
| | | * instantiable relation. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The instantiable relation definition. |
| | | * @return Returns the names of the child managed objects. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to list the managed objects |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | String[] listChildren(InstantiableRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Lists the child managed objects associated with the specified |
| | | * instantiable relation which are a sub-type of the specified |
| | | * managed object definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The instantiable relation definition. |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns the names of the child managed objects which are |
| | | * a sub-type of the specified managed object definition. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to list the managed objects |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | String[] listChildren(InstantiableRelationDefinition<C, S> r, |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> d) |
| | | throws IllegalArgumentException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Lists the child managed objects associated with the specified set |
| | | * relation. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The set relation definition. |
| | | * @return Returns the names of the child managed objects which for |
| | | * set relations are the definition names of each managed |
| | | * object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to list the managed objects because |
| | | * the client does not have the correct privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | String[] listChildren(SetRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Lists the child managed objects associated with the specified set |
| | | * relation which are a sub-type of the specified managed object |
| | | * definition. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The set relation definition. |
| | | * @param d |
| | | * The managed object definition. |
| | | * @return Returns the names of the child managed objects which for |
| | | * set relations are the definition names of each managed |
| | | * object. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to list the managed objects because |
| | | * the client does not have the correct privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | String[] listChildren(SetRelationDefinition<C, S> r, |
| | | AbstractManagedObjectDefinition<? extends C, ? extends S> d) |
| | | throws IllegalArgumentException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the named instantiable child managed object. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The instantiable relation definition. |
| | | * @param name |
| | | * The name of the child managed object to be removed. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the managed object could not be removed because it |
| | | * could not found on the server. |
| | | * @throws OperationRejectedException |
| | | * If the managed object cannot be removed due to some |
| | | * client-side or server-side constraint which cannot be |
| | | * satisfied (for example, if it is referenced by another |
| | | * managed object). |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to remove the managed objects |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void removeChild(InstantiableRelationDefinition<C, S> r, String name) |
| | | throws IllegalArgumentException, ManagedObjectNotFoundException, |
| | | OperationRejectedException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes an optional child managed object. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The optional relation definition. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the managed object could not be removed because it |
| | | * could not found on the server. |
| | | * @throws OperationRejectedException |
| | | * If the managed object cannot be removed due to some |
| | | * client-side or server-side constraint which cannot be |
| | | * satisfied (for example, if it is referenced by another |
| | | * managed object). |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to remove the managed objects |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void removeChild(OptionalRelationDefinition<C, S> r) |
| | | throws IllegalArgumentException, ManagedObjectNotFoundException, |
| | | OperationRejectedException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes s set child managed object. |
| | | * |
| | | * @param <C> |
| | | * The type of client managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param <S> |
| | | * The type of server managed object configuration that the |
| | | * relation definition refers to. |
| | | * @param r |
| | | * The set relation definition. |
| | | * @param name |
| | | * The name of the child managed object to be removed. |
| | | * @throws IllegalArgumentException |
| | | * If the relation definition is not associated with this |
| | | * managed object's definition. |
| | | * @throws ManagedObjectNotFoundException |
| | | * If the managed object could not be removed because it |
| | | * could not found on the server. |
| | | * @throws OperationRejectedException |
| | | * If the managed object cannot be removed due to some |
| | | * client-side or server-side constraint which cannot be |
| | | * satisfied (for example, if it is referenced by another |
| | | * managed object). |
| | | * @throws ConcurrentModificationException |
| | | * If this managed object has been removed from the server |
| | | * by another client. |
| | | * @throws AuthorizationException |
| | | * If the server refuses to remove the managed objects |
| | | * because the client does not have the correct |
| | | * privileges. |
| | | * @throws CommunicationException |
| | | * If the client cannot contact the server due to an |
| | | * underlying communication problem. |
| | | */ |
| | | <C extends ConfigurationClient, S extends Configuration> |
| | | void removeChild(SetRelationDefinition<C, S> r, String name) |
| | | throws IllegalArgumentException, ManagedObjectNotFoundException, |
| | | OperationRejectedException, ConcurrentModificationException, |
| | | AuthorizationException, CommunicationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets a new pending value for the specified property. |
| | | * <p> |
| | | * See the class description for more information regarding pending |
| | | * values. |
| | | * |
| | | * @param <PD> |
| | | * The type of the property to be modified. |
| | | * @param pd |
| | | * The property to be modified. |
| | | * @param value |
| | | * The new pending value for the property, or |
| | | * <code>null</code> if the property should be reset to |
| | | * its default behavior. |
| | | * @throws IllegalPropertyValueException |
| | | * If the new pending value is deemed to be invalid |
| | | * according to the property definition. |
| | | * @throws PropertyIsReadOnlyException |
| | | * If this is not a new managed object and the property is |
| | | * read-only or for monitoring purposes. |
| | | * @throws PropertyIsMandatoryException |
| | | * If an attempt was made to remove a mandatory property. |
| | | * @throws IllegalArgumentException |
| | | * If the specified property definition is not associated |
| | | * with this managed object. |
| | | */ |
| | | <PD> void setPropertyValue(PropertyDefinition<PD> pd, PD value) |
| | | throws IllegalPropertyValueException, PropertyIsReadOnlyException, |
| | | PropertyIsMandatoryException, IllegalArgumentException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets a new pending values for the specified property. |
| | | * <p> |
| | | * See the class description for more information regarding pending |
| | | * values. |
| | | * |
| | | * @param <PD> |
| | | * The type of the property to be modified. |
| | | * @param pd |
| | | * The property to be modified. |
| | | * @param values |
| | | * A non-<code>null</code> set of new pending values for |
| | | * the property (an empty set indicates that the property |
| | | * should be reset to its default behavior). The set will |
| | | * not be referenced by this managed object. |
| | | * @throws IllegalPropertyValueException |
| | | * If a new pending value is deemed to be invalid |
| | | * according to the property definition. |
| | | * @throws PropertyIsSingleValuedException |
| | | * If an attempt was made to add multiple pending values |
| | | * to a single-valued property. |
| | | * @throws PropertyIsReadOnlyException |
| | | * If this is not a new managed object and the property is |
| | | * read-only or for monitoring purposes. |
| | | * @throws PropertyIsMandatoryException |
| | | * If an attempt was made to remove a mandatory property. |
| | | * @throws IllegalArgumentException |
| | | * If the specified property definition is not associated |
| | | * with this managed object. |
| | | */ |
| | | <PD> void setPropertyValues(PropertyDefinition<PD> pd, Collection<PD> values) |
| | | throws IllegalPropertyValueException, PropertyIsSingleValuedException, |
| | | PropertyIsReadOnlyException, PropertyIsMandatoryException, |
| | | IllegalArgumentException; |
| | | |
| | | } |
| opendj-admin/src/main/java/org/opends/server/admin/client/ManagedObjectDecodingException.java
opendj-admin/src/main/java/org/opends/server/admin/client/ManagementContext.java
opendj-admin/src/main/java/org/opends/server/admin/client/MissingMandatoryPropertiesException.java
opendj-admin/src/main/java/org/opends/server/admin/client/OperationRejectedException.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/JNDIDirContextAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/LDAPConnection.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/LDAPDriver.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/LDAPManagedObject.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/LDAPManagementContext.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/LDAPNameBuilder.java
opendj-admin/src/main/java/org/opends/server/admin/client/ldap/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/client/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/client/spi/AbstractManagedObject.java
opendj-admin/src/main/java/org/opends/server/admin/client/spi/Driver.java
opendj-admin/src/main/java/org/opends/server/admin/client/spi/Property.java
opendj-admin/src/main/java/org/opends/server/admin/client/spi/PropertySet.java
opendj-admin/src/main/java/org/opends/server/admin/client/spi/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/condition/ANDCondition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/Condition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/Conditions.java
opendj-admin/src/main/java/org/opends/server/admin/condition/ContainsCondition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/IsPresentCondition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/NOTCondition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/ORCondition.java
opendj-admin/src/main/java/org/opends/server/admin/condition/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/doc/ConfigGuideGeneration.java
opendj-admin/src/main/java/org/opends/server/admin/doc/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/package-info.java
opendj-admin/src/main/java/org/opends/server/admin/server/AbstractConfigListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigAddListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigChangeListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigDeleteListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigExceptionFactory.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigurationAddListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigurationChangeListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConfigurationDeleteListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ConstraintViolationException.java
opendj-admin/src/main/java/org/opends/server/admin/server/DNBuilder.java
opendj-admin/src/main/java/org/opends/server/admin/server/DelayedConfigAddListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerConstraintHandler.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObject.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectAddListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectAddListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectChangeListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectChangeListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectDecodingException.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectDeleteListener.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagedObjectDeleteListenerAdaptor.java
opendj-admin/src/main/java/org/opends/server/admin/server/ServerManagementContext.java
opendj-admin/src/main/java/org/opends/server/admin/server/package-info.java |