diff options
-rw-r--r-- | ChangeLog | 28 | ||||
-rw-r--r-- | netx/net/sourceforge/jnlp/ShortcutDesc.java | 12 | ||||
-rw-r--r-- | netx/net/sourceforge/jnlp/resources/Messages.properties | 1 | ||||
-rw-r--r-- | netx/net/sourceforge/jnlp/runtime/DeploymentConfiguration.java | 596 | ||||
-rw-r--r-- | netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java | 23 |
5 files changed, 660 insertions, 0 deletions
@@ -1,5 +1,33 @@ 2010-10-25 Omair Majid <[email protected]> + * netx/net/sourceforge/jnlp/ShortcutDesc.java: + Add SHORTCUT_NEVER, SHORTCUT_ALWAYS, SHORTCUT_ASK_USER, + SHORTCUT_ASK_USER_IF_HINTED, SHORTCUT_ALWAYS_IF_HINTED, + SHORTCUT_DEFAULT. + * netx/net/sourceforge/jnlp/resources/Messages.properties: + Add RConfigurationError. + * netx/net/sourceforge/jnlp/runtime/DeploymentConfiguration.java: + New file. + (ConfigValue): New class. Holds a configuration value. + (DeploymentConfiguration): New method. + (load): New method. + (getProperty): Likewise. + (getAllPropertyNames): Likewise. + (setProperty): Likewise. + (loadDefaultProperties): Likewise. + (findSystemConfigFile): Likewise. + (loadSystemConfiguration): Likewise. + (loadProperties): Likewise. + (save): Likewise. + (parsePropertiesFile): Likewise. + (mergeMaps): Likewise. + (dumpConfiguration): Likewise. + * netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java: + (initialize): Load configuration. + (getConfiguration): Return the configuration. + +2010-10-25 Omair Majid <[email protected]> + * net/sourceforge/jnlp/ExtensionDesc.java: Import Translator.R and use that. * net/sourceforge/jnlp/JNLPFile.java: Import Translator.R. diff --git a/netx/net/sourceforge/jnlp/ShortcutDesc.java b/netx/net/sourceforge/jnlp/ShortcutDesc.java index 6635dc7..66367bb 100644 --- a/netx/net/sourceforge/jnlp/ShortcutDesc.java +++ b/netx/net/sourceforge/jnlp/ShortcutDesc.java @@ -18,6 +18,18 @@ package net.sourceforge.jnlp; public final class ShortcutDesc { + /** Never create a shortcut */ + public static final String SHORTCUT_NEVER = "NEVER"; + /** Always create a shortcut */ + public static final String SHORTCUT_ALWAYS = "ALWAYS"; + /** Always ask user whether to create a shortcut */ + public static final String SHORTCUT_ASK_USER = "ASK_USER"; + /** Ask user whether to create a shortcut but only if jnlp file asks for it */ + public static final String SHORTCUT_ASK_USER_IF_HINTED = "ASK_IF_HINTED"; + /** Create a desktop shortcut without prompting if the jnlp asks for it */ + public static final String SHORTCUT_ALWAYS_IF_HINTED = "ALWAYS_IF_HINTED"; + public static final String SHORTCUT_DEFAULT = SHORTCUT_ASK_USER_IF_HINTED; + /** the application wants to be placed on the desktop */ private boolean onDesktop = false; diff --git a/netx/net/sourceforge/jnlp/resources/Messages.properties b/netx/net/sourceforge/jnlp/resources/Messages.properties index a962916..4312ea6 100644 --- a/netx/net/sourceforge/jnlp/resources/Messages.properties +++ b/netx/net/sourceforge/jnlp/resources/Messages.properties @@ -119,6 +119,7 @@ RExitNoApp=Can not exit the JVM because the current application cannot be determ RNoLockDir=Unable to create locks directory ({0})
RNestedJarExtration=Unable to extract nested jar.
RUnexpected=Unexpected {0} at {1}
+RConfigurationError=Fatal error while reading the configuration
# Boot options, message should be shorter than this ---------------->
BOUsage=javaws [-run-options] <jnlp file>
diff --git a/netx/net/sourceforge/jnlp/runtime/DeploymentConfiguration.java b/netx/net/sourceforge/jnlp/runtime/DeploymentConfiguration.java new file mode 100644 index 0000000..abfcd1c --- /dev/null +++ b/netx/net/sourceforge/jnlp/runtime/DeploymentConfiguration.java @@ -0,0 +1,596 @@ +// Copyright (C) 2010 Red Hat, Inc. +// +// This library is free software; you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public +// License as published by the Free Software Foundation; either +// version 2.1 of the License, or (at your option) any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public +// License along with this library; if not, write to the Free Software +// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + + +package net.sourceforge.jnlp.runtime; + +import java.io.BufferedOutputStream; +import java.io.BufferedReader; +import java.io.File; +import java.io.FileOutputStream; +import java.io.FileReader; +import java.io.IOException; +import java.io.OutputStream; +import java.io.PrintStream; +import java.io.Reader; +import java.net.MalformedURLException; +import java.net.URL; +import java.util.HashMap; +import java.util.Map; +import java.util.Properties; +import java.util.Set; + +import javax.naming.ConfigurationException; + +import net.sourceforge.jnlp.ShortcutDesc; + +/** + * Manages the various properties and configuration related to deployment. + * + * See: + * http://download.oracle.com/javase/1.5.0/docs/guide/deployment/deployment-guide/properties.html + */ +public final class DeploymentConfiguration { + + /** + * Represents a value for a configuration. Provides methods to get the value + * as well as marking the value as locked. + */ + private final class ConfigValue { + + private String value; + private boolean locked; + + ConfigValue(String value) { + this(value, false); + } + + ConfigValue(String value, boolean locked) { + this.value = value; + this.locked = locked; + } + + ConfigValue(ConfigValue other) { + this(other.value, other.locked); + } + + String get() { + return value; + } + + /** + * Note that setting the value is not enforced - it is the caller's + * responsibility to check if a value is locked or not before setting a + * new value + * + * @param value the new value + */ + void set(String value) { + this.value = value; + } + + /** + * @return true if the value has been marked as locked + */ + boolean isLocked() { + return locked; + } + + /** + * Mark a value as locked + * @param locked + */ + void setLocked(boolean locked) { + this.locked = locked; + } + } + + public static final String DEPLOYMENT_DIR = ".netx"; + public static final String DEPLOYMENT_CONFIG = "deployment.config"; + public static final String DEPLOYMENT_PROPERTIES = "deployment.properties"; + + public static final String DEPLOYMENT_COMMENT = "Netx deployment configuration"; + + public static final int JNLP_ASSOCIATION_NEVER = 0; + public static final int JNLP_ASSOCIATION_NEW_ONLY = 1; + public static final int JNLP_ASSOCIATION_ASK_USER = 2; + public static final int JNLP_ASSOCIATION_REPLACE_ASK = 3; + + /* + * FIXME these should be moved into JavaConsole, but there is a strange + * dependency in the build system. First all of netx is built. Then the + * plugin is built. So we cannot refer to plugin code in here :( + */ + public static final String CONSOLE_HIDE = "HIDE"; + public static final String CONSOLE_SHOW = "SHOW"; + public static final String CONSOLE_DISABLE = "DISABLE"; + + /* FIXME these should be moved into the proxy class */ + public static final int PROXY_TYPE_UNKNOWN = -1; + public static final int PROXY_TYPE_NONE = 0; + public static final int PROXY_TYPE_MANUAL = 1; + public static final int PROXY_TYPE_AUTO = 2; + public static final int PROXY_TYPE_BROWSER = 3; + + public enum ConfigType { + System, User + } + + /** is it mandatory to load the system properties? */ + private boolean systemPropertiesMandatory = false; + + /** The system's deployment.config file */ + private File systemPropertiesFile = null; + /** The user's deployment.config file */ + private File userPropertiesFile = null; + + /** the current deployment properties */ + private Map<String, ConfigValue> currentConfiguration; + + /** the deployment properties that cannot be changed */ + private Map<String, ConfigValue> unchangeableConfiguration; + + public DeploymentConfiguration() { + currentConfiguration = new HashMap<String,ConfigValue>(); + unchangeableConfiguration = new HashMap<String, ConfigValue>(); + } + + /** + * Initialize this deployment configuration by reading configuration files. + * Generally, it will try to continue and ignore errors it finds (such as file not found). + * + * @throws DeploymentException if it encounters a fatal error. + */ + public void load() throws ConfigurationException { + Map<String, ConfigValue> initialProperties = loadDefaultProperties(); + + Map<String, ConfigValue> systemProperties = null; + + /* + * First, try to read the system's deployment.config file to find if + * there is a system-level deployment.poperties file + */ + + File systemConfigFile = findSystemConfigFile(); + if (systemConfigFile != null) { + if (loadSystemConfiguration(systemConfigFile)) { + if (JNLPRuntime.isDebug()) { + System.out.println("System level " + DEPLOYMENT_CONFIG + " is mandatory: " + systemPropertiesMandatory); + } + /* Second, read the System level deployment.properties file */ + systemProperties = loadProperties(ConfigType.System, systemPropertiesFile, + systemPropertiesMandatory); + } + if (systemProperties != null) { + mergeMaps(initialProperties, systemProperties); + } + } + + /* need a copy of the original when we have to save */ + unchangeableConfiguration = new HashMap<String, ConfigValue>(); + Set<String> keys = initialProperties.keySet(); + for (String key : keys) { + unchangeableConfiguration.put(key, new ConfigValue(initialProperties.get(key))); + } + + /* + * Third, read the user's deployment.properties file + */ + userPropertiesFile = new File(System.getProperty("user.home") + File.separator + ".netx" + + File.separator + DEPLOYMENT_PROPERTIES); + Map<String, ConfigValue> userProperties = loadProperties(ConfigType.User, userPropertiesFile, + false); + if (userProperties != null) { + mergeMaps(initialProperties, userProperties); + } + + currentConfiguration = initialProperties; + } + + /** + * Get the value for the given key + * + * @param key the property key + * @return the value for the key, or null if it can not be found + */ + public String getProperty(String key) { + SecurityManager sm = System.getSecurityManager(); + if (sm != null) { + if (userPropertiesFile != null) { + sm.checkRead(userPropertiesFile.toString()); + } + } + + return currentConfiguration.get(key).get(); + } + + /** + * @return a Set containing all the property names + */ + public Set<String> getAllPropertyNames() { + SecurityManager sm = System.getSecurityManager(); + if (sm != null) { + if (userPropertiesFile != null) { + sm.checkRead(userPropertiesFile.toString()); + } + } + + return currentConfiguration.keySet(); + } + + /** + * Sets the value of corresponding to the key. If the value has been marked + * as locked, it is not changed + * + * @param key the key + * @param value the value to be associated with the key + */ + public void setProperty(String key, String value) { + SecurityManager sm = System.getSecurityManager(); + if (sm != null) { + if (userPropertiesFile != null) { + sm.checkWrite(userPropertiesFile.toString()); + } + } + + ConfigValue currentValue = currentConfiguration.get(key); + if (currentValue != null) { + if (!currentValue.isLocked()) { + currentValue.set(value); + } + } else { + currentValue = new ConfigValue(value); + currentConfiguration.put(key, currentValue); + } + } + + /** + * Loads the default properties for deployment + */ + private Map<String, ConfigValue> loadDefaultProperties() { + + final String SYSTEM_HOME = System.getProperty("java.home"); + final String SYSTEM_SECURITY = SYSTEM_HOME + File.separator + "lib" + File.separator + + "security"; + + final String USER_HOME = System.getProperty("user.home") + File.separator + DEPLOYMENT_DIR; + final String USER_SECURITY = USER_HOME + File.separator + "security"; + + /* + * This is more or less a straight copy from the deployment + * configuration page, with occasional replacements of "" or no-defaults + * with null + */ + + String[][] defaults = new String[][] { + /* infrastructure */ + { "deployment.user.cachedir", USER_HOME + File.separator + "cache" }, + { "deployment.system.cachedir", null }, + { "deployment.user.logdir", USER_HOME + File.separator + "log" }, + { "deployment.user.tmp", USER_HOME + File.separator + "tmp" }, + /* certificates and policy files */ + { "deployment.user.security.policy", "file://" + USER_SECURITY + File.separator + "java.policy" }, + { "deployment.user.security.trusted.cacerts", USER_SECURITY + File.separator + "trusted.cacerts" }, + { "deployment.user.security.trusted.jssecacerts", USER_SECURITY + File.separator + "trusted.jssecacerts" }, + { "deployment.user.security.trusted.certs", USER_SECURITY + File.separator + "trusted.certs" }, + { "deployment.user.security.trusted.jssecerts", USER_SECURITY + File.separator + "trusted.jssecerts"}, + { "deployment.user.security.trusted.clientauthcerts", USER_SECURITY + File.separator + "trusted.clientcerts" }, + { "deployment.system.security.policy", null }, + { "deployment.system.security.cacerts", SYSTEM_SECURITY + File.separator + "cacerts" }, + { "deployment.system.security.jssecacerts", SYSTEM_SECURITY + File.separator + "jssecacerts" }, + { "deployment.system.security.trusted.certs", SYSTEM_SECURITY + File.separator + "trusted.certs" }, + { "deployment.system.security.trusted.jssecerts", SYSTEM_SECURITY + File.separator + "trusted.jssecerts" }, + { "deployment.system.security.trusted.clientautcerts", SYSTEM_SECURITY + File.separator + "trusted.clientcerts" }, + /* security access and control */ + { "deployment.security.askgrantdialog.show", String.valueOf(true) }, + { "deployment.security.askgrantdialog.notinca", String.valueOf(true) }, + { "deployment.security.notinca.warning", String.valueOf(true) }, + { "deployment.security.expired.warning", String.valueOf(true) }, + { "deployment.security.jsse.hostmismatch.warning", String.valueOf(true) }, + { "deployment.security.trusted.policy", null }, + { "deployment.security.sandbox.awtwarningwindow", String.valueOf(true) }, + { "deployment.security.sandbox.jnlp.enhanced", String.valueOf(true) }, + { "deployment.security.authenticator", String.valueOf(true) }, + /* networking */ + { "deployment.proxy.type", String.valueOf(PROXY_TYPE_BROWSER) }, + { "deployment.proxy.same", String.valueOf(false) }, + { "deployment.proxy.auto.config.url", null }, + { "deployment.proxy.bypass.list", null }, + { "deployment.proxy.bypass.local", null }, + { "deployment.proxy.http.host", null }, + { "deployment.proxy.http.port", null }, + { "deployment.proxy.https.host", null }, + { "deployment.proxy.https.port", null }, + { "deployment.proxy.ftp.host", null }, + { "deployment.proxy.ftp.port", null }, + { "deployment.proxy.socks.host", null }, + { "deployment.proxy.socks.port", null }, + { "deployment.proxy.override.hosts", null }, + /* cache and optional package repository */ + { "deployment.cache.max.size", String.valueOf("-1") }, + { "deployment.cache.jarcompresson", String.valueOf(0) }, + { "deployment.javapi.cache.enabled", String.valueOf(false) }, + /* java console */ + { "deployment.console.startup.mode", CONSOLE_HIDE }, + /* tracing and logging */ + { "deployment.trace", String.valueOf(false) }, + { "deployment.log", String.valueOf(false) }, + /* JNLP association */ + { "deployment.javaws.associations", String.valueOf(JNLP_ASSOCIATION_ASK_USER) }, + /* desktop integration */ + { "deployment.javaws.shortcut", ShortcutDesc.SHORTCUT_ASK_USER_IF_HINTED}, + /* jre selection */ + { "deployment.javaws.installURL", null }, + /* jre management */ + { "deployment.javaws.autodownload", null }, + /* browser selection */ + { "deployment.browser.path", null }, + /* check for update timeout */ + { "deployment.javaws.update.timeout", String.valueOf(500) } + }; + + HashMap<String, ConfigValue> result = new HashMap<String, ConfigValue>(); + for (int i = 0; i < defaults.length; i++) { + String key = defaults[i][0]; + String actualValue = defaults[i][1]; + boolean locked = false; + ConfigValue value = new ConfigValue(actualValue, locked); + result.put(key, value); + } + + return result; + } + + /** + * @return the location of system-level deployment.config file, or null if none can be found + */ + private File findSystemConfigFile() { + File etcFile = new File(File.separator + "etc" + File.separator + ".java" + File.separator + + "deployment" + File.separator + DEPLOYMENT_CONFIG); + if (etcFile.isFile()) { + return etcFile; + } + + File jreFile = new File(System.getProperty("java.home") + File.separator + "lib" + + File.separator + DEPLOYMENT_CONFIG); + if (jreFile.isFile()) { + return jreFile; + } + + return null; + } + + /** + * Reads the system configuration file and sets the relevant + * system-properties related variables + */ + private boolean loadSystemConfiguration(File configFile) { + + if (JNLPRuntime.isDebug()) { + System.out.println("Loading system configuation from: " + configFile); + } + + Map<String, ConfigValue> systemConfiguration = new HashMap<String, ConfigValue>(); + try { + systemConfiguration = parsePropertiesFile(configFile); + } catch (IOException e) { + if (JNLPRuntime.isDebug()) { + System.out.println("No System level " + DEPLOYMENT_PROPERTIES + " found."); + } + return false; + } + + /* + * at this point, we have read the system deployment.config file + * completely + */ + + try { + String urlString = systemConfiguration.get("deployment.system.config").get(); + if (urlString == null) { + if (JNLPRuntime.isDebug()) { + System.out.println("No System level " + DEPLOYMENT_PROPERTIES + " found."); + } + return false; + } + URL url = new URL(urlString); + if (url.getProtocol().equals("file")) { + systemPropertiesFile = new File(url.getFile()); + if (JNLPRuntime.isDebug()) { + System.out.println("Using System level" + DEPLOYMENT_PROPERTIES + ": " + + systemPropertiesFile); + } + ConfigValue mandatory = systemConfiguration.get("deployment.system.config.mandatory"); + systemPropertiesMandatory = Boolean.valueOf(mandatory == null? null: mandatory.get()); + return true; + } else { + if (JNLPRuntime.isDebug()) { + System.out.println("Remote + " + DEPLOYMENT_PROPERTIES + " not supported"); + } + return false; + } + } catch (MalformedURLException e) { + if (JNLPRuntime.isDebug()) { + System.out.println("Invalid url for " + DEPLOYMENT_PROPERTIES); + } + return false; + } + } + + /** + * Loads the properties file, if one exists + * + * @param type the ConfigType to load + * @param file the File to load Properties from + * @param mandatory indicates if reading this file is mandatory + * + * @throws ConfigurationException if the file is mandatory but cannot be read + */ + private Map<String, ConfigValue> loadProperties(ConfigType type, File file, boolean mandatory) + throws ConfigurationException { + if (file == null || !file.isFile()) { + if (JNLPRuntime.isDebug()) { + System.out.println("No " + type.toString() + " level " + DEPLOYMENT_PROPERTIES + " found."); + } + if (!mandatory) { + return null; + } else { + throw new ConfigurationException(); + } + } + + if (JNLPRuntime.isDebug()) { + System.out.println("Loading " + type.toString() + " level properties from: " + file); + } + try { + return parsePropertiesFile(file); + } catch (IOException e) { + return null; + } + } + + + /** + * Saves all properties that are not part of default or system properties + * + * @throws IOException + */ + public void save() throws IOException { + if (JNLPRuntime.isDebug()) { + System.out.println("Saving properties into " + userPropertiesFile.toString()); + } + Properties toSave = new Properties(); + + for (String key : currentConfiguration.keySet()) { + String oldValue = unchangeableConfiguration.get(key) == null ? null + : unchangeableConfiguration.get(key).get(); + String newValue = currentConfiguration.get(key) == null ? null : currentConfiguration + .get(key).get(); + if (oldValue == null && newValue == null) { + continue; + } else if (oldValue == null && newValue != null) { + toSave.setProperty(key, newValue); + } else if (oldValue != null && newValue == null) { + toSave.setProperty(key, newValue); + } else { // oldValue != null && newValue != null + if (!oldValue.equals(newValue)) { + toSave.setProperty(key, newValue); + } + } + } + + File backupPropertiesFile = new File(userPropertiesFile.toString() + ".old"); + if (userPropertiesFile.isFile()) { + if (!userPropertiesFile.renameTo(backupPropertiesFile)) { + throw new IOException("Error saving backup copy of " + userPropertiesFile); + } + } + + userPropertiesFile.getParentFile().mkdirs(); + OutputStream out = new BufferedOutputStream(new FileOutputStream(userPropertiesFile)); + try { + toSave.store(out, DEPLOYMENT_COMMENT); + } finally { + out.close(); + } + } + + /** + * Reads a properties file and returns a map representing the properties + * + * @param propertiesFile the file to read Properties from + * @param destination the map to which all the properties should be added + * @throws IOException if an IO problem occurs + */ + private Map<String, ConfigValue> parsePropertiesFile(File propertiesFile) throws IOException { + Map<String, ConfigValue> result = new HashMap<String, ConfigValue>(); + + Properties properties = new Properties(); + + Reader reader = new BufferedReader(new FileReader(propertiesFile)); + try { + properties.load(reader); + } finally { + reader.close(); + } + + Set<String> keys = properties.stringPropertyNames(); + for (String key : keys) { + if (key.endsWith(".locked")) { + String realKey = key.substring(0, key.length() - ".locked".length()); + ConfigValue configValue = result.get(realKey); + if (configValue == null) { + configValue = new ConfigValue(null, true); + result.put(realKey, configValue); + } else { + configValue.setLocked(true); + } + } else { + /* when parsing a properties we set value without checking if it is locked or not */ + String newValue = properties.getProperty(key); + ConfigValue configValue = result.get(key); + if (configValue == null) { + configValue = new ConfigValue(newValue); + result.put(key, configValue); + } else { + configValue.set(newValue); + } + } + } + return result; + } + + /** + * Merges two maps while respecting whether the values have been locked or + * not. All values from srcMap are put into finalMap, replacing values in + * finalMap if necessary, unless the value is present and marked as locked + * in finalMap + * + * @param finalMap the destination for putting values + * @param srcMap the source for reading key value pairs + */ + private void mergeMaps(Map<String, ConfigValue> finalMap, Map<String, ConfigValue> srcMap) { + for (String key: srcMap.keySet()) { + ConfigValue configValue = finalMap.get(key); + if (configValue == null) { + configValue = srcMap.get(key); + finalMap.put(key, configValue); + } else { + if (!configValue.isLocked()) { + configValue.set(srcMap.get(key).get()); + } + } + } + } + + /** + * Dumps the configuration to the PrintStream + * + * @param config a map of key,value pairs representing the configuration to + * dump + * @param out the PrintStream to write data to + */ + @SuppressWarnings("unused") + private static void dumpConfiguration(Map<String, ConfigValue> config, PrintStream out) { + System.out.println("KEY: VALUE [Locked]"); + + for (String key : config.keySet()) { + ConfigValue value = config.get(key); + out.println("'" + key + "': '" + value.get() + "'" + + (value.isLocked() ? " [LOCKED]" : "")); + } + } +} diff --git a/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java b/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java index 31e6b06..2484df6 100644 --- a/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java +++ b/netx/net/sourceforge/jnlp/runtime/JNLPRuntime.java @@ -25,6 +25,7 @@ import java.util.*; import java.util.List; import java.security.*; import javax.jnlp.*; +import javax.naming.ConfigurationException; import javax.swing.UIManager; import net.sourceforge.jnlp.*; @@ -59,6 +60,8 @@ public class JNLPRuntime { /** the localized resource strings */ private static ResourceBundle resources; + private static final DeploymentConfiguration config = new DeploymentConfiguration(); + /** the security manager */ private static JNLPSecurityManager security; @@ -183,6 +186,16 @@ public class JNLPRuntime { public static void initialize(boolean isApplication) throws IllegalStateException { checkInitialized(); + try { + config.load(); + } catch (ConfigurationException e) { + /* exit if there is a fatal exception loading the configuration */ + if (isApplication) { + System.out.println(getMessage("RConfigurationError")); + System.exit(1); + } + } + isWebstartApplication = isApplication; //Setting the system property for javawebstart's version. @@ -227,6 +240,7 @@ public class JNLPRuntime { securityDialogMessageHandler = startSecurityThreads(); initialized = true; + } /** @@ -247,6 +261,15 @@ public class JNLPRuntime { } /** + * Gets the Configuration associated with this runtime + * @return a {@link DeploymentConfiguration} object that can be queried to + * find relevant configuration settings + */ + public static DeploymentConfiguration getConfiguration() { + return config; + } + + /** * Returns true if a webstart application has been initialized, and false * for a plugin applet. */ |