You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@oodt.apache.org by ke...@apache.org on 2010/07/15 01:02:32 UTC
svn commit: r964248 [1/2] -
/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/
Author: kelly
Date: Wed Jul 14 23:02:32 2010
New Revision: 964248
URL: http://svn.apache.org/viewvc?rev=964248&view=rev
Log:
WIP OODT-15
Import additional OODT commons: enterprise config, server, executables, etc.
(Does anyone use this crap?)
Added:
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Configuration.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfigurationEntityResolver.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfiguredTestCase.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/EDAException.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServer.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServerConfig.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Executable.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Initializer.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/MultiServer.java
incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Service.java
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Configuration.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Configuration.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Configuration.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Configuration.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,735 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.*;
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.net.UnknownHostException;
+import java.util.*;
+import org.apache.oodt.commons.util.*;
+import org.w3c.dom.*;
+import org.xml.sax.*;
+import javax.naming.Context;
+import javax.naming.InitialContext;
+import javax.naming.NamingException;
+import javax.naming.NoInitialContextException;
+import java.rmi.registry.Registry;
+import java.util.StringTokenizer;
+
+/** EDA Configuration.
+ *
+ * An object of this class represents the configuration information for the EDA software.
+ *
+ * @author Kelly
+ */
+public class Configuration {
+ /** The singleton configuration. */
+ static Configuration configuration = null;
+
+ /** Name of property that specifies the direcotries that contains XML entities. */
+ public static final String ENTITY_DIRS_PROP = "entity.dirs";
+
+ /** Name of the default config file. */
+ public static final String DEFAULT_CONFIG_FILE = ".edarc.xml";
+
+ /** Alternate config file. */
+ public static final String ALT_CONFIG_FILE = ".oodtrc.xml";
+
+ /** Library-location config file. */
+ public static final File LIB_CONFIG_FILE = new File(System.getProperty("java.home", "/") + File.separator + "lib"
+ + File.separator + "edarc.xml");
+
+ /** Non-JRE library location of config file. */
+ public static final File ALT_LIB_CONFIG_FILE = new File(System.getProperty("java.home", "/") + File.separator + ".."
+ + File.separator + "lib" + File.separator + "edarc.xml");
+
+ /** Get the singleton configuration.
+ *
+ * This method returns the singleton configuration object, or creates it if it
+ * doesn't yet exist. To create it, it reads the configuration file specified by
+ * the system property <code>org.apache.oodt.commons.Configuration.url</code> or the file in the
+ * user's home directory called .edarc.xml if the system property isn't
+ * specified. It parses the file and returns a <code>Configuration</code> object
+ * initialized with the data specified therein.
+ *
+ * @throws IOException If reading the configuration file fails.
+ * @throws SAXException If parsing the configuration file fails.
+ * @throws MalformedURLException If the URL specification is invalid.
+ * @return An initialized configuration object.
+ */
+ public static Configuration getConfiguration() throws IOException, SAXException, MalformedURLException {
+ // Got one? Use it.
+ if (configuration != null) return configuration;
+
+ URL url;
+
+ // First preference: URL via the org.apache.oodt.commons.Configuration.url prop.
+ String urlString = System.getProperty("org.apache.oodt.commons.Configuration.url");
+ if (urlString != null) {
+ url = new URL(urlString);
+ } else {
+ File file = null;
+
+ // Second preference: file via the org.apache.oodt.commons.Configuration.file prop.
+ String filename = System.getProperty("org.apache.oodt.commons.Configuration.file");
+ if (filename != null) {
+ file = new File(filename);
+ if (!file.exists()) throw new IOException("File " + file + " not found");
+ } else {
+ List candidates = new ArrayList();
+
+ // Third preference: ~/.edarc.xml
+ File homedir = new File(System.getProperty("user.home", "/"));
+ File homedirfile = new File(homedir, DEFAULT_CONFIG_FILE);
+ candidates.add(homedirfile);
+
+ // Fourth preference: ~/.oodtrc.xml
+ File alt = new File(homedir, ALT_CONFIG_FILE);
+ candidates.add(alt);
+
+ // Fifth and sixth preferences: $EDA_HOME/conf/edarc.xml and $EDA_HOME/etc/edarc.xml
+ String edaHome = System.getProperty("eda.home");
+ if (edaHome != null) {
+ File edaHomeDir = new File(edaHome);
+ candidates.add(new File(new File(edaHomeDir, "conf"), "edarc.xml"));
+ candidates.add(new File(new File(edaHomeDir, "etc"), "edarc.xml"));
+ }
+
+ // Seventh preference: JAVA_HOME/lib/edarc.xml
+ candidates.add(LIB_CONFIG_FILE);
+
+ // Final preference: JAVA_HOME/../lib/edarc.xml (to get out of JRE)
+ candidates.add(ALT_LIB_CONFIG_FILE);
+
+ // Now find one.
+ boolean found = false;
+ for (Iterator i = candidates.iterator(); i.hasNext();) {
+ file = (File) i.next();
+ if (file.exists()) {
+ found = true;
+ break;
+ }
+ }
+ if (found && file == alt)
+ System.err.println("WARNING: Using older config file " + alt + "; rename to "
+ + homedirfile + " as soon as possible.");
+ if (!found) {
+ return getEmptyConfiguration();
+ }
+ }
+ url = file.toURL();
+ }
+
+ return getConfiguration(url);
+
+ }
+
+ /** Get the singleton configuration.
+ *
+ * This method returns the singleton configuration object from a
+ * specified file url. It parses the file and returns a <code>Configuration</code> object
+ * initialized with the data specified therein. Added by Chris Mattmann 12/05/03.
+ *
+ * @throws IOException If an I/O error occurs.
+ * @return An initialized configuration object.
+ */
+ public static Configuration getConfiguration(URL configFileUrl) throws SAXException, IOException {
+ synchronized (Configuration.class) {
+ if (configuration == null)
+ configuration = new Configuration(configFileUrl);
+ }
+ return configuration;
+ }
+
+ private static Configuration getEmptyConfiguration() {
+ synchronized (Configuration.class) {
+ if (configuration == null)
+ configuration = new Configuration();
+ }
+ return configuration;
+ }
+
+
+ /** Get the singleton configuration without exception.
+ *
+ * This method is identical to {@link #getConfiguration} but traps all checked
+ * exceptions. If the configuration can't be read, it returns null.
+ *
+ * @return An initialized configuration object, or null if an error occurred.
+ */
+ public static Configuration getConfigurationWithoutException() {
+ // Got one? Use it. Do this out of a try block for performance.
+ if (configuration != null) return configuration;
+
+ // Try to get it.
+ try {
+ return getConfiguration();
+ } catch (RuntimeException ex) {
+ throw ex;
+ } catch (Exception ex) {
+ System.err.println("Exception " + ex.getClass().getName() + " while getting configuration: "
+ + ex.getMessage());
+ ex.printStackTrace();
+ return null;
+ }
+ }
+
+ Configuration() {
+ serverMgrPort = 7577;
+ nameServerStateFrequency = 6000000;
+ nameServerObjectKey = "StandardNS%20POA";
+ nameServerPort = "10000";
+ nameServerHost = "localhost";
+ nameServerVersion = "1.0";
+ nameServerUsingRIRProtocol = false;
+ webServerDocumentDirectory = new File(System.getProperty("user.home", "/") + "tomcat/webapps/ROOT");
+ webPort = "8080";
+ webHost = "localhost";
+ System.setProperty(WEB_PROTOCOL_PROPERTY, "http");
+ initializeContext();
+ }
+
+ /** Construct a configuration.
+ *
+ * @param url The location of the configuration.
+ * @throws IOException If reading the configuration file fails.
+ * @throws SAXParseException If parsing the configuration file fails.
+ */
+ Configuration(URL url) throws IOException, SAXException {
+ this(new InputSource(url.toString()));
+ }
+
+ Configuration(InputSource inputSource) throws IOException, SAXException {
+ String systemID = inputSource.getSystemId();
+ if (systemID == null) inputSource.setSystemId("file:/unknown");
+
+ // Get the document
+ DOMParser parser = XML.createDOMParser();
+ parser.setEntityResolver(new ConfigurationEntityResolver());
+ parser.setErrorHandler(new ErrorHandler() {
+ public void error(SAXParseException ex) throws SAXException {
+ throw ex;
+ }
+ public void warning(SAXParseException ex) {
+ System.err.println("Warning: " + ex.getMessage());
+ }
+ public void fatalError(SAXParseException ex) throws SAXException {
+ System.err.println("Fatal parse error: " + ex.getMessage());
+ throw ex;
+ }
+ });
+ parser.parse(inputSource);
+ Document document = parser.getDocument();
+ XML.removeComments(document);
+ document.normalize();
+
+ // See if this really is a <configuration> document.
+ if (!document.getDocumentElement().getNodeName().equals("configuration"))
+ throw new SAXException("Configuration " + inputSource.getSystemId() + " is not a <configuration> document");
+
+ NodeList list = document.getDocumentElement().getChildNodes();
+ for (int eachChild = 0; eachChild < list.getLength(); ++eachChild) {
+ Node childNode = list.item(eachChild);
+ if (childNode.getNodeName().equals("webServer")) {
+ NodeList children = childNode.getChildNodes();
+ for (int i = 0; i < children.getLength(); ++i) {
+ Node node = children.item(i);
+ if ("host".equals(node.getNodeName()))
+ webHost = XML.unwrappedText(node);
+ else if ("port".equals(node.getNodeName()))
+ webPort = XML.unwrappedText(node);
+ else if ("dir".equals(node.getNodeName()))
+ webServerDocumentDirectory = new File(XML.unwrappedText(node));
+ }
+ properties.setProperty("org.apache.oodt.commons.Configuration.webServer.baseURL", getWebServerBaseURL());
+ if (webServerDocumentDirectory == null)
+ webServerDocumentDirectory = new File(System.getProperty("user.home", "/")
+ + "/dev/htdocs");
+ } else if (childNode.getNodeName().equals("nameServer")) {
+ Element nameServerNode = (Element) childNode;
+ String nameServerStateFrequencyString = nameServerNode.getAttribute("stateFrequency");
+ if (nameServerStateFrequencyString == null || nameServerStateFrequencyString.length() == 0)
+ nameServerStateFrequency = 0;
+ else try {
+ nameServerStateFrequency = Integer.parseInt(nameServerStateFrequencyString);
+ } catch (NumberFormatException ex) {
+ throw new SAXException("Illegal nun-numeric value \"" + nameServerStateFrequencyString
+ + "\" for stateFrequency attribute");
+ }
+ if (childNode.getFirstChild().getNodeName().equals("rir")) {
+ nameServerUsingRIRProtocol = true;
+ NodeList children = childNode.getFirstChild().getChildNodes();
+ nameServerObjectKey = children.getLength() == 1? XML.unwrappedText(children.item(0)):null;
+ } else {
+ nameServerUsingRIRProtocol = false;
+ nameServerVersion = null;
+ nameServerPort = null;
+ // Must be same as CORBAMgr.NS_OBJECT_KEY:
+ nameServerObjectKey = "StandardNS/NameServer%2DPOA/_root";
+ NodeList children = childNode.getFirstChild().getChildNodes();
+ for (int i = 0; i < children.getLength(); ++i) {
+ Node node = children.item(i);
+ if (node.getNodeName().equals("version"))
+ nameServerVersion = XML.unwrappedText(node);
+ else if (node.getNodeName().equals("host"))
+ nameServerHost = XML.unwrappedText(node);
+ else if (node.getNodeName().equals("port"))
+ nameServerPort = XML.unwrappedText(node);
+ else if (node.getNodeName().equals("objectKey"))
+ nameServerObjectKey = XML.unwrappedText(node);
+ }
+ }
+ } else if (childNode.getNodeName().equals("xml")) {
+ NodeList children = childNode.getChildNodes();
+ for (int i = 0; i < children.getLength(); ++i) {
+ Node xmlNode = children.item(i);
+ if ("entityRef".equals(xmlNode.getNodeName())) {
+ NodeList dirNodes = xmlNode.getChildNodes();
+ StringBuffer refDirs = new StringBuffer(System.getProperty(ENTITY_DIRS_PROP, ""));
+ for (int j = 0; j < dirNodes.getLength(); ++j)
+ refDirs.append(',').append(XML.unwrappedText(dirNodes.item(j)));
+ if (refDirs.length() > 0)
+ System.setProperty(ENTITY_DIRS_PROP, refDirs.charAt(0) == ','?
+ refDirs.substring(1) : refDirs.toString());
+ }
+ }
+ } else if ("serverMgr".equals(childNode.getNodeName())) {
+ serverMgrPort = Integer.parseInt(XML.unwrappedText(childNode.getFirstChild()));
+ } else if (childNode.getNodeName().equals("properties")) {
+ loadProperties(childNode, properties);
+ } else if (childNode.getNodeName().equals("programs")) {
+ NodeList children = childNode.getChildNodes();
+ for (int i = 0; i < children.getLength(); ++i) {
+ // They're all of type execServer---for now.
+ ExecServerConfig esc = new ExecServerConfig(children.item(i));
+ esc.getProperties().setProperty("org.apache.oodt.commons.Configuration.url", inputSource.getSystemId());
+ execServers.add(esc);
+ }
+ }
+ }
+
+ initializeContext();
+ }
+
+ private void initializeContext() {
+ contextEnvironment.put(Context.INITIAL_CONTEXT_FACTORY, "org.apache.oodt.commons.object.jndi.ObjectCtxFactory");
+ String registryList = System.getProperty("org.apache.oodt.commons.rmiregistries", System.getProperty("rmiregistries"));
+ if (registryList == null) {
+ String host = System.getProperty("rmiregistry.host", "localhost");
+ int port = Integer.getInteger("rmiregistry.port", Registry.REGISTRY_PORT).intValue();
+ registryList = "rmi://" + host + ":" + port;
+ }
+ contextEnvironment.put("rmiregistries", registryList);
+ }
+
+ /** Serialize this configuration into a serialized XML document.
+ *
+ * @return Serialized XML version of this configuration.
+ * @throws DOMException If an error occurs constructing the XML structure.
+ */
+ public String toXML() throws DOMException {
+ Document doc = createDocument("configuration");
+ doc.replaceChild(toXML(doc), doc.getDocumentElement());
+ return XML.serialize(doc);
+ }
+
+ /**
+ *
+ * @param document The document to which the XML structure will belong.
+ * @return The root node representing this configuration.
+ * @throws DOMException If an error occurs constructing the XML structure.
+ */
+ public Node toXML(Document document) throws DOMException {
+ // <configuration>
+ Element configurationNode = document.createElement("configuration");
+
+ // <webServer>
+ Element webServerNode = document.createElement("webServer");
+ configurationNode.appendChild(webServerNode);
+
+ // <webServer>
+ // <host>...</host><port>...</port><dir>...</dir>
+ XML.add(webServerNode, "host", webHost);
+ XML.add(webServerNode, "port", webPort);
+ XML.add(webServerNode, "dir", webServerDocumentDirectory.toString());
+
+ // <nameServer>
+ Element nameServerNode = document.createElement("nameServer");
+ nameServerNode.setAttribute("stateFrequency", String.valueOf(nameServerStateFrequency));
+ configurationNode.appendChild(nameServerNode);
+
+ // <nameServer>
+ // <rir> or <iiop>
+ if (nameServerUsingRIRProtocol) {
+ Element rirNode = document.createElement("rir");
+ nameServerNode.appendChild(rirNode);
+ if (nameServerObjectKey != null)
+ XML.add(rirNode, "objectKey", nameServerObjectKey);
+ } else {
+ Element iiopNode = document.createElement("iiop");
+ nameServerNode.appendChild(iiopNode);
+ if (nameServerVersion != null)
+ XML.add(iiopNode, "version", nameServerVersion);
+ XML.add(iiopNode, "host", nameServerHost);
+ if (nameServerPort != null)
+ XML.add(iiopNode, "port", nameServerPort);
+ if (nameServerObjectKey != null)
+ XML.add(iiopNode, "objectKey", nameServerObjectKey);
+ }
+
+ // <xml><entityRef><dir>...
+ if (!getEntityRefDirs().isEmpty()) {
+ Element xmlNode = document.createElement("xml");
+ configurationNode.appendChild(xmlNode);
+ Element entityRefNode = document.createElement("entityRef");
+ xmlNode.appendChild(entityRefNode);
+ XML.add(entityRefNode, "dir", getEntityRefDirs());
+ }
+
+ // <serverMgr><port>...
+ if (getServerMgrPort() != 0) {
+ Element serverMgrNode = document.createElement("serverMgr");
+ configurationNode.appendChild(serverMgrNode);
+ XML.add(serverMgrNode, "port", String.valueOf(getServerMgrPort()));
+ }
+
+ // Global <properties>...</properties>
+ if (properties.size() > 0)
+ dumpProperties(properties, configurationNode);
+
+ // <programs>...
+ if (execServers.size() > 0) {
+ Element programsNode = document.createElement("programs");
+ configurationNode.appendChild(programsNode);
+
+ for (Iterator i = execServers.iterator(); i.hasNext();) {
+ ExecServerConfig esc = (ExecServerConfig) i.next();
+ Element execServerNode = document.createElement("execServer");
+ programsNode.appendChild(execServerNode);
+ XML.add(execServerNode, "class", esc.getClassName());
+ XML.add(execServerNode, "objectKey", esc.getObjectKey());
+ XML.add(execServerNode, "host", esc.getPreferredHost().toString());
+ if (esc.getProperties().size() > 0)
+ dumpProperties(esc.getProperties(), execServerNode);
+ }
+ }
+
+ return configurationNode;
+ }
+
+ /** Merge the properties in the configuration into the given properties.
+ *
+ * Properties that already exist in the <var>targetProps</var> won't be
+ * overwritten.
+ *
+ * @param targetProps The target properties.
+ */
+ public void mergeProperties(Properties targetProps) {
+ for (Iterator i = properties.entrySet().iterator(); i.hasNext();) {
+ Map.Entry entry = (Map.Entry) i.next();
+ if (!targetProps.containsKey(entry.getKey()))
+ targetProps.put(entry.getKey(), entry.getValue());
+ }
+ }
+
+ /** Get the exec-server configurations.
+ *
+ * @return A collection of exec server configurations, each of class {@link ExecServerConfig}.
+ */
+ public Collection getExecServerConfigs() {
+ return execServers;
+ }
+
+ /** Get the exec-server configurations.
+ *
+ * @param clazz The class of exec servers that will be returned.
+ * @return A collection of exec server configurations, each of class {@link ExecServerConfig}.
+ */
+ public Collection getExecServerConfigs(Class clazz) {
+ String className = clazz.getName();
+ Collection execServerConfigs = new ArrayList();
+ for (Iterator i = execServers.iterator(); i.hasNext();) {
+ ExecServerConfig exec = (ExecServerConfig) i.next();
+ if (className.equals(exec.getClassName()))
+ execServerConfigs.add(exec);
+ }
+ return execServerConfigs;
+ }
+
+ /** Get an exec-server configuration.
+ *
+ * @param objectKey The object key of the Exec Server to retrieve.
+ * @return An {@link ExecServerConfig} or null if object key not found.
+ */
+ public ExecServerConfig getExecServerConfig(String objectKey) {
+ ExecServerConfig execServerConfig = null;
+ for (Iterator i = execServers.iterator(); i.hasNext() && execServerConfig == null;) {
+ ExecServerConfig exec = (ExecServerConfig) i.next();
+ if (objectKey.equals(exec.getObjectKey()))
+ execServerConfig = exec;
+ }
+ return execServerConfig;
+ }
+
+ /** Get the web server base URL.
+ *
+ * @return The base web server URL.
+ */
+ public String getWebServerBaseURL() {
+ String proto = System.getProperty(WEB_PROTOCOL_PROPERTY);
+ if (proto == null) {
+ if ("443".equals(webPort)) proto = "https";
+ else proto = "http";
+ }
+ return proto + "://" + webHost + ":" + webPort;
+ }
+
+ /** Get the web server document directory.
+ *
+ * @return The document directory.
+ */
+ public File getWebServerDocumentDirectory() {
+ return webServerDocumentDirectory;
+ }
+
+ /** Get the name server URL.
+ *
+ * @return The name server URL.
+ */
+ public String getNameServerURL() {
+ return getWebServerBaseURL() + "/ns.ior";
+ }
+
+ /** Get the name server port, if any.
+ *
+ * @return The port.
+ */
+ public String getNameServerPort() {
+ return nameServerPort;
+ }
+
+ /** Get the frequency with which the name server saves its state.
+ *
+ * @return The state-save frequency in milliseconds; <= 0 means never save state.
+ */
+ public int getNameServerStateFrequency() {
+ return nameServerStateFrequency;
+ }
+
+ /** Get the object context.
+ *
+ * @return The object context based on this configuration.
+ * @throws NamingException If the context can't be created.
+ */
+ public Context getObjectContext() throws NamingException {
+ Context c = null;
+ final String className = (String) contextEnvironment.get(javax.naming.Context.INITIAL_CONTEXT_FACTORY);
+ if (className == null)
+ c = new InitialContext(contextEnvironment);
+ else try {
+ // Work around iPlanet bug. JNDI uses the thread's context class
+ // loader to load the initial context factory class. For some
+ // reason, that loader fails to find things in iPlanet's
+ // classpath, such as the EDA initial context factory. Here, we
+ // cut a new thread and explicitly set its context class loader to
+ // the application class loader. When JNDI looks up the initial
+ // context factory, the thread's context class loader is the app
+ // class loader, which succeeds.
+ Class clazz = Class.forName(className);
+ final ClassLoader loader = clazz.getClassLoader();
+ InitialContextThread thread = new InitialContextThread(loader);
+ thread.start();
+ try {
+ thread.join();
+ } catch (InterruptedException ex) {
+ throw new NoInitialContextException("Initial context thread interrupted: " + ex.getMessage());
+ }
+ c = thread.getContext();
+ if (c == null)
+ throw thread.getException();
+ } catch (ClassNotFoundException ex) {
+ throw new NoInitialContextException("Class " + className + " not found");
+ }
+ return c;
+ }
+
+ /** Get the entity reference directories.
+ *
+ * @return A list of {@link java.lang.String}s naming directories for entity references.
+ */
+ public List getEntityRefDirs() {
+ List dirs = new ArrayList();
+ for (StringTokenizer t = new StringTokenizer(System.getProperty(ENTITY_DIRS_PROP, ""), ",;|"); t.hasMoreTokens();)
+ dirs.add(t.nextToken());
+ return dirs;
+ }
+
+ /** Get the port number on which the server manager is listening.
+ *
+ * @return The port number, or 0 if there is no server manager.
+ */
+ public int getServerMgrPort() {
+ return serverMgrPort;
+ }
+
+ /** Load the properties described in an XML properties element into the
+ * given properties object.
+ *
+ * @param propertiesNode The XML node which is a <code><properties></code> element.
+ * @param props The properties object to load with properties from <var>propertiesNode</var>.
+ */
+ static void loadProperties(Node propertiesNode, Properties props) {
+ NodeList children = propertiesNode.getChildNodes();
+ for (int i = 0; i < children.getLength(); i += 2) {
+ String key = XML.unwrappedText(children.item(i));
+ String value = XML.unwrappedText(children.item(i+1));
+ props.setProperty(key, value);
+ }
+ }
+
+ /** Dump the properties from the given properties object in XML form, appending
+ * them to the given node under a <properties> element.
+ *
+ * @param props The properties to dump in XML form.
+ * @param node The node to which to append the <properties> element.
+ * @throws DOMException If a DOM error occurs.
+ */
+ static void dumpProperties(Properties props, Node node) {
+ Element propertiesElement = node.getOwnerDocument().createElement("properties");
+ node.appendChild(propertiesElement);
+ for (Iterator i = props.entrySet().iterator(); i.hasNext();) {
+ Map.Entry entry = (Map.Entry) i.next();
+ XML.add(propertiesElement, "key", (String) entry.getKey());
+ XML.add(propertiesElement, "value", (String) entry.getValue());
+ }
+ }
+
+ /** Create a new XML document with the configuration DTD.
+ *
+ * @param name Name to give to the document element.
+ * @returns An XML DOM document with the doctype and the root document empty element in place.
+ * @throws DOMException If we can't create the document.
+ */
+ static Document createDocument(String documentElementName) throws DOMException {
+ DocumentType docType = XML.getDOMImplementation().createDocumentType(documentElementName, DTD_FPI, DTD_URL);
+ Document doc = XML.getDOMImplementation().createDocument(/*namespaceURI*/null, documentElementName, docType);
+ return doc;
+ }
+
+ /** The formal public identifier (FPI) of the configuration document type definition (DTD). */
+ public static final String DTD_FPI = "-//JPL//DTD EDA Configuration 1.0//EN";
+
+ /** The old formal public identifier (FPI) of the configuration document type definition (DTD). */
+ public static final String DTD_OLD_FPI = "-//JPL//DTD OODT Configuration 1.0//EN";
+
+ /** The system identifier of the configuration document type definition (DTD). */
+ public static final String DTD_URL = "http://oodt.jpl.nasa.gov/edm-commons/Configuration.dtd";
+
+ /** Name of the system property that names the web protocol to use. */
+ public static final String WEB_PROTOCOL_PROPERTY = "org.apache.oodt.commons.Configuration.webProtocol";
+
+ /** Global properties. */
+ private Properties properties = new Properties();
+
+ /** Object context environment. */
+ Hashtable contextEnvironment = new Hashtable();
+
+ /** Exec-servers. */
+ private List execServers = new ArrayList();
+
+ /** Web server host. */
+ private String webHost;
+
+ /** Web server port. */
+ private String webPort;
+
+ /** Web server doc dir. */
+ private File webServerDocumentDirectory;
+
+ /** Name server using rir protocol.
+ *
+ * If false, then it's using iiop.
+ */
+ private boolean nameServerUsingRIRProtocol;
+
+ /** Name server version. */
+ private String nameServerVersion;
+
+ /** Name server host. */
+ private String nameServerHost;
+
+ /** Name server port. */
+ private String nameServerPort;
+
+ /** Name server object key. */
+ private String nameServerObjectKey;
+
+ /** How often the name server saves its state. */
+ private int nameServerStateFrequency;
+
+ /** On what port the server manager will listen. */
+ private int serverMgrPort;
+
+ /** Thread to set a context class loader and get a JNDI initial context. */
+ private class InitialContextThread extends Thread {
+ /** Ctor
+ *
+ * @param loader What class loader to use as thread's context class loader.
+ */
+ public InitialContextThread(ClassLoader loader) {
+ setContextClassLoader(loader);
+ }
+
+ public void run() {
+ try {
+ context = new InitialContext(contextEnvironment);
+ } catch (NamingException ex) {
+ exception = ex;
+ } catch (Throwable t) {
+ System.err.println("Unexpected throwable " + t.getClass().getName() + " getting initial context: "
+ + t.getMessage());
+ t.printStackTrace();
+ }
+ }
+
+ /** Get the context.
+ *
+ * <strong>Warning!</strong> Do not call this method until the thread terminates.
+ *
+ * @return The context, or null if the context could not be retrieved.
+ */
+ public Context getContext() {
+ return context;
+ }
+
+ /** Get any exception.
+ *
+ * @return Any exception that occurred while retrieving the context.
+ */
+ public NamingException getException() {
+ return exception;
+ }
+
+ /** JNDI context. */
+ private Context context;
+
+ /** Any exception. */
+ private NamingException exception;
+ }
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfigurationEntityResolver.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfigurationEntityResolver.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfigurationEntityResolver.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfigurationEntityResolver.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,41 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.IOException;
+import org.xml.sax.EntityResolver;
+import org.xml.sax.InputSource;
+import org.xml.sax.SAXException;
+
+/** XML entity resolver for the configuration file.
+ *
+ * This resolver attempts to use a locally accessible configuration.dtd so that we can
+ * bootstrap enterprise applications without http access. You see, The config file
+ * specifies the list of entity directories, but the config file itself is an XML document
+ * that refers to its doctype entity. We therefore resolve the config DTD to a
+ * classpath-acessible copy.
+ *
+ * @author Kelly
+ */
+class ConfigurationEntityResolver implements EntityResolver {
+ public InputSource resolveEntity(String publicID, String systemID) throws SAXException, IOException {
+ if (Configuration.DTD_FPI.equals(publicID) || Configuration.DTD_OLD_FPI.equals(publicID))
+ return new InputSource(Configuration.class.getResourceAsStream("Configuration.dtd"));
+ return null;
+ }
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfiguredTestCase.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfiguredTestCase.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfiguredTestCase.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ConfiguredTestCase.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,79 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.BufferedInputStream;
+import junit.framework.TestCase;
+import org.xml.sax.InputSource;
+import java.io.InputStream;
+import java.io.IOException;
+import java.io.StringReader;
+
+/**
+ * Base test case for tests that need the Configuration object.
+ *
+ * @author Kelly
+ */
+public abstract class ConfiguredTestCase extends TestCase {
+ /**
+ * Creates a new {@link ConfiguredTestCase} instance.
+ *
+ * @param caseName Case name.
+ */
+ protected ConfiguredTestCase(String caseName) {
+ super(caseName);
+ }
+
+ /**
+ * Set up a test Configuration object.
+ *
+ * @throws Exception if an error occurs.
+ */
+ protected void setUp() throws Exception {
+ super.setUp();
+ if (Configuration.configuration == null) {
+ try {
+ StringReader reader = new StringReader(TSTDOC);
+ InputSource is = new InputSource(reader);
+ is.setEncoding("UTF-8");
+ is.setPublicId("-//JPL//XML EDM Test Configuration 0.0.0//EN");
+ is.setSystemId("internal:test-edarc.xml");
+ Configuration.configuration = new Configuration(is);
+ reader.close();
+ } catch (IOException ex) {
+ ex.printStackTrace();
+ throw new IllegalStateException("Unexpected IOException: " + ex.getMessage());
+ }
+ }
+ }
+
+ /** Test configuration, as a document. */
+ private static final String TSTDOC = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE configuration PUBLIC"
+ + " \"-//JPL//DTD EDA Configuration 1.0//EN\" \"http://oodt.jpl.nasa.gov/edm-commons/Configuration.dtd\">\n"
+ + "<configuration><webServer><host>www.jpl.nasa.gov</host><port>81</port><dir>/non/existent/htdocs</dir>"
+ + "</webServer><nameServer><iiop><version>1</version><host>oodt.jpl.nasa.gov</host><port>82</port>"
+ + "<objectKey>StandardNS/NameServer%2DPOA/_test</objectKey></iiop></nameServer><ldapServer>"
+ + "<host>ldap.jpl.nasa.gov</host><port>83</port><managerDN>cn=GeorgeTestostoles,dc=test,dc=zone</managerDN>"
+ + "<password>h1ghly;s3cr3t</password></ldapServer><xml><parser>crimson</parser><entityRef>"
+ + "<dir>/non/existent/htdocs/xml</dir><dir>/non/existent/htdocs/dtd</dir></entityRef></xml><serverMgr>"
+ + "<port>84</port></serverMgr><properties><key>global</key><value>1</value><key>override</key><value>2</value>"
+ + "</properties><programs><execServer><class>TestServer</class><objectKey>urn:eda:rmi:TestObject</objectKey>"
+ + "<host>oodt.jpl.nasa.gov</host><properties><key>local</key><value>3</value><key>override</key><value>4</value>"
+ + "</properties></execServer><client><class>TestClient</class><properties><key>local</key><value>5</value>"
+ + "<key>override</key><value>6</value></properties></client></programs></configuration>";
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/EDAException.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/EDAException.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/EDAException.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/EDAException.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,33 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+public class EDAException extends Exception {
+ public EDAException(String msg) {
+ super(msg);
+ }
+
+ public EDAException(Throwable cause) {
+ super(cause);
+ }
+
+ public EDAException(String msg, Throwable cause) {
+ super(msg, cause);
+ }
+}
+
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServer.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServer.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServer.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServer.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,474 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.*;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.net.*;
+import java.rmi.RMISecurityManager;
+import java.util.*;
+import javax.naming.Context;
+import javax.naming.NamingException;
+import org.apache.oodt.commons.io.Log;
+import org.apache.oodt.commons.util.*;
+import org.apache.xmlrpc.XmlRpcClientLite;
+import org.apache.xmlrpc.XmlRpcServer;
+import org.w3c.dom.*;
+import org.xml.sax.*;
+import java.rmi.Remote;
+import java.rmi.server.RemoteStub;
+import java.rmi.server.UnicastRemoteObject;
+import java.rmi.server.RemoteObject;
+import java.rmi.server.RemoteRef;
+import java.io.ObjectOutputStream;
+import java.io.ByteArrayOutputStream;
+import org.apache.oodt.commons.io.Base64EncodingOutputStream;
+
+/** Server execution program.
+ *
+ * This is an executable class that starts a JPL EDA server.
+ *
+ * @author Kelly
+ */
+public class ExecServer {
+ /** Start a server.
+ *
+ * The command-line should have two arguments:
+ *
+ * <ol>
+ * <li>The fully-qualified class name of the server to execute.</li>
+ * <li>The object name of the server to register with the naming service.</li>
+ * </ol>
+ *
+ * @param argv The command-line arguments
+ */
+ public static void main(String[] argv) {
+ if (argv.length < 2) {
+ System.err.println("Usage: class-name-of-server object-name");
+ System.exit(1);
+ }
+
+ String className = argv[0];
+ String name = argv[1];
+
+ // Enable support of our special URLs, like stdin:
+ System.setProperty("java.protocol.handler.pkgs", "org.apache.oodt.commons.net.protocol");
+
+ try {
+ // Get the configuration.
+ configuration = Configuration.getConfiguration();
+ configuration.mergeProperties(System.getProperties());
+
+ // Set up the logger.
+ LogInit.init(System.getProperties(), name);
+
+ // Run initializers
+ try {
+ runInitializers();
+ } catch (EDAException ex) {
+ ex.printStackTrace();
+ System.exit(1);
+ }
+
+ // Create it.
+ final ExecServer server = new ExecServer(name, className);
+
+ // Print it.
+ if (Boolean.getBoolean(PRINT_IOR_PROPERTY)) {
+ if (server.getServant() instanceof RemoteObject) {
+ RemoteObject remoteObject = (RemoteObject) server.getServant();
+ RemoteStub remoteStub = (RemoteStub) RemoteObject.toStub(remoteObject);
+ RemoteRef ref = remoteStub.getRef();
+ System.out.print("RMI:");
+ System.out.flush();
+ ObjectOutputStream objOut
+ = new ObjectOutputStream(new Base64EncodingOutputStream(System.out));
+ objOut.writeObject(ref);
+ objOut.flush();
+ System.out.println();
+ } else {
+ org.omg.PortableServer.Servant servant=(org.omg.PortableServer.Servant)server.getServant();
+ org.omg.CORBA.ORB orb = servant._orb();
+ System.out.println(orb.object_to_string(servant._this_object(orb)));
+ }
+ System.out.flush();
+ }
+
+ // Bind it.
+ if (!Boolean.getBoolean(DISABLE_BINDING)) {
+ binder = new Binder(name, server);
+ binder.start();
+ }
+
+ // Prepare for the inevitable
+ Runtime.getRuntime().addShutdownHook(new Thread() {
+ public void run() {
+ server.shutdown0();
+ }
+ });
+
+ // We're done here.
+ for (;;) try {
+ Thread.currentThread().join();
+ } catch (InterruptedException ignore) {}
+ } catch (IOException ex) {
+ System.err.println("I/O error during initialization: " + ex.getMessage());
+ ex.printStackTrace();
+ } catch (SAXParseException ex) {
+ System.err.println("Error in the configuration file at line " + ex.getLineNumber() + ", column "
+ + ex.getColumnNumber() + ": " + ex.getMessage());
+ } catch (SAXException ex) {
+ System.err.println("Error " + ex.getClass().getName() + " while attempting to parse the configuration"
+ + " file: " + ex.getMessage());
+ } catch (javax.naming.NamingException ex) {
+ System.err.println("Naming/directory error: " + ex.getClass().getName() + ": " + ex.getMessage());
+ } catch (java.lang.reflect.InvocationTargetException ex) {
+ Throwable target = ex.getTargetException();
+ System.err.println("Constructor for \"" + className + "\" threw " + target.getClass().getName() + ": "
+ + ex.getMessage());
+ target.printStackTrace();
+ } catch (RuntimeException ex) {
+ throw ex;
+ } catch (Exception ex) {
+ System.err.println("Exception " + ex.getClass().getName() + " initializing server \"" + name
+ + "\" with class \"" + className + "\": " + ex.getMessage());
+ ex.printStackTrace();
+ }
+ System.exit(1);
+ }
+
+ protected ExecServer(String name) {
+ this.name = name;
+ }
+
+ /** Create a new executable server.
+ *
+ * @param name Name of the server
+ * @param className Name of class that implements the server.
+ * @throws ClassNotFoundException If the class for <var>className</var> can't be found.
+ * @throws NoSuchMethodException If the constructor for <var>className</var> taking a single <code>ExecServer</code>
+ * can't be found.
+ * @throws InstantiationException If the class for <var>className</var> is abstract or is an interface.
+ * @throws IllegalAccessException If the class for <var>className</var> isn't public.
+ * @throws InvocationTargetException If an exception occurs in the constructor for <var>className</var>.
+ * @throws DOMException If the server's status document can't be created.
+ * @throws UnknownHostException If the local host name can't be determined.
+ */
+ public ExecServer(String name, String className) throws ClassNotFoundException, NoSuchMethodException,
+ InstantiationException, IllegalAccessException, InvocationTargetException, DOMException, UnknownHostException {
+ this.name = name;
+
+ // Find the class and the required constructor.
+ Class clazz = Class.forName(className);
+ Constructor ctor = clazz.getConstructor(new Class[]{ExecServer.class});
+
+ // Invoke the constructor to create the servant.
+ servant = ctor.newInstance(new Object[]{this});
+ Date startDate = new Date();
+
+ // Create the XML-RPC interface to this server.
+ xmlrpcServer = new XmlRpcServer();
+ xmlrpcServer.addHandler("server", this);
+
+ // Create the server status document.
+ DocumentType docType = XML.getDOMImplementation().createDocumentType("server", STATUS_FPI, STATUS_URL);
+ statusDocument = XML.getDOMImplementation().createDocument(/*namespaceURI*/null, "server", docType);
+ Element serverElement = statusDocument.getDocumentElement();
+ XML.add(serverElement, "name", name);
+ XML.add(serverElement, "class", className);
+ XML.add(serverElement, "state", "up");
+ Element startElement = statusDocument.createElement("start");
+ serverElement.appendChild(startElement);
+ Element userElement = statusDocument.createElement("user");
+ startElement.appendChild(userElement);
+ XML.add(userElement, "name", System.getProperty("user.name", "UNKNOWN"));
+ XML.add(userElement, "cwd", System.getProperty("user.dir", "UNKNOWN"));
+ XML.add(userElement, "home", System.getProperty("user.home", "UNKNOWN"));
+ Element dateElement = statusDocument.createElement("date");
+ startElement.appendChild(dateElement);
+ dateElement.setAttribute("ms", String.valueOf(startDate.getTime()));
+ dateElement.appendChild(statusDocument.createTextNode(startDate.toString()));
+ XML.add(startElement, "config", System.getProperty("org.apache.oodt.commons.Configuration.url", "UNKNOWN"));
+ Element hostElement = statusDocument.createElement("host");
+ serverElement.appendChild(hostElement);
+ XML.add(hostElement, "name", InetAddress.getLocalHost().getHostName());
+ Element osElement = statusDocument.createElement("os");
+ hostElement.appendChild(osElement);
+ XML.add(osElement, "name", System.getProperty("os.name", "UNKNOWN"));
+ XML.add(osElement, "version", System.getProperty("os.version", "UNKNOWN"));
+ XML.add(osElement, "arch", System.getProperty("os.arch", "UNKNOWN"));
+ Element vmElement = statusDocument.createElement("vm");
+ serverElement.appendChild(vmElement);
+ XML.add(vmElement, "name", System.getProperty("java.vm.name", "UNKNOWN"));
+ XML.add(vmElement, "version", System.getProperty("java.version", "UNKNOWN"));
+ XML.add(vmElement, "classpath", System.getProperty("java.class.path", "UNKNOWN"));
+ XML.add(vmElement, "extdirs", System.getProperty("java.ext.dirs", "UNKNOWN"));
+ logElement = statusDocument.createElement("log");
+ serverElement.appendChild(logElement);
+ }
+
+ /** Get my name.
+ *
+ * @return The name under which I'm registered in teh naming context.
+ */
+ public String getName() {
+ return name;
+ }
+
+ /** Return the servant for this executable server.
+ *
+ * @return The servant.
+ */
+ public Object getServant() {
+ return servant;
+ }
+
+ /** Control this server.
+ *
+ * @param command Command to send to the server.
+ * @return Results of <var>command</var>.
+ */
+ public byte[] control(byte[] command) {
+ return xmlrpcServer.execute(new ByteArrayInputStream(command));
+ }
+
+ /** Return the server's class name.
+ *
+ * @return Its class name.
+ */
+ public String getServerClassName() {
+ return className;
+ }
+
+ /** Return status of this server.
+ *
+ * @return Its status.
+ */
+ public String getServerStatus() {
+ // Update the status document with the current log.
+ for (Iterator i = LogInit.MEMORY_LOGGER.getMessages().iterator(); i.hasNext();) {
+ String message = (String) i.next();
+ Element messageElement = statusDocument.createElement("message");
+ messageElement.setAttribute("xml:space", "preserve");
+ messageElement.appendChild(statusDocument.createTextNode(message));
+ logElement.appendChild(messageElement);
+ }
+
+ // Serialize the document.
+ String rc = XML.serialize(statusDocument);
+
+ // Remove all the log messages from the document.
+ NodeList children = logElement.getChildNodes();
+ for (int i = 0; i < children.getLength(); ++i)
+ logElement.removeChild(children.item(i));
+
+ // Return the serialized form, which included the log messages.
+ System.err.println(rc);
+ return rc;
+ }
+
+ /** Set a system property.
+ *
+ * This uses the property manager to notify property change listeners.
+ *
+ * @param key Property's name.
+ * @param value New value.
+ * @return Zero (return required for XML-RPC access).
+ */
+ public int setSystemProperty(String key, String value) {
+ System.err.println("Setting system property \"" + key + "\" to \"" + value + "\"");
+ PropertyMgr.setProperty(key, value);
+ return 0;
+ }
+
+ /**
+ * Call the server manager on the local system.
+ *
+ * @param port What port on the local system the server manager is listening.
+ * @param user User name to use for authentication.
+ * @param password Authenticator for <var>user</var>.
+ * @param method What method in the server manager to call.
+ * @param params Parameters to pass to the method named by <var>method</var>.
+ * @return The return value from the method named by <var>method</var>.
+ * @throws Exception If any error occurs.
+ */
+ public Object callLocalServerManager(int port, String user, String password, String method, List params) throws Exception {
+ XmlRpcClientLite local = new XmlRpcClientLite("localhost", port);
+ local.setBasicAuthentication(user, password);
+ return local.execute(method, new Vector(params));
+ }
+
+ /** Shut down and exit.
+ *
+ * @return Zero.
+ */
+ public int shutdown() {
+ // Log it.
+ System.err.println("Received shutdown command");
+
+ // Make sure we actually exit sometime soon.
+ new Thread() {
+ public void run() {
+ try {
+ Thread.sleep(15000);
+ } catch (InterruptedException ignore) {}
+ System.exit(1);
+ }
+ }.start();
+
+ // Clean up.
+ shutdown0();
+
+ // And exit.
+ System.err.println("Calling System.exit with status code 0");
+ System.exit(0);
+ return 0;
+ }
+
+ private void shutdown0() {
+ // Unbind.
+ if (!Boolean.getBoolean(DISABLE_BINDING)) try {
+ binder.stopBinding();
+ Context objectContext = configuration.getObjectContext();
+ objectContext.unbind(getName());
+ objectContext.close();
+ } catch (NamingException ignore) {}
+
+ // Kill the ORB. YEAH! KILL IT, KILL IT, KIIIIIIIIIIIIIIL IIIIIIIIT!!!!!!!1
+ try {
+ if (servant instanceof org.omg.PortableServer.Servant) {
+ org.omg.PortableServer.Servant s = (org.omg.PortableServer.Servant) servant;
+ org.omg.CORBA.ORB orb = s._orb();
+ orb.shutdown(false/*=>terminate without waiting for reqs to complete*/);
+ }
+ } catch (Throwable ignore) {}
+ }
+
+ /**
+ * Binding thread.
+ */
+ private static class Binder extends Thread {
+ public Binder(String name, ExecServer server) {
+ super("Binder for " + name);
+ setDaemon(true);
+ this.name = name;
+ this.server = server;
+ keepBinding = true;
+ }
+ public void run() {
+ while (shouldKeepBinding()) try {
+ Context objectContext = configuration.getObjectContext();
+ objectContext.rebind(name, server.getServant());
+ objectContext.close();
+ } catch (Throwable ex) {
+ System.err.println("Exception binding at " + new Date() + "; will keep trying...");
+ ex.printStackTrace();
+ } finally {
+ try {
+ Thread.sleep(REBIND_PERIOD);
+ } catch (InterruptedException ignore) {}
+ }
+ }
+ public synchronized void stopBinding() {
+ keepBinding = false;
+ }
+ private synchronized boolean shouldKeepBinding() {
+ return keepBinding;
+ }
+ private boolean keepBinding;
+ private String name;
+ private ExecServer server;
+ }
+
+ /**
+ * Run all initializers.
+ *
+ * This instantiates and calls the {@link Initializer#initialize} method of each
+ * initializer specified by class name in a comma separated list of classes in the
+ * system properties. The property name is <code>org.apache.oodt.commons.initializers</code>, or
+ * if not defined, <code>org.apache.oodt.commons.ExecServer.initializers</code>, or if not
+ * defined, <code>initializers</code>. And if that one's not defined, then none
+ * are run.
+ *
+ * @throws EDAException if an error occurs.
+ */
+ public static void runInitializers() throws EDAException {
+ String initList = System.getProperty("org.apache.oodt.commons.initializers",
+ System.getProperty("org.apache.oodt.commons.ExecServer.initializers", System.getProperty("initializers", "")));
+ for (Iterator i = org.apache.oodt.commons.util.Utility.parseCommaList(initList); i.hasNext();) {
+ String iname = (String) i.next();
+ try {
+ Class initClass = Class.forName(iname);
+ Initializer init = (Initializer) initClass.newInstance();
+ init.initialize();
+ } catch (ClassNotFoundException ex) {
+ System.err.println("Initializer \"" + iname + "\" not found; aborting");
+ throw new EDAException(ex);
+ } catch (InstantiationException ex) {
+ System.err.println("Initializer \"" + iname + "\" is abstract; aborting");
+ throw new EDAException(ex);
+ } catch (IllegalAccessException ex) {
+ System.err.println("Initializer \"" + iname + "\" isn't public; aborting");
+ throw new EDAException(ex);
+ } catch (EDAException ex) {
+ System.err.println("Initializer \"" + iname + "\" failed: " + ex.getMessage());
+ throw new EDAException(ex);
+ }
+ }
+ }
+
+ /** The configuration. */
+ private static Configuration configuration;
+
+ /** Object key name. */
+ protected String name;
+
+ /** The servant. */
+ private Object servant;
+
+ /** The server class name. */
+ private String className;
+
+ /** Current binder, if any. */
+ private static Binder binder;
+
+ /** Server's status document. */
+ private Document statusDocument;
+
+ /** The <log> element within the status document. */
+ private Element logElement;
+
+ /** The XML-RPC interface to this server. */
+ private XmlRpcServer xmlrpcServer;
+
+ /** Status DTD formal public identifier. */
+ public static final String STATUS_FPI = "-//JPL//DTD EDA Server Status 1.0";
+
+ /** Status DTD system identifier. */
+ public static final String STATUS_URL = "http://oodt.jpl.nasa.gov/edm-commons/xml/serverStatus.dtd";
+
+ /** Name of the property that prints the server's IOR or RMI handle. */
+ public static final String PRINT_IOR_PROPERTY = "org.apache.oodt.commons.ExecServer.printIOR";
+
+ /** Name of the property that prevents binding of this object with the naming service. */
+ public static final String DISABLE_BINDING = "org.apache.oodt.commons.ExecServer.disableBinding";
+
+ /** How long to wait before bind attempts, in ms. */
+ private static final long REBIND_PERIOD = Long.getLong("org.apache.oodt.commons.ExecServer.rebindPeriod", 30*60*1000).longValue();
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServerConfig.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServerConfig.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServerConfig.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/ExecServerConfig.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,192 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.*;
+import java.net.InetAddress;
+import java.net.UnknownHostException;
+import java.util.*;
+import org.apache.oodt.commons.util.Documentable;
+import org.apache.oodt.commons.util.XML;
+import org.w3c.dom.DOMException;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.Node;
+import org.w3c.dom.NodeList;
+import org.xml.sax.SAXException;
+
+/** Configuration for an EDA exec-server.
+ *
+ * @author Kelly
+ */
+public class ExecServerConfig extends Executable implements Documentable {
+ /** Create an exec-server configuration.
+ *
+ * @param className Name of the class to execute.
+ * @param objectKey Object key under which class will register.
+ * @param properties Properties for the server.
+ */
+ public ExecServerConfig(String className, String objectKey, InetAddress preferredHost, Properties properties) {
+ this.className = className;
+ this.objectKey = objectKey;
+ this.preferredHost = preferredHost;
+ this.properties = properties;
+ }
+
+ /** Create an exec-server configuration.
+ *
+ * @param xml XML DOM description, must be an <execServer> element.
+ * @throws SAXException If <var>xml</var> is invalid.
+ * @throws UnknownHostException If the <var>xml</var> refers to an unknown host name.
+ */
+ public ExecServerConfig(Node xml) throws SAXException, UnknownHostException {
+ properties = new Properties();
+ preferredHost = org.apache.oodt.commons.net.Net.getLoopbackAddress();
+ NodeList children = xml.getChildNodes();
+ className = XML.unwrappedText(children.item(0));
+ objectKey = XML.unwrappedText(children.item(1));
+ for (int i = 2; i < children.getLength(); ++i) {
+ Node child = children.item(i);
+ String name = child.getNodeName();
+ if ("host".equals(name))
+ preferredHost = InetAddress.getByName(XML.unwrappedText(children.item(2)));
+ else if ("properties".equals(name))
+ Configuration.loadProperties(child, properties);
+ else throw new SAXException("Unknown node " + name + " in exec server XML");
+ }
+ }
+
+ /** Create an exec-server configuration.
+ *
+ * @param xml Serialized XML description.
+ * @throws SAXException If we can't parse <var>xml</var>.
+ * @throws UnknownHostException If the <var>xml</var> refers to an unknown host name.
+ */
+ public ExecServerConfig(String xml) throws SAXException, UnknownHostException {
+ this(XML.parse(xml).getDocumentElement());
+ }
+
+ protected String[] getCommandLine() {
+ String[] commandLine = new String[6 + properties.size()];
+ commandLine[0] = "java";
+ commandLine[1] = "-Xms" + initialHeap;
+ commandLine[2] = "-Xmx" + maxHeap;
+ int index = 3;
+ for (Iterator i = properties.entrySet().iterator(); i.hasNext();) {
+ Map.Entry entry = (Map.Entry) i.next();
+ commandLine[index++] = "-D" + entry.getKey() + "=" + entry.getValue();
+ }
+ commandLine[index++] = "org.apache.oodt.commons.ExecServer";
+ commandLine[index++] = className;
+ commandLine[index++] = objectKey;
+ return commandLine;
+ }
+
+ /** Get the class name I'm going to execute.
+ *
+ * @return The class name.
+ */
+ public String getClassName() {
+ return className;
+ }
+
+ /** Get the object key I'm going to use.
+ *
+ * @return The object key.
+ */
+ public String getObjectKey() {
+ return objectKey;
+ }
+
+ /** Get the properties for my process.
+ *
+ * @return The properties.
+ */
+ public Properties getProperties() {
+ return properties;
+ }
+
+ /** Get the preferred host.
+ *
+ * @return The host on which this server prefers to run.
+ */
+ public InetAddress getPreferredHost() {
+ return preferredHost;
+ }
+
+ public int hashCode() {
+ return className.hashCode() ^ objectKey.hashCode() ^ properties.hashCode();
+ }
+
+ public boolean equals(Object rhs) {
+ if (rhs == this) return true;
+ if (rhs == null || !(rhs instanceof ExecServerConfig)) return false;
+ ExecServerConfig obj = (ExecServerConfig) rhs;
+ return className.equals(obj.className) && objectKey.equals(obj.objectKey) && properties.equals(obj.properties);
+ }
+
+ public String toString() {
+ return className + " " + objectKey;
+ }
+
+ public Node toXML(Document doc) throws DOMException {
+ Element execServerElement = doc.createElement("execServer");
+ XML.add(execServerElement, "class", getClassName());
+ XML.add(execServerElement, "objectKey", getObjectKey());
+ XML.add(execServerElement, "preferredHost", getPreferredHost().toString());
+ Configuration.dumpProperties(getProperties(), execServerElement);
+ return execServerElement;
+ }
+
+ /** Yield this exce-server configuration as serialized XML.
+ *
+ * @return This object as a string serialized XML document.
+ * @throws DOMException If we can't create the XML document.
+ */
+ public String toXML() throws DOMException {
+ Document doc = Configuration.createDocument("execServer");
+ doc.replaceChild(toXML(doc), doc.getDocumentElement());
+ return XML.serialize(doc);
+ }
+
+ /** Class name for the ExecServer to execute. */
+ private String className;
+
+ /** Instance name. */
+ private String objectKey;
+
+ /** Properties for the server. */
+ private Properties properties;
+
+ /** Preferred host. */
+ private InetAddress preferredHost;
+
+ /** Initial heap size. */
+ private static String initialHeap;
+
+ /** Max heap size. */
+ private static String maxHeap;
+
+ /** Initialize the heap sizes. */
+ static {
+ Properties props = new Properties();
+ org.apache.oodt.commons.util.Utility.loadProperties(props, ExecServerConfig.class, "ExecServerConfig.properties");
+ initialHeap = props.getProperty("initialHeap", "32m");
+ maxHeap = props.getProperty("maxHeap", "128m");
+ }
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Executable.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Executable.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Executable.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Executable.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,116 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+import java.io.*;
+import java.util.*;
+
+/** An executable object.
+ *
+ * Objects of this class are programs that can be executed asynchronously. Their standard
+ * output and standard error streams are shared with the parent process' standard output
+ * and error streams.
+ *
+ * @author Kelly
+ */
+public abstract class Executable {
+ /** Construct an executable.
+ */
+ public Executable() {}
+
+ /** Get the command-line.
+ *
+ * @return Command-line.
+ */
+ protected abstract String[] getCommandLine();
+
+ /** Start executing this program.
+ *
+ * If any error occurs while launching the program, this method notes a message to
+ * stderr, but otherwise takes no further action.
+ */
+ public void execute() {
+ // We force program execution to be asynchronous by cutting a new thread.
+ new Thread() {
+ public void run() {
+ try {
+ process = Runtime.getRuntime().exec(getCommandLine());
+
+ // Read all output (standard and error output)
+ // from the process and pass it to the user.
+ redirect(process.getErrorStream(), System.err);
+ redirect(process.getInputStream(), System.out);
+ } catch (IOException ex) {
+ System.err.println("Can't execute command \"" + getCommandLine()[0] + "\": "
+ + ex.getMessage());
+ }
+ }
+
+ /** Redirect the given input onto the given output.
+ *
+ * @param in The stream to read.
+ * @param out Where to write it.
+ */
+ private void redirect(final InputStream in, final OutputStream out) {
+ // Do this in the background, too.
+ new Thread() {
+ public void run() {
+ try {
+ byte[] buf = new byte[1024];
+ for (;;) {
+ int numRead = in.read(buf);
+ if (numRead == -1) {
+ in.close();
+ break;
+ }
+ out.write(buf, 0, numRead);
+ }
+ } catch (IOException ex) {
+ try {
+ in.close();
+ } catch (IOException ignore) {}
+ }
+ }
+ }.start();
+ }
+ }.start();
+
+ // Spin until the process field is set.
+ while (process == null)
+ Thread.yield();
+ }
+
+ /** Wait for the process to terminate.
+ *
+ * @throws InterruptedException If the thread waiting for the termination is interrupted.
+ * @return The exit value of the process.
+ */
+ public int waitFor() throws InterruptedException {
+ return process.waitFor();
+ }
+
+ /** Terminate this process.
+ */
+ public void terminate() {
+ process.destroy();
+ }
+
+ /** The process backing this executable. */
+ protected Process process;
+
+}
Added: incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Initializer.java
URL: http://svn.apache.org/viewvc/incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Initializer.java?rev=964248&view=auto
==============================================================================
--- incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Initializer.java (added)
+++ incubator/oodt/trunk/commons/src/main/java/org/apache/oodt/commons/Initializer.java Wed Jul 14 23:02:32 2010
@@ -0,0 +1,33 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.oodt.commons;
+
+/**
+ * Initializer for an enterprise application.
+ *
+ * @author Kelly
+ * @version $Revision: 1.1.1.1 $
+ */
+public interface Initializer {
+ /**
+ * Initialize the appliction.
+ *
+ * @throws EDAException if an error occurs.
+ */
+ void initialize() throws EDAException;
+}