From e7dfa40c0ada0bb2d3bcbf7f153e496b5454f1cd Mon Sep 17 00:00:00 2001
From: Violette Roche-Montane <violette.roche-montane@forgerock.com>
Date: Thu, 10 Apr 2014 11:32:37 +0000
Subject: [PATCH] Checkpoint for OPENDJ-1303 "opendj-cli" - OPENDJ-1343 Migrate dsconfig Rewritten DSConfig connection. dsconfig package. - Removed from dsconfig package the dependency on the SecureconnectionCliArgs and LDAPConsoleInteraction. - Removed unused class InternalManagementContextFactory
---
opendj-sdk/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java | 290 +++++++++++++++++++++++++++++++++++++++------------------
1 files changed, 198 insertions(+), 92 deletions(-)
diff --git a/opendj-sdk/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java b/opendj-sdk/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
index f1ac91e..dcabc64 100644
--- a/opendj-sdk/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
+++ b/opendj-sdk/opendj-cli/src/main/java/com/forgerock/opendj/cli/ConnectionFactoryProvider.java
@@ -29,6 +29,7 @@
import static com.forgerock.opendj.cli.ArgumentConstants.*;
import static com.forgerock.opendj.cli.CliMessages.*;
import static com.forgerock.opendj.cli.CliConstants.DEFAULT_LDAP_PORT;
+import static com.forgerock.opendj.cli.Utils.getHostNameForLdapUrl;
import java.io.File;
import java.io.FileInputStream;
@@ -39,7 +40,7 @@
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.CertificateException;
-import java.util.logging.Logger;
+import java.util.concurrent.TimeUnit;
import javax.net.ssl.SSLContext;
import javax.net.ssl.TrustManager;
@@ -47,6 +48,7 @@
import javax.net.ssl.X509TrustManager;
import org.forgerock.i18n.LocalizableMessage;
+import org.forgerock.i18n.slf4j.LocalizedLogger;
import org.forgerock.opendj.ldap.ConnectionFactory;
import org.forgerock.opendj.ldap.KeyManagers;
import org.forgerock.opendj.ldap.LDAPConnectionFactory;
@@ -66,90 +68,62 @@
/**
* A connection factory designed for use with command line tools.
*/
-public class ConnectionFactoryProvider {
- /**
- * The Logger.
- */
- static final Logger LOG = Logger.getLogger(ConnectionFactoryProvider.class.getName());
+public final class ConnectionFactoryProvider {
+ /** The Logger. */
+ static final LocalizedLogger logger = LocalizedLogger.getLoggerForThisClass();
- /**
- * The 'hostName' global argument.
- */
+ /** The 'hostName' global argument. */
private StringArgument hostNameArg = null;
- /**
- * The 'port' global argument.
- */
+ /** The 'port' global argument. */
private IntegerArgument portArg = null;
- /**
- * The 'bindDN' global argument.
- */
+ /** The 'bindDN' global argument. */
private StringArgument bindNameArg = null;
- /**
- * The 'bindPasswordFile' global argument.
- */
+ /** The 'bindPasswordFile' global argument. */
private FileBasedArgument bindPasswordFileArg = null;
- /**
- * The 'bindPassword' global argument.
- */
+ /** The 'password' value. */
+ private char[] password = null;
+
+ /** The 'bindPassword' global argument. */
private StringArgument bindPasswordArg = null;
- /**
- * The 'trustAllArg' global argument.
- */
+ /** The 'connectTimeOut' global argument. */
+ private IntegerArgument connectTimeOut = null;
+
+ /** The 'trustAllArg' global argument. */
private BooleanArgument trustAllArg = null;
- /**
- * The 'trustStore' global argument.
- */
+ /** The 'trustStore' global argument. */
private StringArgument trustStorePathArg = null;
- /**
- * The 'trustStorePassword' global argument.
- */
+ /** The 'trustStorePassword' global argument. */
private StringArgument trustStorePasswordArg = null;
- /**
- * The 'trustStorePasswordFile' global argument.
- */
+ /** The 'trustStorePasswordFile' global argument. */
private FileBasedArgument trustStorePasswordFileArg = null;
- /**
- * The 'keyStore' global argument.
- */
+ /** The 'keyStore' global argument. */
private StringArgument keyStorePathArg = null;
- /**
- * The 'keyStorePassword' global argument.
- */
+ /** The 'keyStorePassword' global argument. */
private StringArgument keyStorePasswordArg = null;
- /**
- * The 'keyStorePasswordFile' global argument.
- */
+ /** The 'keyStorePasswordFile' global argument. */
private FileBasedArgument keyStorePasswordFileArg = null;
- /**
- * The 'certNicknameArg' global argument.
- */
+ /** The 'certNicknameArg' global argument. */
private StringArgument certNicknameArg = null;
- /**
- * The 'useSSLArg' global argument.
- */
+ /** The 'useSSLArg' global argument. */
private BooleanArgument useSSLArg = null;
- /**
- * The 'useStartTLSArg' global argument.
- */
+ /** The 'useStartTLSArg' global argument. */
private BooleanArgument useStartTLSArg = null;
- /**
- * Argument indicating a SASL option.
- */
+ /** Argument indicating a SASL option. */
private StringArgument saslOptionArg = null;
/**
@@ -163,23 +137,33 @@
*/
private final BooleanArgument usePasswordPolicyControlArg;
+ /** The port number to used to connect. */
private int port = DEFAULT_LDAP_PORT;
+ /** The SSL context linked to this connection. */
private SSLContext sslContext;
+ /** The basic connection factory. */
private ConnectionFactory connFactory;
/** The authenticated connection factory. */
protected ConnectionFactory authenticatedConnFactory;
+ /** The bind request to connect with. */
private BindRequest bindRequest = null;
+ /** The console application linked to this connection in interactive mode. */
private final ConsoleApplication app;
+ /** The LDAP options for this connection. */
private LDAPOptions options;
+ /** If this connection should be an admin connection. */
+ private boolean isAdminConnection = false;
+
/**
- * Default constructor to create a connection factory designed for use with command line tools.
+ * Default constructor to create a connection factory designed for use with command line tools,
+ * adding basic LDAP connection arguments to the specified parser (e.g: hostname, bindname...etc).
*
* @param argumentParser
* The argument parser.
@@ -190,11 +174,12 @@
*/
public ConnectionFactoryProvider(final ArgumentParser argumentParser,
final ConsoleApplication app) throws ArgumentException {
- this(argumentParser, app, "cn=Directory Manager", DEFAULT_LDAP_PORT, false, null);
+ this(argumentParser, app, CliConstants.DEFAULT_ROOT_USER_DN, DEFAULT_LDAP_PORT, false, null);
}
/**
- * Default constructor to create a connection factory designed for use with command line tools.
+ * Default constructor to create a connection factory designed for use with command line tools,
+ * adding basic LDAP connection arguments to the specified parser (e.g: hostname, bindname...etc).
*
* @param argumentParser
* The argument parser.
@@ -205,13 +190,14 @@
* @throws ArgumentException
* If an error occurs during parsing the arguments.
*/
- public ConnectionFactoryProvider(final ArgumentParser argumentParser,
- final ConsoleApplication app, final LDAPOptions options) throws ArgumentException {
- this(argumentParser, app, "cn=Directory Manager", DEFAULT_LDAP_PORT, false, options);
+ public ConnectionFactoryProvider(final ArgumentParser argumentParser, final ConsoleApplication app,
+ final LDAPOptions options) throws ArgumentException {
+ this(argumentParser, app, CliConstants.DEFAULT_ROOT_USER_DN, DEFAULT_LDAP_PORT, false, options);
}
/**
- * Constructor to create a connection factory designed for use with command line tools.
+ * Constructor to create a connection factory designed for use with command line tools,
+ * adding basic LDAP connection arguments to the specified parser (e.g: hostname, bindname...etc).
*
* @param argumentParser
* The argument parser.
@@ -303,6 +289,9 @@
reportAuthzIDArg = CommonArguments.getReportAuthzId();
argumentParser.addArgument(reportAuthzIDArg);
+ connectTimeOut = CommonArguments.getConnectTimeOut();
+ argumentParser.addArgument(connectTimeOut);
+
usePasswordPolicyControlArg =
new BooleanArgument("usepwpolicycontrol", null, OPTION_LONG_USE_PW_POLICY_CTL,
INFO_DESCRIPTION_USE_PWP_CONTROL.get());
@@ -311,15 +300,50 @@
}
/**
- * Returns the host name.
+ * Returns the connect time out.
+ *
+ * @return The connect time out value.
+ */
+ public int getConnectTimeout() {
+ if (connectTimeOut.isPresent()) {
+ try {
+ return connectTimeOut.getIntValue();
+ } catch (ArgumentException e) {
+ return Integer.valueOf(connectTimeOut.getDefaultValue());
+ }
+ }
+ return Integer.valueOf(connectTimeOut.getDefaultValue());
+ }
+
+
+ /**
+ * Returns the host name if the argument is present otherwise, if the application
+ * is interactive, prompt the user for it.
*
* @return The host name value.
+ * @throws ArgumentException
+ * If the host name cannot be retrieved.
*/
- public String getHostname() {
+ public String getHostname() throws ArgumentException {
+ String value = "";
+
if (hostNameArg.isPresent()) {
- return hostNameArg.getValue();
+ value = hostNameArg.getValue();
+ } else if (app.isInteractive()) {
+ try {
+ value = app.readInput(INFO_DESCRIPTION_HOST.get(),
+ hostNameArg.getDefaultValue() == null ? value : hostNameArg.getDefaultValue());
+ app.println();
+ hostNameArg.addValue(value);
+ hostNameArg.setPresent(true);
+ } catch (ClientException e) {
+ throw new ArgumentException(ERR_ERROR_CANNOT_READ_HOST_NAME.get(), e);
+ }
+ } else {
+ return hostNameArg.getDefaultValue() == null ? value : hostNameArg.getDefaultValue();
}
- return hostNameArg.getDefaultValue();
+
+ return getHostNameForLdapUrl(value);
}
/**
@@ -357,20 +381,46 @@
}
/**
- * Checks if any conflicting arguments are present, build the connection with
- * selected arguments and returns the connection factory.
+ * Checks if any conflicting arguments are present, build the connection with selected arguments and returns the
+ * connection factory. If the application is interactive, it will prompt the user for missing parameters.
*
* @return The connection factory.
* @throws ArgumentException
- * If an error occurs during the parsing of the arguments. (conflicting
- * arguments or if an error occurs during building SSL context).
+ * If an error occurs during the parsing of the arguments.
+ * (conflicting arguments or if an error occurs during building SSL context).
*/
public ConnectionFactory getConnectionFactory() throws ArgumentException {
if (connFactory == null) {
- port = portArg.getIntValue();
+ port = portArg.isPresent() ? portArg.getIntValue() : 0;
checkForConflictingArguments();
+ if (app.isInteractive()) {
+ if (!hostNameArg.isPresent() || port == 0 || !bindNameArg.isPresent()
+ || (!bindPasswordArg.isPresent() && !bindPasswordFileArg.isPresent())) {
+ app.printHeader(INFO_LDAP_CONN_HEADING_CONNECTION_PARAMETERS.get());
+ }
+ if (!hostNameArg.isPresent()) {
+ getHostname();
+ }
+ if (port == 0) {
+ LocalizableMessage portMsg;
+ if (isAdminConnection) {
+ portMsg = INFO_DESCRIPTION_ADMIN_PORT.get();
+ } else {
+ portMsg = INFO_DESCRIPTION_PORT.get();
+ }
+ port = app.askPort(portMsg, Integer.valueOf(portArg.getDefaultValue()), logger);
+ app.println();
+ }
+ if (!bindNameArg.isPresent()) {
+ getBindName();
+ }
+ if (!bindPasswordArg.isPresent() && !bindPasswordFileArg.isPresent()) {
+ getPassword();
+ }
+ }
+
try {
if (useSSLArg.isPresent() || useStartTLSArg.isPresent()) {
String clientAlias;
@@ -403,13 +453,14 @@
if (sslContext != null) {
options.setSSLContext(sslContext).setUseStartTLS(useStartTLSArg.isPresent());
}
+ options.setConnectTimeout(getConnectTimeout(), TimeUnit.MILLISECONDS);
connFactory = new LDAPConnectionFactory(hostNameArg.getValue(), port, options);
}
return connFactory;
}
/**
- * Verifies if the arguments are not conflicting together or if they are readable.
+ * Verifies if the connection arguments are not conflicting together or if they are readable.
*
* @throws ArgumentException
* If arguments are conflicting or if the files cannot be read,
@@ -502,13 +553,13 @@
}
/**
- * Returns <CODE>true</CODE> if we can read on the provided path and
- * <CODE>false</CODE> otherwise.
+ * Returns {@code true} if we can read on the provided path and
+ * {@code false} otherwise.
*
* @param path
* the path.
- * @return <CODE>true</CODE> if we can read on the provided path and
- * <CODE>false</CODE> otherwise.
+ * @return {@code true} if we can read on the provided path and
+ * {@code false} otherwise.
*/
private boolean canReadPath(final String path) {
final File file = new File(path);
@@ -555,17 +606,34 @@
return value;
}
- private String getBindName() throws ArgumentException {
+ /**
+ * Returns the bind name if the argument is present otherwise, in interactive mode, it
+ * will prompt the user.
+ *
+ * @return The bind name used for this connection.
+ * @throws ArgumentException
+ * If the bind name cannot be retrieved.
+ */
+ public String getBindName() throws ArgumentException {
String value = "";
if (bindNameArg.isPresent()) {
value = bindNameArg.getValue();
} else if (app.isInteractive()) {
+ LocalizableMessage bindMsg;
+ if (isAdminConnection) {
+ bindMsg = INFO_DESCRIPTION_ADMIN_BINDDN.get();
+ } else {
+ bindMsg = INFO_DESCRIPTION_BINDDN.get();
+ }
try {
- value =
- app.readInput(LocalizableMessage.raw("Bind name:"), bindNameArg
- .getDefaultValue() == null ? value : bindNameArg.getDefaultValue());
+ value = app.readInput(bindMsg,
+ bindNameArg.getDefaultValue() == null ? value : bindNameArg.getDefaultValue());
+ app.println();
+ bindNameArg.clearValues();
+ bindNameArg.addValue(value);
+ bindNameArg.setPresent(true);
} catch (ClientException e) {
- throw new ArgumentException(LocalizableMessage.raw("Unable to read bind name"), e);
+ throw new ArgumentException(ERR_ERROR_CANNOT_READ_BIND_NAME.get(), e);
}
}
@@ -669,9 +737,14 @@
* interactions requiring access to a key manager.
* @throws java.security.KeyStoreException
* If a problem occurs while interacting with the key store.
+ * @throws IOException
+ * If there is an I/O or format problem with the keystore data.
+ * @throws NoSuchAlgorithmException
+ * If a problem occurs while loading with the key store.
+ * @throws CertificateException
+ * If a problem occurs while loading with the key store.
*/
-
- private X509KeyManager getKeyManager(String keyStoreFile) throws KeyStoreException,
+ public X509KeyManager getKeyManager(String keyStoreFile) throws KeyStoreException,
IOException, NoSuchAlgorithmException, CertificateException {
if (keyStoreFile == null) {
// Lookup the file name through the JDK property.
@@ -725,29 +798,40 @@
}
/**
- * Get the password which has to be used for the command. If no password was
- * specified, return null.
+ * Get the password which has to be used for the command. In interactive mode, if
+ * the password arguments are missing, the user will be prompted.
*
* @return The password stored into the specified file on by the command
- * line argument, or null it if not specified.
+ * line argument, or empty it if not specified.
+ * @throws ArgumentException
+ * If a problem occurs while interacting with the password.
*/
- private char[] getPassword() throws ArgumentException {
+ public char[] getPassword() throws ArgumentException {
char[] value = "".toCharArray();
if (bindPasswordArg.isPresent()) {
value = bindPasswordArg.getValue().toCharArray();
} else if (bindPasswordFileArg.isPresent()) {
value = bindPasswordFileArg.getValue().toCharArray();
+ } else if (password != null) {
+ return password;
}
if (value.length == 0 && app.isInteractive()) {
- try {
- value = app.readPassword(LocalizableMessage.raw("Bind Password:"));
- } catch (ClientException e) {
- throw new ArgumentException(LocalizableMessage.raw("Unable to read password"), e);
+ LocalizableMessage msg;
+ if (isAdminConnection) {
+ msg = INFO_LDAPAUTH_PASSWORD_PROMPT.get(getBindName());
+ } else {
+ msg = INFO_DESCRIPTION_BINDPASSWORD.get();
}
+ try {
+ value = app.readPassword(msg);
+ app.println();
+ } catch (ClientException e) {
+ throw new ArgumentException(ERR_ERROR_CANNOT_READ_PASSWORD.get(), e);
+ }
+ password = value;
}
-
return value;
}
@@ -791,7 +875,7 @@
return new PromptingTrustManager(app, tm);
}
- return null;
+ return tm;
}
/**
@@ -831,4 +915,26 @@
return option.substring(equalPos + 1, option.length());
}
+
+ /**
+ * Specifies if this connection should be an administrator connection. If sets as one, the messages prompted to the
+ * user will be different as a normal connection. E.g if set :
+ *
+ * <pre>
+ * >>>> Specify OpenDJ LDAP connection parameters
+ *
+ * Directory server administration port number [4444]:
+ * </pre>
+ *
+ * vs normal mode
+ *
+ * <pre>
+ * >>>> Specify OpenDJ LDAP connection parameters
+ *
+ * Directory server port number [1389]:
+ * </pre>
+ */
+ public void setIsAnAdminConnection() {
+ isAdminConnection = true;
+ }
}
--
Gitblit v1.10.0