001/* 002 * The contents of this file are subject to the terms of the Common Development and 003 * Distribution License (the License). You may not use this file except in compliance with the 004 * License. 005 * 006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the 007 * specific language governing permission and limitations under the License. 008 * 009 * When distributing Covered Software, include this CDDL Header Notice in each file and include 010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL 011 * Header, with the fields enclosed by brackets [] replaced by your own identifying 012 * information: "Portions Copyright [year] [name of copyright owner]". 013 * 014 * Copyright 2006-2009 Sun Microsystems, Inc. 015 * Portions Copyright 2014-2016 ForgeRock AS. 016 */ 017package org.opends.server.api; 018import org.forgerock.i18n.LocalizableMessage; 019 020 021 022import java.util.List; 023 024import org.forgerock.opendj.server.config.server.PasswordStorageSchemeCfg; 025import org.forgerock.opendj.config.server.ConfigException; 026import org.opends.server.types.*; 027import org.forgerock.opendj.ldap.ByteString; 028import org.forgerock.opendj.ldap.ByteSequence; 029 030 031/** 032 * This class defines the set of methods and structures that must be 033 * implemented by a Directory Server module that implements a password 034 * storage scheme. Each subclass may only implement a single password 035 * storage scheme type. 036 * 037 * @param <T> The type of configuration handled by this 038 * password storage scheme 039 */ 040@org.opends.server.types.PublicAPI( 041 stability=org.opends.server.types.StabilityLevel.UNCOMMITTED, 042 mayInstantiate=false, 043 mayExtend=true, 044 mayInvoke=false) 045public abstract class 046 PasswordStorageScheme <T extends PasswordStorageSchemeCfg> 047{ 048 /** 049 * Initializes this password storage scheme handler based on the 050 * information in the provided configuration entry. It should also 051 * register itself with the Directory Server for the particular 052 * storage scheme that it will manage. 053 * 054 * @param configuration The configuration entry that contains the 055 * information to use to initialize this 056 * password storage scheme handler. 057 * 058 * @throws ConfigException If an unrecoverable problem arises in 059 * the process of performing the 060 * initialization. 061 * 062 * @throws InitializationException If a problem occurs during 063 * initialization that is not 064 * related to the server 065 * configuration. 066 */ 067 public abstract void initializePasswordStorageScheme( 068 T configuration) 069 throws ConfigException, InitializationException; 070 071 072 073 /** 074 * Indicates whether the provided configuration is acceptable for 075 * this password storage scheme. It should be possible to call this 076 * method on an uninitialized password storage scheme instance in 077 * order to determine whether the password storage scheme would be 078 * able to use the provided configuration. 079 * <BR><BR> 080 * Note that implementations which use a subclass of the provided 081 * configuration class will likely need to cast the configuration 082 * to the appropriate subclass type. 083 * 084 * @param configuration The password storage scheme 085 * configuration for which to make the 086 * determination. 087 * @param unacceptableReasons A list that may be used to hold the 088 * reasons that the provided 089 * configuration is not acceptable. 090 * 091 * @return {@code true} if the provided configuration is acceptable 092 * for this password storage scheme, or {@code false} if 093 * not. 094 */ 095 public boolean isConfigurationAcceptable( 096 PasswordStorageSchemeCfg configuration, 097 List<LocalizableMessage> unacceptableReasons) 098 { 099 // This default implementation does not perform any special 100 // validation. It should be overridden by password storage scheme 101 // implementations that wish to perform more detailed validation. 102 return true; 103 } 104 105 106 107 /** 108 * Performs any necessary finalization that might be required when 109 * this password storage scheme is no longer needed (e.g., the 110 * scheme is disabled or the server is shutting down). 111 */ 112 public void finalizePasswordStorageScheme() 113 { 114 // No implementation required by default. 115 } 116 117 118 119 /** 120 * Retrieves the name of the password storage scheme provided by 121 * this handler. 122 * 123 * @return The name of the password storage scheme provided by this 124 * handler. 125 */ 126 public abstract String getStorageSchemeName(); 127 128 129 130 /** 131 * Encodes the provided plaintext password for this storage scheme, 132 * without the name of the associated scheme. Note that the 133 * provided plaintext password should not be altered in any way. 134 * 135 * @param plaintext The plaintext version of the password. 136 * 137 * @return The password that has been encoded using this storage 138 * scheme. 139 * 140 * @throws DirectoryException If a problem occurs while 141 * processing. 142 */ 143 public abstract ByteString encodePassword(ByteSequence plaintext) 144 throws DirectoryException; 145 146 147 148 /** 149 * Encodes the provided plaintext password for this storage scheme, 150 * prepending the name of the scheme in curly braces. Note that the 151 * provided plaintext password should not be altered in any way. 152 * 153 * @param plaintext The plaintext version of the password. 154 * 155 * @return The encoded password, including the name of the storage 156 * scheme. 157 * 158 * @throws DirectoryException If a problem occurs while 159 * processing. 160 */ 161 public abstract ByteString encodePasswordWithScheme( 162 ByteSequence plaintext) 163 throws DirectoryException; 164 165 166 167 168 /** 169 * Indicates whether the provided plaintext password included in a 170 * bind request matches the given stored value. The provided stored 171 * value should not include the scheme name in curly braces. 172 * 173 * @param plaintextPassword The plaintext password provided by the 174 * user as part of a simple bind attempt. 175 * @param storedPassword The stored password to compare against 176 * the provided plaintext password. 177 * 178 * @return {@code true} if the provided plaintext password matches 179 * the provided stored password, or {@code false} if not. 180 */ 181 public abstract boolean passwordMatches( 182 ByteSequence plaintextPassword, 183 ByteSequence storedPassword); 184 185 186 187 /** 188 * Indicates whether this password storage scheme supports the 189 * ability to interact with values using the authentication password 190 * syntax defined in RFC 3112. 191 * 192 * @return {@code true} if this password storage scheme supports 193 * the ability to interact with values using the 194 * authentication password syntax, or {@code false} if it 195 * does not. 196 */ 197 public abstract boolean supportsAuthPasswordSyntax(); 198 199 200 201 /** 202 * Retrieves the scheme name that should be used with this password 203 * storage scheme when it is used in the context of the 204 * authentication password syntax. This default implementation will 205 * return the same value as the {@code getStorageSchemeName} method. 206 * 207 * @return The scheme name that should be used with this password 208 * storage scheme when it is used in the context of the 209 * authentication password syntax. 210 */ 211 public String getAuthPasswordSchemeName() 212 { 213 return getStorageSchemeName(); 214 } 215 216 217 218 /** 219 * Encodes the provided plaintext password for this storage scheme 220 * using the authentication password syntax defined in RFC 3112. 221 * Note that the provided plaintext password should not be altered 222 * in any way. 223 * 224 * @param plaintext The plaintext version of the password. 225 * 226 * @return The password that has been encoded in the authentication 227 * password syntax. 228 * 229 * @throws DirectoryException If a problem occurs while processing 230 * of if this storage scheme does not 231 * support the authentication password 232 * syntax. 233 */ 234 public abstract ByteString encodeAuthPassword( 235 ByteSequence plaintext) throws DirectoryException; 236 237 238 239 /** 240 * Indicates whether the provided plaintext password matches the 241 * encoded password using the authentication password syntax with 242 * the given authInfo and authValue components. 243 * 244 * @param plaintextPassword The plaintext password provided by the 245 * user. 246 * @param authInfo The authInfo component of the password 247 * encoded in the authentication password 248 * syntax. 249 * @param authValue The authValue component of the 250 * password encoded in the authentication 251 * password syntax. 252 * 253 * @return {@code true} if the provided plaintext password matches 254 * the encoded password according to the authentication 255 * password info syntax, or {@code false} if it does not or 256 * this storage scheme does not support the authentication 257 * password syntax. 258 */ 259 public abstract boolean authPasswordMatches( 260 ByteSequence plaintextPassword, 261 String authInfo, String authValue); 262 263 264 265 /** 266 * Indicates whether this storage scheme is reversible (i.e., it is 267 * possible to obtain the original plaintext value from the stored 268 * password). 269 * 270 * @return {@code true} if this is a reversible password storage 271 * scheme, or {@code false} if it is not. 272 */ 273 public abstract boolean isReversible(); 274 275 276 277 /** 278 * Retrieves the original plaintext value for the provided stored 279 * password. Note that this should only be called if 280 * {@code isReversible} returns {@code true}. 281 * 282 * @param storedPassword The password for which to obtain the 283 * plaintext value. It should not include 284 * the scheme name in curly braces. 285 * 286 * @return The plaintext value for the provided stored password. 287 * 288 * @throws DirectoryException If it is not possible to obtain the 289 * plaintext value for the provided 290 * stored password. 291 */ 292 public abstract ByteString getPlaintextValue( 293 ByteSequence storedPassword) 294 throws DirectoryException; 295 296 297 298 /** 299 * Retrieves the original plaintext value for the provided password 300 * stored in the authPassword syntax. Note that this should only be 301 * called if {@code isReversible} returns {@code true}. 302 * 303 * @param authInfo The authInfo component of the password encoded 304 * in the authentication password syntax. 305 * @param authValue The authValue component of the password 306 * encoded in the authentication password syntax. 307 * 308 * @return The plaintext value for the provided stored password. 309 * 310 * @throws DirectoryException If it is not possible to obtain the 311 * plaintext value for the provided 312 * stored password, or if this storage 313 * scheme does not support the 314 * authPassword syntax.. 315 */ 316 public abstract ByteString getAuthPasswordPlaintextValue( 317 String authInfo, String authValue) 318 throws DirectoryException; 319 320 321 322 /** 323 * Indicates whether this password storage scheme should be 324 * considered "secure". If the encoding used for this scheme does 325 * not obscure the value at all, or if it uses a method that is 326 * trivial to reverse (e.g., base64), then it should not be 327 * considered secure. 328 * <BR><BR> 329 * This may be used to determine whether a password may be included 330 * in a set of search results, including the possibility of 331 * overriding access controls in the case that access controls would 332 * allow the password to be returned but the password is considered 333 * too insecure to reveal. 334 * 335 * @return {@code false} if it may be trivial to discover the 336 * original plain-text password from the encoded form, or 337 * {@code true} if the scheme offers sufficient protection 338 * that revealing the encoded password will not easily 339 * reveal the corresponding plain-text value. 340 */ 341 public abstract boolean isStorageSchemeSecure(); 342} 343