opends/src/server/org/opends/server/api/DirectoryThread.java
@@ -141,18 +141,11 @@ task = null; } String forceDaemonStr = System.getProperty(PROPERTY_FORCE_DAEMON_THREADS); if (forceDaemonStr != null) { String lowerStr = toLowerCase(forceDaemonStr); if (lowerStr.equals("true") || lowerStr.equals("yes") || lowerStr.equals("on") || lowerStr.equals("1")) if (DirectoryServer.getEnvironmentConfig().forceDaemonThreads()) { setDaemon(true); } } } opends/src/server/org/opends/server/config/ConfigConstants.java
@@ -2723,6 +2723,15 @@ /** * The default name of the file that holds the configuration for the Directory * Server. It should exist below the directory specified by the * {@code CONFIG_DIR_NAME}. */ public static final String CONFIG_FILE_NAME = "config.ldif"; /** * The DN of the entry that will serve as the root for the Directory Server * configuration. */ opends/src/server/org/opends/server/core/DirectoryServer.java
@@ -262,6 +262,9 @@ // The configuration manager that will handle the certificate mapper. private CertificateMapperConfigManager certificateMapperConfigManager; // The class used to provide the config handler implementation. private Class configClass; // The configuration handler for the Directory Server. private ConfigHandler configHandler; @@ -398,6 +401,9 @@ // The crypto manager for the Directory Server. private CryptoManager cryptoManager; // The environment configuration for the Directory Server. private DirectoryEnvironmentConfig environmentConfig; // The shutdown hook that has been registered with the server. private DirectoryServerShutdownHook shutdownHook; @@ -420,6 +426,10 @@ // The configuration manager for extended operation handlers. private ExtendedOperationConfigManager extendedOperationConfigManager; // The path to the file containing the Directory Server configuration, or the // information needed to bootstrap the configuration handler. private File configFile; // The group manager for the Directory Server. private GroupManager groupManager; @@ -535,13 +545,6 @@ // The set of allowed task classes. private Set<String> allowedTasks; // The fully-qualified name of the configuration handler class. private String configClass; // The path to the file containing the Directory Server configuration, or the // information needed to bootstrap the configuration handler. private String configFile; // The time that the server was started, formatted in UTC time. private String startTimeUTC; @@ -597,11 +600,28 @@ */ private DirectoryServer() { this(new DirectoryEnvironmentConfig()); } /** * Creates a new instance of the Directory Server. This will allow only a * single instance of the server per JVM. * * @param config The environment configuration to use for the Directory * Server instance. */ private DirectoryServer(DirectoryEnvironmentConfig config) { environmentConfig = config; isBootstrapped = false; isRunning = false; shuttingDown = false; lockdownMode = false; serverErrorResultCode = ResultCode.OTHER; startupDebugLogPublisher = null; startupErrorLogPublisher = null; operatingSystem = OperatingSystem.forName(System.getProperty("os.name")); } @@ -627,20 +647,72 @@ * reference to it. This should only be used in the context of an in-core * restart after the existing server has been shut down. * * @param config The environment configuration for the Directory Server. * * @return The new instance of the Directory Server that is associated with * this JVM. */ private static DirectoryServer getNewInstance() private static DirectoryServer getNewInstance(DirectoryEnvironmentConfig config) { synchronized (directoryServer) { return directoryServer = new DirectoryServer(); return directoryServer = new DirectoryServer(config); } } /** * Retrieves the environment configuration for the Directory Server. * * @return The environment configuration for the Directory Server. */ public static DirectoryEnvironmentConfig getEnvironmentConfig() { return directoryServer.environmentConfig; } /** * Sets the environment configuration for the Directory Server. This method * may only be invoked when the server is not running. * * @param config The environment configuration for the Directory Server. * * @throws InitializationException If the Directory Server is currently * running. */ private void setEnvironmentConfig(DirectoryEnvironmentConfig config) throws InitializationException { if (isRunning) { int msgID = MSGID_CANNOT_SET_ENVIRONMENT_CONFIG_WHILE_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } environmentConfig = config; } /** * Indicates whether the Directory Server is currently running. * * @return {@code true} if the server is currently running, or {@code false} * if not. */ public static boolean isRunning() { return directoryServer.isRunning; } /** * Bootstraps the appropriate Directory Server structures that may be needed * by client-side tools. This is not intended for use in running the server * itself. @@ -788,16 +860,24 @@ // Install default debug and error loggers for use until enough of the // configuration has been read to allow the real loggers to be installed. removeAllAccessLogPublishers(); for (AccessLogPublisher p : environmentConfig.getAccessLoggers()) { addAccessLogPublisher(p); } startupErrorLogPublisher = TextErrorLogPublisher.getStartupTextErrorPublisher( new TextWriter.STDOUT()); addErrorLogPublisher(startupErrorLogPublisher); removeAllErrorLogPublishers(); for (ErrorLogPublisher p : environmentConfig.getErrorLoggers()) { addErrorLogPublisher(p); } startupDebugLogPublisher = TextDebugLogPublisher.getStartupTextDebugPublisher( new TextWriter.STDOUT()); addDebugLogPublisher(startupDebugLogPublisher); removeAllDebugLogPublishers(); for (DebugLogPublisher p : environmentConfig.getDebugLoggers()) { addDebugLogPublisher(p); } // Create the MBean server that we will use for JMX interaction. initializeJMX(); @@ -891,8 +971,45 @@ public void initializeConfiguration(String configClass, String configFile) throws InitializationException { this.configClass = configClass; this.configFile = configFile; Class cfgClass; try { cfgClass = Class.forName(configClass); } catch (Exception e) { if (debugEnabled()) { TRACER.debugCaught(DebugLogLevel.ERROR, e); } int msgID = MSGID_CANNOT_LOAD_CONFIG_HANDLER_CLASS; String message = getMessage(msgID, configClass, stackTraceToSingleLineString(e)); throw new InitializationException(msgID, message, e); } File cfgFile = new File(configFile); environmentConfig.setConfigClass(cfgClass); environmentConfig.setConfigFile(cfgFile); initializeConfiguration(); } /** * Instantiates the configuration handler and loads the Directory Server * configuration. * * @throws InitializationException If a problem occurs while trying to * initialize the config handler. */ public void initializeConfiguration() throws InitializationException { this.configClass = environmentConfig.getConfigClass(); this.configFile = environmentConfig.getConfigFile(); // Make sure that administration framework definition classes are loaded. @@ -904,23 +1021,7 @@ // Load and instantiate the configuration handler class. Class handlerClass; try { handlerClass = Class.forName(configClass); } catch (Exception e) { if (debugEnabled()) { TRACER.debugCaught(DebugLogLevel.ERROR, e); } int msgID = MSGID_CANNOT_LOAD_CONFIG_HANDLER_CLASS; String message = getMessage(msgID, configClass, e); throw new InitializationException(msgID, message, e); } Class handlerClass = configClass; try { configHandler = (ConfigHandler) handlerClass.newInstance(); @@ -941,7 +1042,8 @@ // Perform the handler-specific initialization. try { configHandler.initializeConfigHandler(configFile, false); configHandler.initializeConfigHandler(configFile.getAbsolutePath(), false); } catch (InitializationException ie) { @@ -976,7 +1078,7 @@ */ public static String getConfigFile() { return directoryServer.configFile; return directoryServer.configFile.getAbsolutePath(); } @@ -1054,11 +1156,8 @@ // Determine whether or not we should start the connection handlers. String disableProperty = System.getProperty(PROPERTY_DISABLE_CONNECTION_HANDLERS); boolean startConnectionHandlers = ((disableProperty == null) || (! disableProperty.equalsIgnoreCase("true"))); (! environmentConfig.disableConnectionHandlers()); // Initialize all the schema elements. @@ -1225,8 +1324,15 @@ sendAlertNotification(this, ALERT_TYPE_SERVER_STARTED, msgID, message); if (startupDebugLogPublisher != null) { removeDebugLogPublisher(startupDebugLogPublisher); } if (startupErrorLogPublisher != null) { removeErrorLogPublisher(startupErrorLogPublisher); } // If a server.starting file exists, then remove it. @@ -2176,7 +2282,7 @@ try { configHandler.initializeConfigHandler(configFile, true); configHandler.initializeConfigHandler(configFile.getAbsolutePath(), true); } catch (InitializationException ie) { @@ -2860,24 +2966,16 @@ { if (directoryServer.configHandler == null) { String serverRoot = System.getProperty(PROPERTY_SERVER_ROOT); if (serverRoot == null) { serverRoot = System.getenv(ENV_VAR_INSTANCE_ROOT); } File serverRoot = directoryServer.environmentConfig.getServerRoot(); if (serverRoot != null) { return serverRoot; return serverRoot.getAbsolutePath(); } else { // We don't know where the server root is, so we'll have to assume it's // the current working directory. return System.getProperty("user.dir"); } } else { return directoryServer.configHandler.getServerRoot(); @@ -8283,10 +8381,29 @@ */ public static void restart(String className, String reason) { restart(className, reason, directoryServer.environmentConfig); } /** * Causes the Directory Server to perform an in-core restart. This will * cause virtually all components of the Directory Server to shut down, and * once that has completed it will be restarted. * * @param className The fully-qualified name of the Java class that * initiated the shutdown. * @param reason The human-readable reason that the directory server is * shutting down. * @param config The environment configuration to use for the server. */ public static void restart(String className, String reason, DirectoryEnvironmentConfig config) { try { shutDown(className, reason); reinitialize(); reinitialize(config); directoryServer.startServer(); } catch (Exception e) @@ -8300,23 +8417,52 @@ } } /** * Reinitializes the server following a shutdown, preparing it for * a call to <code>startServer</code>. * Reinitializes the server following a shutdown, preparing it for a call to * {@code startServer}. * * @return The new Directory Server instance created during the * reinitialization process. * * @throws InitializationException If a problem occurs while trying to * initialize the config handler or * bootstrap that server. */ public static void reinitialize() throws InitializationException public static DirectoryServer reinitialize() throws InitializationException { String configClass = directoryServer.configClass; String configFile = directoryServer.configFile; getNewInstance(); directoryServer.bootstrapServer(); directoryServer.initializeConfiguration(configClass, configFile); return reinitialize(directoryServer.environmentConfig); } /** * Reinitializes the server following a shutdown, preparing it for a call to * {@code startServer}. * * @param config The environment configuration for the Directory Server. * * @return The new Directory Server instance created during the * reinitialization process. * * @throws InitializationException If a problem occurs while trying to * initialize the config handler or * bootstrap that server. */ public static DirectoryServer reinitialize(DirectoryEnvironmentConfig config) throws InitializationException { getNewInstance(config); LockManager.reinitializeLockTable(); directoryServer.bootstrapServer(); directoryServer.initializeConfiguration(); return directoryServer; } /** * Retrieves the maximum number of concurrent client connections that may be * established. @@ -9217,10 +9363,45 @@ } // Create an environment configuration for the server and populate a number // of appropriate properties. TextErrorLogPublisher startupErrorLogPublisher = null; TextDebugLogPublisher startupDebugLogPublisher = null; DirectoryEnvironmentConfig environmentConfig = new DirectoryEnvironmentConfig(); try { environmentConfig.setProperty(PROPERTY_CONFIG_CLASS, configClass.getValue()); environmentConfig.setProperty(PROPERTY_CONFIG_FILE, configFile.getValue()); startupErrorLogPublisher = TextErrorLogPublisher.getStartupTextErrorPublisher( new TextWriter.STDOUT()); environmentConfig.addErrorLogger(startupErrorLogPublisher); startupDebugLogPublisher = TextDebugLogPublisher.getStartupTextDebugPublisher( new TextWriter.STDOUT()); environmentConfig.addDebugLogger(startupDebugLogPublisher); } catch (Exception e) { // This shouldn't happen. For the methods we are using, the exception is // just a guard against making changes with the server running. } // Bootstrap and start the Directory Server. DirectoryServer directoryServer = DirectoryServer.getInstance(); try { directoryServer.startupErrorLogPublisher = startupErrorLogPublisher; directoryServer.startupDebugLogPublisher = startupDebugLogPublisher; directoryServer.setEnvironmentConfig(environmentConfig); directoryServer.bootstrapServer(); directoryServer.initializeConfiguration(configClass.getValue(), configFile.getValue()); opends/src/server/org/opends/server/core/LockFileManager.java
@@ -574,14 +574,9 @@ */ public static String getLockDirectoryPath() { String lockDirectory = System.getProperty(PROPERTY_LOCK_DIRECTORY); if ((lockDirectory == null) || (lockDirectory.length() == 0)) { lockDirectory = DirectoryServer.getServerRoot() + File.separator + LOCKS_DIRECTORY; } return lockDirectory; File lockDirectory = DirectoryServer.getEnvironmentConfig().getLockDirectory(); return lockDirectory.getAbsolutePath(); } opends/src/server/org/opends/server/core/SchemaConfigManager.java
@@ -117,14 +117,9 @@ */ public static String getSchemaDirectoryPath() { String schemaDirPath = System.getProperty(PROPERTY_SCHEMA_DIRECTORY); if ((schemaDirPath == null) || (schemaDirPath.length() == 0)) { schemaDirPath = DirectoryServer.getServerRoot() + File.separator + PATH_SCHEMA_DIR; } return schemaDirPath; File schemaDir = DirectoryServer.getEnvironmentConfig().getSchemaDirectory(); return schemaDir.getAbsolutePath(); } opends/src/server/org/opends/server/extensions/ConfigFileHandler.java
@@ -655,38 +655,11 @@ } // Determine the appropriate server root for the Directory Server. First, // do this by looking for a Java property. If that isn't specified, then // look for an environment variable, and if all else fails then try to // figure it out from the location of the configuration file. String rootDirStr = System.getProperty(PROPERTY_SERVER_ROOT); if (rootDirStr == null) { rootDirStr = System.getenv(ENV_VAR_INSTANCE_ROOT); } if (rootDirStr != null) { try { File serverRootFile = new File(rootDirStr); serverRoot = serverRootFile.getAbsolutePath(); } catch (Exception e) { if (debugEnabled()) { TRACER.debugCaught(DebugLogLevel.ERROR, e); } int msgID = MSGID_CONFIG_CANNOT_DETERMINE_SERVER_ROOT; String message = getMessage(msgID, ENV_VAR_INSTANCE_ROOT); throw new InitializationException(msgID, message); } } if (serverRoot == null) // Determine the appropriate server root. If it's not defined in the // environment config, then try to figure it out from the location of the // configuration file. File rootFile = DirectoryServer.getEnvironmentConfig().getServerRoot(); if (rootFile == null) { try { @@ -725,6 +698,10 @@ throw new InitializationException(msgID, message); } } else { serverRoot = rootFile.getAbsolutePath(); } // Register with the Directory Server as an alert generator. opends/src/server/org/opends/server/messages/CoreMessages.java
@@ -6380,6 +6380,97 @@ CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 639; /** * The message ID for the message that will be used if an attempt is made to * change the directory environment configuration while the server is running. * This does not take any arguments. */ public static final int MSGID_DIRCFG_SERVER_ALREADY_RUNNING = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 640; /** * The message ID for the message that will be used if an invalid server root * directory is specified. This takes a single argument, which is the invalid * server root directory. */ public static final int MSGID_DIRCFG_INVALID_SERVER_ROOT = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 641; /** * The message ID for the message that will be used if an invalid * configuration file is specified. This takes a single argument, which is * the invalid configuration file. */ public static final int MSGID_DIRCFG_INVALID_CONFIG_FILE = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 642; /** * The message ID for the message that will be used if an invalid config * handler class is specified. This takes a single argument, which is the * fully-qualified class name. */ public static final int MSGID_DIRCFG_INVALID_CONFIG_CLASS = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 643; /** * The message ID for the message that will be used if an invalid schema * directory is specified. This takes a single argument, which is the invalid * schema directory. */ public static final int MSGID_DIRCFG_INVALID_SCHEMA_DIRECTORY = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 644; /** * The message ID for the message that will be used if an invalid lock * directory is specified. This takes a single argument, which is the invalid * lock directory. */ public static final int MSGID_DIRCFG_INVALID_LOCK_DIRECTORY = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 645; /** * The message ID for the message that will be used if an invalid concurrency * level is specified. This takes a single argument, which is the invalid * concurrency level. */ public static final int MSGID_DIRCFG_INVALID_CONCURRENCY_LEVEL = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 646; /** * The message ID for the message that will be used if an invalid lock table * size is specified. This takes a single argument, which is the invalid lock * table size. */ public static final int MSGID_DIRCFG_INVALID_LOCK_TABLE_SIZE = CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_ERROR | 647; /** * The message ID for the message that will be used if an attempt is made to * alter the server environment configuration while the server is running. * This does not take any arguments. */ public static final int MSGID_CANNOT_SET_ENVIRONMENT_CONFIG_WHILE_RUNNING = CATEGORY_MASK_CORE | SEVERITY_MASK_FATAL_ERROR | 648; /** * Associates a set of generic messages with the message IDs defined * in this class. @@ -6608,6 +6699,10 @@ "threads in the Directory Server was reduced"); registerMessage(MSGID_CANNOT_SET_ENVIRONMENT_CONFIG_WHILE_RUNNING, "The Directory Server is currently running. The " + "environment configuration may not be altered while the " + "server is online"); registerMessage(MSGID_CANNOT_BOOTSTRAP_WHILE_RUNNING, "The Directory Server is currently running. The " + "configuration may not be bootstrapped while the server " + @@ -8696,6 +8791,35 @@ "Unable to register network group %s with the Directory " + "Server because another network group with the same " + "network group ID is already registered"); registerMessage(MSGID_DIRCFG_SERVER_ALREADY_RUNNING, "The Directory Server is currently running. Environment " + "configuration changes are not allowed with the server " + "running"); registerMessage(MSGID_DIRCFG_INVALID_SERVER_ROOT, "The specified server root directory '%s' is invalid. " + "The specified path must exist and must be a directory"); registerMessage(MSGID_DIRCFG_INVALID_CONFIG_FILE, "The specified config file path '%s' is invalid. " + "The specified path must exist and must be a file"); registerMessage(MSGID_DIRCFG_INVALID_CONFIG_CLASS, "The specified config handler class '%s' is invalid. " + "The specified class must be a subclass of the " + "org.opends.server.api.ConfigHandler superclass"); registerMessage(MSGID_DIRCFG_INVALID_SCHEMA_DIRECTORY, "The specified schema configuration directory '%s' is " + "invalid. The specified path must exist and must be a " + "directory"); registerMessage(MSGID_DIRCFG_INVALID_LOCK_DIRECTORY, "The specified lock directory '%s' is invalid. The " + "specified path must exist and must be a directory"); registerMessage(MSGID_DIRCFG_INVALID_CONCURRENCY_LEVEL, "The specified lock table concurrency level %d is " + "invalid. It must be an integer value greater than zero"); registerMessage(MSGID_DIRCFG_INVALID_LOCK_TABLE_SIZE, "The specified initial lock table size %d is invalid. " + "It must be an integer value greater than zero"); } } opends/src/server/org/opends/server/messages/UtilityMessages.java
@@ -1753,6 +1753,15 @@ /** * The message ID for the message that will be used if an attempt is made to * start the Directory Server if it is already running. It does not take any * arguments. */ public static final int MSGID_EMBEDUTILS_SERVER_ALREADY_RUNNING = CATEGORY_MASK_UTIL | SEVERITY_MASK_SEVERE_ERROR | 167; /** * Associates a set of generic messages with the message IDs defined in this * class. */ @@ -2333,6 +2342,11 @@ registerMessage(MSGID_EXPCHECK_TRUSTMGR_SERVER_CERT_NOT_YET_VALID, "Refusing to trust server or issuer certificate '%s' " + "because it is not valid until %s"); registerMessage(MSGID_EMBEDUTILS_SERVER_ALREADY_RUNNING, "The Directory Server cannot be started because it is " + "already running"); } } opends/src/server/org/opends/server/types/DirectoryEnvironmentConfig.java
New file @@ -0,0 +1,1177 @@ /* * 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 * * * Portions Copyright 2007 Sun Microsystems, Inc. */ package org.opends.server.types; import java.io.File; import java.util.ArrayList; import java.util.Enumeration; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.Properties; import org.opends.server.api.AccessLogPublisher; import org.opends.server.api.ConfigHandler; import org.opends.server.api.DebugLogPublisher; import org.opends.server.api.ErrorLogPublisher; import org.opends.server.core.DirectoryServer; import org.opends.server.extensions.ConfigFileHandler; import static org.opends.server.config.ConfigConstants.*; import static org.opends.server.messages.CoreMessages.*; import static org.opends.server.messages.MessageHandler.*; import static org.opends.server.util.ServerConstants.*; /** * This class provides a set of properties that may control various * aspects of the server environment. Note that these properties may * only be altered before the Directory Server is started. Any * attempt to change an environment configuration property while the * server is running will be rejected. */ public final class DirectoryEnvironmentConfig { // The set of access loggers that should be put in place before the // server is started. private final ArrayList<AccessLogPublisher> accessLoggers; // The set of debug loggers that should be put in place before the // server is started. private final ArrayList<DebugLogPublisher> debugLoggers; // The set of error loggers that should be put in place before the // server is started. private final ArrayList<ErrorLogPublisher> errorLoggers; // The set of properties for the environment config. private final HashMap<String,String> configProperties; /** * Creates a new directory environment configuration initialized * from the system properties defined in the JVM. */ public DirectoryEnvironmentConfig() { this(System.getProperties()); } /** * Creates a new directory environment configuration initialized * with a copy of the provided set of properties. * * @param properties The properties to use when initializing this * environment configuration, or {@code null} * to use an empty set of properties. */ public DirectoryEnvironmentConfig(Properties properties) { configProperties = new HashMap<String,String>(); if (properties != null) { Enumeration propertyNames = properties.propertyNames(); while (propertyNames.hasMoreElements()) { Object o = propertyNames.nextElement(); configProperties.put(String.valueOf(o), String.valueOf(properties.get(o))); } } accessLoggers = new ArrayList<AccessLogPublisher>(); debugLoggers = new ArrayList<DebugLogPublisher>(); errorLoggers = new ArrayList<ErrorLogPublisher>(); } /** * Creates a new directory environment configuration initialized * with a copy of the provided set of properties. * * @param properties The properties to use when initializing this * environment configuration, or {@code null} * to use an empty set of properties. */ public DirectoryEnvironmentConfig(Map<String,String> properties) { if (properties == null) { configProperties = new HashMap<String,String>(); } else { configProperties = new HashMap<String,String>(properties); } accessLoggers = new ArrayList<AccessLogPublisher>(); debugLoggers = new ArrayList<DebugLogPublisher>(); errorLoggers = new ArrayList<ErrorLogPublisher>(); } /** * Retrieves the property with the specified name. The check will * first be made in the local config properties, but if no value is * found then the JVM system properties will be checked. * * @param name The name of the property to retrieve. * * @return The property with the specified name, or {@code null} if * no such property is defined. */ public String getProperty(String name) { String value = configProperties.get(name); if (value == null) { value = System.getProperty(name); } return value; } /** * Specifies a property with the given name and value. If a * property is already defined with the given name, then its value * will be replaced with the provided value, or the property will be * removed if the given value is {@code null}. * * @param name The name of the property to set. * @param value The value of the property to set, or {@code null} * if the property is to be removed. * * @return The previous value held for the property, or * {@code null} if it was not previously set. * * @throws InitializationException If the Directory Server is * already running. */ public String setProperty(String name, String value) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if (value == null) { return configProperties.remove(name); } else { return configProperties.put(name, value); } } /** * Retrieves the directory that should be considered the server * root. The determination will first be based on the properties * defined in this config object. If no value is found there, then * the JVM system properties will be checked, followed by an * environment variable. * * @return The directory that should be considered the server root, * or {@code null} if it is not defined. */ public File getServerRoot() { String serverRootPath = getProperty(PROPERTY_SERVER_ROOT); if (serverRootPath == null) { serverRootPath = System.getenv(ENV_VAR_INSTANCE_ROOT); } if (serverRootPath == null) { return null; } else { return new File(serverRootPath); } } /** * Specifies the directory that should be considered the server * root. Any relative path used in the server should be considered * relative to the server root. * * @param serverRoot The directory that should be considered the * server root. * * @return The previous server root, or {@code null} if there was * none. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * server root. */ public File setServerRoot(File serverRoot) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if ((! serverRoot.exists()) || (! serverRoot.isDirectory())) { int msgID = MSGID_DIRCFG_INVALID_SERVER_ROOT; String message = getMessage(msgID, serverRoot.getAbsolutePath()); throw new InitializationException(msgID, message); } String serverRootPath; try { serverRootPath = serverRoot.getCanonicalPath(); } catch (Exception e) { serverRootPath = serverRoot.getAbsolutePath(); } String oldRootPath = setProperty(PROPERTY_SERVER_ROOT, serverRootPath); if (oldRootPath == null) { return null; } else { return new File(oldRootPath); } } /** * Retrieves the configuration file that should be used to * initialize the Directory Server config handler. If no default * configuration file is specified, then the server will attempt to * use "config/config.ldif" below the server root if it exists. * * @return The configuration file that should be used to initialize * the Directory Server config handler, or {@code null} if * no configuration file is defined. */ public File getConfigFile() { String configFilePath = getProperty(PROPERTY_CONFIG_FILE); if (configFilePath == null) { File serverRoot = getServerRoot(); if (serverRoot != null) { File configDir = new File(serverRoot, CONFIG_DIR_NAME); File configFile = new File(configDir, CONFIG_FILE_NAME); if (configFile.exists()) { return configFile; } } return null; } else { return new File(configFilePath); } } /** * Specifies the configuration file that should be used to * initialize the Directory Server config handler. * * @param configFile The configuration file that should be used to * initialize the Directory Server config * handler. * * @return The previously-defined configuration file, or * {@code null} if none was defined. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * configuration file. */ public File setConfigFile(File configFile) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if ((! configFile.exists()) || (! configFile.isFile())) { int msgID = MSGID_DIRCFG_INVALID_CONFIG_FILE; String message = getMessage(msgID, configFile.getAbsolutePath()); throw new InitializationException(msgID, message); } String configFilePath; try { configFilePath = configFile.getCanonicalPath(); } catch (Exception e) { configFilePath = configFile.getAbsolutePath(); } String oldConfigFilePath = setProperty(PROPERTY_CONFIG_FILE, configFilePath); if (oldConfigFilePath == null) { return null; } else { return new File(oldConfigFilePath); } } /** * Retrieves the class that provides the Directory Server * configuration handler implementation. If no config handler class * is defined, or if a problem occurs while attempting to determine * the config handler class, then a default class of * org.opends.server.extensions.ConfigFileHandler will be returned. * * @return The class that provides the Directory Server * configuration handler implementation. */ public Class getConfigClass() { String className = getProperty(PROPERTY_CONFIG_CLASS); if (className == null) { return ConfigFileHandler.class; } else { try { return Class.forName(className); } catch (Exception e) { return ConfigFileHandler.class; } } } /** * Specifies the class that provides the Directory Server * configuration handler implementation. The class must be a * subclass of the org.opends.server.api.ConfigHandler superclass. * * @param configClass The class that proviedes the Directory * Server configuration handler implementation. * * @return The class that was previously configured to provide the * Directory Server configuration handler implementation, * or {@code null} if none was defined. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * config handler class. */ public Class setConfigClass(Class configClass) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if (! (ConfigHandler.class.isAssignableFrom(configClass))) { int msgID = MSGID_DIRCFG_INVALID_CONFIG_CLASS; String message = getMessage(msgID, configClass.getName()); throw new InitializationException(msgID, message); } String oldClassName = setProperty(PROPERTY_CONFIG_CLASS, configClass.getName()); if (oldClassName == null) { return null; } else { try { return Class.forName(oldClassName); } catch (Exception e) { return null; } } } /** * Retrieves the directory that contains the server schema * configuration files. If no value is defined, but a default * directory of "config/schema" exists below the server root, then * that will be returned. * * @return The directory that contains the server schema * configuration files, or {@code null} if none is defined. */ public File getSchemaDirectory() { String schemaDirectoryPath = getProperty(PROPERTY_SCHEMA_DIRECTORY); if (schemaDirectoryPath == null) { File serverRoot = getServerRoot(); if (serverRoot != null) { File schemaDir = new File(serverRoot.getAbsolutePath() + File.separator + PATH_SCHEMA_DIR); if (schemaDir.exists() && schemaDir.isDirectory()) { return schemaDir; } } return null; } else { return new File(schemaDirectoryPath); } } /** * Specifies the directory that should contain the server schema * configuration files. It must exist and must be a directory. * * @param schemaDirectory The directory that should contain the * server schema configuration files. * * @return The previously-defined schema configuration directory, * or {@code null} if none was defined. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * schema directory. */ public File setSchemaDirectory(File schemaDirectory) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if ((! schemaDirectory.exists()) || (! schemaDirectory.isDirectory())) { int msgID = MSGID_DIRCFG_INVALID_SCHEMA_DIRECTORY; String message = getMessage(msgID, schemaDirectory.getAbsolutePath()); throw new InitializationException(msgID, message); } String schemaDirectoryPath; try { schemaDirectoryPath = schemaDirectory.getCanonicalPath(); } catch (Exception e) { schemaDirectoryPath = schemaDirectory.getAbsolutePath(); } String oldSchemaDir = setProperty(PROPERTY_SCHEMA_DIRECTORY, schemaDirectoryPath); if (oldSchemaDir == null) { return null; } else { return new File(oldSchemaDir); } } /** * Retrieves the directory that should be used to hold the server * lock files. If no value is defined, then the server will attempt * to use a default directory of "locks" below the server root. * * @return The directory that should be used to hold the server * lock files, or {@code null} if it cannot be determined. */ public File getLockDirectory() { String lockFilePath = getProperty(PROPERTY_LOCK_DIRECTORY); if (lockFilePath == null) { File serverRoot = getServerRoot(); if (serverRoot == null) { return null; } else { return new File(serverRoot, LOCKS_DIRECTORY); } } else { return new File(lockFilePath); } } /** * Specifies the directory that should be used to hold the server * lock files. If the specified path already exists, then it must * be a directory and its contents must be writable by the server. * If it does not exist, then its parent directory must exist and * the server should have permission to create a new subdirectory in * it. * * @param lockDirectory The directory that should be used to hold * the server lock files. * * @return The previously-defined lock directory, or {@code null} * if none was defined. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided lock * directory. */ public File setLockDirectory(File lockDirectory) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if (lockDirectory.exists()) { if (! lockDirectory.isDirectory()) { int msgID = MSGID_DIRCFG_INVALID_LOCK_DIRECTORY; String message = getMessage(msgID, lockDirectory.getAbsolutePath()); throw new InitializationException(msgID, message); } } else { File parentFile = lockDirectory.getParentFile(); if (! (parentFile.exists() && parentFile.isDirectory())) { int msgID = MSGID_DIRCFG_INVALID_LOCK_DIRECTORY; String message = getMessage(msgID, lockDirectory.getAbsolutePath()); throw new InitializationException(msgID, message); } } String lockDirectoryPath; try { lockDirectoryPath = lockDirectory.getCanonicalPath(); } catch (Exception e) { lockDirectoryPath = lockDirectory.getAbsolutePath(); } String oldLockDir = setProperty(PROPERTY_LOCK_DIRECTORY, lockDirectoryPath); if (oldLockDir == null) { return null; } else { return new File(oldLockDir); } } /** * Indicates whether the Directory Server startup process should * skip the connection handler creation and initialization phases. * * @return {@code true} if the Directory Server should not start * its connection handlers, or {@code false} if the * connection handlers should be enabled. */ public boolean disableConnectionHandlers() { String disableStr = getProperty(PROPERTY_DISABLE_CONNECTION_HANDLERS); if (disableStr == null) { return false; } return disableStr.equalsIgnoreCase("true"); } /** * Specifies whether the Directory Server startup process should * skip the connection handler creation and initialization phases. * * @param disableConnectionHandlers Indicates whether the * Directory Server should skip * the connection handler * creation and initialization * phases. * * @return The previous setting for this configuration option. If * no previous value was specified, then {@code false} will * be returned. * * @throws InitializationException If the Directory Server is * already running. */ public boolean setDisableConnectionHandlers( boolean disableConnectionHandlers) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } String oldDisableStr = setProperty(PROPERTY_DISABLE_CONNECTION_HANDLERS, String.valueOf(disableConnectionHandlers)); if (oldDisableStr == null) { return false; } else { return oldDisableStr.equalsIgnoreCase("true"); } } /** * Indicates whether all threads created by the Directory Server * should be created as daemon threads. * * @return {@code true} if all threads created by the Directory * Server should be created as daemon threads, or * {@code false} if not. */ public boolean forceDaemonThreads() { String forceDaemonStr = getProperty(PROPERTY_FORCE_DAEMON_THREADS); if (forceDaemonStr == null) { return false; } else { return forceDaemonStr.equalsIgnoreCase("true"); } } /** * Specifies whether all threads created by the Directory Server * should be created as daemon threads. * * @param forceDaemonThreads Indicates whether all threads created * by the Directory Server should be * created as daemon threads. * * @return The previous setting for this configuration option. If * no previous value was specified, then {@code false} will * be returned. * * @throws InitializationException If the Directory Server is * already running. */ public boolean setForceDaemonThreads(boolean forceDaemonThreads) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } String oldForceDaemonStr = setProperty(PROPERTY_FORCE_DAEMON_THREADS, String.valueOf(forceDaemonThreads)); if (oldForceDaemonStr == null) { return false; } else { return oldForceDaemonStr.equalsIgnoreCase("true"); } } /** * Indicates whether the Directory Server should be allowed to use * the {@code Runtime.exec()} method to be able to launch external * commands on the underlying system. * * @return {@code true} if the Directory Server should be allowed * to use {@code Runtime.exec()}, or {@code false} if not. */ public boolean disableExec() { String disableStr = getProperty(PROPERTY_DISABLE_EXEC); if (disableStr == null) { return false; } else { return disableStr.equalsIgnoreCase("true"); } } /** * Specifies whether the Directory Server should be allowed to use * the {@code Runtime.exec()} method to be able to launch external * commands on the underlying system. * * @param disableExec Indicates whether the Directory Server * should be allowed to launch external * commands on the underlying system. * * @return The previous setting for this configuration option. If * no previous value was specified, then {@code false} will * be returned. * * @throws InitializationException If the Directory Server is * already running. */ public boolean setDisableExec(boolean disableExec) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } String oldDisableStr = setProperty(PROPERTY_DISABLE_EXEC, String.valueOf(disableExec)); if (oldDisableStr == null) { return false; } else { return oldDisableStr.equalsIgnoreCase("true"); } } /** * Retrieves the concurrency level for the Directory Server lock * table. * * @return The concurrency level for the Directory Server lock * table. */ public int getLockManagerConcurrencyLevel() { String levelStr = getProperty(PROPERTY_LOCK_MANAGER_CONCURRENCY_LEVEL); if (levelStr == null) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } int concurrencyLevel = -1; try { concurrencyLevel = Integer.parseInt(levelStr); } catch (Exception e) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } if (concurrencyLevel <= 0) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } else { return concurrencyLevel; } } /** * Specifies the concurrency level for the Directory Server lock * table. This should be set to the maximum number of threads that * could attempt to interact with the lock table at any given time. * * @param concurrencyLevel The concurrency level for the Directory * Server lock manager. * * @return The previously-configured concurrency level. If there * was no previously-configured value, then the default * concurrency level will be returned. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * concurrency level value. */ public int setLockManagerConcurrencyLevel(int concurrencyLevel) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if (concurrencyLevel <= 0) { int msgID = MSGID_DIRCFG_INVALID_CONCURRENCY_LEVEL; String message = getMessage(msgID, concurrencyLevel); throw new InitializationException(msgID, message); } String concurrencyStr = setProperty(PROPERTY_LOCK_MANAGER_CONCURRENCY_LEVEL, String.valueOf(concurrencyLevel)); if (concurrencyStr == null) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } else { try { return Integer.parseInt(concurrencyStr); } catch (Exception e) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } } } /** * Retrieves the initial table size for the server lock table. This * can be used to ensure that the lock table has the appropriate * size for the expected number of locks that will be held at any * given time. * * @return The initial table size for the server lock table. */ public int getLockManagerTableSize() { String sizeStr = getProperty(PROPERTY_LOCK_MANAGER_TABLE_SIZE); if (sizeStr == null) { return LockManager.DEFAULT_INITIAL_TABLE_SIZE; } else { try { return Integer.parseInt(sizeStr); } catch (Exception e) { return LockManager.DEFAULT_INITIAL_TABLE_SIZE; } } } /** * Specifies the initial table size for the server lock table. This * can be used to ensure taht the lock table has the appropriate * size for the expected number of locks that will be held at any * given time. * * @param lockTableSize The initial table size for the server lock * table. * * @return The previously-configured initial lock table size. If * there was no previously-configured value, then the * default initial table size will be returned. * * @throws InitializationException If the Directory Server is * already running or there is a * problem with the provided * initial table size. */ public int setLockManagerTableSize(int lockTableSize) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } if (lockTableSize <= 0) { int msgID = MSGID_DIRCFG_INVALID_LOCK_TABLE_SIZE; String message = getMessage(msgID, lockTableSize); throw new InitializationException(msgID, message); } String concurrencyStr = setProperty(PROPERTY_LOCK_MANAGER_TABLE_SIZE, String.valueOf(lockTableSize)); if (concurrencyStr == null) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } else { try { return Integer.parseInt(concurrencyStr); } catch (Exception e) { return LockManager.DEFAULT_CONCURRENCY_LEVEL; } } } /** * Retrieves the list of access loggers that should be enabled in * the server during the startup process. Note that these loggers * will not be automatically disabled when startup is complete, so * if they are no longer needed then they should be manually removed * from the server using the * {@code AccessLogger.removeAccessLogPublisher} method. * * @return The list of access loggers that should be enabled in the * server during the startup process. */ public List<AccessLogPublisher> getAccessLoggers() { return accessLoggers; } /** * Adds the provided access logger to the set of loggers that should * be enabled in the server during the startup process. * * @param accessLogger The access logger that should be added to * the set of loggers enabled in the server * during the startup process. * * @throws InitializationException If the Directory Server is * already running. */ public void addAccessLogger(AccessLogPublisher accessLogger) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } accessLoggers.add(accessLogger); } /** * Retrieves the list of error loggers that should be enabled in * the server during the startup process. Note that these loggers * will not be automatically disabled when startup is complete, so * if they are no longer needed then they should be manually removed * from the server using the * {@code ErrorLogger.removeErrorLogPublisher} method. * * @return The list of error loggers that should be enabled in the * server during the startup process. */ public List<ErrorLogPublisher> getErrorLoggers() { return errorLoggers; } /** * Adds the provided error logger to the set of loggers that should * be enabled in the server during the startup process. * * @param errorLogger The error logger that should be added to the * set of loggers enabled in the server during * the startup process. * * @throws InitializationException If the Directory Server is * already running. */ public void addErrorLogger(ErrorLogPublisher errorLogger) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } errorLoggers.add(errorLogger); } /** * Retrieves the list of debug loggers that should be enabled in * the server during the startup process. Note that these loggers * will not be automatically disabled when startup is complete, so * if they are no longer needed then they should be manually removed * from the server using the * {@code DebugLogger.removeDebugLogPublisher} method. * * @return The list of debug loggers that should be enabled in the * server during the startup process. */ public List<DebugLogPublisher> getDebugLoggers() { return debugLoggers; } /** * Adds the provided debug logger to the set of loggers that should * be enabled in the server during the startup process. * * @param debugLogger The debug logger that should be added to * the set of loggers enabled in the server * during the startup process. * * @throws InitializationException If the Directory Server is * already running. */ public void addDebugLogger(DebugLogPublisher debugLogger) throws InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_DIRCFG_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } debugLoggers.add(debugLogger); } } opends/src/server/org/opends/server/types/LockManager.java
@@ -33,8 +33,10 @@ import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantReadWriteLock; import static org.opends.server.loggers.debug.DebugLogger.*; import org.opends.server.core.DirectoryServer; import org.opends.server.loggers.debug.DebugTracer; import static org.opends.server.loggers.debug.DebugLogger.*; import static org.opends.server.util.ServerConstants.*; import static org.opends.server.util.StaticUtils.*; @@ -88,49 +90,69 @@ // Initialize all of the lock variables. // Initialize the lock table. static { // Determine the concurrency level to use. We'll let it be // specified by a system property, but if it isn't specified then // we'll set the default value based on the number of CPUs in the // system. int concurrencyLevel = -1; String propertyStr = System.getProperty(PROPERTY_LOCK_MANAGER_CONCURRENCY_LEVEL); if (propertyStr != null) { try { concurrencyLevel = Integer.parseInt(propertyStr); } catch (Exception e) {} } if (concurrencyLevel <= 0) { concurrencyLevel = Math.max(DEFAULT_CONCURRENCY_LEVEL, (2*Runtime.getRuntime().availableProcessors())); } // Set the lock table size either to a user-defined value from a // property or a hard-coded default. int lockTableSize = DEFAULT_INITIAL_TABLE_SIZE; propertyStr = System.getProperty(PROPERTY_LOCK_MANAGER_TABLE_SIZE); if (propertyStr != null) { try { lockTableSize = Integer.parseInt(propertyStr); } catch (Exception e) {} } // Create an empty table for holding the entry locks. DirectoryEnvironmentConfig environmentConfig = DirectoryServer.getEnvironmentConfig(); lockTable = new ConcurrentHashMap<DN,ReentrantReadWriteLock>( lockTableSize, DEFAULT_LOAD_FACTOR, concurrencyLevel); environmentConfig.getLockManagerTableSize(), DEFAULT_LOAD_FACTOR, environmentConfig.getLockManagerConcurrencyLevel()); } /** * Recreates the lock table. This should be called only in the * case that the Directory Server is in the process of an in-core * restart because it will destroy the existing lock table. */ public synchronized static void reinitializeLockTable() { ConcurrentHashMap<DN,ReentrantReadWriteLock> oldTable = lockTable; DirectoryEnvironmentConfig environmentConfig = DirectoryServer.getEnvironmentConfig(); lockTable = new ConcurrentHashMap<DN,ReentrantReadWriteLock>( environmentConfig.getLockManagerTableSize(), DEFAULT_LOAD_FACTOR, environmentConfig.getLockManagerConcurrencyLevel()); if (! oldTable.isEmpty()) { for (DN dn : oldTable.keySet()) { try { ReentrantReadWriteLock lock = oldTable.get(dn); if (lock.isWriteLocked()) { TRACER.debugWarning("Found stale write lock on " + dn.toString()); } else if (lock.getReadLockCount() > 0) { TRACER.debugWarning("Found stale read lock on " + dn.toString()); } else { TRACER.debugWarning("Found stale unheld lock on " + dn.toString()); } } catch (Exception e) { if (debugEnabled()) { TRACER.debugCaught(DebugLogLevel.ERROR, e); } } } oldTable.clear(); } } opends/src/server/org/opends/server/util/EmbeddedUtils.java
New file @@ -0,0 +1,119 @@ /* * 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 * * * Portions Copyright 2007 Sun Microsystems, Inc. */ package org.opends.server.util; import org.opends.server.config.ConfigException; import org.opends.server.core.DirectoryServer; import org.opends.server.types.DirectoryEnvironmentConfig; import org.opends.server.types.InitializationException; import static org.opends.server.messages.MessageHandler.*; import static org.opends.server.messages.UtilityMessages.*; import static org.opends.server.util.ServerConstants.*; /** * This class provides a number of utility methods for using OpenDS in an * embedded manner (i.e., running within the same JVM as another application and * controlled by that application). */ public final class EmbeddedUtils { /** * Indicates whether the Directory Server is currently running. * * @return {@code true} if the server is currently running, or {@code false} * if not. */ public static boolean isRunning() { return DirectoryServer.isRunning(); } /** * Attempts to start the Directory Server. * * @param config The environment configuration to use for the server. * * @throws ConfigException If a configuration problem is detected during * the server initialization or startup process. * * @throws InitializationException If the Directory Server is already * running, or if an error occurs during * server initialization or startup. */ public static void startServer(DirectoryEnvironmentConfig config) throws ConfigException, InitializationException { if (DirectoryServer.isRunning()) { int msgID = MSGID_EMBEDUTILS_SERVER_ALREADY_RUNNING; String message = getMessage(msgID); throw new InitializationException(msgID, message); } DirectoryServer directoryServer = DirectoryServer.reinitialize(config); directoryServer.startServer(); } /** * Attempts to stop the Directory Server. * * @param className The name of the class that initiated the shutdown. * @param reason A message explaining the reason for the shutdown. */ public static void stopServer(String className, String reason) { DirectoryServer.shutDown(className, reason); } /** * Attempts to restart the Directory Server. This will perform an in-core * restart in which the existing server instance will be shut down, a new * instance will be created, and it will be reinitialized and restarted. * * @param className The name of the class that initiated the restart. * @param reason A message explaining the reason for the retart. * @param config The environment configuration to use for the new server * instance. */ public static void restartServer(String className, String reason, DirectoryEnvironmentConfig config) { DirectoryServer.restart(className, reason, config); } } opends/src/server/org/opends/server/util/ServerConstants.java
@@ -2431,6 +2431,25 @@ /** * The name of the system property that can be used to specify the * fully-qualified name of theclass that provides the Director Server config * handler implementation. */ public static final String PROPERTY_CONFIG_CLASS = "org.opends.server.ConfigClass"; /** * The name of the system property that can be used to specify the path to the * configuration file that should be used to initialize the config handler. */ public static final String PROPERTY_CONFIG_FILE = "org.opends.server.ConfigFile"; /** * The name of the system property that can be used to disable any connection * handler that may be enabled in the server configuration. This may be used * to start the server in a mode where it will not accept any external opends/src/server/org/opends/server/util/StaticUtils.java
@@ -2264,15 +2264,7 @@ */ public static boolean mayUseExec() { String s = System.getProperty(PROPERTY_DISABLE_EXEC); if (s == null) { return true; } s = toLowerCase(s); return (s.equals("false") || s.equals("off") || s.equals("no") || s.equals("0")); return (! DirectoryServer.getEnvironmentConfig().disableExec()); } opends/tests/unit-tests-testng/src/server/org/opends/server/TestCaseUtils.java
@@ -69,12 +69,14 @@ import org.opends.server.protocols.ldap.BindResponseProtocolOp; import org.opends.server.tools.LDAPModify; import org.opends.server.tools.dsconfig.DSConfig; import org.opends.server.types.DN; import org.opends.server.types.DirectoryEnvironmentConfig; import org.opends.server.types.DirectoryException; import org.opends.server.types.DN; import org.opends.server.types.FilePermission; import org.opends.server.types.InitializationException; import org.opends.server.types.OperatingSystem; import org.opends.server.types.ResultCode; import org.opends.server.util.EmbeddedUtils; import static org.testng.Assert.*; @@ -304,53 +306,27 @@ serverJmxSocket.close(); serverLdapsSocket.close(); // Actually start the server and set a variable that will prevent us from // needing to do it again. System.setProperty(PROPERTY_SERVER_ROOT, testRoot.getAbsolutePath()); System.setProperty(PROPERTY_FORCE_DAEMON_THREADS, "true"); String configClass = ConfigFileHandler.class.getName(); String configFile = testConfigDir.getAbsolutePath() + File.separator + "config.ldif"; // Create a configuration for the server. DirectoryEnvironmentConfig config = new DirectoryEnvironmentConfig(); config.setServerRoot(testRoot); config.setForceDaemonThreads(true); config.setConfigClass(ConfigFileHandler.class); config.setConfigFile(new File(testConfigDir, "config.ldif")); DirectoryServer directoryServer = DirectoryServer.getInstance(); directoryServer.bootstrapServer(); directoryServer.initializeConfiguration(configClass, configFile); String debugTarget = System.getProperty("org.opends.test.debug.target"); if(debugTarget != null) { System.setProperty("org.opends.server.debug.enabled", "true"); System.setProperty("org.opends.server.debug.target.1", debugTarget); } try { TextDebugLogPublisher startupDebugPublisher = TextDebugLogPublisher.getStartupTextDebugPublisher( TestListener.DEBUG_TEXT_WRITER); DebugLogger.removeAllDebugLogPublishers(); DebugLogger.addDebugLogPublisher(startupDebugPublisher); TextErrorLogPublisher startupErrorPublisher = TextErrorLogPublisher.getStartupTextErrorPublisher( TestListener.ERROR_TEXT_WRITER); ErrorLogger.removeAllErrorLogPublishers(); ErrorLogger.addErrorLogPublisher(startupErrorPublisher); TextAccessLogPublisher startupAccessPublisher = config.addAccessLogger( TextAccessLogPublisher.getStartupTextAccessPublisher( TestListener.ACCESS_TEXT_WRITER, false); AccessLogger.removeAllAccessLogPublishers(); AccessLogger.addAccessLogPublisher(startupAccessPublisher); } catch(Exception e) { System.out.println("Error installing test log publishers: " + e.toString()); } TestListener.ACCESS_TEXT_WRITER, false)); directoryServer.startServer(); config.addErrorLogger( TextErrorLogPublisher.getStartupTextErrorPublisher( TestListener.ERROR_TEXT_WRITER)); config.addDebugLogger( TextDebugLogPublisher.getStartupTextDebugPublisher( TestListener.DEBUG_TEXT_WRITER)); EmbeddedUtils.startServer(config); assertTrue(InvocationCounterPlugin.startupCalled());