diff --git a/src/org/redkale/source/FilterColumn.java b/src/org/redkale/source/FilterColumn.java index dd6de780b..72f11b8f3 100644 --- a/src/org/redkale/source/FilterColumn.java +++ b/src/org/redkale/source/FilterColumn.java @@ -5,9 +5,9 @@ */ package org.redkale.source; -import java.lang.annotation.*; import static java.lang.annotation.ElementType.FIELD; import static java.lang.annotation.RetentionPolicy.RUNTIME; +import java.lang.annotation.*; /** * @@ -46,4 +46,11 @@ public @interface FilterColumn { */ FilterExpress express() default FilterExpress.EQUAL; + /** + * 当标记的字段类型是数组/Collection类型且express不是IN/NOTIN时,则构建过滤条件时会遍历字段值的元素来循环构建表达式,元素之间的关系是AND或OR由该值来确定 + * + * @return 数组元素间的表达式是否AND关系 + */ + boolean itemand() default true; + } diff --git a/src/org/redkale/source/FilterJoinNode.java b/src/org/redkale/source/FilterJoinNode.java index 80a374896..3bfc9f916 100644 --- a/src/org/redkale/source/FilterJoinNode.java +++ b/src/org/redkale/source/FilterJoinNode.java @@ -5,15 +5,18 @@ */ package org.redkale.source; -import java.io.*; +import java.io.Serializable; import java.util.*; -import java.util.concurrent.atomic.*; +import java.util.concurrent.atomic.AtomicBoolean; import java.util.function.*; -import org.redkale.util.*; +import static org.redkale.source.FilterExpress.EQUAL; +import org.redkale.util.Attribute; /** * - *
详情见: http://www.redkale.org + *
+ * 详情见: http://www.redkale.org
+ *
* @author zhangjx
*/
public class FilterJoinNode extends FilterNode {
@@ -27,41 +30,55 @@ public class FilterJoinNode extends FilterNode {
public FilterJoinNode() {
}
- protected FilterJoinNode(Class joinClass, String[] joinColumns, String column, Serializable value) {
- this(joinClass, joinColumns, column, null, value);
- }
-
- protected FilterJoinNode(Class joinClass, String[] joinColumns, String column, FilterExpress express, Serializable value) {
+ protected FilterJoinNode(Class joinClass, String[] joinColumns, String column, FilterExpress express, boolean itemand, Serializable value) {
Objects.requireNonNull(joinClass);
Objects.requireNonNull(joinColumns);
+ if (express == null && value != null) {
+ if (value instanceof Range) {
+ express = FilterExpress.BETWEEN;
+ } else if (value instanceof Collection) {
+ express = FilterExpress.IN;
+ } else if (value.getClass().isArray()) {
+ express = FilterExpress.IN;
+ }
+ }
this.joinClass = joinClass;
this.joinColumns = joinColumns;
this.column = column;
- this.express = express;
+ this.express = express == null ? EQUAL : express;
+ this.itemand = itemand;
this.value = value;
}
protected FilterJoinNode(FilterJoinNode node) {
- this(node.joinClass, node.joinColumns, node.column, node.express, node.value);
+ this(node.joinClass, node.joinColumns, node.column, node.express, node.itemand, node.value);
this.joinEntity = node.joinEntity;
this.or = node.or;
this.nodes = node.nodes;
}
public static FilterJoinNode create(Class joinClass, String joinColumn, String column, Serializable value) {
- return new FilterJoinNode(joinClass, new String[]{joinColumn}, column, value);
+ return create(joinClass, new String[]{joinColumn}, column, value);
}
public static FilterJoinNode create(Class joinClass, String joinColumn, String column, FilterExpress express, Serializable value) {
- return new FilterJoinNode(joinClass, new String[]{joinColumn}, column, express, value);
+ return create(joinClass, new String[]{joinColumn}, column, express, value);
+ }
+
+ public static FilterJoinNode create(Class joinClass, String joinColumn, String column, FilterExpress express, boolean itemand, Serializable value) {
+ return create(joinClass, new String[]{joinColumn}, column, express, itemand, value);
}
public static FilterJoinNode create(Class joinClass, String[] joinColumns, String column, Serializable value) {
- return new FilterJoinNode(joinClass, joinColumns, column, value);
+ return create(joinClass, joinColumns, column, null, value);
}
public static FilterJoinNode create(Class joinClass, String[] joinColumns, String column, FilterExpress express, Serializable value) {
- return new FilterJoinNode(joinClass, joinColumns, column, express, value);
+ return create(joinClass, joinColumns, column, express, true, value);
+ }
+
+ public static FilterJoinNode create(Class joinClass, String[] joinColumns, String column, FilterExpress express, boolean itemand, Serializable value) {
+ return new FilterJoinNode(joinClass, joinColumns, column, express, itemand, value);
}
@Override
@@ -87,6 +104,7 @@ public class FilterJoinNode extends FilterNode {
this.nodes = new FilterNode[]{new FilterJoinNode(node), node};
this.column = null;
this.express = null;
+ this.itemand = true;
this.value = null;
this.joinClass = null;
this.joinEntity = null;
@@ -260,7 +278,7 @@ public class FilterJoinNode extends FilterNode {
StringBuilder sb = new StringBuilder();
String[] joinColumns = node.joinColumns;
sb.append(" INNER JOIN ").append(node.joinEntity.getTable()).append(" ").append(joinTabalis.get(node.joinClass))
- .append(" ON ").append(info.getSQLColumn("a", joinColumns[0])).append(" = ").append(node.joinEntity.getSQLColumn(joinTabalis.get(node.joinClass), joinColumns[0]));
+ .append(" ON ").append(info.getSQLColumn("a", joinColumns[0])).append(" = ").append(node.joinEntity.getSQLColumn(joinTabalis.get(node.joinClass), joinColumns[0]));
for (int i = 1; i < joinColumns.length; i++) {
sb.append(" AND ").append(info.getSQLColumn("a", joinColumns[i])).append(" = ").append(node.joinEntity.getSQLColumn(joinTabalis.get(node.joinClass), joinColumns[i]));
}
diff --git a/src/org/redkale/source/FilterNode.java b/src/org/redkale/source/FilterNode.java
index fecb95135..9ba5311cd 100644
--- a/src/org/redkale/source/FilterNode.java
+++ b/src/org/redkale/source/FilterNode.java
@@ -28,6 +28,8 @@ public class FilterNode {
protected Serializable value;
+ protected boolean itemand;
+
//----------------------------------------------
protected boolean or;
@@ -36,21 +38,40 @@ public class FilterNode {
public FilterNode() {
}
- protected FilterNode(String col, FilterExpress exp, Serializable val) {
+ protected FilterNode(String col, FilterExpress exp, boolean itemand, Serializable val) {
Objects.requireNonNull(col);
if (exp == null) {
if (val instanceof Range) {
exp = FilterExpress.BETWEEN;
} else if (val instanceof Collection) {
- exp = FilterExpress.IN;
+ if (!((Collection) val).isEmpty()) {
+ Object subval = null;
+ for (Object obj : (Collection) val) { //取第一个值
+ subval = obj;
+ break;
+ }
+ if (subval instanceof Range) {
+ exp = FilterExpress.BETWEEN;
+ } else if (subval instanceof Collection) {
+ exp = FilterExpress.IN;
+ } else if (subval != null && val.getClass().isArray()) {
+ exp = FilterExpress.IN;
+ }
+ } else { //空集合
+ exp = FilterExpress.IN;
+ }
} else if (val != null && val.getClass().isArray()) {
- exp = FilterExpress.IN;
- } else {
- exp = FilterExpress.EQUAL;
+ Class comp = val.getClass().getComponentType();
+ if (Range.class.isAssignableFrom(comp)) {
+ exp = FilterExpress.BETWEEN;
+ } else if (comp.isArray() || Collection.class.isAssignableFrom(comp)) {
+ exp = FilterExpress.IN;
+ }
}
}
this.column = col;
- this.express = exp;
+ this.express = exp == null ? EQUAL : exp;
+ this.itemand = itemand;
this.value = val;
}
@@ -63,7 +84,11 @@ public class FilterNode {
}
public final FilterNode and(String column, FilterExpress express, Serializable value) {
- return and(new FilterNode(column, express, value));
+ return and(column, express, true, value);
+ }
+
+ public final FilterNode and(String column, FilterExpress express, boolean itemand, Serializable value) {
+ return and(new FilterNode(column, express, itemand, value));
}
public final FilterNode or(FilterNode node) {
@@ -75,7 +100,11 @@ public class FilterNode {
}
public final FilterNode or(String column, FilterExpress express, Serializable value) {
- return or(new FilterNode(column, express, value));
+ return or(column, express, true, value);
+ }
+
+ public final FilterNode or(String column, FilterExpress express, boolean itemand, Serializable value) {
+ return or(new FilterNode(column, express, itemand, value));
}
protected FilterNode any(FilterNode node, boolean signor) {
@@ -83,6 +112,7 @@ public class FilterNode {
if (this.column == null) {
this.column = node.column;
this.express = node.express;
+ this.itemand = node.itemand;
this.value = node.value;
return this;
}
@@ -98,12 +128,13 @@ public class FilterNode {
this.nodes = newsiblings;
return this;
}
- FilterNode newnode = new FilterNode(this.column, this.express, this.value);
+ FilterNode newnode = new FilterNode(this.column, this.express, this.itemand, this.value);
newnode.or = this.or;
newnode.nodes = this.nodes;
this.nodes = new FilterNode[]{newnode, node};
this.column = null;
this.express = null;
+ this.itemand = true;
this.or = signor;
this.value = null;
return this;
@@ -206,16 +237,81 @@ public class FilterNode {
}
public static FilterNode create(String column, FilterExpress express, Serializable value) {
- return new FilterNode(column, express, value);
+ return create(column, express, true, value);
+ }
+
+ public static FilterNode create(String column, FilterExpress express, boolean itemand, Serializable value) {
+ return new FilterNode(column, express, itemand, value);
+ }
+
+ private boolean needSplit(final Object val0) {
+ return needSplit(express, val0);
+ }
+
+ private static boolean needSplit(final FilterExpress express, final Object val0) {
+ boolean items = express != IN && express != NOTIN; //是否数组集合的表达式
+ if (!items) {
+ if (val0.getClass().isArray()) {
+ Class comp = val0.getClass().getComponentType();
+ if (!(comp.isPrimitive() || CharSequence.class.isAssignableFrom(comp) || Number.class.isAssignableFrom(comp))) {
+ items = true;
+ }
+ } else if (val0 instanceof Collection) {
+ for (Object fv : (Collection) val0) {
+ if (fv == null) continue;
+ Class comp = fv.getClass();
+ if (!(comp.isPrimitive() || CharSequence.class.isAssignableFrom(comp) || Number.class.isAssignableFrom(comp))) {
+ items = true;
+ }
+ break; //只需检测第一个值
+ }
+ }
+ }
+ return items;
}
protected final