Merge pull request #123 from wenshao/master

修正sql执行的bug,并且补充单元测试。
This commit is contained in:
温高铁
2012-08-29 17:52:04 -07:00
2 changed files with 222 additions and 26 deletions
@@ -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<Object> 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<String, Object> 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);
@@ -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.<Object> asList(2, 3)));
Assert.assertEquals(6, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? * ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(-1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(2, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? / ?", Arrays.<Object> asList(6, 3)));
}
public void test_add() throws Exception {
Assert.assertEquals(5, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(6, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(7, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(4, 3)));
}
public void test_add_1() throws Exception {
Assert.assertEquals(5.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(2.0, 3)));
Assert.assertEquals(6.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(3.0, 3)));
Assert.assertEquals(7.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(4.0, 3)));
}
public void test_add_2() throws Exception {
Assert.assertEquals(5.1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(2.1, 3)));
Assert.assertEquals(6.2, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(3.2, 3)));
Assert.assertEquals(7.3, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(4.3, 3)));
}
public void test_add_3() throws Exception {
Assert.assertEquals(5.1D,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(2.1D, 3)));
Assert.assertEquals(6.2D,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(3.2D, 3)));
Assert.assertEquals(7.3D,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(4.3D, 3)));
}
public void test_add_4() throws Exception {
Assert.assertEquals(5.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(2, 3.0)));
Assert.assertEquals(6.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(3, 3.0)));
Assert.assertEquals(7.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?", Arrays.<Object> asList(4, 3.0)));
}
public void test_add_5() throws Exception {
Assert.assertEquals(new BigInteger("5"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(2, new BigInteger("3"))));
Assert.assertEquals(new BigInteger("6"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(3, new BigInteger("3"))));
Assert.assertEquals(new BigInteger("7"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(4, new BigInteger("3"))));
}
public void test_add_6() throws Exception {
Assert.assertEquals(new BigDecimal("5"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(2, new BigDecimal("3"))));
Assert.assertEquals(new BigDecimal("6"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(3, new BigDecimal("3"))));
Assert.assertEquals(new BigDecimal("7"),
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? + ?",
Arrays.<Object> asList(4, new BigDecimal("3"))));
}
public void test_sub() throws Exception {
Assert.assertEquals(-1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(1, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(4, 3)));
}
public void test_sub_1() throws Exception {
Assert.assertEquals(-1.0,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(2.0, 3)));
Assert.assertEquals(0.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(3.0, 3)));
Assert.assertEquals(1.0, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(4.0, 3)));
}
public void test_sub_2() throws Exception {
Assert.assertEquals(2.1 - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(2.1, 3)));
Assert.assertEquals(3.2 - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(3.2, 3)));
Assert.assertEquals(4.3 - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(4.3, 3)));
}
public void test_sub_3() throws Exception {
Assert.assertEquals(2.1D - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(2.1D, 3)));
Assert.assertEquals(3.2D - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(3.2D, 3)));
Assert.assertEquals(4.3D - 3,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? - ?", Arrays.<Object> asList(4.3D, 3)));
}
public void test_lt() throws Exception {
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(4, 3)));
}
public void test_lt_1() throws Exception {
Assert.assertEquals(true,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(2.0, 3)));
Assert.assertEquals(false,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(3.0, 3)));
Assert.assertEquals(false,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? < ?", Arrays.<Object> asList(4.0, 3)));
}
public void test_ltEq() throws Exception {
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(false,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(4, 3)));
}
public void test_ltEq_1() throws Exception {
Assert.assertEquals(true,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(2.0, 3)));
Assert.assertEquals(true,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(3.0, 3)));
Assert.assertEquals(false,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? <= ?", Arrays.<Object> asList(4.0, 3)));
}
public void test_gt() throws Exception {
Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(false, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? > ?", Arrays.<Object> asList(4, 3)));
}
public void test_gtEq() throws Exception {
Assert.assertEquals(false,
SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays.<Object> asList(2, 3)));
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays.<Object> asList(3, 3)));
Assert.assertEquals(true, SQLEvalVisitorUtils.evalExpr(JdbcUtils.MYSQL, "? >= ?", Arrays.<Object> asList(4, 3)));
}
}