001/* 002 * CDDL HEADER START 003 * 004 * The contents of this file are subject to the terms of the 005 * Common Development and Distribution License, Version 1.0 only 006 * (the "License"). You may not use this file except in compliance 007 * with the License. 008 * 009 * You can obtain a copy of the license at legal-notices/CDDLv1_0.txt 010 * or http://forgerock.org/license/CDDLv1.0.html. 011 * See the License for the specific language governing permissions 012 * and limitations under the License. 013 * 014 * When distributing Covered Code, include this CDDL HEADER in each 015 * file and include the License file at legal-notices/CDDLv1_0.txt. 016 * If applicable, add the following below this CDDL HEADER, with the 017 * fields enclosed by brackets "[]" replaced with your own identifying 018 * information: 019 * Portions Copyright [yyyy] [name of copyright owner] 020 * 021 * CDDL HEADER END 022 * 023 * 024 * Copyright 2008 Sun Microsystems, Inc. 025 * Portions Copyright 2015 ForgeRock AS. 026 */ 027package org.opends.server.admin; 028 029 030 031import java.util.Arrays; 032import java.util.HashMap; 033import java.util.List; 034import java.util.Map; 035import java.util.SortedSet; 036import java.util.TreeSet; 037 038 039 040/** 041 * A default managed object which should be created when a parent 042 * managed object is created. Default managed objects are associated 043 * with a {@link RelationDefinition}. 044 * 045 * @param <C> 046 * The type of client default managed object configuration. 047 * @param <S> 048 * The type of server default managed object configuration. 049 */ 050public final class DefaultManagedObject 051 <C extends ConfigurationClient, S extends Configuration> 052 implements PropertyProvider { 053 054 /** 055 * An interface for incrementally constructing default managed 056 * objects. 057 * 058 * @param <C> 059 * The type of client default managed object configuration. 060 * @param <S> 061 * The type of server default managed object configuration. 062 */ 063 public static final class Builder 064 <C extends ConfigurationClient, S extends Configuration> { 065 066 /** The default managed object's definition. */ 067 private final ManagedObjectDefinition<C, S> definition; 068 069 /** The string encoded default managed object's properties. */ 070 private final Map<String, List<String>> propertyStringValues = new HashMap<>(); 071 072 /** 073 * Creates a new default managed object builder. 074 * 075 * @param definition 076 * The default managed object's definition. 077 */ 078 public Builder(ManagedObjectDefinition<C, S> definition) { 079 this.definition = definition; 080 } 081 082 083 084 /** 085 * Construct a default managed object based on the properties of 086 * this builder. 087 * 088 * @return Returns the new default managed object. 089 */ 090 public DefaultManagedObject<C, S> getInstance() { 091 return new DefaultManagedObject<>(definition, propertyStringValues); 092 } 093 094 095 096 /** 097 * Defines a property's values for the default managed object. 098 * 099 * @param name 100 * The name of the property. 101 * @param values 102 * One or more property values in the string 103 * representation. 104 */ 105 public void setPropertyValues(String name, String... values) { 106 if (values == null || values.length == 0) { 107 throw new IllegalArgumentException( 108 "null or empty values specified for property " + name); 109 } 110 111 propertyStringValues.put(name, Arrays.asList(values)); 112 } 113 } 114 115 /** The default managed object's definition. */ 116 private final ManagedObjectDefinition<C, S> definition; 117 118 /** The string encoded default managed object's properties. */ 119 private final Map<String, List<String>> propertyStringValues; 120 121 122 123 /** Private constructor. */ 124 private DefaultManagedObject(ManagedObjectDefinition<C, S> definition, 125 Map<String, List<String>> propertyStringValues) { 126 this.definition = definition; 127 this.propertyStringValues = propertyStringValues; 128 } 129 130 131 132 /** 133 * Gets the managed object definition associated with this default 134 * managed object. 135 * 136 * @return Returns the managed object definition associated with 137 * this default managed object. 138 */ 139 public ManagedObjectDefinition<C, S> getManagedObjectDefinition() { 140 return definition; 141 } 142 143 144 145 /** 146 * Gets a mutable copy of the set of property values for the 147 * specified property. 148 * 149 * @param <T> 150 * The type of the property to be retrieved. 151 * @param pd 152 * The property to be retrieved. 153 * @return Returns a newly allocated set containing a copy of the 154 * property's values. An empty set indicates that the 155 * property has no values defined and any default behavior 156 * is applicable. 157 * @throws IllegalArgumentException 158 * If the property definition is not associated with this 159 * managed object's definition. 160 */ 161 public <T> SortedSet<T> getPropertyValues(PropertyDefinition<T> pd) 162 throws IllegalArgumentException { 163 // Validate the property definition. 164 definition.getPropertyDefinition(pd.getName()); 165 166 // Do a defensive copy. 167 SortedSet<T> values = new TreeSet<>(pd); 168 List<String> stringValues = propertyStringValues.get(pd.getName()); 169 if (stringValues != null) { 170 for (String stringValue : stringValues) { 171 values.add(pd.decodeValue(stringValue)); 172 } 173 } 174 return values; 175 } 176 177 178 179 /** 180 * Performs run-time initialization of properties. 181 * 182 * @throws Exception 183 * If this default managed object could not be 184 * initialized. 185 */ 186 void initialize() throws Exception { 187 // FIXME: it would be nice if we could decode all property values 188 // at this point. However this is not possible on the server side 189 // since some properties will be determined to be invalid since 190 // the schema is not loaded. 191 192 // Validate provided property names. 193 for (String name : propertyStringValues.keySet()) { 194 definition.getPropertyDefinition(name); 195 } 196 } 197}