You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cayenne.apache.org by aa...@apache.org on 2007/08/01 21:42:46 UTC

svn commit: r561931 - in /cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc: EJBQLConditionTranslator.java EJBQLUpdateFieldTranslator.java EJBQLUpdateTranslator.java

Author: aadamchik
Date: Wed Aug  1 12:42:44 2007
New Revision: 561931

URL: http://svn.apache.org/viewvc?view=rev&rev=561931
Log:
CAY-837 EJBQL Update Statement Support
(translator refactoring to reuse Condition translator or UpdateField which is semantically very close)

Added:
    cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateFieldTranslator.java
Modified:
    cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLConditionTranslator.java
    cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateTranslator.java

Modified: cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLConditionTranslator.java
URL: http://svn.apache.org/viewvc/cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLConditionTranslator.java?view=diff&rev=561931&r1=561930&r2=561931
==============================================================================
--- cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLConditionTranslator.java (original)
+++ cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLConditionTranslator.java Wed Aug  1 12:42:44 2007
@@ -37,7 +37,7 @@
  */
 class EJBQLConditionTranslator extends EJBQLBaseVisitor {
 
-    private EJBQLTranslationContext context;
+    protected EJBQLTranslationContext context;
 
     private List multiColumnOperands;
 

Added: cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateFieldTranslator.java
URL: http://svn.apache.org/viewvc/cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateFieldTranslator.java?view=auto&rev=561931
==============================================================================
--- cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateFieldTranslator.java (added)
+++ cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateFieldTranslator.java Wed Aug  1 12:42:44 2007
@@ -0,0 +1,58 @@
+/*****************************************************************
+ *   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.access.jdbc;
+
+import org.apache.cayenne.ejbql.EJBQLException;
+import org.apache.cayenne.ejbql.EJBQLExpression;
+
+/**
+ * @since 3.0
+ * @author Andrus Adamchik
+ */
+class EJBQLUpdateFieldTranslator extends EJBQLConditionTranslator {
+
+    public EJBQLUpdateFieldTranslator(EJBQLTranslationContext context) {
+        super(context);
+    }
+
+    public boolean visitUpdateField(EJBQLExpression expression, int finishedChildIndex) {
+
+        EJBQLPathTranslator pathTranslator = new EJBQLPathTranslator(context) {
+
+            protected void appendMultiColumnPath(EJBQLMultiColumnOperand operand) {
+                throw new EJBQLException(
+                        "Multi-column paths are not yet supported in UPDATEs");
+            }
+
+            public boolean visitUpdateField(
+                    EJBQLExpression expression,
+                    int finishedChildIndex) {
+                return visitPath(expression, finishedChildIndex);
+            }
+        };
+
+        expression.visit(pathTranslator);
+        return false;
+    }
+
+    public boolean visitUpdateValue(EJBQLExpression expression) {
+        context.append(" =");
+        return true;
+    }
+}

Modified: cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateTranslator.java
URL: http://svn.apache.org/viewvc/cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateTranslator.java?view=diff&rev=561931&r1=561930&r2=561931
==============================================================================
--- cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateTranslator.java (original)
+++ cayenne/main/trunk/framework/cayenne-jdk1.4-unpublished/src/main/java/org/apache/cayenne/access/jdbc/EJBQLUpdateTranslator.java Wed Aug  1 12:42:44 2007
@@ -18,15 +18,8 @@
  ****************************************************************/
 package org.apache.cayenne.access.jdbc;
 
-import java.math.BigDecimal;
-import java.util.Map;
-
-import org.apache.cayenne.ObjectId;
-import org.apache.cayenne.Persistent;
 import org.apache.cayenne.ejbql.EJBQLBaseVisitor;
-import org.apache.cayenne.ejbql.EJBQLException;
 import org.apache.cayenne.ejbql.EJBQLExpression;
-import org.apache.cayenne.ejbql.parser.EJBQLPositionalInputParameter;
 
 /**
  * A translator of EJBQL UPDATE statements into SQL.
@@ -72,155 +65,7 @@
             context.append(" SET");
         }
 
-        return true;
-    }
-
-    public boolean visitUpdateField(EJBQLExpression expression, int finishedChildIndex) {
-
-        EJBQLPathTranslator pathTranslator = new EJBQLPathTranslator(context) {
-
-            protected void appendMultiColumnPath(EJBQLMultiColumnOperand operand) {
-                throw new EJBQLException(
-                        "Multi-column paths are not yet supported in UPDATEs");
-            }
-
-            public boolean visitUpdateField(
-                    EJBQLExpression expression,
-                    int finishedChildIndex) {
-                return visitPath(expression, finishedChildIndex);
-            }
-        };
-
-        expression.visit(pathTranslator);
+        expression.visit(new EJBQLUpdateFieldTranslator(context));
         return false;
-    }
-
-    public boolean visitUpdateValue(EJBQLExpression expression) {
-        context.append(" =");
-        return true;
-    }
-
-    // TODO: andrus, 7/31/2007 - all literal processing (visitStringLiteral,
-    // visitIntegerLiteral, visitDecimalLiteral, visitBooleanLiteral,
-    // visitPositionalInputParameter, visitnamedInputParameter) is duplicated in
-    // EJBQLConditionalTranslator - may need to refactor
-    // one current difference is support of multi-column matching by
-    // EJBQLConditionalTranslator/
-    public boolean visitStringLiteral(EJBQLExpression expression) {
-        if (expression.getText() == null) {
-            context.append("null");
-        }
-        else {
-            // note that String Literal text is already wrapped in single quotes, with
-            // quotes that are part of the string escaped.
-            context.append(" #bind(").append(expression.getText()).append(" 'VARCHAR')");
-        }
-
-        return true;
-    }
-
-    public boolean visitBooleanLiteral(EJBQLExpression expression) {
-        if (expression.getText() == null) {
-            context.append("null");
-        }
-        else {
-            Object value = new Boolean(expression.getText());
-            String var = context.bindParameter(value);
-            context.append(" #bind($").append(var).append(" 'BOOLEAN')");
-        }
-
-        return true;
-    }
-
-    public boolean visitIntegerLiteral(EJBQLExpression expression) {
-        if (expression.getText() == null) {
-            context.append("null");
-        }
-        else {
-            Object value;
-
-            try {
-                value = new Integer(expression.getText());
-            }
-            catch (NumberFormatException nfex) {
-                throw new EJBQLException("Invalid integer: " + expression.getText());
-            }
-
-            String var = context.bindParameter(value);
-            context.append(" #bind($").append(var).append(" 'INTEGER')");
-        }
-        return true;
-    }
-
-    public boolean visitDecimalLiteral(EJBQLExpression expression) {
-        if (expression.getText() == null) {
-            context.append("null");
-        }
-        else {
-            Object value;
-
-            try {
-                value = new BigDecimal(expression.getText());
-            }
-            catch (NumberFormatException nfex) {
-                throw new EJBQLException("Invalid decimal: " + expression.getText());
-            }
-
-            String var = context.bindParameter(value);
-            context.append(" #bind($").append(var).append(" 'DECIMAL')");
-        }
-        return true;
-    }
-
-    public boolean visitPositionalInputParameter(EJBQLPositionalInputParameter expression) {
-
-        String parameter = context.bindPositionalParameter(expression.getPosition());
-        processParameter(parameter);
-        return true;
-    }
-
-    public boolean visitNamedInputParameter(EJBQLExpression expression) {
-        String parameter = context.bindNamedParameter(expression.getText());
-        processParameter(parameter);
-        return true;
-    }
-
-    private void processParameter(String boundName) {
-        Object object = context.getBoundParameter(boundName);
-
-        Map map = null;
-        if (object instanceof Persistent) {
-            map = ((Persistent) object).getObjectId().getIdSnapshot();
-        }
-        else if (object instanceof ObjectId) {
-            map = ((ObjectId) object).getIdSnapshot();
-        }
-        else if (object instanceof Map) {
-            map = (Map) object;
-        }
-
-        if (map != null) {
-            if (map.size() == 1) {
-                context.rebindParameter(boundName, map.values().iterator().next());
-            }
-            else {
-                throw new EJBQLException(
-                        "Multi-column paths are not yet supported in UPDATEs");
-            }
-        }
-
-        if (object != null) {
-            context.append(" #bind($").append(boundName).append(")");
-        }
-        else {
-            // this is a hack to prevent execptions on DB's like Derby for expressions
-            // "X = NULL". The 'VARCHAR' parameter is totally bogus, but seems to work on
-            // all tested DB's... Also note what JPA spec, chapter 4.11 says: "Comparison
-            // or arithmetic operations with a NULL value always yield an unknown value."
-
-            // TODO: andrus 6/28/2007 Ideally we should track the type of the current
-            // expression to provide a meaningful type.
-            context.append(" #bind($").append(boundName).append(" 'VARCHAR')");
-        }
     }
 }