diff --git a/exist-core/pom.xml b/exist-core/pom.xml
index 23c34c992d7..b73fe462ba0 100644
--- a/exist-core/pom.xml
+++ b/exist-core/pom.xml
@@ -698,12 +698,15 @@
src/main/java/org/exist/xquery/Cardinality.java
src/test/java/org/exist/xquery/ImportModuleTest.java
src/test/java/org/exist/xquery/XQueryContextAttributesTest.java
+ src/main/java/org/exist/xquery/functions/AccessUtil.java
+ src/test/java/org/exist/xquery/functions/fn/FunEnvironmentTest.java
src/main/java/org/exist/xquery/functions/map/MapType.java
src/test/java/org/exist/xquery/functions/session/AbstractSessionTest.java
src/test/java/org/exist/xquery/functions/xmldb/AbstractXMLDBTest.java
src/test/java/org/exist/xquery/functions/session/AttributeTest.java
src/test/java/org/exist/xquery/functions/xmldb/XMLDBAuthenticateTest.java
src/main/java/org/exist/xquery/functions/util/Eval.java
+ src/test/java/org/exist/xquery/functions/util/SystemPropertyTest.java
src/test/java/org/exist/xquery/util/URIUtilsTest.java
src/main/java/org/exist/xquery/value/ArrayListValueSequence.java
src/test/java/org/exist/xquery/value/BifurcanMapTest.java
@@ -846,12 +849,15 @@ The original license statement is also included below.]]>
src/main/java/org/exist/xquery/Cardinality.java
src/test/java/org/exist/xquery/ImportModuleTest.java
src/test/java/org/exist/xquery/XQueryContextAttributesTest.java
+ src/main/java/org/exist/xquery/functions/AccessUtil.java
+ src/test/java/org/exist/xquery/functions/fn/FunEnvironmentTest.java
src/main/java/org/exist/xquery/functions/map/MapType.java
src/test/java/org/exist/xquery/functions/session/AbstractSessionTest.java
src/test/java/org/exist/xquery/functions/xmldb/AbstractXMLDBTest.java
src/test/java/org/exist/xquery/functions/session/AttributeTest.java
src/test/java/org/exist/xquery/functions/xmldb/XMLDBAuthenticateTest.java
src/main/java/org/exist/xquery/functions/util/Eval.java
+ src/test/java/org/exist/xquery/functions/util/SystemPropertyTest.java
src/test/java/org/exist/xquery/util/URIUtilsTest.java
src/main/java/org/exist/xquery/value/ArrayListValueSequence.java
src/test/java/org/exist/xquery/value/BifurcanMapTest.java
diff --git a/exist-core/src/main/java/org/exist/SystemProperties.java b/exist-core/src/main/java/org/exist/ExistSystemProperties.java
similarity index 52%
rename from exist-core/src/main/java/org/exist/SystemProperties.java
rename to exist-core/src/main/java/org/exist/ExistSystemProperties.java
index ba3214ab18f..1c1c03c4608 100644
--- a/exist-core/src/main/java/org/exist/SystemProperties.java
+++ b/exist-core/src/main/java/org/exist/ExistSystemProperties.java
@@ -24,32 +24,41 @@
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;
+import java.util.Set;
-import com.evolvedbinary.j8fu.lazy.LazyVal;
+import com.evolvedbinary.j8fu.lazy.AtomicLazyVal;
+import net.jcip.annotations.ThreadSafe;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
/**
*
- * @author aretter
+ * @author Adam Retter
*/
-public class SystemProperties {
+@ThreadSafe
+public class ExistSystemProperties {
- private static final Logger LOG = LogManager.getLogger(SystemProperties.class);
- private static final SystemProperties instance = new SystemProperties();
+ public static final String PROP_PRODUCT_NAME = "product-name";
+ public static final String PROP_PRODUCT_VERSION = "product-version";
+ public static final String PROP_PRODUCT_BUILD = "product-build";
+ public static final String PROP_GIT_BRANCH = "git-branch";
+ public static final String PROP_GIT_COMMIT = "git-commit";
- private final LazyVal properties = new LazyVal<>(this::load);
+ private static final Logger LOG = LogManager.getLogger(ExistSystemProperties.class);
+ private static final ExistSystemProperties instance = new ExistSystemProperties();
- public final static SystemProperties getInstance() {
+ private final AtomicLazyVal properties = new AtomicLazyVal<>(this::load);
+
+ public final static ExistSystemProperties getInstance() {
return instance;
}
- private SystemProperties() {
+ private ExistSystemProperties() {
}
private Properties load() {
final Properties properties = new Properties();
- try (final InputStream is = SystemProperties.class.getResourceAsStream("system.properties")) {
+ try (final InputStream is = ExistSystemProperties.class.getResourceAsStream("system.properties")) {
if (is != null) {
properties.load(is);
}
@@ -59,11 +68,20 @@ private Properties load() {
return properties;
}
- public String getSystemProperty(final String propertyName) {
+ public String getExistSystemProperty(final String propertyName) {
return properties.get().getProperty(propertyName);
}
- public String getSystemProperty(final String propertyName, final String defaultValue) {
+ public String getExistSystemProperty(final String propertyName, final String defaultValue) {
return properties.get().getProperty(propertyName, defaultValue);
}
+
+ /**
+ * Get the available eXist System Properties.
+ *
+ * @return the available eXist System Properties.
+ */
+ public Set getAvailableExistSystemProperties() {
+ return properties.get().stringPropertyNames();
+ }
}
\ No newline at end of file
diff --git a/exist-core/src/main/java/org/exist/Version.java b/exist-core/src/main/java/org/exist/Version.java
index c86dc623f0c..f22c328d521 100644
--- a/exist-core/src/main/java/org/exist/Version.java
+++ b/exist-core/src/main/java/org/exist/Version.java
@@ -36,12 +36,12 @@ public final class Version {
static {
- final SystemProperties systemProperties = SystemProperties.getInstance();
- NAME = systemProperties.getSystemProperty("product-name", "eXist");
- VERSION = systemProperties.getSystemProperty("product-version");
- BUILD = systemProperties.getSystemProperty("product-build");
- GIT_BRANCH = systemProperties.getSystemProperty("git-branch");
- GIT_COMMIT = systemProperties.getSystemProperty("git-commit");
+ final ExistSystemProperties existSystemProperties = ExistSystemProperties.getInstance();
+ NAME = existSystemProperties.getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_NAME, "eXist");
+ VERSION = existSystemProperties.getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION);
+ BUILD = existSystemProperties.getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_BUILD);
+ GIT_BRANCH = existSystemProperties.getExistSystemProperty(ExistSystemProperties.PROP_GIT_BRANCH);
+ GIT_COMMIT = existSystemProperties.getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT);
}
public static String getProductName() {
diff --git a/exist-core/src/main/java/org/exist/client/ClientFrame.java b/exist-core/src/main/java/org/exist/client/ClientFrame.java
index 05fe7834b77..432dc14a806 100644
--- a/exist-core/src/main/java/org/exist/client/ClientFrame.java
+++ b/exist-core/src/main/java/org/exist/client/ClientFrame.java
@@ -21,7 +21,7 @@
*/
package org.exist.client;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.backup.Backup;
import org.exist.backup.CreateBackupDialog;
import org.exist.backup.GuiRestoreServiceTaskListener;
@@ -1724,7 +1724,7 @@ protected static Properties getLoginData(final Properties props) {
final ConnectionDialog connectionDialog = new ConnectionDialog(null, true, defaultConnectionSettings, Boolean.parseBoolean(props.getProperty(InteractiveClient.LOCAL_MODE, InteractiveClient.LOCAL_MODE_DEFAULT)), Boolean.parseBoolean(props.getProperty(InteractiveClient.NO_EMBED_MODE, InteractiveClient.NO_EMBED_MODE_DEFAULT)));
- connectionDialog.setTitle(SystemProperties.getInstance().getSystemProperty("product-name", "eXist-db") + " " + SystemProperties.getInstance().getSystemProperty("product-version", "unknown") + " Database Login");
+ connectionDialog.setTitle(ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_NAME, "eXist-db") + " " + ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "unknown") + " Database Login");
connectionDialog.addDialogCompleteWithResponseCallback(connection -> {
properties.setProperty(InteractiveClient.USER, connection.getUsername());
diff --git a/exist-core/src/main/java/org/exist/client/InteractiveClient.java b/exist-core/src/main/java/org/exist/client/InteractiveClient.java
index 0c7faa6fd03..66e08ca9b1a 100644
--- a/exist-core/src/main/java/org/exist/client/InteractiveClient.java
+++ b/exist-core/src/main/java/org/exist/client/InteractiveClient.java
@@ -44,9 +44,8 @@
import javax.xml.transform.OutputKeys;
import org.apache.tools.ant.DirectoryScanner;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.dom.persistent.XMLUtil;
-import org.exist.security.ACLPermission;
import org.exist.security.Account;
import org.exist.security.Permission;
import org.exist.security.SecurityManager;
@@ -2517,12 +2516,12 @@ public void printNotice() {
public String getNotice() {
final StringBuilder builder = new StringBuilder();
- builder.append(SystemProperties.getInstance().getSystemProperty("product-name", "eXist-db"));
+ builder.append(ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_NAME, "eXist-db"));
builder.append(" version ");
- builder.append(SystemProperties.getInstance().getSystemProperty("product-version", "unknown"));
- if (!"".equals(SystemProperties.getInstance().getSystemProperty("git-commit", ""))) {
+ builder.append(ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "unknown"));
+ if (!"".equals(ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT, ""))) {
builder.append(" (");
- builder.append(SystemProperties.getInstance().getSystemProperty("git-commit", "(unknown Git commit ID)"));
+ builder.append(ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT, "(unknown Git commit ID)"));
builder.append(")");
}
builder.append(", Copyright (C) 2001-");
diff --git a/exist-core/src/main/java/org/exist/jetty/JettyStart.java b/exist-core/src/main/java/org/exist/jetty/JettyStart.java
index 7ec2737ab68..3d882410c43 100644
--- a/exist-core/src/main/java/org/exist/jetty/JettyStart.java
+++ b/exist-core/src/main/java/org/exist/jetty/JettyStart.java
@@ -33,7 +33,7 @@
import org.eclipse.jetty.util.MultiException;
import org.eclipse.jetty.util.component.LifeCycle;
import org.eclipse.jetty.xml.XmlConfiguration;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.http.servlets.ExistExtensionServlet;
import org.exist.start.CompatibleJavaVersionCheck;
import org.exist.start.Main;
@@ -190,9 +190,9 @@ public synchronized void run(final String[] args, final Observer observer) {
logger.info("Running as user '{}'", System.getProperty("user.name", "(unknown user.name)"));
logger.info("[eXist Home : {}]", System.getProperty("exist.home", "unknown"));
- logger.info("[eXist Version : {}]", SystemProperties.getInstance().getSystemProperty("product-version", "unknown"));
- logger.info("[eXist Build : {}]", SystemProperties.getInstance().getSystemProperty("product-build", "unknown"));
- logger.info("[Git commit : {}]", SystemProperties.getInstance().getSystemProperty("git-commit", "unknown"));
+ logger.info("[eXist Version : {}]", ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "unknown"));
+ logger.info("[eXist Build : {}]", ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_BUILD, "unknown"));
+ logger.info("[Git commit : {}]", ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT, "unknown"));
logger.info("[Operating System : {} {} {}]", System.getProperty("os.name"), System.getProperty("os.version"), System.getProperty("os.arch"));
logger.info("[log4j.configurationFile : {}]", System.getProperty("log4j.configurationFile"));
diff --git a/exist-core/src/main/java/org/exist/launcher/SplashScreen.java b/exist-core/src/main/java/org/exist/launcher/SplashScreen.java
index 08689214d79..baf381e2d0b 100644
--- a/exist-core/src/main/java/org/exist/launcher/SplashScreen.java
+++ b/exist-core/src/main/java/org/exist/launcher/SplashScreen.java
@@ -21,6 +21,7 @@
*/
package org.exist.launcher;
+import org.exist.ExistSystemProperties;
import org.exist.jetty.JettyStart;
import org.exist.storage.BrokerPool;
@@ -31,8 +32,6 @@
import java.util.Observable;
import java.util.Observer;
-import org.exist.SystemProperties;
-
/**
* Display a splash screen showing the eXist-db logo and a status line.
*
@@ -67,11 +66,11 @@ public SplashScreen(Launcher launcher) {
getContentPane().add(imageLabel, BorderLayout.NORTH);
// version label
- final SystemProperties sysProps = SystemProperties.getInstance();
+ final ExistSystemProperties sysProps = ExistSystemProperties.getInstance();
final StringBuilder builder = new StringBuilder();
builder.append("Version ");
- builder.append(sysProps.getSystemProperty("product-version", "unknown"));
- final String gitCommit = sysProps.getSystemProperty("git-commit");
+ builder.append(sysProps.getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "unknown"));
+ final String gitCommit = sysProps.getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT);
if (gitCommit != null && !gitCommit.isEmpty()) {
builder.append(" (");
builder.append(gitCommit, 0, Math.min(7, gitCommit.length()));
diff --git a/exist-core/src/main/java/org/exist/management/impl/SystemInfo.java b/exist-core/src/main/java/org/exist/management/impl/SystemInfo.java
index e5b92ca8eca..0fb8cfe79db 100644
--- a/exist-core/src/main/java/org/exist/management/impl/SystemInfo.java
+++ b/exist-core/src/main/java/org/exist/management/impl/SystemInfo.java
@@ -24,7 +24,7 @@
import java.nio.charset.Charset;
import java.util.Locale;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
/**
* Class SystemInfo
@@ -38,22 +38,22 @@ public class SystemInfo implements SystemInfoMXBean {
@Override
public String getProductName() {
- return SystemProperties.getInstance().getSystemProperty("product-name","eXist");
+ return ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_NAME,"eXist");
}
@Override
public String getProductVersion() {
- return SystemProperties.getInstance().getSystemProperty("product-version","unknown");
+ return ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION,"unknown");
}
@Override
public String getProductBuild() {
- return SystemProperties.getInstance().getSystemProperty("product-build","unknown");
+ return ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_BUILD,"unknown");
}
@Override
public String getGitCommit() {
- return SystemProperties.getInstance().getSystemProperty("git-commit", "unknown Git commit ID");
+ return ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_GIT_COMMIT, "unknown Git commit ID");
}
@Override
diff --git a/exist-core/src/main/java/org/exist/repo/ClasspathHelper.java b/exist-core/src/main/java/org/exist/repo/ClasspathHelper.java
index a41b76a6345..9afd3586075 100644
--- a/exist-core/src/main/java/org/exist/repo/ClasspathHelper.java
+++ b/exist-core/src/main/java/org/exist/repo/ClasspathHelper.java
@@ -23,7 +23,7 @@
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.start.Classpath;
import org.exist.start.EXistClassLoader;
import org.exist.storage.BrokerPool;
@@ -108,7 +108,7 @@ private static void scanPackages(BrokerPool pool, Classpath classpath) {
private static boolean isCompatible(final Package pkg) throws PackageException {
// determine the eXist-db version this package is compatible with
final Collection processorDeps = pkg.getProcessorDeps();
- final String procVersion = SystemProperties.getInstance().getSystemProperty("product-version", "1.0");
+ final String procVersion = ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "1.0");
PackageLoader.Version requiresExistVersion = null;
for (final ProcessorDependency dependency: processorDeps) {
if (Deployment.PROCESSOR_NAME.equals(dependency.getProcessor())) {
diff --git a/exist-core/src/main/java/org/exist/repo/Deployment.java b/exist-core/src/main/java/org/exist/repo/Deployment.java
index d4692a75070..869ccbf9b81 100644
--- a/exist-core/src/main/java/org/exist/repo/Deployment.java
+++ b/exist-core/src/main/java/org/exist/repo/Deployment.java
@@ -25,7 +25,7 @@
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.exist.EXistException;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.collections.Collection;
import org.exist.collections.triggers.TriggerException;
import org.exist.dom.QName;
@@ -286,7 +286,7 @@ public Optional installAndDeploy(final DBBroker broker, final Txn transa
}
private void checkProcessorVersion(final PackageLoader.Version version) throws PackageException {
- final String procVersion = SystemProperties.getInstance().getSystemProperty("product-version", "1.0");
+ final String procVersion = ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, "1.0");
final DependencyVersion depVersion = version.getDependencyVersion();
if (!depVersion.isCompatible(procVersion)) {
diff --git a/exist-core/src/main/java/org/exist/util/Configuration.java b/exist-core/src/main/java/org/exist/util/Configuration.java
index e83ebcda02a..cdb4a944e31 100644
--- a/exist-core/src/main/java/org/exist/util/Configuration.java
+++ b/exist-core/src/main/java/org/exist/util/Configuration.java
@@ -413,9 +413,6 @@ private void configureXQuery( Element xquery ) throws DatabaseConfigurationExcep
* @throws DatabaseConfigurationException
*/
private void loadModuleClasses( Element xquery, Map> modulesClassMap, Map modulesSourceMap, Map>> moduleParameters) throws DatabaseConfigurationException {
- // add the standard function module
- modulesClassMap.put(Namespaces.XPATH_FUNCTIONS_NS, org.exist.xquery.functions.fn.FnModule.class);
-
// add other modules specified in configuration
final NodeList builtins = xquery.getElementsByTagName(XQUERY_BUILTIN_MODULES_CONFIGURATION_MODULES_ELEMENT_NAME);
@@ -477,6 +474,11 @@ private void loadModuleClasses( Element xquery, Map> modulesCla
}
}
}
+
+ // if not specified in the conf.xml, then add the standard function module anyway
+ if (!modulesClassMap.containsKey(Namespaces.XPATH_FUNCTIONS_NS)) {
+ modulesClassMap.put(Namespaces.XPATH_FUNCTIONS_NS, org.exist.xquery.functions.fn.FnModule.class);
+ }
}
/**
diff --git a/exist-core/src/main/java/org/exist/webstart/JnlpWriter.java b/exist-core/src/main/java/org/exist/webstart/JnlpWriter.java
index 89e2c83cc3f..d8b5f7d5111 100644
--- a/exist-core/src/main/java/org/exist/webstart/JnlpWriter.java
+++ b/exist-core/src/main/java/org/exist/webstart/JnlpWriter.java
@@ -35,7 +35,7 @@
import org.apache.commons.io.FilenameUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
-import org.exist.SystemProperties;
+import org.exist.ExistSystemProperties;
import org.exist.util.FileUtils;
import org.apache.commons.io.output.UnsynchronizedByteArrayOutputStream;
@@ -101,7 +101,7 @@ void writeJnlpXML(JnlpJarFiles jnlpFiles, HttpServletRequest request,
writer.writeAttribute("codebase", codeBase);
writer.writeAttribute("href", "exist.jnlp");
- String version = SystemProperties.getInstance().getSystemProperty("product-version", null);
+ String version = ExistSystemProperties.getInstance().getExistSystemProperty(ExistSystemProperties.PROP_PRODUCT_VERSION, null);
if(version!=null){
writer.writeAttribute("version", version);
}
diff --git a/exist-core/src/main/java/org/exist/xquery/AbstractInternalModule.java b/exist-core/src/main/java/org/exist/xquery/AbstractInternalModule.java
index 5d33ed848e8..29ad602cc3f 100644
--- a/exist-core/src/main/java/org/exist/xquery/AbstractInternalModule.java
+++ b/exist-core/src/main/java/org/exist/xquery/AbstractInternalModule.java
@@ -84,6 +84,15 @@ protected List extends Object> getParameter(final String paramName) {
return parameters.get(paramName);
}
+ /**
+ * Get the module parameters.
+ *
+ * @return the module parameters.
+ */
+ protected Map> getParameters() {
+ return parameters;
+ }
+
@Override
public void setContextItem(final Sequence contextItem) {
// not used for internal modules
diff --git a/exist-core/src/main/java/org/exist/xquery/XQueryContext.java b/exist-core/src/main/java/org/exist/xquery/XQueryContext.java
index 4ebea126e94..7e4f76ffaa4 100644
--- a/exist-core/src/main/java/org/exist/xquery/XQueryContext.java
+++ b/exist-core/src/main/java/org/exist/xquery/XQueryContext.java
@@ -51,6 +51,8 @@
import com.evolvedbinary.j8fu.function.QuadFunctionE;
import com.evolvedbinary.j8fu.tuple.Tuple2;
import com.ibm.icu.text.Collator;
+import io.lacuna.bifurcan.IMap;
+import io.lacuna.bifurcan.LinearMap;
import it.unimi.dsi.fastutil.Hash;
import it.unimi.dsi.fastutil.objects.*;
import net.jcip.annotations.Immutable;
@@ -372,7 +374,10 @@ public class XQueryContext implements BinaryValueManager, Context {
protected Profiler profiler;
//For holding the environment variables
- private Map envs;
+ private IMap envs;
+
+ //For holding the Java System Properties
+ private IMap props;
private ContextUpdateListener updateListener = null;
@@ -2732,13 +2737,33 @@ public void resolveForwardReferences() throws XPathException {
*
* @return Map of environment variables
*/
- public Map getEnvironmentVariables() {
+ public io.lacuna.bifurcan.IMap getEnvironmentVariables() {
if (envs == null) {
- envs = System.getenv();
+ envs = io.lacuna.bifurcan.Map.from(System.getenv());
}
return envs;
}
+ /**
+ * Get Java System properties. The properties shall not change
+ * during execution of query.
+ *
+ * @return Map of Java System Properties
+ */
+ public io.lacuna.bifurcan.IMap getJavaSystemProperties() {
+ if (props == null) {
+ final IMap strProps = new LinearMap<>();
+ for (final Map.Entry