diff --git a/nop-commons/src/main/java/io/nop/commons/type/StdSqlType.java b/nop-commons/src/main/java/io/nop/commons/type/StdSqlType.java index 6358999d2..c868b0c25 100644 --- a/nop-commons/src/main/java/io/nop/commons/type/StdSqlType.java +++ b/nop-commons/src/main/java/io/nop/commons/type/StdSqlType.java @@ -188,4 +188,11 @@ public static StdSqlType fromStdName(String stdName) { public static StdSqlType fromStdDataTYpe(StdDataType dataType) { return stdTypeMap.get(dataType); } + + public static StdSqlType fromJavaClass(Class clazz) { + StdDataType dataType = StdDataType.fromJavaClass(clazz); + if (dataType == null) + return null; + return StdSqlType.fromStdDataTYpe(dataType); + } } \ No newline at end of file diff --git a/nop-commons/src/main/java/io/nop/commons/util/MathHelper.java b/nop-commons/src/main/java/io/nop/commons/util/MathHelper.java index becdb7382..f14070748 100644 --- a/nop-commons/src/main/java/io/nop/commons/util/MathHelper.java +++ b/nop-commons/src/main/java/io/nop/commons/util/MathHelper.java @@ -49,6 +49,7 @@ import java.util.IdentityHashMap; import java.util.List; import java.util.Objects; +import java.util.concurrent.atomic.AtomicLong; import static io.nop.api.core.convert.ConvertHelper.toBigDecimal; import static io.nop.api.core.convert.ConvertHelper.toBigInteger; @@ -168,6 +169,12 @@ public static Number getPrimitiveDefaultValue(Class forClass) { private static IRandom s_randomImpl = DefaultThreadLocalRandom.INSTANCE; + private static AtomicLong s_seq = new AtomicLong(); + + public static long nextSeq() { + return s_seq.incrementAndGet(); + } + /** * 缺省返回ThreadLocalRandom */ diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBitValueLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBitValueLiteral.java index 8440b59e5..27f638604 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBitValueLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBitValueLiteral.java @@ -7,8 +7,12 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlBitValueLiteral; public class SqlBitValueLiteral extends _SqlBitValueLiteral { - + @Override + public StdSqlType getSqlType() { + return StdSqlType.TINYINT; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBooleanLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBooleanLiteral.java index 7c91830f3..a73ede920 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBooleanLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlBooleanLiteral.java @@ -7,8 +7,12 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlBooleanLiteral; public class SqlBooleanLiteral extends _SqlBooleanLiteral { - + @Override + public StdSqlType getSqlType() { + return StdSqlType.BOOLEAN; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlDateTimeLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlDateTimeLiteral.java index d422751b5..ba6aafa66 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlDateTimeLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlDateTimeLiteral.java @@ -7,8 +7,12 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlDateTimeLiteral; public class SqlDateTimeLiteral extends _SqlDateTimeLiteral { - + @Override + public StdSqlType getSqlType() { + return StdSqlType.DATETIME; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlHexadecimalLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlHexadecimalLiteral.java index 64bcdedf0..466012c9a 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlHexadecimalLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlHexadecimalLiteral.java @@ -7,8 +7,12 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlHexadecimalLiteral; public class SqlHexadecimalLiteral extends _SqlHexadecimalLiteral { - + @Override + public StdSqlType getSqlType() { + return StdSqlType.BIGINT; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlLiteral.java index 3fbc7d29c..dcfe60e14 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlLiteral.java @@ -7,7 +7,9 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlLiteral; public abstract class SqlLiteral extends _SqlLiteral { + public abstract StdSqlType getSqlType(); } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNullLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNullLiteral.java index aefab3824..c48befc6f 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNullLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNullLiteral.java @@ -7,8 +7,12 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlNullLiteral; public class SqlNullLiteral extends _SqlNullLiteral { - + @Override + public StdSqlType getSqlType() { + return StdSqlType.ANY; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNumberLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNumberLiteral.java index bc6927206..317b4cb75 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNumberLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlNumberLiteral.java @@ -7,6 +7,7 @@ */ package io.nop.orm.eql.ast; +import io.nop.commons.type.StdSqlType; import io.nop.commons.util.StringHelper; import io.nop.orm.eql.ast._gen._SqlNumberLiteral; @@ -15,4 +16,11 @@ public class SqlNumberLiteral extends _SqlNumberLiteral { public Number getNumberValue() { return StringHelper.parseNumber(getValue()); } + + @Override + public StdSqlType getSqlType() { + Number num = getNumberValue(); + StdSqlType sqlType = StdSqlType.fromJavaClass(num.getClass()); + return sqlType == null ? StdSqlType.DECIMAL : sqlType; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlStringLiteral.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlStringLiteral.java index 12687d568..fd0466e98 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlStringLiteral.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/ast/SqlStringLiteral.java @@ -8,6 +8,7 @@ package io.nop.orm.eql.ast; import io.nop.api.core.exceptions.NopException; +import io.nop.commons.type.StdSqlType; import io.nop.orm.eql.ast._gen._SqlStringLiteral; import static io.nop.core.CoreErrors.ARG_AST_NODE; @@ -20,4 +21,9 @@ protected void checkMandatory(String propName, Object value) { throw new NopException(ERR_LANG_AST_NODE_PROP_NOT_ALLOW_EMPTY).loc(getLocation()) .param(ARG_AST_NODE, getASTType()).param(ARG_PROP_NAME, propName); } + + @Override + public StdSqlType getSqlType() { + return StdSqlType.VARCHAR; + } } diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/ExprTypeResolver.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/ExprTypeResolver.java index 4c0ace586..b4f3c36cf 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/ExprTypeResolver.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/ExprTypeResolver.java @@ -17,6 +17,7 @@ import io.nop.orm.eql.ast.SqlBinaryExpr; import io.nop.orm.eql.ast.SqlDateTimeLiteral; import io.nop.orm.eql.ast.SqlExpr; +import io.nop.orm.eql.ast.SqlLiteral; import io.nop.orm.eql.ast.SqlRegularFunction; import io.nop.orm.eql.meta.ISqlExprMeta; import io.nop.orm.eql.meta.SingleColumnExprMeta; @@ -80,6 +81,10 @@ private StdSqlType resolveType(SqlExpr expr) { break; } } + if(type == StdSqlType.OTHER){ + if(expr instanceof SqlLiteral) + return ((SqlLiteral) expr).getSqlType(); + } if (type == null) type = StdSqlType.ANY; return type; diff --git a/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/SqlParamTypeResolver.java b/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/SqlParamTypeResolver.java index 2349df7d9..090b46310 100644 --- a/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/SqlParamTypeResolver.java +++ b/nop-orm-eql/src/main/java/io/nop/orm/eql/compile/SqlParamTypeResolver.java @@ -15,6 +15,7 @@ import io.nop.orm.eql.ast.EqlASTVisitor; import io.nop.orm.eql.ast.SqlAssignment; import io.nop.orm.eql.ast.SqlBinaryExpr; +import io.nop.orm.eql.ast.SqlExpr; import io.nop.orm.eql.ast.SqlParameterMarker; import io.nop.orm.eql.meta.ISqlExprMeta; import io.nop.orm.eql.meta.SingleColumnExprMeta; @@ -64,15 +65,26 @@ public void visitSqlParameterMarker(SqlParameterMarker node) { case SqlBinaryExpr: { SqlBinaryExpr binaryExpr = (SqlBinaryExpr) parent; StdSqlType sqlType; + SqlExpr otherExpr; if (binaryExpr.getLeft() == node) { + otherExpr = binaryExpr.getRight(); resolvedMeta = binaryExpr.getRight().getResolvedExprMeta(); sqlType = binaryExpr.getOperator().getLeftSqlType(); } else { + otherExpr = binaryExpr.getLeft(); resolvedMeta = binaryExpr.getLeft().getResolvedExprMeta(); sqlType = binaryExpr.getOperator().getRightSqlType(); } + + // 比较算符要求相同的类型 + if (resolvedMeta == null && binaryExpr.getOperator().isCompareOp()) { + resolvedMeta = new ExprTypeResolver(dialect).resolveExprMeta(otherExpr); + } + if (resolvedMeta == null) { IDataParameterBinder binder = dialect.getDataParameterBinder(sqlType.getStdDataType(), sqlType); + if (binder == null) + binder = DataParameterBinders.ANY; resolvedMeta = new SingleColumnExprMeta("?", binder, ExprOrmDataType.fromSqlType(sqlType)); } break; diff --git a/nop-orm/src/main/java/io/nop/orm/support/OrmMappingTableMeta.java b/nop-orm/src/main/java/io/nop/orm/support/OrmMappingTableMeta.java index f8de8c996..961a26034 100644 --- a/nop-orm/src/main/java/io/nop/orm/support/OrmMappingTableMeta.java +++ b/nop-orm/src/main/java/io/nop/orm/support/OrmMappingTableMeta.java @@ -1,6 +1,5 @@ package io.nop.orm.support; -import io.nop.api.core.util.Guard; import io.nop.commons.util.CollectionHelper; import io.nop.commons.util.StringHelper; import io.nop.orm.model.IEntityModel; @@ -23,7 +22,7 @@ public OrmMappingTableMeta(IEntityModel mappingTable) { this.refProp1 = CollectionHelper.first(rels); this.refProp2 = CollectionHelper.last(rels); - Guard.checkArgument(rels.size() == 2, "mappingTable must contains two to-one relations"); + // Guard.checkArgument(rels.size() == 2, "mappingTable must contains two to-one relations"); } /** diff --git a/nop-orm/src/test/java/io/nop/orm/impl/TestOrmTemplate.java b/nop-orm/src/test/java/io/nop/orm/impl/TestOrmTemplate.java index 648a7e934..c95532533 100644 --- a/nop-orm/src/test/java/io/nop/orm/impl/TestOrmTemplate.java +++ b/nop-orm/src/test/java/io/nop/orm/impl/TestOrmTemplate.java @@ -110,6 +110,15 @@ public void testSupports() { } } + @Test + public void testParamValueType() { + txn().runInTransaction(null, TransactionPropagation.SUPPORTS, txn -> { + SQL sql = SQL.begin().sql("select o,2 from io.nop.app.SimsClass o where 1=? and date(o.createdTime) > ?", 3,"2002-01-03").end(); + orm().findAll(sql); + return null; + }); + } + @Test public void testEntityId() { SimsClass entity = (SimsClass) orm().newEntity(SimsClass.class.getName());