From 179a37c102f71ffca788a9d3c14c29c42a79ffa4 Mon Sep 17 00:00:00 2001 From: wenshao Date: Thu, 30 Aug 2012 08:33:50 +0800 Subject: [PATCH 1/2] add eval testcase & bug fixed --- .../sql/visitor/SQLEvalVisitorUtils.java | 84 +++++++++++++------ 1 file changed, 58 insertions(+), 26 deletions(-) diff --git a/src/main/java/com/alibaba/druid/sql/visitor/SQLEvalVisitorUtils.java b/src/main/java/com/alibaba/druid/sql/visitor/SQLEvalVisitorUtils.java index 75c73975d0..f74248d20a 100644 --- a/src/main/java/com/alibaba/druid/sql/visitor/SQLEvalVisitorUtils.java +++ b/src/main/java/com/alibaba/druid/sql/visitor/SQLEvalVisitorUtils.java @@ -19,7 +19,6 @@ import static com.alibaba.druid.sql.visitor.SQLEvalVisitor.EVAL_VALUE; import java.math.BigDecimal; import java.math.BigInteger; -import java.math.RoundingMode; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.Arrays; @@ -32,7 +31,6 @@ import com.alibaba.druid.sql.SQLUtils; import com.alibaba.druid.sql.ast.SQLExpr; import com.alibaba.druid.sql.ast.SQLObject; import com.alibaba.druid.sql.ast.expr.SQLBinaryOpExpr; -import com.alibaba.druid.sql.ast.expr.SQLBinaryOperator; import com.alibaba.druid.sql.ast.expr.SQLCharExpr; import com.alibaba.druid.sql.ast.expr.SQLNumericLiteralExpr; import com.alibaba.druid.sql.ast.expr.SQLVariantRefExpr; @@ -64,7 +62,7 @@ public class SQLEvalVisitorUtils { return sqlObject.getAttributes().get(EVAL_VALUE); } - + public static Object eval(String dbType, SQLObject sqlObject, List parameters) { return eval(dbType, sqlObject, parameters, true); } @@ -88,15 +86,15 @@ public class SQLEvalVisitorUtils { if (JdbcUtils.MYSQL.equals(dbType)) { return new MySqlEvalVisitorImpl(); } - + if (JdbcUtils.H2.equals(dbType)) { return new MySqlEvalVisitorImpl(); } - + if (JdbcUtils.ORACLE.equals(dbType)) { return new OracleEvalVisitor(); } - + if (JdbcUtils.POSTGRESQL.equals(dbType)) { return new PGEvalVisitor(); } @@ -121,9 +119,42 @@ public class SQLEvalVisitorUtils { return false; } - if (SQLBinaryOperator.Add.equals(x.getOperator())) { - Object value = _add(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); - x.putAttribute(EVAL_VALUE, value); + Object value = null; + switch (x.getOperator()) { + case Add: + value = _add(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case Subtract: + value = _sub(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case Multiply: + value = _multi(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case Divide: + value = _div(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case GreaterThan: + value = _gt(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case GreaterThanOrEqual: + value = _gteq(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case LessThan: + value = _lt(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + case LessThanOrEqual: + value = _lteq(x.getLeft().getAttribute(EVAL_VALUE), x.getRight().getAttributes().get(EVAL_VALUE)); + x.putAttribute(EVAL_VALUE, value); + break; + default: + break; } return false; @@ -133,9 +164,9 @@ public class SQLEvalVisitorUtils { if (!"?".equals(x.getName())) { return false; } - + Map attributes = x.getAttributes(); - + int varIndex = x.getIndex(); if (varIndex != -1 && visitor.getParameters().size() > varIndex) { @@ -368,21 +399,6 @@ public class SQLEvalVisitorUtils { return null; } - BigDecimal decimalA = _decimal(a); - BigDecimal decimalB = _decimal(b); - - try { - return decimalA.divide(decimalB); - } catch (ArithmeticException ex) { - return decimalA.divide(decimalB, 4, RoundingMode.CEILING); - } - } - - public static Object _div2(Object a, Object b) { - if (a == null || b == null) { - return null; - } - if (a instanceof BigDecimal || b instanceof BigDecimal) { return _decimal(a).divide(_decimal(b)); } @@ -607,6 +623,14 @@ public class SQLEvalVisitorUtils { if (a instanceof BigInteger || b instanceof BigInteger) { return _bigInt(a).add(_bigInt(b)); } + + if (a instanceof Double || b instanceof Double) { + return _double(a) + _double(b); + } + + if (a instanceof Float || b instanceof Float) { + return _float(a) + _float(b); + } if (a instanceof Long || b instanceof Long) { return _long(a) + _long(b); @@ -647,6 +671,14 @@ public class SQLEvalVisitorUtils { if (a instanceof BigInteger || b instanceof BigInteger) { return _bigInt(a).subtract(_bigInt(b)); } + + if (a instanceof Double || b instanceof Double) { + return _double(a) - _double(b); + } + + if (a instanceof Float || b instanceof Float) { + return _float(a) - _float(b); + } if (a instanceof Long || b instanceof Long) { return _long(a) - _long(b); From 19aeef87b8f8f3ebec68e724afd8dab920acb88b Mon Sep 17 00:00:00 2001 From: wenshao Date: Thu, 30 Aug 2012 08:50:10 +0800 Subject: [PATCH 2/2] add eval testcase & bug fixed --- .../bvt/sql/eval/SQLEvalVisitorUtilsTest.java | 164 ++++++++++++++++++ 1 file changed, 164 insertions(+) create mode 100644 src/test/java/com/alibaba/druid/bvt/sql/eval/SQLEvalVisitorUtilsTest.java diff --git a/src/test/java/com/alibaba/druid/bvt/sql/eval/SQLEvalVisitorUtilsTest.java b/src/test/java/com/alibaba/druid/bvt/sql/eval/SQLEvalVisitorUtilsTest.java new file mode 100644 index 0000000000..e0dc1bb92b --- /dev/null +++ b/src/test/java/com/alibaba/druid/bvt/sql/eval/SQLEvalVisitorUtilsTest.java @@ -0,0 +1,164 @@ +package com.alibaba.druid.bvt.sql.eval; + +import java.math.BigDecimal; +import java.math.BigInteger; +import java.util.Arrays; + +import junit.framework.Assert; +import junit.framework.TestCase; + +import com.alibaba.druid.sql.visitor.SQLEvalVisitorUtils; +import com.alibaba.druid.util.JdbcUtils; + +public class SQLEvalVisitorUtilsTest extends TestCase { + + public void test_instance() throws Exception { + new SQLEvalVisitorUtils(); + } + + public void test_evalExpr() throws Exception { + Assert.assertEquals(5, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", 2, 3)); + Assert.assertEquals(6, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? * ?", 2, 3)); + Assert.assertEquals(-1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", 2, 3)); + Assert.assertEquals(2, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? / ?", 6, 3)); + } + + public void test_evalExpr_2() throws Exception { + Assert.assertEquals(5, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2, 3))); + Assert.assertEquals(6, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? * ?", Arrays. asList(2, 3))); + Assert.assertEquals(-1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(2, 3))); + Assert.assertEquals(2, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? / ?", Arrays. asList(6, 3))); + } + + public void test_add() throws Exception { + Assert.assertEquals(5, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2, 3))); + Assert.assertEquals(6, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(3, 3))); + Assert.assertEquals(7, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(4, 3))); + } + + public void test_add_1() throws Exception { + Assert.assertEquals(5.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2.0, 3))); + Assert.assertEquals(6.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(3.0, 3))); + Assert.assertEquals(7.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(4.0, 3))); + } + + public void test_add_2() throws Exception { + Assert.assertEquals(5.1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2.1, 3))); + Assert.assertEquals(6.2, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(3.2, 3))); + Assert.assertEquals(7.3, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(4.3, 3))); + } + + public void test_add_3() throws Exception { + Assert.assertEquals(5.1D, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2.1D, 3))); + Assert.assertEquals(6.2D, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(3.2D, 3))); + Assert.assertEquals(7.3D, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(4.3D, 3))); + } + + public void test_add_4() throws Exception { + Assert.assertEquals(5.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(2, 3.0))); + Assert.assertEquals(6.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(3, 3.0))); + Assert.assertEquals(7.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays. asList(4, 3.0))); + } + + public void test_add_5() throws Exception { + Assert.assertEquals(new BigInteger("5"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(2, new BigInteger("3")))); + Assert.assertEquals(new BigInteger("6"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(3, new BigInteger("3")))); + Assert.assertEquals(new BigInteger("7"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(4, new BigInteger("3")))); + } + + public void test_add_6() throws Exception { + Assert.assertEquals(new BigDecimal("5"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(2, new BigDecimal("3")))); + Assert.assertEquals(new BigDecimal("6"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(3, new BigDecimal("3")))); + Assert.assertEquals(new BigDecimal("7"), + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", + Arrays. asList(4, new BigDecimal("3")))); + } + + public void test_sub() throws Exception { + Assert.assertEquals(-1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(2, 3))); + Assert.assertEquals(0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(3, 3))); + Assert.assertEquals(1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(4, 3))); + } + + public void test_sub_1() throws Exception { + Assert.assertEquals(-1.0, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(2.0, 3))); + Assert.assertEquals(0.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(3.0, 3))); + Assert.assertEquals(1.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(4.0, 3))); + } + + public void test_sub_2() throws Exception { + Assert.assertEquals(2.1 - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(2.1, 3))); + Assert.assertEquals(3.2 - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(3.2, 3))); + Assert.assertEquals(4.3 - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(4.3, 3))); + } + + public void test_sub_3() throws Exception { + Assert.assertEquals(2.1D - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(2.1D, 3))); + Assert.assertEquals(3.2D - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(3.2D, 3))); + Assert.assertEquals(4.3D - 3, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays. asList(4.3D, 3))); + } + + public void test_lt() throws Exception { + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(2, 3))); + Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(3, 3))); + Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(4, 3))); + } + + public void test_lt_1() throws Exception { + Assert.assertEquals(true, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(2.0, 3))); + Assert.assertEquals(false, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(3.0, 3))); + Assert.assertEquals(false, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays. asList(4.0, 3))); + } + + public void test_ltEq() throws Exception { + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(2, 3))); + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(3, 3))); + Assert.assertEquals(false, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(4, 3))); + } + + public void test_ltEq_1() throws Exception { + Assert.assertEquals(true, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(2.0, 3))); + Assert.assertEquals(true, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(3.0, 3))); + Assert.assertEquals(false, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays. asList(4.0, 3))); + } + + public void test_gt() throws Exception { + Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays. asList(2, 3))); + Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays. asList(3, 3))); + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays. asList(4, 3))); + } + + public void test_gtEq() throws Exception { + Assert.assertEquals(false, + SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays. asList(2, 3))); + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays. asList(3, 3))); + Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays. asList(4, 3))); + } +}