You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by oh...@apache.org on 2014/01/06 15:56:38 UTC

svn commit: r1555839 - in /commons/proper/configuration/trunk/src: main/java/org/apache/commons/configuration/ main/java/org/apache/commons/configuration/builder/combined/ main/java/org/apache/commons/configuration/tree/ test/java/org/apache/commons/co...

Author: oheger
Date: Mon Jan  6 14:56:38 2014
New Revision: 1555839

URL: http://svn.apache.org/r1555839
Log:
[CONFIGURATION-563] DefaultExpressionEngine is now immutable.

An instance is initialized with a DefaultExpressionEngineSymbols object. The
set methods for changing symbols have been removed.

Modified:
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/BaseHierarchicalConfiguration.java
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/CombinedConfiguration.java
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/HierarchicalConfigurationConverter.java
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/builder/combined/CombinedConfigurationBuilder.java
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultConfigurationKey.java
    commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultExpressionEngine.java
    commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestCombinedConfiguration.java
    commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestConfigurationUtils.java
    commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestHierarchicalConfiguration.java
    commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultConfigurationKey.java
    commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultExpressionEngine.java

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/BaseHierarchicalConfiguration.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/BaseHierarchicalConfiguration.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/BaseHierarchicalConfiguration.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/BaseHierarchicalConfiguration.java Mon Jan  6 14:56:38 2014
@@ -42,6 +42,7 @@ import org.apache.commons.configuration.
 import org.apache.commons.configuration.tree.ConfigurationNodeVisitorAdapter;
 import org.apache.commons.configuration.tree.DefaultConfigurationNode;
 import org.apache.commons.configuration.tree.DefaultExpressionEngine;
+import org.apache.commons.configuration.tree.DefaultExpressionEngineSymbols;
 import org.apache.commons.configuration.tree.ExpressionEngine;
 import org.apache.commons.configuration.tree.NodeAddData;
 
@@ -324,7 +325,7 @@ public class BaseHierarchicalConfigurati
     {
         if (defaultExpressionEngine == null)
         {
-            defaultExpressionEngine = new DefaultExpressionEngine();
+            defaultExpressionEngine = new DefaultExpressionEngine(DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS);
         }
         return defaultExpressionEngine;
     }

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/CombinedConfiguration.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/CombinedConfiguration.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/CombinedConfiguration.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/CombinedConfiguration.java Mon Jan  6 14:56:38 2014
@@ -193,7 +193,7 @@ public class CombinedConfiguration exten
     private static final long serialVersionUID = 8338574525528692307L;
 
     /** Constant for the expression engine for parsing the at path. */
-    private static final DefaultExpressionEngine AT_ENGINE = new DefaultExpressionEngine();
+    private static final DefaultExpressionEngine AT_ENGINE = DefaultExpressionEngine.INSTANCE;
 
     /** Constant for the default node combiner. */
     private static final NodeCombiner DEFAULT_COMBINER = new UnionCombiner();

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/HierarchicalConfigurationConverter.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/HierarchicalConfigurationConverter.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/HierarchicalConfigurationConverter.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/HierarchicalConfigurationConverter.java Mon Jan  6 14:56:38 2014
@@ -61,7 +61,7 @@ abstract class HierarchicalConfiguration
     {
         if (config != null)
         {
-            DefaultExpressionEngine exprEngine = new DefaultExpressionEngine();
+            DefaultExpressionEngine exprEngine = DefaultExpressionEngine.INSTANCE;
             DefaultConfigurationKey keyEmpty =
                     new DefaultConfigurationKey(exprEngine);
             DefaultConfigurationKey keyLast = keyEmpty;

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/builder/combined/CombinedConfigurationBuilder.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/builder/combined/CombinedConfigurationBuilder.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/builder/combined/CombinedConfigurationBuilder.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/builder/combined/CombinedConfigurationBuilder.java Mon Jan  6 14:56:38 2014
@@ -55,7 +55,7 @@ import org.apache.commons.configuration.
 import org.apache.commons.configuration.interpol.Lookup;
 import org.apache.commons.configuration.io.FileSystem;
 import org.apache.commons.configuration.resolver.CatalogResolver;
-import org.apache.commons.configuration.tree.DefaultExpressionEngine;
+import org.apache.commons.configuration.tree.DefaultExpressionEngineSymbols;
 import org.apache.commons.configuration.tree.OverrideCombiner;
 import org.apache.commons.configuration.tree.UnionCombiner;
 import org.xml.sax.EntityResolver;
@@ -265,52 +265,52 @@ public class CombinedConfigurationBuilde
             + ".CONFIG_BEAN_FACTORY_NAME";
 
     /** Constant for the reserved name attribute. */
-    static final String ATTR_NAME = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
+    static final String ATTR_NAME = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
             + XMLBeanDeclaration.RESERVED_PREFIX
             + "name"
-            + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+            + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the name of the at attribute. */
     static final String ATTR_ATNAME = "at";
 
     /** Constant for the reserved at attribute. */
-    static final String ATTR_AT_RES = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
+    static final String ATTR_AT_RES = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
             + XMLBeanDeclaration.RESERVED_PREFIX
             + ATTR_ATNAME
-            + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+            + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the at attribute without the reserved prefix. */
-    static final String ATTR_AT = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
-            + ATTR_ATNAME + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+    static final String ATTR_AT = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
+            + ATTR_ATNAME + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the name of the optional attribute. */
     static final String ATTR_OPTIONALNAME = "optional";
 
     /** Constant for the reserved optional attribute. */
-    static final String ATTR_OPTIONAL_RES = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
+    static final String ATTR_OPTIONAL_RES = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
             + XMLBeanDeclaration.RESERVED_PREFIX
             + ATTR_OPTIONALNAME
-            + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+            + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the optional attribute without the reserved prefix. */
-    static final String ATTR_OPTIONAL = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
-            + ATTR_OPTIONALNAME + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+    static final String ATTR_OPTIONAL = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
+            + ATTR_OPTIONALNAME + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the file name attribute. */
-    static final String ATTR_FILENAME = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
-            + "fileName" + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+    static final String ATTR_FILENAME = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
+            + "fileName" + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the forceCreate attribute. */
-    static final String ATTR_FORCECREATE = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
+    static final String ATTR_FORCECREATE = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
             + XMLBeanDeclaration.RESERVED_PREFIX
             + "forceCreate"
-            + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+            + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /** Constant for the reload attribute. */
-    static final String ATTR_RELOAD = DefaultExpressionEngine.DEFAULT_ATTRIBUTE_START
+    static final String ATTR_RELOAD = DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_START
             + XMLBeanDeclaration.RESERVED_PREFIX
             + "reload"
-            + DefaultExpressionEngine.DEFAULT_ATTRIBUTE_END;
+            + DefaultExpressionEngineSymbols.DEFAULT_ATTRIBUTE_END;
 
     /**
      * Constant for the tag attribute for providers.

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultConfigurationKey.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultConfigurationKey.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultConfigurationKey.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultConfigurationKey.java Mon Jan  6 14:56:38 2014
@@ -136,7 +136,7 @@ public class DefaultConfigurationKey
         if (keyBuffer.length() > 0 && !isAttributeKey(property)
                 && key.length() > 0)
         {
-            keyBuffer.append(getExpressionEngine().getPropertyDelimiter());
+            keyBuffer.append(getSymbols().getPropertyDelimiter());
         }
 
         keyBuffer.append(key);
@@ -164,9 +164,9 @@ public class DefaultConfigurationKey
      */
     public DefaultConfigurationKey appendIndex(int index)
     {
-        keyBuffer.append(getExpressionEngine().getIndexStart());
+        keyBuffer.append(getSymbols().getIndexStart());
         keyBuffer.append(index);
-        keyBuffer.append(getExpressionEngine().getIndexEnd());
+        keyBuffer.append(getSymbols().getIndexEnd());
         return this;
     }
 
@@ -263,7 +263,7 @@ public class DefaultConfigurationKey
             int i = 0;
             while (i < k.length()
                     && String.valueOf(k.charAt(i)).equals(
-                            getExpressionEngine().getPropertyDelimiter()))
+                            getSymbols().getPropertyDelimiter()))
             {
                 i++;
             }
@@ -339,9 +339,9 @@ public class DefaultConfigurationKey
             return false;
         }
 
-        return key.startsWith(getExpressionEngine().getAttributeStart())
-                && (getExpressionEngine().getAttributeEnd() == null || key
-                        .endsWith(getExpressionEngine().getAttributeEnd()));
+        return key.startsWith(getSymbols().getAttributeStart())
+                && (getSymbols().getAttributeEnd() == null || key
+                        .endsWith(getSymbols().getAttributeEnd()));
     }
 
     /**
@@ -365,10 +365,10 @@ public class DefaultConfigurationKey
         else
         {
             StringBuilder buf = new StringBuilder();
-            buf.append(getExpressionEngine().getAttributeStart()).append(key);
-            if (getExpressionEngine().getAttributeEnd() != null)
+            buf.append(getSymbols().getAttributeStart()).append(key);
+            if (getSymbols().getAttributeEnd() != null)
             {
-                buf.append(getExpressionEngine().getAttributeEnd());
+                buf.append(getSymbols().getAttributeEnd());
             }
             return buf.toString();
         }
@@ -403,7 +403,7 @@ public class DefaultConfigurationKey
             String result = key;
             while (hasLeadingDelimiter(result))
             {
-                result = result.substring(getExpressionEngine()
+                result = result.substring(getSymbols()
                         .getPropertyDelimiter().length());
             }
             return result;
@@ -429,7 +429,7 @@ public class DefaultConfigurationKey
             {
                 result = result
                         .substring(0, result.length()
-                                - getExpressionEngine().getPropertyDelimiter()
+                                - getSymbols().getPropertyDelimiter()
                                         .length());
             }
             return result;
@@ -467,9 +467,9 @@ public class DefaultConfigurationKey
      */
     private boolean hasTrailingDelimiter(String key)
     {
-        return key.endsWith(getExpressionEngine().getPropertyDelimiter())
-                && (getExpressionEngine().getEscapedDelimiter() == null || !key
-                        .endsWith(getExpressionEngine().getEscapedDelimiter()));
+        return key.endsWith(getSymbols().getPropertyDelimiter())
+                && (getSymbols().getEscapedDelimiter() == null || !key
+                        .endsWith(getSymbols().getEscapedDelimiter()));
     }
 
     /**
@@ -481,9 +481,9 @@ public class DefaultConfigurationKey
      */
     private boolean hasLeadingDelimiter(String key)
     {
-        return key.startsWith(getExpressionEngine().getPropertyDelimiter())
-                && (getExpressionEngine().getEscapedDelimiter() == null || !key
-                        .startsWith(getExpressionEngine().getEscapedDelimiter()));
+        return key.startsWith(getSymbols().getPropertyDelimiter())
+                && (getSymbols().getEscapedDelimiter() == null || !key
+                        .startsWith(getSymbols().getEscapedDelimiter()));
     }
 
     /**
@@ -496,9 +496,9 @@ public class DefaultConfigurationKey
     {
         return key
                 .substring(
-                        getExpressionEngine().getAttributeStart().length(),
+                        getSymbols().getAttributeStart().length(),
                         key.length()
-                                - ((getExpressionEngine().getAttributeEnd() != null) ? getExpressionEngine()
+                                - ((getSymbols().getAttributeEnd() != null) ? getSymbols()
                                         .getAttributeEnd().length()
                                         : 0));
     }
@@ -511,13 +511,23 @@ public class DefaultConfigurationKey
      */
     private String unescapeDelimiters(String key)
     {
-        return (getExpressionEngine().getEscapedDelimiter() == null) ? key
-                : StringUtils.replace(key, getExpressionEngine()
-                        .getEscapedDelimiter(), getExpressionEngine()
+        return (getSymbols().getEscapedDelimiter() == null) ? key
+                : StringUtils.replace(key, getSymbols()
+                        .getEscapedDelimiter(), getSymbols()
                         .getPropertyDelimiter());
     }
 
     /**
+     * Returns the symbols object from the associated expression engine.
+     *
+     * @return the {@code DefaultExpressionEngineSymbols}
+     */
+    private DefaultExpressionEngineSymbols getSymbols()
+    {
+        return getExpressionEngine().getSymbols();
+    }
+
+    /**
      * Escapes the delimiters in the specified string.
      *
      * @param key the key to be escaped
@@ -525,10 +535,10 @@ public class DefaultConfigurationKey
      */
     private String escapeDelimiters(String key)
     {
-        return (getExpressionEngine().getEscapedDelimiter() == null || key
-                .indexOf(getExpressionEngine().getPropertyDelimiter()) < 0) ? key
-                : StringUtils.replace(key, getExpressionEngine()
-                        .getPropertyDelimiter(), getExpressionEngine()
+        return (getSymbols().getEscapedDelimiter() == null || key
+                .indexOf(getSymbols().getPropertyDelimiter()) < 0) ? key
+                : StringUtils.replace(key, getSymbols()
+                        .getPropertyDelimiter(), getSymbols()
                         .getEscapedDelimiter());
     }
 
@@ -749,7 +759,7 @@ public class DefaultConfigurationKey
             while (startIndex < length()
                     && hasLeadingDelimiter(keyBuffer.substring(startIndex)))
             {
-                startIndex += getExpressionEngine().getPropertyDelimiter()
+                startIndex += getSymbols().getPropertyDelimiter()
                         .length();
             }
 
@@ -775,7 +785,7 @@ public class DefaultConfigurationKey
         private String nextKeyPart()
         {
             int attrIdx = keyBuffer.toString().indexOf(
-                    getExpressionEngine().getAttributeStart(), startIndex);
+                    getSymbols().getAttributeStart(), startIndex);
             if (attrIdx < 0 || attrIdx == startIndex)
             {
                 attrIdx = length();
@@ -807,7 +817,7 @@ public class DefaultConfigurationKey
 
             do
             {
-                delimiterPos = key.indexOf(getExpressionEngine()
+                delimiterPos = key.indexOf(getSymbols()
                         .getPropertyDelimiter(), delimiterPos);
                 if (delimiterPos < 0 || delimiterPos >= endPos)
                 {
@@ -839,7 +849,7 @@ public class DefaultConfigurationKey
          */
         private int escapedPosition(String key, int pos)
         {
-            if (getExpressionEngine().getEscapedDelimiter() == null)
+            if (getSymbols().getEscapedDelimiter() == null)
             {
                 // nothing to escape
                 return -1;
@@ -851,14 +861,14 @@ public class DefaultConfigurationKey
                 return -1;
             }
 
-            int escapePos = key.indexOf(getExpressionEngine()
+            int escapePos = key.indexOf(getSymbols()
                     .getEscapedDelimiter(), pos - escapeOffset);
             if (escapePos <= pos && escapePos >= 0)
             {
                 // The found delimiter is escaped. Next valid search position
                 // is behind the escaped delimiter.
                 return escapePos
-                        + getExpressionEngine().getEscapedDelimiter().length();
+                        + getSymbols().getEscapedDelimiter().length();
             }
             else
             {
@@ -885,8 +895,8 @@ public class DefaultConfigurationKey
          */
         private int escapeOffset()
         {
-            return getExpressionEngine().getEscapedDelimiter().indexOf(
-                    getExpressionEngine().getPropertyDelimiter());
+            return getSymbols().getEscapedDelimiter().indexOf(
+                    getSymbols().getPropertyDelimiter());
         }
 
         /**
@@ -922,10 +932,10 @@ public class DefaultConfigurationKey
 
             try
             {
-                int idx = key.lastIndexOf(getExpressionEngine().getIndexStart());
+                int idx = key.lastIndexOf(getSymbols().getIndexStart());
                 if (idx > 0)
                 {
-                    int endidx = key.indexOf(getExpressionEngine().getIndexEnd(),
+                    int endidx = key.indexOf(getSymbols().getIndexEnd(),
                             idx);
 
                     if (endidx > idx + 1)
@@ -958,9 +968,9 @@ public class DefaultConfigurationKey
          */
         private boolean isAttributeEmulatingMode()
         {
-            return getExpressionEngine().getAttributeEnd() == null
-                    && StringUtils.equals(getExpressionEngine()
-                            .getPropertyDelimiter(), getExpressionEngine()
+            return getSymbols().getAttributeEnd() == null
+                    && StringUtils.equals(getSymbols()
+                            .getPropertyDelimiter(), getSymbols()
                             .getAttributeStart());
         }
     }

Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultExpressionEngine.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultExpressionEngine.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultExpressionEngine.java (original)
+++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/tree/DefaultExpressionEngine.java Mon Jan  6 14:56:38 2014
@@ -99,6 +99,16 @@ import org.apache.commons.lang3.StringUt
  * It is also possible to set custom values for these properties so that you can
  * adapt a {@code DefaultExpressionEngine} to your personal needs.
  * </p>
+ * <p>
+ * The concrete symbols used by an instance are determined by a
+ * {@link DefaultExpressionEngineSymbols} object passed to the constructor.
+ * By providing a custom symbols object the syntax for querying properties in
+ * a hierarchical configuration can be altered.
+ * </p>
+ * <p>
+ * Instances of this class are thread-safe and can be shared between multiple
+ * hierarchical configuration objects.
+ * </p>
  *
  * @since 1.3
  * @author <a
@@ -108,169 +118,43 @@ import org.apache.commons.lang3.StringUt
  */
 public class DefaultExpressionEngine implements ExpressionEngine
 {
-    /** Constant for the default property delimiter. */
-    public static final String DEFAULT_PROPERTY_DELIMITER = ".";
-
-    /** Constant for the default escaped property delimiter. */
-    public static final String DEFAULT_ESCAPED_DELIMITER = DEFAULT_PROPERTY_DELIMITER
-            + DEFAULT_PROPERTY_DELIMITER;
-
-    /** Constant for the default attribute start marker. */
-    public static final String DEFAULT_ATTRIBUTE_START = "[@";
-
-    /** Constant for the default attribute end marker. */
-    public static final String DEFAULT_ATTRIBUTE_END = "]";
-
-    /** Constant for the default index start marker. */
-    public static final String DEFAULT_INDEX_START = "(";
-
-    /** Constant for the default index end marker. */
-    public static final String DEFAULT_INDEX_END = ")";
-
-    /** Stores the property delimiter. */
-    private String propertyDelimiter = DEFAULT_PROPERTY_DELIMITER;
-
-    /** Stores the escaped property delimiter. */
-    private String escapedDelimiter = DEFAULT_ESCAPED_DELIMITER;
-
-    /** Stores the attribute start marker. */
-    private String attributeStart = DEFAULT_ATTRIBUTE_START;
-
-    /** Stores the attribute end marker. */
-    private String attributeEnd = DEFAULT_ATTRIBUTE_END;
-
-    /** Stores the index start marker. */
-    private String indexStart = DEFAULT_INDEX_START;
-
-    /** stores the index end marker. */
-    private String indexEnd = DEFAULT_INDEX_END;
-
-    /**
-     * Sets the attribute end marker.
-     *
-     * @return the attribute end marker
-     */
-    public String getAttributeEnd()
-    {
-        return attributeEnd;
-    }
-
-    /**
-     * Sets the attribute end marker.
-     *
-     * @param attributeEnd the attribute end marker; can be <b>null</b> if no
-     * end marker is needed
-     */
-    public void setAttributeEnd(String attributeEnd)
-    {
-        this.attributeEnd = attributeEnd;
-    }
-
-    /**
-     * Returns the attribute start marker.
-     *
-     * @return the attribute start marker
-     */
-    public String getAttributeStart()
-    {
-        return attributeStart;
-    }
-
-    /**
-     * Sets the attribute start marker. Attribute start and end marker are used
-     * together to detect attributes in a property key.
-     *
-     * @param attributeStart the attribute start marker
-     */
-    public void setAttributeStart(String attributeStart)
-    {
-        this.attributeStart = attributeStart;
-    }
-
-    /**
-     * Returns the escaped property delimiter string.
-     *
-     * @return the escaped property delimiter
-     */
-    public String getEscapedDelimiter()
-    {
-        return escapedDelimiter;
-    }
-
-    /**
-     * Sets the escaped property delimiter string. With this string a delimiter
-     * that belongs to the key of a property can be escaped. If for instance
-     * &quot;.&quot; is used as property delimiter, you can set the escaped
-     * delimiter to &quot;\.&quot; and can then escape the delimiter with a back
-     * slash.
-     *
-     * @param escapedDelimiter the escaped delimiter string
-     */
-    public void setEscapedDelimiter(String escapedDelimiter)
-    {
-        this.escapedDelimiter = escapedDelimiter;
-    }
-
-    /**
-     * Returns the index end marker.
-     *
-     * @return the index end marker
-     */
-    public String getIndexEnd()
-    {
-        return indexEnd;
-    }
-
     /**
-     * Sets the index end marker.
-     *
-     * @param indexEnd the index end marker
-     */
-    public void setIndexEnd(String indexEnd)
-    {
-        this.indexEnd = indexEnd;
-    }
-
-    /**
-     * Returns the index start marker.
-     *
-     * @return the index start marker
+     * A default instance of this class that is used as expression engine for
+     * hierarchical configurations per default.
      */
-    public String getIndexStart()
-    {
-        return indexStart;
-    }
+    public static final DefaultExpressionEngine INSTANCE =
+            new DefaultExpressionEngine(
+                    DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS);
 
-    /**
-     * Sets the index start marker. Index start and end marker are used together
-     * to detect indices in a property key.
-     *
-     * @param indexStart the index start marker
-     */
-    public void setIndexStart(String indexStart)
-    {
-        this.indexStart = indexStart;
-    }
+    /** The symbols used by this instance. */
+    private final DefaultExpressionEngineSymbols symbols;
 
     /**
-     * Returns the property delimiter.
+     * Creates a new instance of {@code DefaultExpressionEngine} and initializes
+     * its symbols.
      *
-     * @return the property delimiter
+     * @param syms the object with the symbols (must not be <b>null</b>)
+     * @throws IllegalArgumentException if the symbols are <b>null</b>
      */
-    public String getPropertyDelimiter()
+    public DefaultExpressionEngine(DefaultExpressionEngineSymbols syms)
     {
-        return propertyDelimiter;
+        if (syms == null)
+        {
+            throw new IllegalArgumentException("Symbols must not be null!");
+        }
+        symbols = syms;
     }
 
     /**
-     * Sets the property delimiter. This string is used to split the parts of a
-     * property key.
+     * Returns the {@code DefaultExpressionEngineSymbols} object associated with
+     * this instance.
      *
-     * @param propertyDelimiter the property delimiter
+     * @return the {@code DefaultExpressionEngineSymbols} used by this engine
+     * @since 2.0
      */
-    public void setPropertyDelimiter(String propertyDelimiter)
+    public DefaultExpressionEngineSymbols getSymbols()
     {
-        this.propertyDelimiter = propertyDelimiter;
+        return symbols;
     }
 
     /**

Modified: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestCombinedConfiguration.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestCombinedConfiguration.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestCombinedConfiguration.java (original)
+++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestCombinedConfiguration.java Mon Jan  6 14:56:38 2014
@@ -35,8 +35,6 @@ import java.util.Set;
 import java.util.concurrent.CountDownLatch;
 import java.util.concurrent.atomic.AtomicInteger;
 
-import junit.framework.Assert;
-
 import org.apache.commons.configuration.SynchronizerTestImpl.Methods;
 import org.apache.commons.configuration.convert.DefaultListDelimiterHandler;
 import org.apache.commons.configuration.event.ConfigurationEvent;
@@ -49,6 +47,7 @@ import org.apache.commons.configuration.
 import org.apache.commons.configuration.sync.Synchronizer;
 import org.apache.commons.configuration.tree.ConfigurationNode;
 import org.apache.commons.configuration.tree.DefaultExpressionEngine;
+import org.apache.commons.configuration.tree.DefaultExpressionEngineSymbols;
 import org.apache.commons.configuration.tree.NodeCombiner;
 import org.apache.commons.configuration.tree.OverrideCombiner;
 import org.apache.commons.configuration.tree.UnionCombiner;
@@ -588,13 +587,17 @@ public class TestCombinedConfiguration
         child.setListDelimiterHandler(new DefaultListDelimiterHandler(','));
         child.addProperty("test(a)", "1,2,3");
         config.addConfiguration(child);
-        DefaultExpressionEngine engineQuery = new DefaultExpressionEngine();
-        engineQuery.setIndexStart("<");
-        engineQuery.setIndexEnd(">");
+        DefaultExpressionEngine engineQuery =
+                new DefaultExpressionEngine(
+                        new DefaultExpressionEngineSymbols.Builder(
+                                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                                .setIndexStart("<").setIndexEnd(">").create());
         config.setExpressionEngine(engineQuery);
-        DefaultExpressionEngine engineConvert = new DefaultExpressionEngine();
-        engineConvert.setIndexStart("[");
-        engineConvert.setIndexEnd("]");
+        DefaultExpressionEngine engineConvert =
+                new DefaultExpressionEngine(
+                        new DefaultExpressionEngineSymbols.Builder(
+                                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                                .setIndexStart("[").setIndexEnd("]").create());
         config.setConversionExpressionEngine(engineConvert);
         assertEquals("Wrong property 1", "1", config.getString("test(a)<0>"));
         assertEquals("Wrong property 2", "2", config.getString("test(a)<1>"));
@@ -801,7 +804,8 @@ public class TestCombinedConfiguration
     public void testSetConversionExpressionEngineSynchronized()
     {
         SynchronizerTestImpl sync = setUpSynchronizerTest();
-        config.setConversionExpressionEngine(new DefaultExpressionEngine());
+        config.setConversionExpressionEngine(new DefaultExpressionEngine(
+                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS));
         sync.verify(Methods.BEGIN_WRITE, Methods.END_WRITE);
         assertNull("Root node was constructed", config.getRootNode());
     }
@@ -1000,9 +1004,9 @@ public class TestCombinedConfiguration
          */
         public void checkEvent(int expectedInvalidate, int expectedOthers)
         {
-            Assert.assertEquals("Wrong number of invalidate events",
+            assertEquals("Wrong number of invalidate events",
                     expectedInvalidate, invalidateEvents);
-            Assert.assertEquals("Wrong number of other events", expectedOthers,
+            assertEquals("Wrong number of other events", expectedOthers,
                     otherEvents);
         }
     }

Modified: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestConfigurationUtils.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestConfigurationUtils.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestConfigurationUtils.java (original)
+++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestConfigurationUtils.java Mon Jan  6 14:56:38 2014
@@ -40,6 +40,7 @@ import org.apache.commons.configuration.
 import org.apache.commons.configuration.ex.ConfigurationRuntimeException;
 import org.apache.commons.configuration.sync.NoOpSynchronizer;
 import org.apache.commons.configuration.tree.DefaultExpressionEngine;
+import org.apache.commons.configuration.tree.DefaultExpressionEngineSymbols;
 import org.apache.commons.configuration.tree.ExpressionEngine;
 import org.easymock.EasyMock;
 import org.junit.After;
@@ -216,9 +217,11 @@ public class TestConfigurationUtils
         Configuration conf = new BaseConfiguration();
         conf.addProperty("test(a)", Boolean.TRUE);
         conf.addProperty("test(b)", Boolean.FALSE);
-        DefaultExpressionEngine engine = new DefaultExpressionEngine();
-        engine.setIndexStart("[");
-        engine.setIndexEnd("]");
+        DefaultExpressionEngine engine =
+                new DefaultExpressionEngine(
+                        new DefaultExpressionEngineSymbols.Builder(
+                                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                                .setIndexStart("[").setIndexEnd("]").create());
         HierarchicalConfiguration hc = ConfigurationUtils
                 .convertToHierarchical(conf, engine);
         assertTrue("Wrong value for test(a)", hc.getBoolean("test(a)"));
@@ -233,7 +236,9 @@ public class TestConfigurationUtils
     public void testConvertHierarchicalToHierarchicalEngine()
     {
         BaseHierarchicalConfiguration hc = new BaseHierarchicalConfiguration();
-        ExpressionEngine engine = new DefaultExpressionEngine();
+        ExpressionEngine engine =
+                new DefaultExpressionEngine(
+                        DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS);
         assertSame("Created new configuration", hc, ConfigurationUtils
                 .convertToHierarchical(hc, engine));
         assertSame("Engine was not set", engine, hc.getExpressionEngine());
@@ -248,7 +253,9 @@ public class TestConfigurationUtils
     public void testConvertHierarchicalToHierarchicalNullEngine()
     {
         BaseHierarchicalConfiguration hc = new BaseHierarchicalConfiguration();
-        ExpressionEngine engine = new DefaultExpressionEngine();
+        ExpressionEngine engine =
+                new DefaultExpressionEngine(
+                        DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS);
         hc.setExpressionEngine(engine);
         assertSame("Created new configuration", hc, ConfigurationUtils
                 .convertToHierarchical(hc, null));

Modified: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestHierarchicalConfiguration.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestHierarchicalConfiguration.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestHierarchicalConfiguration.java (original)
+++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/TestHierarchicalConfiguration.java Mon Jan  6 14:56:38 2014
@@ -40,6 +40,7 @@ import org.apache.commons.configuration.
 import org.apache.commons.configuration.tree.DefaultConfigurationKey;
 import org.apache.commons.configuration.tree.DefaultConfigurationNode;
 import org.apache.commons.configuration.tree.DefaultExpressionEngine;
+import org.apache.commons.configuration.tree.DefaultExpressionEngineSymbols;
 import org.apache.commons.configuration.tree.ExpressionEngine;
 import org.junit.Before;
 import org.junit.Test;
@@ -449,7 +450,7 @@ public class TestHierarchicalConfigurati
      */
     private static DefaultConfigurationKey createConfigurationKey()
     {
-        return new DefaultConfigurationKey(new DefaultExpressionEngine());
+        return new DefaultConfigurationKey(DefaultExpressionEngine.INSTANCE);
     }
 
     @Test(expected = IllegalArgumentException.class)
@@ -473,7 +474,7 @@ public class TestHierarchicalConfigurati
         for(int i = 0; i <= maxIdx; i++)
         {
             DefaultConfigurationKey key =
-                    new DefaultConfigurationKey(new DefaultExpressionEngine(),
+                    new DefaultConfigurationKey(DefaultExpressionEngine.INSTANCE,
                             "tables.table(0).fields");
             key.append("field").appendIndex(i).append("name");
             assertNotNull(config.getProperty(key.toString()));
@@ -1275,10 +1276,12 @@ public class TestHierarchicalConfigurati
 
     private ExpressionEngine createAlternativeExpressionEngine()
     {
-        DefaultExpressionEngine engine = new DefaultExpressionEngine();
-        engine.setPropertyDelimiter("/");
-        engine.setIndexStart("[");
-        engine.setIndexEnd("]");
+        DefaultExpressionEngine engine =
+                new DefaultExpressionEngine(
+                        new DefaultExpressionEngineSymbols.Builder(
+                                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                                .setPropertyDelimiter("/").setIndexStart("[")
+                                .setIndexEnd("]").create());
         return engine;
     }
 

Modified: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultConfigurationKey.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultConfigurationKey.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultConfigurationKey.java (original)
+++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultConfigurationKey.java Mon Jan  6 14:56:38 2014
@@ -53,7 +53,7 @@ public class TestDefaultConfigurationKey
     @Before
     public void setUp() throws Exception
     {
-        expressionEngine = new DefaultExpressionEngine();
+        expressionEngine = DefaultExpressionEngine.INSTANCE;
         key = new DefaultConfigurationKey(expressionEngine);
     }
 
@@ -91,6 +91,17 @@ public class TestDefaultConfigurationKey
     }
 
     /**
+     * Returns a builder for symbols with default property settings.
+     *
+     * @return the initialized builder object
+     */
+    private DefaultExpressionEngineSymbols.Builder symbols()
+    {
+        return new DefaultExpressionEngineSymbols.Builder(
+                expressionEngine.getSymbols());
+    }
+
+    /**
      * Tests if attribute keys are correctly detected if no end markers are set.
      * (In this test case we use the same delimiter for attributes as for simple
      * properties.)
@@ -98,16 +109,20 @@ public class TestDefaultConfigurationKey
     @Test
     public void testIsAttributeKeyWithoutEndMarkers()
     {
-        expressionEngine.setAttributeEnd(null);
-        expressionEngine
-                .setAttributeStart(DefaultExpressionEngine.DEFAULT_PROPERTY_DELIMITER);
+        DefaultExpressionEngineSymbols symbols =
+                symbols()
+                        .setAttributeEnd(null)
+                        .setAttributeStart(
+                                DefaultExpressionEngineSymbols.DEFAULT_PROPERTY_DELIMITER)
+                        .create();
+        expressionEngine = new DefaultExpressionEngine(symbols);
+        key = new DefaultConfigurationKey(expressionEngine);
         assertTrue(
                 "Attribute key not detected",
-                key
-                        .isAttributeKey(DefaultExpressionEngine.DEFAULT_PROPERTY_DELIMITER
-                                + "test"));
-        assertFalse("Property key considered as attribute key", key
-                .isAttributeKey(TESTATTR));
+                key.isAttributeKey(DefaultExpressionEngineSymbols.DEFAULT_PROPERTY_DELIMITER
+                        + "test"));
+        assertFalse("Property key considered as attribute key",
+                key.isAttributeKey(TESTATTR));
     }
 
     /**
@@ -143,7 +158,7 @@ public class TestDefaultConfigurationKey
         assertEquals("Key was not trimmed", "test", key.trim(".test."));
         assertEquals("Null key could not be processed", "", key.trim(null));
         assertEquals("Delimiter could not be processed", "", key
-                .trim(DefaultExpressionEngine.DEFAULT_PROPERTY_DELIMITER));
+                .trim(DefaultExpressionEngineSymbols.DEFAULT_PROPERTY_DELIMITER));
     }
 
     /**
@@ -170,13 +185,16 @@ public class TestDefaultConfigurationKey
     }
 
     /**
-     * Tests appending keys that contain delimiters when no escpaped delimiter
+     * Tests appending keys that contain delimiters when no escaped delimiter
      * is defined.
      */
     @Test
     public void testAppendDelimitersWithoutEscaping()
     {
-        expressionEngine.setEscapedDelimiter(null);
+        expressionEngine =
+                new DefaultExpressionEngine(symbols().setEscapedDelimiter(null)
+                        .create());
+        key = new DefaultConfigurationKey(expressionEngine);
         key.append("key.......").append("test").append(".");
         key.append(".more").append("..tests");
         assertEquals("Wrong constructed key", "key.test.more.tests", key
@@ -216,9 +234,14 @@ public class TestDefaultConfigurationKey
     @Test
     public void testConstructAttributeKeyWithoutEndMarkers()
     {
-        expressionEngine.setAttributeEnd(null);
-        expressionEngine.setAttributeStart(expressionEngine
-                .getPropertyDelimiter());
+        DefaultExpressionEngineSymbols symbols =
+                symbols()
+                        .setAttributeEnd(null)
+                        .setAttributeStart(
+                                expressionEngine.getSymbols()
+                                        .getPropertyDelimiter()).create();
+        expressionEngine = new DefaultExpressionEngine(symbols);
+        key = new DefaultConfigurationKey(expressionEngine);
         assertEquals("Wrong attribute key", ".test", key
                 .constructAttributeKey("test"));
         assertEquals("Attribute key was incorrectly converted", ".test", key
@@ -428,7 +451,10 @@ public class TestDefaultConfigurationKey
     @Test
     public void testIterateAlternativeEscapeDelimiter()
     {
-        expressionEngine.setEscapedDelimiter("\\.");
+        expressionEngine =
+                new DefaultExpressionEngine(symbols()
+                        .setEscapedDelimiter("\\.").create());
+        key = new DefaultConfigurationKey(expressionEngine);
         key.append("\\.my\\.elem");
         key.append("trailing\\.dot\\.");
         key.append(".strange");
@@ -446,7 +472,10 @@ public class TestDefaultConfigurationKey
     @Test
     public void testIterateWithoutEscapeDelimiter()
     {
-        expressionEngine.setEscapedDelimiter(null);
+        expressionEngine =
+                new DefaultExpressionEngine(symbols()
+                        .setEscapedDelimiter(null).create());
+        key = new DefaultConfigurationKey(expressionEngine);
         key.append("..my..elem.trailing..dot...strange");
         assertEquals("Wrong key", "my..elem.trailing..dot...strange", key
                 .toString());
@@ -507,9 +536,14 @@ public class TestDefaultConfigurationKey
     @Test
     public void testIterateAttributeEqualsPropertyDelimiter()
     {
-        expressionEngine.setAttributeEnd(null);
-        expressionEngine.setAttributeStart(expressionEngine
-                .getPropertyDelimiter());
+        expressionEngine =
+                new DefaultExpressionEngine(
+                        symbols()
+                                .setAttributeEnd(null)
+                                .setAttributeStart(
+                                        DefaultExpressionEngineSymbols.DEFAULT_PROPERTY_DELIMITER)
+                                .create());
+        key = new DefaultConfigurationKey(expressionEngine);
         key.append("this.isa.key");
         DefaultConfigurationKey.KeyIterator kit = key.iterator();
         assertEquals("Wrong first key part", "this", kit.next());

Modified: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultExpressionEngine.java
URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultExpressionEngine.java?rev=1555839&r1=1555838&r2=1555839&view=diff
==============================================================================
--- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultExpressionEngine.java (original)
+++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/tree/TestDefaultExpressionEngine.java Mon Jan  6 14:56:38 2014
@@ -52,16 +52,36 @@ public class TestDefaultExpressionEngine
     { "docid", "name", "creationDate", "authorID", "version"}};
 
     /** The object to be tested. */
-    DefaultExpressionEngine engine;
+    private DefaultExpressionEngine engine;
 
     /** The root of a hierarchy with configuration nodes. */
-    ConfigurationNode root;
+    private ConfigurationNode root;
 
     @Before
     public void setUp() throws Exception
     {
         root = setUpNodes();
-        engine = new DefaultExpressionEngine();
+        engine = DefaultExpressionEngine.INSTANCE;
+    }
+
+    /**
+     * Tests whether the default instance is initialized with default symbols.
+     */
+    @Test
+    public void testDefaultSymbols()
+    {
+        assertSame("Wrong default symbols",
+                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS,
+                engine.getSymbols());
+    }
+
+    /**
+     * Tries to create an instance without symbols.
+     */
+    @Test(expected = IllegalArgumentException.class)
+    public void testInitNoSymbols()
+    {
+        new DefaultExpressionEngine(null);
     }
 
     /**
@@ -129,8 +149,14 @@ public class TestDefaultExpressionEngine
     @Test
     public void testQueryAttributeEmulation()
     {
-        engine.setAttributeEnd(null);
-        engine.setAttributeStart(engine.getPropertyDelimiter());
+        DefaultExpressionEngineSymbols symbols =
+                new DefaultExpressionEngineSymbols.Builder(
+                        DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                        .setAttributeEnd(null)
+                        .setAttributeStart(
+                                DefaultExpressionEngineSymbols.DEFAULT_PROPERTY_DELIMITER)
+                        .create();
+        engine = new DefaultExpressionEngine(symbols);
         checkKeyValue("tables.table(0).name", "name", tables[0]);
         checkKeyValue("tables.table(0).type", "type", tabTypes[0]);
         checkKey("tables.table.type", "type", 2);
@@ -219,7 +245,7 @@ public class TestDefaultExpressionEngine
     }
 
     /**
-     * Tests obtaining node keys when a different syntax is set.
+     * Tests obtaining node keys if a different syntax is set.
      */
     @Test
     public void testNodeKeyWithAlternativeSyntax()
@@ -229,10 +255,24 @@ public class TestDefaultExpressionEngine
                 .getChild(0).getChild(0), "tables"));
         assertEquals("Wrong attribute key", "@test", engine.nodeKey(root
                 .getAttribute(0), ""));
+    }
 
-        engine.setAttributeStart(engine.getPropertyDelimiter());
-        assertEquals("Wrong attribute key", "/test", engine.nodeKey(root
-                .getAttribute(0), ""));
+    /**
+     * Tests obtaining node keys if a different syntax is set and the same
+     * string is used as property delimiter and attribute start marker.
+     */
+    @Test
+    public void testNodeKeyWithAlternativeSyntaxAttributePropertyDelimiter()
+    {
+        setUpAlternativeSyntax();
+        DefaultExpressionEngineSymbols symbols =
+                new DefaultExpressionEngineSymbols.Builder(engine.getSymbols())
+                        .setAttributeStart(
+                                engine.getSymbols().getPropertyDelimiter())
+                        .create();
+        engine = new DefaultExpressionEngine(symbols);
+        assertEquals("Wrong attribute key", "/test",
+                engine.nodeKey(root.getAttribute(0), ""));
     }
 
     /**
@@ -330,14 +370,20 @@ public class TestDefaultExpressionEngine
     }
 
     /**
-     * Tests add operations when property and attribute delimiters are equal.
+     * Tests add operations if property and attribute delimiters are equal.
      * Then it is not possible to add new attribute nodes.
      */
     @Test
     public void testPrepareAddWithSameAttributeDelimiter()
     {
-        engine.setAttributeEnd(null);
-        engine.setAttributeStart(engine.getPropertyDelimiter());
+        DefaultExpressionEngineSymbols symbols =
+                new DefaultExpressionEngineSymbols.Builder(
+                        DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS)
+                        .setAttributeEnd(null)
+                        .setAttributeStart(
+                                DefaultExpressionEngineSymbols.DEFAULT_SYMBOLS
+                                        .getPropertyDelimiter()).create();
+        engine = new DefaultExpressionEngine(symbols);
 
         NodeAddData data = engine.prepareAdd(root, "tables.table(0).test");
         assertEquals("Wrong name of new node", "test", data.getNewNodeName());
@@ -459,12 +505,12 @@ public class TestDefaultExpressionEngine
      */
     private void setUpAlternativeSyntax()
     {
-        engine.setAttributeEnd(null);
-        engine.setAttributeStart("@");
-        engine.setPropertyDelimiter("/");
-        engine.setEscapedDelimiter(null);
-        engine.setIndexStart("[");
-        engine.setIndexEnd("]");
+        DefaultExpressionEngineSymbols symbols =
+                new DefaultExpressionEngineSymbols.Builder()
+                        .setAttributeEnd(null).setAttributeStart("@")
+                        .setPropertyDelimiter("/").setEscapedDelimiter(null)
+                        .setIndexStart("[").setIndexEnd("]").create();
+        engine = new DefaultExpressionEngine(symbols);
     }
 
     /**