cayenne-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From ntimof...@apache.org
Subject [10/13] cayenne git commit: CAY-2345 Own template renderer as a replacement for Velocity - move Velocity to separate module - remove dependencies on commons-lang
Date Wed, 16 Aug 2017 15:37:02 GMT
CAY-2345 Own template renderer as a replacement for Velocity
  - move Velocity to separate module
  - remove dependencies on commons-lang


Project: http://git-wip-us.apache.org/repos/asf/cayenne/repo
Commit: http://git-wip-us.apache.org/repos/asf/cayenne/commit/f734851f
Tree: http://git-wip-us.apache.org/repos/asf/cayenne/tree/f734851f
Diff: http://git-wip-us.apache.org/repos/asf/cayenne/diff/f734851f

Branch: refs/heads/master
Commit: f734851f4f7ef71eb95d78c8432c94035f1d9e20
Parents: 54feb97
Author: Nikita Timofeev <stariy95@gmail.com>
Authored: Wed Aug 9 16:42:09 2017 +0300
Committer: Nikita Timofeev <stariy95@gmail.com>
Committed: Wed Aug 16 18:30:02 2017 +0300

----------------------------------------------------------------------
 cayenne-ant/pom.xml                             |  14 -
 .../org/apache/cayenne/gen/StringUtils.java     |  14 +-
 .../dbsync/reverse/dbload/ExportedKey.java      |   2 +-
 .../merge/builders/DbAttributeBuilder.java      |   5 +-
 .../dbsync/merge/builders/DbEntityBuilder.java  |   4 +-
 .../dbsync/merge/builders/DefaultBuilder.java   |   6 +-
 .../dbsync/merge/builders/ObjEntityBuilder.java |   4 +-
 cayenne-server/pom.xml                          |   5 -
 .../access/jdbc/RowDescriptorBuilder.java       |   4 +-
 .../configuration/server/ServerModule.java      |   2 -
 .../template/SQLTemplateRenderingUtils.java     |  37 +
 .../apache/cayenne/util/CompareToBuilder.java   | 717 +++++++++++++++++++
 .../main/java/org/apache/cayenne/util/Util.java |  26 +
 .../ConcurrentLinkedHashMap.java                |  86 +--
 .../apache/cayenne/velocity/BindDirective.java  | 158 ----
 .../cayenne/velocity/BindEqualDirective.java    |  57 --
 .../cayenne/velocity/BindNotEqualDirective.java |  56 --
 .../velocity/BindObjectEqualDirective.java      | 164 -----
 .../velocity/BindObjectNotEqualDirective.java   |  70 --
 .../apache/cayenne/velocity/ChainDirective.java | 112 ---
 .../apache/cayenne/velocity/ChunkDirective.java |  75 --
 .../cayenne/velocity/ResultDirective.java       | 202 ------
 .../velocity/SQLTemplateRenderingUtils.java     |  37 -
 .../velocity/SQLTemplateResourceManager.java    | 106 ---
 .../velocity/VelocitySQLTemplateProcessor.java  | 208 ------
 .../template/directive/BindDirectiveIT.java     | 239 +++++++
 .../template/directive/ResultDirectiveIT.java   | 112 +++
 .../cayenne/velocity/BindDirectiveIT.java       | 239 -------
 .../cayenne/velocity/ResultDirectiveIT.java     | 112 ---
 .../SQLTemplateResourceManagerTest.java         |  77 --
 .../VelocitySQLTemplateProcessorTest.java       | 234 ------
 .../VelocitySQLTemplateProcessor_ChainTest.java | 184 -----
 ...VelocitySQLTemplateProcessor_SelectTest.java | 109 ---
 cayenne-velocity/pom.xml                        |  87 +++
 .../apache/cayenne/velocity/BindDirective.java  | 158 ++++
 .../cayenne/velocity/BindEqualDirective.java    |  57 ++
 .../cayenne/velocity/BindNotEqualDirective.java |  56 ++
 .../velocity/BindObjectEqualDirective.java      | 164 +++++
 .../velocity/BindObjectNotEqualDirective.java   |  70 ++
 .../apache/cayenne/velocity/ChainDirective.java | 112 +++
 .../apache/cayenne/velocity/ChunkDirective.java |  75 ++
 .../cayenne/velocity/ResultDirective.java       | 202 ++++++
 .../velocity/SQLTemplateResourceManager.java    | 106 +++
 .../apache/cayenne/velocity/VelocityModule.java |  35 +
 .../velocity/VelocitySQLTemplateProcessor.java  | 209 ++++++
 .../velocity/VelocityServerModuleProvider.java  |  50 ++
 ...iguration.server.CayenneServerModuleProvider |  20 +
 .../SQLTemplateResourceManagerTest.java         |  77 ++
 .../VelocitySQLTemplateProcessorTest.java       | 234 ++++++
 .../VelocitySQLTemplateProcessor_ChainTest.java | 184 +++++
 ...VelocitySQLTemplateProcessor_SelectTest.java | 109 +++
 docs/doc/pom.xml                                |   5 -
 modeler/cayenne-modeler/pom.xml                 |  25 +-
 modeler/cayenne-wocompat/pom.xml                |  32 +-
 pom.xml                                         |   7 +-
 55 files changed, 3202 insertions(+), 2349 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-ant/pom.xml
----------------------------------------------------------------------
diff --git a/cayenne-ant/pom.xml b/cayenne-ant/pom.xml
index 9b12f4e..6773efb 100644
--- a/cayenne-ant/pom.xml
+++ b/cayenne-ant/pom.xml
@@ -39,34 +39,20 @@
         <dependency>
             <groupId>org.apache.ant</groupId>
             <artifactId>ant</artifactId>
-            <scope>compile</scope>
         </dependency>
 		<dependency>
-			<groupId>commons-collections</groupId>
-			<artifactId>commons-collections</artifactId>
-            <scope>compile</scope>
-		</dependency>
-		<dependency>
-			<groupId>org.apache.velocity</groupId>
-			<artifactId>velocity</artifactId>
-            <scope>compile</scope>
-		</dependency>
-		<dependency>
 			<groupId>org.apache.cayenne</groupId>
 			<artifactId>cayenne-cgen</artifactId>
 			<version>${project.version}</version>
-            <scope>compile</scope>
 		</dependency>
         <dependency>
             <groupId>org.apache.cayenne</groupId>
             <artifactId>cayenne-dbsync</artifactId>
             <version>${project.version}</version>
-            <scope>compile</scope>
         </dependency>
 		<dependency>
 			<groupId>foundrylogic.vpp</groupId>
 			<artifactId>vpp</artifactId>
-            <scope>compile</scope>
 		</dependency>
 
         <!-- Test Dependencies -->

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-cgen/src/main/java/org/apache/cayenne/gen/StringUtils.java
----------------------------------------------------------------------
diff --git a/cayenne-cgen/src/main/java/org/apache/cayenne/gen/StringUtils.java b/cayenne-cgen/src/main/java/org/apache/cayenne/gen/StringUtils.java
index 778a09b..85e328e 100644
--- a/cayenne-cgen/src/main/java/org/apache/cayenne/gen/StringUtils.java
+++ b/cayenne-cgen/src/main/java/org/apache/cayenne/gen/StringUtils.java
@@ -82,11 +82,7 @@ public class StringUtils {
      * @since 1.1
      */
     public String capitalized(String name) {
-        if (name == null || name.length() == 0)
-            return name;
-
-        char c = Character.toUpperCase(name.charAt(0));
-        return (name.length() == 1) ? Character.toString(c) : c + name.substring(1);
+        return Util.capitalized(name);
     }
 
     /**
@@ -94,12 +90,8 @@ public class StringUtils {
      * 
      * @since 1.2
      */
-    public static String uncapitalized(String aString) {
-        if (aString == null || aString.length() == 0)
-            return aString;
-
-        char c = Character.toLowerCase(aString.charAt(0));
-        return (aString.length() == 1) ? Character.toString(c) : c + aString.substring(1);
+    public String uncapitalized(String aString) {
+        return Util.uncapitalized(aString);
     }
 
     /**

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-dbsync/src/main/java/org/apache/cayenne/dbsync/reverse/dbload/ExportedKey.java
----------------------------------------------------------------------
diff --git a/cayenne-dbsync/src/main/java/org/apache/cayenne/dbsync/reverse/dbload/ExportedKey.java b/cayenne-dbsync/src/main/java/org/apache/cayenne/dbsync/reverse/dbload/ExportedKey.java
index 5443dfc..6d5f25c 100644
--- a/cayenne-dbsync/src/main/java/org/apache/cayenne/dbsync/reverse/dbload/ExportedKey.java
+++ b/cayenne-dbsync/src/main/java/org/apache/cayenne/dbsync/reverse/dbload/ExportedKey.java
@@ -21,7 +21,7 @@ package org.apache.cayenne.dbsync.reverse.dbload;
 
 import org.apache.cayenne.util.EqualsBuilder;
 import org.apache.cayenne.util.HashCodeBuilder;
-import org.apache.commons.lang.builder.CompareToBuilder;
+import org.apache.cayenne.util.CompareToBuilder;
 
 import java.sql.ResultSet;
 import java.sql.SQLException;

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbAttributeBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbAttributeBuilder.java b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbAttributeBuilder.java
index 99739da..094a904 100644
--- a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbAttributeBuilder.java
+++ b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbAttributeBuilder.java
@@ -22,8 +22,7 @@ import org.apache.cayenne.datafactory.DictionaryValueProvider;
 import org.apache.cayenne.datafactory.ValueProvider;
 import org.apache.cayenne.dba.TypesMapping;
 import org.apache.cayenne.map.DbAttribute;
-
-import static org.apache.commons.lang.StringUtils.isEmpty;
+import org.apache.cayenne.util.Util;
 
 /**
  * @since 4.0.
@@ -101,7 +100,7 @@ public class DbAttributeBuilder extends DefaultBuilder<DbAttribute> {
 
     @Override
     public DbAttribute build() {
-        if (isEmpty(obj.getName())) {
+        if (Util.isEmptyString(obj.getName())) {
             name();
         }
 

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbEntityBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbEntityBuilder.java b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbEntityBuilder.java
index 03f0738..5afeedf 100644
--- a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbEntityBuilder.java
+++ b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DbEntityBuilder.java
@@ -20,7 +20,7 @@ package org.apache.cayenne.dbsync.merge.builders;
 
 import org.apache.cayenne.map.DbAttribute;
 import org.apache.cayenne.map.DbEntity;
-import org.apache.commons.lang.StringUtils;
+import org.apache.cayenne.util.Util;
 
 /**
  * @since 4.0.
@@ -73,7 +73,7 @@ public class DbEntityBuilder extends DefaultBuilder<DbEntity> {
     @Override
     public DbEntity build() {
         if (obj.getName() == null) {
-            obj.setName(StringUtils.capitalize(getRandomJavaName()));
+            obj.setName(Util.capitalized(getRandomJavaName()));
         }
 
         return obj;

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DefaultBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DefaultBuilder.java b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DefaultBuilder.java
index 559347b..e44ef38 100644
--- a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DefaultBuilder.java
+++ b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/DefaultBuilder.java
@@ -19,7 +19,7 @@
 package org.apache.cayenne.dbsync.merge.builders;
 
 import org.apache.cayenne.datafactory.DataFactory;
-import org.apache.commons.lang.StringUtils;
+import org.apache.cayenne.util.Util;
 
 /**
  * @since 4.0.
@@ -39,10 +39,10 @@ public abstract class DefaultBuilder<T> implements Builder<T> {
         int count = dataFactory.getNumberBetween(1, 5);
         StringBuilder res = new StringBuilder();
         for (int i = 0; i < count; i++) {
-            res.append(StringUtils.capitalize(dataFactory.getRandomWord()));
+            res.append(Util.capitalized(dataFactory.getRandomWord()));
         }
 
-        return StringUtils.uncapitalize(res.toString());
+        return Util.uncapitalized(res.toString());
     }
 
     @Override

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/ObjEntityBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/ObjEntityBuilder.java b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/ObjEntityBuilder.java
index f2f701c..df52e0e 100644
--- a/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/ObjEntityBuilder.java
+++ b/cayenne-dbsync/src/test/java/org/apache/cayenne/dbsync/merge/builders/ObjEntityBuilder.java
@@ -20,7 +20,7 @@ package org.apache.cayenne.dbsync.merge.builders;
 
 import org.apache.cayenne.map.ObjAttribute;
 import org.apache.cayenne.map.ObjEntity;
-import org.apache.commons.lang.StringUtils;
+import org.apache.cayenne.util.Util;
 
 /**
  * @since 4.0.
@@ -69,7 +69,7 @@ public class ObjEntityBuilder extends DefaultBuilder<ObjEntity> {
     @Override
     public ObjEntity build() {
         if (obj.getName() == null) {
-            obj.setName(StringUtils.capitalize(getRandomJavaName()));
+            obj.setName(Util.capitalized(getRandomJavaName()));
         }
 
         return obj;

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/pom.xml
----------------------------------------------------------------------
diff --git a/cayenne-server/pom.xml b/cayenne-server/pom.xml
index d5d604d..4414f43 100644
--- a/cayenne-server/pom.xml
+++ b/cayenne-server/pom.xml
@@ -49,11 +49,6 @@
 			<artifactId>commons-collections</artifactId>
 			<scope>compile</scope>
 		</dependency>
-		<dependency>
-			<groupId>org.apache.velocity</groupId>
-			<artifactId>velocity</artifactId>
-			<scope>compile</scope>
-		</dependency>
 
 		<!-- Optional dependencies... things that might have been placed in submodules... -->
 		<dependency>

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/access/jdbc/RowDescriptorBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/access/jdbc/RowDescriptorBuilder.java b/cayenne-server/src/main/java/org/apache/cayenne/access/jdbc/RowDescriptorBuilder.java
index 90151c0..ab100af 100644
--- a/cayenne-server/src/main/java/org/apache/cayenne/access/jdbc/RowDescriptorBuilder.java
+++ b/cayenne-server/src/main/java/org/apache/cayenne/access/jdbc/RowDescriptorBuilder.java
@@ -31,8 +31,8 @@ import java.util.Set;
 import org.apache.cayenne.CayenneRuntimeException;
 import org.apache.cayenne.access.types.ExtendedType;
 import org.apache.cayenne.access.types.ExtendedTypeMap;
+import org.apache.cayenne.util.Util;
 import org.apache.commons.collections.Transformer;
-import org.apache.commons.lang.StringUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -143,7 +143,7 @@ public class RowDescriptorBuilder {
         }
 
         if(validateDuplicateColumnNames && !duplicates.isEmpty()) {
-            logger.warn("Found duplicated columns '" + StringUtils.join(duplicates, "', '") + "' in row descriptor. " +
+            logger.warn("Found duplicated columns '" + Util.join(duplicates, "', '") + "' in row descriptor. " +
                     "This can lead to errors when converting result to persistent objects.");
         }
 

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/configuration/server/ServerModule.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/configuration/server/ServerModule.java b/cayenne-server/src/main/java/org/apache/cayenne/configuration/server/ServerModule.java
index e951c49..49018ef 100644
--- a/cayenne-server/src/main/java/org/apache/cayenne/configuration/server/ServerModule.java
+++ b/cayenne-server/src/main/java/org/apache/cayenne/configuration/server/ServerModule.java
@@ -117,7 +117,6 @@ import org.apache.cayenne.tx.DefaultTransactionManager;
 import org.apache.cayenne.tx.TransactionFactory;
 import org.apache.cayenne.tx.TransactionFilter;
 import org.apache.cayenne.tx.TransactionManager;
-import org.apache.cayenne.velocity.VelocitySQLTemplateProcessor;
 import org.xml.sax.XMLReader;
 
 import java.util.Calendar;
@@ -409,7 +408,6 @@ public class ServerModule implements Module {
         binder.bind(TransactionManager.class).to(DefaultTransactionManager.class);
         binder.bind(RowReaderFactory.class).to(DefaultRowReaderFactory.class);
 
-//        binder.bind(SQLTemplateProcessor.class).to(VelocitySQLTemplateProcessor.class);
         binder.bind(SQLTemplateProcessor.class).to(CayenneSQLTemplateProcessor.class);
 
         binder.bind(HandlerFactory.class).to(DefaultHandlerFactory.class);

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/template/SQLTemplateRenderingUtils.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/template/SQLTemplateRenderingUtils.java b/cayenne-server/src/main/java/org/apache/cayenne/template/SQLTemplateRenderingUtils.java
new file mode 100644
index 0000000..f468a9e
--- /dev/null
+++ b/cayenne-server/src/main/java/org/apache/cayenne/template/SQLTemplateRenderingUtils.java
@@ -0,0 +1,37 @@
+/*****************************************************************
+ *   Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ ****************************************************************/
+
+package org.apache.cayenne.template;
+
+import org.apache.cayenne.exp.ExpressionFactory;
+
+/**
+ * Implements utility methods used inside Velocity templates when rendering
+ * SQLTemplates.
+ * 
+ * @since 1.1
+ */
+public class SQLTemplateRenderingUtils {
+	/**
+	 * Returns the result of evaluation of expression with object.
+	 */
+	public Object cayenneExp(Object object, String expression) {
+		return ExpressionFactory.exp(expression).evaluate(object);
+	}
+}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/util/CompareToBuilder.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/util/CompareToBuilder.java b/cayenne-server/src/main/java/org/apache/cayenne/util/CompareToBuilder.java
new file mode 100644
index 0000000..0235910
--- /dev/null
+++ b/cayenne-server/src/main/java/org/apache/cayenne/util/CompareToBuilder.java
@@ -0,0 +1,717 @@
+/*****************************************************************
+ *   Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ ****************************************************************/
+
+package org.apache.cayenne.util;
+
+import java.util.Comparator;
+
+/**
+ * Assists in implementing {@link java.lang.Comparable#compareTo(Object)} methods.
+ *
+ * This code is based on CompareToBuilder from commons-lang v2.6
+ *
+ * @since 4.1
+ */
+public class CompareToBuilder {
+    /**
+     * Current state of the comparison as appended fields are checked.
+     */
+    private int comparison;
+
+    /**
+     * <p>Constructor for CompareToBuilder.</p>
+     *
+     * <p>Starts off assuming that the objects are equal. Multiple calls are
+     * then made to the various append methods, followed by a call to
+     * {@link #toComparison} to get the result.</p>
+     */
+    public CompareToBuilder() {
+        super();
+        comparison = 0;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * <p>Appends to the <code>builder</code> the <code>compareTo(Object)</code>
+     * result of the superclass.</p>
+     *
+     * @param superCompareTo  result of calling <code>super.compareTo(Object)</code>
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder appendSuper(int superCompareTo) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = superCompareTo;
+        return this;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * <p>Appends to the <code>builder</code> the comparison of
+     * two <code>Object</code>s.</p>
+     *
+     * <ol>
+     * <li>Check if <code>lhs == rhs</code></li>
+     * <li>Check if either <code>lhs</code> or <code>rhs</code> is <code>null</code>,
+     *     a <code>null</code> object is less than a non-<code>null</code> object</li>
+     * <li>Check the object contents</li>
+     * </ol>
+     *
+     * <p><code>lhs</code> must either be an array or implement {@link Comparable}.</p>
+     *
+     * @param lhs  left-hand object
+     * @param rhs  right-hand object
+     * @return this - used to chain append calls
+     * @throws ClassCastException  if <code>rhs</code> is not assignment-compatible
+     *  with <code>lhs</code>
+     */
+    public CompareToBuilder append(Object lhs, Object rhs) {
+        return append(lhs, rhs, null);
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the comparison of
+     * two <code>Object</code>s.</p>
+     *
+     * <ol>
+     * <li>Check if <code>lhs == rhs</code></li>
+     * <li>Check if either <code>lhs</code> or <code>rhs</code> is <code>null</code>,
+     *     a <code>null</code> object is less than a non-<code>null</code> object</li>
+     * <li>Check the object contents</li>
+     * </ol>
+     *
+     * <p>If <code>lhs</code> is an array, array comparison methods will be used.
+     * Otherwise <code>comparator</code> will be used to compare the objects.
+     * If <code>comparator</code> is <code>null</code>, <code>lhs</code> must
+     * implement {@link Comparable} instead.</p>
+     *
+     * @param lhs  left-hand object
+     * @param rhs  right-hand object
+     * @param comparator  <code>Comparator</code> used to compare the objects,
+     *  <code>null</code> means treat lhs as <code>Comparable</code>
+     * @return this - used to chain append calls
+     * @throws ClassCastException  if <code>rhs</code> is not assignment-compatible
+     *  with <code>lhs</code>
+     * @since 2.0
+     */
+    public CompareToBuilder append(Object lhs, Object rhs, Comparator comparator) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.getClass().isArray()) {
+            // switch on type of array, to dispatch to the correct handler
+            // handles multi dimensional arrays
+            // throws a ClassCastException if rhs is not the correct array type
+            if (lhs instanceof long[]) {
+                append((long[]) lhs, (long[]) rhs);
+            } else if (lhs instanceof int[]) {
+                append((int[]) lhs, (int[]) rhs);
+            } else if (lhs instanceof short[]) {
+                append((short[]) lhs, (short[]) rhs);
+            } else if (lhs instanceof char[]) {
+                append((char[]) lhs, (char[]) rhs);
+            } else if (lhs instanceof byte[]) {
+                append((byte[]) lhs, (byte[]) rhs);
+            } else if (lhs instanceof double[]) {
+                append((double[]) lhs, (double[]) rhs);
+            } else if (lhs instanceof float[]) {
+                append((float[]) lhs, (float[]) rhs);
+            } else if (lhs instanceof boolean[]) {
+                append((boolean[]) lhs, (boolean[]) rhs);
+            } else {
+                // not an array of primitives
+                // throws a ClassCastException if rhs is not an array
+                append((Object[]) lhs, (Object[]) rhs, comparator);
+            }
+        } else {
+            // the simple case, not an array, just test the element
+            if (comparator == null) {
+                comparison = ((Comparable) lhs).compareTo(rhs);
+            } else {
+                comparison = comparator.compare(lhs, rhs);
+            }
+        }
+        return this;
+    }
+
+    //-------------------------------------------------------------------------
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>long</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(long lhs, long rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Long.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>int</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(int lhs, int rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Integer.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>short</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(short lhs, short rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Short.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>char</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(char lhs, char rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Character.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>byte</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(byte lhs, byte rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Byte.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the comparison of
+     * two <code>double</code>s.</p>
+     *
+     * <p>This handles NaNs, Infinities, and <code>-0.0</code>.</p>
+     *
+     * <p>It is compatible with the hash code generated by
+     * <code>HashCodeBuilder</code>.</p>
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(double lhs, double rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Double.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the comparison of
+     * two <code>float</code>s.</p>
+     *
+     * <p>This handles NaNs, Infinities, and <code>-0.0</code>.</p>
+     *
+     * <p>It is compatible with the hash code generated by
+     * <code>HashCodeBuilder</code>.</p>
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(float lhs, float rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        comparison = Float.compare(lhs, rhs);
+        return this;
+    }
+
+    /**
+     * Appends to the <code>builder</code> the comparison of
+     * two <code>booleans</code>s.
+     *
+     * @param lhs  left-hand value
+     * @param rhs  right-hand value
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(boolean lhs, boolean rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (!lhs) {
+            comparison = -1;
+        } else {
+            comparison = +1;
+        }
+        return this;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>Object</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a short length array is less than a long length array</li>
+     *  <li>Check array contents element by element using {@link #append(Object, Object, Comparator)}</li>
+     * </ol>
+     *
+     * <p>This method will also will be called for the top level of multi-dimensional,
+     * ragged, and multi-typed arrays.</p>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     * @throws ClassCastException  if <code>rhs</code> is not assignment-compatible
+     *  with <code>lhs</code>
+     */
+    public CompareToBuilder append(Object[] lhs, Object[] rhs) {
+        return append(lhs, rhs, null);
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>Object</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a short length array is less than a long length array</li>
+     *  <li>Check array contents element by element using {@link #append(Object, Object, Comparator)}</li>
+     * </ol>
+     *
+     * <p>This method will also will be called for the top level of multi-dimensional,
+     * ragged, and multi-typed arrays.</p>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @param comparator  <code>Comparator</code> to use to compare the array elements,
+     *  <code>null</code> means to treat <code>lhs</code> elements as <code>Comparable</code>.
+     * @return this - used to chain append calls
+     * @throws ClassCastException  if <code>rhs</code> is not assignment-compatible
+     *  with <code>lhs</code>
+     * @since 2.0
+     */
+    public CompareToBuilder append(Object[] lhs, Object[] rhs, Comparator comparator) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i], comparator);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>long</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(long, long)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(long[] lhs, long[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>int</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(int, int)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(int[] lhs, int[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>short</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(short, short)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(short[] lhs, short[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>char</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(char, char)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(char[] lhs, char[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>byte</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(byte, byte)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(byte[] lhs, byte[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>double</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(double, double)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(double[] lhs, double[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>float</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(float, float)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(float[] lhs, float[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    /**
+     * <p>Appends to the <code>builder</code> the deep comparison of
+     * two <code>boolean</code> arrays.</p>
+     *
+     * <ol>
+     *  <li>Check if arrays are the same using <code>==</code></li>
+     *  <li>Check if for <code>null</code>, <code>null</code> is less than non-<code>null</code></li>
+     *  <li>Check array length, a shorter length array is less than a longer length array</li>
+     *  <li>Check array contents element by element using {@link #append(boolean, boolean)}</li>
+     * </ol>
+     *
+     * @param lhs  left-hand array
+     * @param rhs  right-hand array
+     * @return this - used to chain append calls
+     */
+    public CompareToBuilder append(boolean[] lhs, boolean[] rhs) {
+        if (comparison != 0) {
+            return this;
+        }
+        if (lhs == rhs) {
+            return this;
+        }
+        if (lhs == null) {
+            comparison = -1;
+            return this;
+        }
+        if (rhs == null) {
+            comparison = +1;
+            return this;
+        }
+        if (lhs.length != rhs.length) {
+            comparison = (lhs.length < rhs.length) ? -1 : +1;
+            return this;
+        }
+        for (int i = 0; i < lhs.length && comparison == 0; i++) {
+            append(lhs[i], rhs[i]);
+        }
+        return this;
+    }
+
+    //-----------------------------------------------------------------------
+    /**
+     * Returns a negative integer, a positive integer, or zero as
+     * the <code>builder</code> has judged the "left-hand" side
+     * as less than, greater than, or equal to the "right-hand"
+     * side.
+     *
+     * @return final comparison result
+     */
+    public int toComparison() {
+        return comparison;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/util/Util.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/util/Util.java b/cayenne-server/src/main/java/org/apache/cayenne/util/Util.java
index ff477ff..e2575d9 100644
--- a/cayenne-server/src/main/java/org/apache/cayenne/util/Util.java
+++ b/cayenne-server/src/main/java/org/apache/cayenne/util/Util.java
@@ -238,6 +238,32 @@ public class Util {
 	}
 
 	/**
+	 * Capitalizes the first letter of the property name.
+	 *
+	 * @since 4.1
+	 */
+	public static String capitalized(String name) {
+		if (name == null || name.length() == 0)
+			return name;
+
+		char c = Character.toUpperCase(name.charAt(0));
+		return (name.length() == 1) ? Character.toString(c) : c + name.substring(1);
+	}
+
+	/**
+	 * Returns string with lowercased first letter
+	 *
+	 * @since 4.2
+	 */
+	public static String uncapitalized(String aString) {
+		if (aString == null || aString.length() == 0)
+			return aString;
+
+		char c = Character.toLowerCase(aString.charAt(0));
+		return (aString.length() == 1) ? Character.toString(c) : c + aString.substring(1);
+	}
+
+	/**
 	 * Creates Serializable object copy using serialization/deserialization.
 	 */
 	@SuppressWarnings("unchecked")

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/util/concurrentlinkedhashmap/ConcurrentLinkedHashMap.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/util/concurrentlinkedhashmap/ConcurrentLinkedHashMap.java b/cayenne-server/src/main/java/org/apache/cayenne/util/concurrentlinkedhashmap/ConcurrentLinkedHashMap.java
index a2f6e51..91f15f2 100644
--- a/cayenne-server/src/main/java/org/apache/cayenne/util/concurrentlinkedhashmap/ConcurrentLinkedHashMap.java
+++ b/cayenne-server/src/main/java/org/apache/cayenne/util/concurrentlinkedhashmap/ConcurrentLinkedHashMap.java
@@ -169,7 +169,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         BUFFER_MASK = buffers - 1;
     }
 
-    static final int ceilingNextPowerOfTwo(int x) {
+    static int ceilingNextPowerOfTwo(int x) {
         // From Hacker's Delight, Chapter 3, Harry S. Warren Jr.
         return 1 << (Integer.SIZE - Integer.numberOfLeadingZeros(x - 1));
     }
@@ -228,7 +228,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         // The data store and its maximum capacity
         concurrencyLevel = builder.concurrencyLevel;
         capacity = Math.min(builder.capacity, MAXIMUM_CAPACITY);
-        data = new ConcurrentHashMap<K, Node>(
+        data = new ConcurrentHashMap<>(
                 builder.initialCapacity,
                 0.75f,
                 concurrencyLevel);
@@ -239,13 +239,13 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         nextOrder = Integer.MIN_VALUE;
         drainedOrder = Integer.MIN_VALUE;
         evictionLock = new ReentrantLock();
-        evictionDeque = new LinkedDeque<Node>();
-        drainStatus = new AtomicReference<DrainStatus>(DrainStatus.IDLE);
+        evictionDeque = new LinkedDeque<>();
+        drainStatus = new AtomicReference<>(DrainStatus.IDLE);
 
         buffers = (Queue<Task>[]) new Queue[NUMBER_OF_BUFFERS];
         bufferLengths = new AtomicIntegerArray(NUMBER_OF_BUFFERS);
         for (int i = 0; i < NUMBER_OF_BUFFERS; i++) {
-            buffers[i] = new ConcurrentLinkedQueue<Task>();
+            buffers[i] = new ConcurrentLinkedQueue<>();
         }
 
         // The notification queue and listener
@@ -755,7 +755,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         checkNotNull(value);
 
         final int weight = weigher.weightOf(value);
-        final WeightedValue<V> weightedValue = new WeightedValue<V>(value, weight);
+        final WeightedValue<V> weightedValue = new WeightedValue<>(value, weight);
         final Node node = new Node(key, weightedValue);
 
         for (;;) {
@@ -831,7 +831,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         checkNotNull(value);
 
         final int weight = weigher.weightOf(value);
-        final WeightedValue<V> weightedValue = new WeightedValue<V>(value, weight);
+        final WeightedValue<V> weightedValue = new WeightedValue<>(value, weight);
 
         final Node node = data.get(key);
         if (node == null) {
@@ -858,7 +858,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         checkNotNull(newValue);
 
         final int weight = weigher.weightOf(newValue);
-        final WeightedValue<V> newWeightedValue = new WeightedValue<V>(newValue, weight);
+        final WeightedValue<V> newWeightedValue = new WeightedValue<>(newValue, weight);
 
         final Node node = data.get(key);
         if (node == null) {
@@ -965,7 +965,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
             int initialCapacity = (weigher == Weighers.singleton()) ? Math.min(
                     limit,
                     weightedSize()) : 16;
-            Set<K> keys = new LinkedHashSet<K>(initialCapacity);
+            Set<K> keys = new LinkedHashSet<>(initialCapacity);
             Iterator<Node> iterator = ascending
                     ? evictionDeque.iterator()
                     : evictionDeque.descendingIterator();
@@ -1070,7 +1070,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
             int initialCapacity = (weigher == Weighers.singleton()) ? Math.min(
                     limit,
                     weightedSize()) : 16;
-            Map<K, V> map = new LinkedHashMap<K, V>(initialCapacity);
+            Map<K, V> map = new LinkedHashMap<>(initialCapacity);
             Iterator<Node> iterator = ascending
                     ? evictionDeque.iterator()
                     : evictionDeque.descendingIterator();
@@ -1171,7 +1171,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
          */
         boolean tryToRetire(WeightedValue<V> expect) {
             if (expect.isAlive()) {
-                WeightedValue<V> retired = new WeightedValue<V>(
+                WeightedValue<V> retired = new WeightedValue<>(
                         expect.value,
                         -expect.weight);
                 return compareAndSet(expect, retired);
@@ -1189,7 +1189,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
                 if (!current.isAlive()) {
                     return;
                 }
-                WeightedValue<V> retired = new WeightedValue<V>(
+                WeightedValue<V> retired = new WeightedValue<>(
                         current.value,
                         -current.weight);
                 if (compareAndSet(current, retired)) {
@@ -1205,7 +1205,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         void makeDead() {
             for (;;) {
                 WeightedValue<V> current = get();
-                WeightedValue<V> dead = new WeightedValue<V>(current.value, 0);
+                WeightedValue<V> dead = new WeightedValue<>(current.value, 0);
                 if (compareAndSet(current, dead)) {
                     weightedSize -= Math.abs(current.weight);
                     return;
@@ -1397,7 +1397,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
     }
 
     /** An entry that allows updates to write through to the map. */
-    final class WriteThroughEntry extends SimpleEntry<K, V> {
+    final class WriteThroughEntry extends AbstractMap.SimpleEntry<K, V> {
 
         static final long serialVersionUID = 1;
 
@@ -1412,7 +1412,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         }
 
         Object writeReplace() {
-            return new SimpleEntry<K, V>(this);
+            return new AbstractMap.SimpleEntry<>(this);
         }
     }
 
@@ -1574,7 +1574,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
     static final long serialVersionUID = 1;
 
     Object writeReplace() {
-        return new SerializationProxy<K, V>(this);
+        return new SerializationProxy<>(this);
     }
 
     private void readObject(ObjectInputStream stream) throws InvalidObjectException {
@@ -1771,7 +1771,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
         public Builder<K, V> weigher(Weigher<? super V> weigher) {
             this.weigher = (weigher == Weighers.singleton())
                     ? Weighers.<V> singleton()
-                    : new BoundedWeigher<V>(weigher);
+                    : new BoundedWeigher<>(weigher);
             return this;
         }
 
@@ -1820,7 +1820,7 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
             if (capacity < 0) {
                 throw new IllegalStateException();
             }
-            ConcurrentLinkedHashMap<K, V> map = new ConcurrentLinkedHashMap<K, V>(this);
+            ConcurrentLinkedHashMap<K, V> map = new ConcurrentLinkedHashMap<>(this);
             if (executor != DEFAULT_EXECUTOR) {
                 ScheduledExecutorService es = (ScheduledExecutorService) executor;
                 es.scheduleWithFixedDelay(new CatchUpTask(map), delay, delay, unit);
@@ -1828,54 +1828,4 @@ public class ConcurrentLinkedHashMap<K, V> extends AbstractMap<K, V> implements
             return map;
         }
     }
-
-    // a class similar to AbstractMap.SimpleEntry. Needed for JDK 5 compatibility. Java 6
-    // exposes it to external users.
-    static class SimpleEntry<K, V> implements Entry<K, V> {
-
-        K key;
-        V value;
-
-        public SimpleEntry(K key, V value) {
-            this.key = key;
-            this.value = value;
-        }
-
-        public SimpleEntry(Entry<K, V> e) {
-            this.key = e.getKey();
-            this.value = e.getValue();
-        }
-
-        public K getKey() {
-            return key;
-        }
-
-        public V getValue() {
-            return value;
-        }
-
-        public V setValue(V value) {
-            V oldValue = this.value;
-            this.value = value;
-            return oldValue;
-        }
-
-        @Override
-        public boolean equals(Object o) {
-            if (!(o instanceof Entry))
-                return false;
-            Entry e = (Entry) o;
-            return eq(key, e.getKey()) && eq(value, e.getValue());
-        }
-
-        @Override
-        public int hashCode() {
-            return ((key == null) ? 0 : key.hashCode())
-                    ^ ((value == null) ? 0 : value.hashCode());
-        }
-
-        private static boolean eq(Object o1, Object o2) {
-            return (o1 == null ? o2 == null : o1.equals(o2));
-        }
-    }
 }

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindDirective.java
deleted file mode 100644
index 94080d6..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindDirective.java
+++ /dev/null
@@ -1,158 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-import java.util.Collection;
-import java.util.Iterator;
-
-import org.apache.cayenne.access.translator.ParameterBinding;
-import org.apache.cayenne.dba.TypesMapping;
-import org.apache.cayenne.util.ConversionUtil;
-import org.apache.velocity.context.InternalContextAdapter;
-import org.apache.velocity.exception.MethodInvocationException;
-import org.apache.velocity.exception.ParseErrorException;
-import org.apache.velocity.exception.ResourceNotFoundException;
-import org.apache.velocity.runtime.directive.Directive;
-import org.apache.velocity.runtime.parser.node.Node;
-
-/**
- * A custom Velocity directive to create a PreparedStatement parameter text.
- * There are the following possible invocation formats inside the template:
- * 
- * <pre>
- * #bind(value) - e.g. #bind($xyz)
- * #bind(value jdbc_type_name) - e.g. #bind($xyz 'VARCHAR'). This is the most common and useful form.
- * #bind(value jdbc_type_name, scale) - e.g. #bind($xyz 'VARCHAR' 2)
- * </pre>
- * <p>
- * Other examples:
- * </p>
- * <p>
- * <strong>Binding literal parameter value:</strong>
- * </p>
- * <p>
- * <code>"WHERE SOME_COLUMN &gt; #bind($xyz)"</code> produces
- * <code>"WHERE SOME_COLUMN &gt; ?"</code> and also places the value of the
- * "xyz" parameter in the context "bindings" collection.
- * </p>
- * <p>
- * <strong>Binding ID column of a DataObject value:</strong>
- * </p>
- * <p>
- * <code>"WHERE ID_COL1 = #bind($helper.cayenneExp($xyz, 'db:ID_COL2')) 
- * AND ID_COL2 = #bind($helper.cayenneExp($xyz, 'db:ID_COL2'))"</code> produces
- * <code>"WHERE ID_COL1 = ? AND ID_COL2 = ?"</code> and also places the values
- * of id columns of the DataObject parameter "xyz" in the context "bindings"
- * collection.
- * </p>
- * 
- * @since 1.1
- */
-public class BindDirective extends Directive {
-
-	@Override
-	public String getName() {
-		return "bind";
-	}
-
-	@Override
-	public int getType() {
-		return LINE;
-	}
-
-	/**
-	 * Extracts the value of the object property to render and passes control to
-	 * {@link #render(InternalContextAdapter, Writer, ParameterBinding)} to do
-	 * the actual rendering.
-	 */
-	@Override
-	public boolean render(InternalContextAdapter context, Writer writer, Node node) throws IOException,
-			ResourceNotFoundException, ParseErrorException, MethodInvocationException {
-
-		Object value = getChild(context, node, 0);
-		Object type = getChild(context, node, 1);
-		int scale = ConversionUtil.toInt(getChild(context, node, 2), -1);
-		String typeString = type != null ? type.toString() : null;
-
-		if (value instanceof Collection) {
-			Iterator<?> it = ((Collection) value).iterator();
-			while (it.hasNext()) {
-				render(context, writer, node, it.next(), typeString, scale);
-
-				if (it.hasNext()) {
-					writer.write(',');
-				}
-			}
-		} else {
-			render(context, writer, node, value, typeString, scale);
-		}
-
-		return true;
-	}
-
-	/**
-	 * @since 3.0
-	 */
-	protected void render(InternalContextAdapter context, Writer writer, Node node, Object value, String typeString,
-			int scale) throws IOException, ParseErrorException {
-
-		int jdbcType = TypesMapping.NOT_DEFINED;
-		if (typeString != null) {
-			jdbcType = TypesMapping.getSqlTypeByName(typeString);
-		} else if (value != null) {
-			jdbcType = TypesMapping.getSqlTypeByJava(value.getClass());
-		} else {
-			// value is null, set JDBC type to NULL
-			jdbcType = TypesMapping.getSqlTypeByName(TypesMapping.SQL_NULL);
-		}
-
-		if (jdbcType == TypesMapping.NOT_DEFINED) {
-			throw new ParseErrorException("Can't determine JDBC type of binding (" + value + ", " + typeString
-					+ ") at line " + node.getLine() + ", column " + node.getColumn());
-		}
-
-		render(context, writer, new ParameterBinding(value, jdbcType, scale));
-	}
-
-	protected void render(InternalContextAdapter context, Writer writer, ParameterBinding binding) throws IOException {
-
-		bind(context, binding);
-		writer.write('?');
-	}
-
-	protected Object getChild(InternalContextAdapter context, Node node, int i) throws MethodInvocationException {
-		return (i >= 0 && i < node.jjtGetNumChildren()) ? node.jjtGetChild(i).value(context) : null;
-	}
-
-	/**
-	 * Adds value to the list of bindings in the context.
-	 */
-	protected void bind(InternalContextAdapter context, ParameterBinding binding) {
-
-		Collection bindings = (Collection) context.getInternalUserContext().get(
-				VelocitySQLTemplateProcessor.BINDINGS_LIST_KEY);
-
-		if (bindings != null) {
-			bindings.add(binding);
-		}
-	}
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindEqualDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindEqualDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindEqualDirective.java
deleted file mode 100644
index bf9c820..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindEqualDirective.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-
-import org.apache.cayenne.access.translator.ParameterBinding;
-import org.apache.velocity.context.InternalContextAdapter;
-
-/**
- * A custom Velocity directive to create a PreparedStatement parameter text
- * for "= ?". If null value is encountered, generated text will look like "IS NULL".
- * Usage in Velocity template is "WHERE SOME_COLUMN #bindEqual($xyz)".
- * 
- * @since 1.1
- */
-public class BindEqualDirective extends BindDirective {
-
-    @Override
-    public String getName() {
-        return "bindEqual";
-    }
-
-    @Override
-    protected void render(
-        InternalContextAdapter context,
-        Writer writer,
-        ParameterBinding binding)
-        throws IOException {
-
-        if (binding.getValue() != null) {
-            bind(context, binding);
-            writer.write("= ?");
-        }
-        else {
-            writer.write("IS NULL");
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindNotEqualDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindNotEqualDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindNotEqualDirective.java
deleted file mode 100644
index af548da..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindNotEqualDirective.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-
-import org.apache.cayenne.access.translator.ParameterBinding;
-import org.apache.velocity.context.InternalContextAdapter;
-
-/**
- * A custom Velocity directive to create a PreparedStatement parameter text for "&lt;&gt;?".
- * If null value is encountered, generated text will look like "IS NOT NULL". Usage in
- * Velocity template is "WHERE SOME_COLUMN #bindNotEqual($xyz)".
- * 
- * @since 1.1
- */
-public class BindNotEqualDirective extends BindDirective {
-
-    @Override
-    public String getName() {
-        return "bindNotEqual";
-    }
-
-    @Override
-    protected void render(
-            InternalContextAdapter context,
-            Writer writer,
-            ParameterBinding binding) throws IOException {
-
-        if (binding.getValue() != null) {
-            bind(context, binding);
-            writer.write("<> ?");
-        }
-        else {
-            writer.write("IS NOT NULL");
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectEqualDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectEqualDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectEqualDirective.java
deleted file mode 100644
index 8394673..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectEqualDirective.java
+++ /dev/null
@@ -1,164 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-import java.sql.Types;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Map;
-
-import org.apache.cayenne.ObjectId;
-import org.apache.cayenne.Persistent;
-import org.apache.cayenne.access.translator.ParameterBinding;
-import org.apache.cayenne.dba.TypesMapping;
-import org.apache.velocity.context.InternalContextAdapter;
-import org.apache.velocity.exception.MethodInvocationException;
-import org.apache.velocity.exception.ParseErrorException;
-import org.apache.velocity.exception.ResourceNotFoundException;
-import org.apache.velocity.runtime.parser.node.Node;
-
-/**
- * A custom Velocity directive to create a set of SQL conditions to match an ObjectId of
- * an object. Usage in Velocity template is "WHERE #bindObjectEqual($object)" or "WHERE
- * #bindObjectEqual($object $columns $idValues)".
- * 
- * @since 3.0
- */
-public class BindObjectEqualDirective extends BindDirective {
-
-    @Override
-    public String getName() {
-        return "bindObjectEqual";
-    }
-
-    @Override
-    public boolean render(InternalContextAdapter context, Writer writer, Node node)
-            throws IOException, ResourceNotFoundException, ParseErrorException,
-            MethodInvocationException {
-
-        Object object = getChild(context, node, 0);
-        Map idMap = toIdMap(object);
-
-        Object sqlColumns = getChild(context, node, 1);
-        Object idColumns = getChild(context, node, 2);
-
-        if (idMap == null) {
-            // assume null object, and bind all null values
-
-            if (sqlColumns == null || idColumns == null) {
-                throw new ParseErrorException("Invalid parameters. "
-                        + "Either object has to be set "
-                        + "or sqlColumns and idColumns or both.");
-            }
-
-            idMap = Collections.EMPTY_MAP;
-        }
-        else if (sqlColumns == null || idColumns == null) {
-            // infer SQL columns from ID columns
-            sqlColumns = idMap.keySet().toArray();
-            idColumns = sqlColumns;
-        }
-
-        Object[] sqlColumnsArray = toArray(sqlColumns);
-        Object[] idColumnsArray = toArray(idColumns);
-
-        if (sqlColumnsArray.length != idColumnsArray.length) {
-            throw new ParseErrorException(
-                    "SQL columns and ID columns arrays have different sizes.");
-        }
-
-        for (int i = 0; i < sqlColumnsArray.length; i++) {
-
-            Object value = idMap.get(idColumnsArray[i]);
-
-            int jdbcType = (value != null) ? TypesMapping.getSqlTypeByJava(value
-                    .getClass()) : Types.INTEGER;
-
-            renderColumn(context, writer, sqlColumnsArray[i], i);
-            writer.write(' ');
-            render(context, writer, new ParameterBinding(value, jdbcType, -1));
-        }
-
-        return true;
-    }
-
-    protected Object[] toArray(Object columns) {
-        if (columns instanceof Collection) {
-            return ((Collection) columns).toArray();
-        }
-        else if (columns.getClass().isArray()) {
-            return (Object[]) columns;
-        }
-        else {
-            return new Object[] {
-                columns
-            };
-        }
-    }
-
-    protected Map toIdMap(Object object) throws ParseErrorException {
-        if (object instanceof Persistent) {
-            return ((Persistent) object).getObjectId().getIdSnapshot();
-        }
-        else if (object instanceof ObjectId) {
-            return ((ObjectId) object).getIdSnapshot();
-        }
-        else if(object instanceof Map) {
-            return (Map) object;
-        }
-        else if (object != null) {
-            throw new ParseErrorException(
-                    "Invalid object parameter, expected Persistent or ObjectId or null: "
-                            + object);
-        }
-        else {
-            return null;
-        }
-    }
-
-    protected void renderColumn(
-            InternalContextAdapter context,
-            Writer writer,
-            Object columnName,
-            int columnIndex) throws IOException {
-
-        if (columnIndex > 0) {
-            writer.write(" AND ");
-        }
-
-        writer.write(columnName.toString());
-    }
-
-    @Override
-    protected void render(
-            InternalContextAdapter context,
-            Writer writer,
-            ParameterBinding binding) throws IOException {
-
-        if (binding.getValue() != null) {
-            bind(context, binding);
-            writer.write("= ?");
-        }
-        else {
-            writer.write("IS NULL");
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectNotEqualDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectNotEqualDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectNotEqualDirective.java
deleted file mode 100644
index 6c95852..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/BindObjectNotEqualDirective.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-
-import org.apache.cayenne.access.translator.ParameterBinding;
-import org.apache.velocity.context.InternalContextAdapter;
-
-/**
- * A custom Velocity directive to create a set of SQL conditions to check unequality of an
- * ObjectId of an object. Usage in Velocity template is "WHERE
- * #bindObjectNotEqual($object)" or "WHERE #bindObjectNotEqual($object $columns
- * $idValues)".
- * 
- * @since 3.0
- */
-public class BindObjectNotEqualDirective extends BindObjectEqualDirective {
-
-    @Override
-    public String getName() {
-        return "bindObjectNotEqual";
-    }
-
-    @Override
-    protected void renderColumn(
-            InternalContextAdapter context,
-            Writer writer,
-            Object columnName,
-            int columnIndex) throws IOException {
-
-        if (columnIndex > 0) {
-            writer.write(" OR ");
-        }
-
-        writer.write(columnName.toString());
-    }
-
-    @Override
-    protected void render(
-            InternalContextAdapter context,
-            Writer writer,
-            ParameterBinding binding) throws IOException {
-
-        if (binding.getValue() != null) {
-            bind(context, binding);
-            writer.write("<> ?");
-        }
-        else {
-            writer.write("IS NOT NULL");
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChainDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChainDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChainDirective.java
deleted file mode 100644
index acd0f8c..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChainDirective.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.StringWriter;
-import java.io.Writer;
-
-import org.apache.velocity.context.InternalContextAdapter;
-import org.apache.velocity.exception.MethodInvocationException;
-import org.apache.velocity.exception.ParseErrorException;
-import org.apache.velocity.exception.ResourceNotFoundException;
-import org.apache.velocity.runtime.directive.Directive;
-import org.apache.velocity.runtime.parser.node.ASTDirective;
-import org.apache.velocity.runtime.parser.node.Node;
-
-/**
- * A custom Velocity directive to conditionally join a number of {@link ChunkDirective chunks}.
- * Usage of chain is the following:
- * 
- * <pre>
- * #chain(operator) - e.g. #chain(' AND ')
- * #chain(operator prefix) - e.g. #chain(' AND ' 'WHERE ')</pre>
- * 
- * <p><code>operator</code> (e.g. AND, OR, etc.) is used to join chunks that are included
- * in a chain. <code>prefix</code> is inserted if a chain contains at least one chunk.
- * </p>
- * 
- * @since 1.1
- */
-public class ChainDirective extends Directive {
-
-    @Override
-    public String getName() {
-        return "chain";
-    }
-
-    @Override
-    public int getType() {
-        return BLOCK;
-    }
-
-    @Override
-    public boolean render(InternalContextAdapter context, Writer writer, Node node)
-        throws
-            IOException,
-            ResourceNotFoundException,
-            ParseErrorException,
-            MethodInvocationException {
-
-        int size = node.jjtGetNumChildren();
-        if (size == 0) {
-            return true;
-        }
-
-        // BLOCK is the last child
-        Node block = node.jjtGetChild(node.jjtGetNumChildren() - 1);
-        String join = (size > 1) ? (String) node.jjtGetChild(0).value(context) : "";
-        String prefix = (size > 2) ? (String) node.jjtGetChild(1).value(context) : "";
-
-        // if there is a conditional prefix, use a separate buffer for children
-        StringWriter childWriter = new StringWriter(30);
-
-        int len = block.jjtGetNumChildren();
-        int includedChunks = 0;
-        for (int i = 0; i < len; i++) {
-            Node child = block.jjtGetChild(i);
-
-            // if this is a "chunk", evaluate its expression and prepend join if included...
-            if (child instanceof ASTDirective
-                && "chunk".equals(((ASTDirective) child).getDirectiveName())) {
-
-                if (child.jjtGetNumChildren() < 2
-                    || child.jjtGetChild(0).value(context) != null) {
-
-                    if (includedChunks > 0) {
-                        childWriter.write(join);
-                    }
-
-                    includedChunks++;
-                }
-            }
-
-            child.render(context, childWriter);
-        }
-
-        if (includedChunks > 0) {
-            childWriter.flush();
-            writer.write(prefix);
-            writer.write(childWriter.toString());
-        }
-
-        return true;
-    }
-}

http://git-wip-us.apache.org/repos/asf/cayenne/blob/f734851f/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChunkDirective.java
----------------------------------------------------------------------
diff --git a/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChunkDirective.java b/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChunkDirective.java
deleted file mode 100644
index 5ff0a5e..0000000
--- a/cayenne-server/src/main/java/org/apache/cayenne/velocity/ChunkDirective.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/*****************************************************************
- *   Licensed to the Apache Software Foundation (ASF) under one
- *  or more contributor license agreements.  See the NOTICE file
- *  distributed with this work for additional information
- *  regarding copyright ownership.  The ASF licenses this file
- *  to you under the Apache License, Version 2.0 (the
- *  "License"); you may not use this file except in compliance
- *  with the License.  You may obtain a copy of the License at
- *
- *    http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing,
- *  software distributed under the License is distributed on an
- *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- *  KIND, either express or implied.  See the License for the
- *  specific language governing permissions and limitations
- *  under the License.
- ****************************************************************/
-
-package org.apache.cayenne.velocity;
-
-import java.io.IOException;
-import java.io.Writer;
-
-import org.apache.velocity.context.InternalContextAdapter;
-import org.apache.velocity.exception.MethodInvocationException;
-import org.apache.velocity.exception.ParseErrorException;
-import org.apache.velocity.exception.ResourceNotFoundException;
-import org.apache.velocity.runtime.directive.Directive;
-import org.apache.velocity.runtime.parser.node.Node;
-
-/**
- * A custom Velocity directive to describe a conditional chunk of a {@link ChainDirective chain}.
- * Usage of chunk is the following:
- * 
- * <pre>
- * #chunk()...#end - e.g. #chunk()A = 5#end
- * #chunk($paramKey)...#end - e.g. #chunk($a)A = $a#end
- * </pre>
- * <p>
- * If context contains paramKey and it's value isn't null, chunk is included in the
- * chain, and if it is not the first chunk, it is prefixed with chain join (OR/AND).
- * If context doesn't contain paramKey or it's value is null, chunk is skipped.
- * @since 1.1
- */
-public class ChunkDirective extends Directive {
-
-    @Override
-    public String getName() {
-        return "chunk";
-    }
-
-    @Override
-    public int getType() {
-        return BLOCK;
-    }
-
-    @Override
-    public boolean render(InternalContextAdapter context, Writer writer, Node node)
-            throws IOException, ResourceNotFoundException, ParseErrorException,
-            MethodInvocationException {
-
-        // first child is an expression, second is BLOCK
-        if (node.jjtGetNumChildren() > 1 && node.jjtGetChild(0).value(context) == null) {
-            // skip this chunk
-            return false;
-        }
-
-        // BLOCK is the last child
-        Node block = node.jjtGetChild(node.jjtGetNumChildren() - 1);
-        block.render(context, writer);
-        return true;
-    }
-
-}


Mime
View raw message