mirror of
https://gitee.com/best_handsome/mybatis-plus-join
synced 2025-07-25 00:00:12 +08:00
自连接和关联同一张表N次
This commit is contained in:
parent
d4a0843225
commit
ad1360e3c6
@ -186,7 +186,7 @@ public class MPJInterceptor implements Interceptor {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
Field field = fieldMap.get(i.getColumProperty());
|
Field field = fieldMap.get(i.getColumProperty());
|
||||||
columnSet.add(i.getColumProperty());
|
columnSet.add(i.getTagColumn());
|
||||||
if (Objects.nonNull(field)) {
|
if (Objects.nonNull(field)) {
|
||||||
ResultMapping.Builder builder = new ResultMapping.Builder(ms.getConfiguration(), i.getColumProperty(),
|
ResultMapping.Builder builder = new ResultMapping.Builder(ms.getConfiguration(), i.getColumProperty(),
|
||||||
i.getTagColumn(), field.getType());
|
i.getTagColumn(), field.getType());
|
||||||
|
@ -5,11 +5,11 @@ import com.baomidou.mybatisplus.core.toolkit.support.SFunction;
|
|||||||
import com.github.yulichang.toolkit.Constant;
|
import com.github.yulichang.toolkit.Constant;
|
||||||
import com.github.yulichang.toolkit.LambdaUtils;
|
import com.github.yulichang.toolkit.LambdaUtils;
|
||||||
import com.github.yulichang.toolkit.support.ColumnCache;
|
import com.github.yulichang.toolkit.support.ColumnCache;
|
||||||
|
import com.github.yulichang.wrapper.segments.Select;
|
||||||
import com.github.yulichang.wrapper.segments.SelectCache;
|
import com.github.yulichang.wrapper.segments.SelectCache;
|
||||||
import lombok.AllArgsConstructor;
|
import lombok.AllArgsConstructor;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
import lombok.EqualsAndHashCode;
|
import lombok.EqualsAndHashCode;
|
||||||
import lombok.Getter;
|
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
@ -28,27 +28,22 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
* 关联的表
|
* 关联的表
|
||||||
*/
|
*/
|
||||||
protected TableList tableList = new TableList();
|
protected TableList tableList = new TableList();
|
||||||
/**
|
|
||||||
* 表别名
|
|
||||||
*/
|
|
||||||
@Getter
|
|
||||||
protected String index;
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected <X> String columnToString(X column, boolean isJoin) {
|
protected <X> String columnToString(String index, X column, boolean isJoin) {
|
||||||
return columnToString((SFunction<?, ?>) column, isJoin);
|
return columnToString(index, (SFunction<?, ?>) column, isJoin);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@SafeVarargs
|
@SafeVarargs
|
||||||
protected final <X> String columnsToString(boolean isJoin, X... columns) {
|
protected final <X> String columnsToString(String index, boolean isJoin, X... columns) {
|
||||||
return Arrays.stream(columns).map(i -> columnToString((SFunction<?, ?>) i, isJoin)).collect(joining(StringPool.COMMA));
|
return Arrays.stream(columns).map(i -> columnToString(index, (SFunction<?, ?>) i, isJoin)).collect(joining(StringPool.COMMA));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String columnToString(SFunction<?, ?> column, boolean isJoin) {
|
protected String columnToString(String index, SFunction<?, ?> column, boolean isJoin) {
|
||||||
Class<?> entityClass = LambdaUtils.getEntityClass(column);
|
Class<?> entityClass = LambdaUtils.getEntityClass(column);
|
||||||
return Constant.TABLE_ALIAS + getDefault(entityClass, isJoin) + StringPool.DOT +
|
return Constant.TABLE_ALIAS + getDefault(index, entityClass, isJoin) + StringPool.DOT +
|
||||||
getCache(column).getTagColumn();
|
getCache(column).getTagColumn();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -58,26 +53,42 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
return cacheMap.get(LambdaUtils.getName(fn));
|
return cacheMap.get(LambdaUtils.getName(fn));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String getDefault(Class<?> clazz, boolean isJoin) {
|
protected String getDefault(String index, Class<?> clazz, boolean isJoin) {
|
||||||
|
if (Objects.isNull(index)) {
|
||||||
|
if (Objects.equals(clazz, getEntityClass())) {
|
||||||
|
return StringPool.EMPTY;
|
||||||
|
}
|
||||||
|
//正序
|
||||||
|
Table table = tableList.getPositive(clazz);
|
||||||
|
return Objects.isNull(table.index) ? StringPool.EMPTY : table.index;
|
||||||
|
}
|
||||||
Table table = tableList.get(clazz, index);
|
Table table = tableList.get(clazz, index);
|
||||||
if (Objects.nonNull(table.getIndex())) {
|
if (Objects.nonNull(table.getIndex())) {
|
||||||
if (getEntityClass() == null) {
|
if (isJoin) {
|
||||||
return table.getIndex();
|
//除自己以外的倒序第一个
|
||||||
}
|
Table t = tableList.getOrElse(clazz, index);
|
||||||
if (isJoin && joinClass == getEntityClass()) {
|
if (Objects.isNull(t.getIndex())) {
|
||||||
return StringPool.EMPTY;
|
return StringPool.EMPTY;
|
||||||
}
|
}
|
||||||
|
return t.getIndex();
|
||||||
|
}
|
||||||
return table.getIndex();
|
return table.getIndex();
|
||||||
}
|
}
|
||||||
return StringPool.EMPTY;
|
return StringPool.EMPTY;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected String getDefaultSelect(Class<?> clazz, boolean myself) {
|
protected String getDefaultSelect(String index, Class<?> clazz, Select s) {
|
||||||
|
if (s.isLabel()) {
|
||||||
|
if (Objects.nonNull(s.getIndex())) {
|
||||||
|
return s.getIndex();
|
||||||
|
} else {
|
||||||
|
Table table = tableList.get(s.getClazz());
|
||||||
|
return Objects.isNull(table.index) ? StringPool.EMPTY : table.index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
//外层select
|
||||||
Table table = tableList.get(clazz, index);
|
Table table = tableList.get(clazz, index);
|
||||||
if (Objects.nonNull(table.getIndex())) {
|
if (Objects.nonNull(table.getIndex())) {
|
||||||
if (myself) {
|
|
||||||
return StringPool.EMPTY;
|
|
||||||
}
|
|
||||||
return table.getIndex();
|
return table.getIndex();
|
||||||
}
|
}
|
||||||
return StringPool.EMPTY;
|
return StringPool.EMPTY;
|
||||||
@ -85,7 +96,7 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
|
|
||||||
public static class TableList {
|
public static class TableList {
|
||||||
|
|
||||||
private static final Table DEFAULT_TABLE = new Table(null, null);
|
private static final Table DEFAULT_TABLE = new Table(null, StringPool.EMPTY);
|
||||||
|
|
||||||
private final List<Table> list = new ArrayList<>();
|
private final List<Table> list = new ArrayList<>();
|
||||||
|
|
||||||
@ -93,8 +104,12 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
this.list.add(new Table(clazz, index));
|
this.list.add(new Table(clazz, index));
|
||||||
}
|
}
|
||||||
|
|
||||||
private Table get(Class<?> clazz) {
|
public Table get(Class<?> clazz) {
|
||||||
for (Table t : list) {
|
if (list.isEmpty()) {
|
||||||
|
return DEFAULT_TABLE;
|
||||||
|
}
|
||||||
|
for (int i = list.size() - 1; i >= 0; i--) {
|
||||||
|
Table t = list.get(i);
|
||||||
if (clazz == t.clazz) {
|
if (clazz == t.clazz) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
@ -102,15 +117,49 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
return DEFAULT_TABLE;
|
return DEFAULT_TABLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public Table get(Class<?> clazz, String index) {
|
public Table get(Class<?> clazz, String index) {
|
||||||
if (Objects.isNull(index)) {
|
if (Objects.isNull(index)) {
|
||||||
return get(clazz);
|
return get(clazz);
|
||||||
}
|
}
|
||||||
|
if (list.isEmpty()) {
|
||||||
|
return DEFAULT_TABLE;
|
||||||
|
}
|
||||||
|
//倒序
|
||||||
|
for (int i = list.size() - 1; i >= 0; i--) {
|
||||||
|
Table t = list.get(i);
|
||||||
|
if (clazz == t.clazz && Objects.equals(index, t.getIndex())) {
|
||||||
|
return t;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return get(clazz);
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unused")
|
||||||
|
public Table getPositive(Class<?> clazz, String index) {
|
||||||
|
if (Objects.isNull(index)) {
|
||||||
|
return get(clazz);
|
||||||
|
}
|
||||||
|
if (list.isEmpty()) {
|
||||||
|
return DEFAULT_TABLE;
|
||||||
|
}
|
||||||
for (Table t : list) {
|
for (Table t : list) {
|
||||||
if (clazz == t.clazz && Objects.equals(index, t.getIndex())) {
|
if (clazz == t.clazz && Objects.equals(index, t.getIndex())) {
|
||||||
return t;
|
return t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return getPositive(clazz);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Table getPositive(Class<?> clazz) {
|
||||||
|
if (list.isEmpty()) {
|
||||||
|
return DEFAULT_TABLE;
|
||||||
|
}
|
||||||
|
for (Table t : list) {
|
||||||
|
if (clazz == t.clazz) {
|
||||||
|
return t;
|
||||||
|
}
|
||||||
|
}
|
||||||
return DEFAULT_TABLE;
|
return DEFAULT_TABLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -125,14 +174,33 @@ public abstract class MPJAbstractLambdaWrapper<T, Children extends MPJAbstractLa
|
|||||||
public boolean isEmpty() {
|
public boolean isEmpty() {
|
||||||
return list.isEmpty();
|
return list.isEmpty();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Table getOrElse(Class<?> clazz, String index) {
|
||||||
|
if (Objects.isNull(index)) {
|
||||||
|
return get(clazz);
|
||||||
|
}
|
||||||
|
//倒序
|
||||||
|
for (int i = list.size() - 1; i >= 0; i--) {
|
||||||
|
Table t = list.get(i);
|
||||||
|
if (clazz == t.clazz) {
|
||||||
|
if (Objects.equals(index, t.getIndex())) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (Integer.parseInt(t.getIndex()) < Integer.parseInt(index)) {
|
||||||
|
return t;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return DEFAULT_TABLE;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Data
|
@Data
|
||||||
@EqualsAndHashCode
|
@EqualsAndHashCode
|
||||||
@AllArgsConstructor
|
@AllArgsConstructor
|
||||||
public static class Table {
|
public static class Table {
|
||||||
private Class<?> clazz;
|
private final Class<?> clazz;
|
||||||
|
|
||||||
private String index;
|
private final String index;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -41,6 +41,11 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
* 占位符
|
* 占位符
|
||||||
*/
|
*/
|
||||||
protected final Children typedThis = (Children) this;
|
protected final Children typedThis = (Children) this;
|
||||||
|
/**
|
||||||
|
* 表别名
|
||||||
|
*/
|
||||||
|
@Getter
|
||||||
|
protected String index;
|
||||||
/**
|
/**
|
||||||
* 必要度量
|
* 必要度量
|
||||||
*/
|
*/
|
||||||
@ -191,13 +196,13 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children between(boolean condition, SFunction<X, ?> column, Object val1, Object val2) {
|
public <X> Children between(boolean condition, SFunction<X, ?> column, Object val1, Object val2) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), BETWEEN,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), BETWEEN,
|
||||||
() -> formatParam(null, val1), AND, () -> formatParam(null, val2)));
|
() -> formatParam(null, val1), AND, () -> formatParam(null, val2)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children notBetween(boolean condition, SFunction<X, ?> column, Object val1, Object val2) {
|
public <X> Children notBetween(boolean condition, SFunction<X, ?> column, Object val1, Object val2) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_BETWEEN,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), NOT_BETWEEN,
|
||||||
() -> formatParam(null, val1), AND, () -> formatParam(null, val2)));
|
() -> formatParam(null, val1), AND, () -> formatParam(null, val2)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -269,43 +274,43 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children isNull(boolean condition, SFunction<X, ?> column) {
|
public <X> Children isNull(boolean condition, SFunction<X, ?> column) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), IS_NULL));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), IS_NULL));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children isNotNull(boolean condition, SFunction<X, ?> column) {
|
public <X> Children isNotNull(boolean condition, SFunction<X, ?> column) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), IS_NOT_NULL));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), IS_NOT_NULL));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children in(boolean condition, SFunction<X, ?> column, Collection<?> coll) {
|
public <X> Children in(boolean condition, SFunction<X, ?> column, Collection<?> coll) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), IN, inExpression(coll)));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), IN, inExpression(coll)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children in(boolean condition, SFunction<X, ?> column, Object... values) {
|
public <X> Children in(boolean condition, SFunction<X, ?> column, Object... values) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), IN, inExpression(values)));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), IN, inExpression(values)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children notIn(boolean condition, SFunction<X, ?> column, Collection<?> coll) {
|
public <X> Children notIn(boolean condition, SFunction<X, ?> column, Collection<?> coll) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_IN, inExpression(coll)));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), NOT_IN, inExpression(coll)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children notIn(boolean condition, SFunction<X, ?> column, Object... values) {
|
public <X> Children notIn(boolean condition, SFunction<X, ?> column, Object... values) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_IN, inExpression(values)));
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), NOT_IN, inExpression(values)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children inSql(boolean condition, SFunction<X, ?> column, String inValue) {
|
public <X> Children inSql(boolean condition, SFunction<X, ?> column, String inValue) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), IN,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), IN,
|
||||||
() -> String.format("(%s)", inValue)));
|
() -> String.format("(%s)", inValue)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <X> Children notInSql(boolean condition, SFunction<X, ?> column, String inValue) {
|
public <X> Children notInSql(boolean condition, SFunction<X, ?> column, String inValue) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_IN,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), NOT_IN,
|
||||||
() -> String.format("(%s)", inValue)));
|
() -> String.format("(%s)", inValue)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -313,7 +318,7 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
public <R> Children groupBy(boolean condition, List<SFunction<R, ?>> columns) {
|
public <R> Children groupBy(boolean condition, List<SFunction<R, ?>> columns) {
|
||||||
return maybeDo(condition, () -> {
|
return maybeDo(condition, () -> {
|
||||||
if (CollectionUtils.isNotEmpty(columns)) {
|
if (CollectionUtils.isNotEmpty(columns)) {
|
||||||
String one = (StringPool.COMMA + columnsToString(false, columns));
|
String one = (StringPool.COMMA + columnsToString(index, false, columns));
|
||||||
final String finalOne = one;
|
final String finalOne = one;
|
||||||
appendSqlSegments(GROUP_BY, () -> finalOne);
|
appendSqlSegments(GROUP_BY, () -> finalOne);
|
||||||
}
|
}
|
||||||
@ -323,9 +328,9 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
@Override
|
@Override
|
||||||
public <X> Children groupBy(boolean condition, SFunction<X, ?> column, SFunction<X, ?>... columns) {
|
public <X> Children groupBy(boolean condition, SFunction<X, ?> column, SFunction<X, ?>... columns) {
|
||||||
return maybeDo(condition, () -> {
|
return maybeDo(condition, () -> {
|
||||||
String one = columnToString(column, false);
|
String one = columnToString(index, column, false);
|
||||||
if (ArrayUtils.isNotEmpty(columns)) {
|
if (ArrayUtils.isNotEmpty(columns)) {
|
||||||
one += (StringPool.COMMA + columnsToString(false, columns));
|
one += (StringPool.COMMA + columnsToString(index, false, columns));
|
||||||
}
|
}
|
||||||
final String finalOne = one;
|
final String finalOne = one;
|
||||||
appendSqlSegments(GROUP_BY, () -> finalOne);
|
appendSqlSegments(GROUP_BY, () -> finalOne);
|
||||||
@ -338,7 +343,7 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
final SqlKeyword mode = ASC;
|
final SqlKeyword mode = ASC;
|
||||||
if (CollectionUtils.isNotEmpty(columns)) {
|
if (CollectionUtils.isNotEmpty(columns)) {
|
||||||
columns.forEach(c -> appendSqlSegments(ORDER_BY,
|
columns.forEach(c -> appendSqlSegments(ORDER_BY,
|
||||||
columnToSqlSegment(columnSqlInjectFilter(c), false), mode));
|
columnToSqlSegment(index, columnSqlInjectFilter(c), false), mode));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -349,7 +354,7 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
final SqlKeyword mode = DESC;
|
final SqlKeyword mode = DESC;
|
||||||
if (CollectionUtils.isNotEmpty(columns)) {
|
if (CollectionUtils.isNotEmpty(columns)) {
|
||||||
columns.forEach(c -> appendSqlSegments(ORDER_BY,
|
columns.forEach(c -> appendSqlSegments(ORDER_BY,
|
||||||
columnToSqlSegment(columnSqlInjectFilter(c), false), mode));
|
columnToSqlSegment(index, columnSqlInjectFilter(c), false), mode));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -358,10 +363,10 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
public <X> Children orderBy(boolean condition, boolean isAsc, SFunction<X, ?> column, SFunction<X, ?>... columns) {
|
public <X> Children orderBy(boolean condition, boolean isAsc, SFunction<X, ?> column, SFunction<X, ?>... columns) {
|
||||||
return maybeDo(condition, () -> {
|
return maybeDo(condition, () -> {
|
||||||
final SqlKeyword mode = isAsc ? ASC : DESC;
|
final SqlKeyword mode = isAsc ? ASC : DESC;
|
||||||
appendSqlSegments(ORDER_BY, columnToSqlSegment(column, false), mode);
|
appendSqlSegments(ORDER_BY, columnToSqlSegment(index, column, false), mode);
|
||||||
if (ArrayUtils.isNotEmpty(columns)) {
|
if (ArrayUtils.isNotEmpty(columns)) {
|
||||||
Arrays.stream(columns).forEach(c -> appendSqlSegments(ORDER_BY,
|
Arrays.stream(columns).forEach(c -> appendSqlSegments(ORDER_BY,
|
||||||
columnToSqlSegment(columnSqlInjectFilter(c), false), mode));
|
columnToSqlSegment(index, columnSqlInjectFilter(c), false), mode));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -408,7 +413,7 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
* <p>拼接 LIKE 以及 值</p>
|
* <p>拼接 LIKE 以及 值</p>
|
||||||
*/
|
*/
|
||||||
protected <X> Children likeValue(boolean condition, SqlKeyword keyword, SFunction<X, ?> column, Object val, SqlLike sqlLike) {
|
protected <X> Children likeValue(boolean condition, SqlKeyword keyword, SFunction<X, ?> column, Object val, SqlLike sqlLike) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), keyword,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), keyword,
|
||||||
() -> formatParam(null, SqlUtils.concatLike(val, sqlLike))));
|
() -> formatParam(null, SqlUtils.concatLike(val, sqlLike))));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -421,13 +426,13 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
* @param val 条件值
|
* @param val 条件值
|
||||||
*/
|
*/
|
||||||
protected <X> Children addCondition(boolean condition, SFunction<X, ?> column, SqlKeyword sqlKeyword, Object val) {
|
protected <X> Children addCondition(boolean condition, SFunction<X, ?> column, SqlKeyword sqlKeyword, Object val) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, true), sqlKeyword,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), sqlKeyword,
|
||||||
() -> formatParam(null, val)));
|
() -> formatParam(null, val)));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected <X, S> Children addCondition(boolean condition, SFunction<X, ?> column, SqlKeyword sqlKeyword, SFunction<S, ?> val) {
|
protected <X, S> Children addCondition(boolean condition, SFunction<X, ?> column, SqlKeyword sqlKeyword, SFunction<S, ?> val) {
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), sqlKeyword,
|
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(index, column, false), sqlKeyword,
|
||||||
columnToSqlSegment(val, true)));
|
columnToSqlSegment(index, val, true)));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -609,14 +614,14 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
/**
|
/**
|
||||||
* 获取 columnName
|
* 获取 columnName
|
||||||
*/
|
*/
|
||||||
protected final <X> ISqlSegment columnToSqlSegment(SFunction<X, ?> column, boolean isJoin) {
|
protected final <X> ISqlSegment columnToSqlSegment(String index, SFunction<X, ?> column, boolean isJoin) {
|
||||||
return () -> columnToString(column, isJoin);
|
return () -> columnToString(index, column, isJoin);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取 columnName
|
* 获取 columnName
|
||||||
*/
|
*/
|
||||||
protected <X> String columnToString(X column, boolean isJoin) {
|
protected <X> String columnToString(String index, X column, boolean isJoin) {
|
||||||
return (String) column;
|
return (String) column;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -625,8 +630,8 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
*
|
*
|
||||||
* @param columns 多字段
|
* @param columns 多字段
|
||||||
*/
|
*/
|
||||||
protected <X> String columnsToString(boolean isJoin, X... columns) {
|
protected <X> String columnsToString(String index, boolean isJoin, X... columns) {
|
||||||
return Arrays.stream(columns).map(i -> this.columnToString(i, isJoin)).collect(joining(StringPool.COMMA));
|
return Arrays.stream(columns).map(i -> this.columnToString(index, i, isJoin)).collect(joining(StringPool.COMMA));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -675,36 +680,4 @@ public abstract class MPJAbstractWrapper<T, Children extends MPJAbstractWrapper<
|
|||||||
public <R, S> Children le(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val) {
|
public <R, S> Children le(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val) {
|
||||||
return addCondition(condition, column, LE, val);
|
return addCondition(condition, column, LE, val);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, S, U> Children between(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<U, ?> val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), BETWEEN,
|
|
||||||
columnToSqlSegment(val1, true), AND, columnToSqlSegment(val2, true)));
|
|
||||||
}
|
|
||||||
|
|
||||||
public <R, S> Children between(boolean condition, SFunction<R, ?> column, Object val1, SFunction<S, ?> val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), BETWEEN,
|
|
||||||
() -> formatParam(null, val1), AND, columnToSqlSegment(val2, true)));
|
|
||||||
}
|
|
||||||
|
|
||||||
public <R, S> Children between(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, Object val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), BETWEEN,
|
|
||||||
columnToSqlSegment(val1, true), AND, () -> formatParam(null, val2)));
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public <R, S, U> Children notBetween(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<U, ?> val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_BETWEEN,
|
|
||||||
columnToSqlSegment(val1, true), AND, columnToSqlSegment(val2, true)));
|
|
||||||
}
|
|
||||||
|
|
||||||
public <R, U> Children notBetween(boolean condition, SFunction<R, ?> column, Object val1, SFunction<U, ?> val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_BETWEEN,
|
|
||||||
() -> formatParam(null, val1), AND, columnToSqlSegment(val2, true)));
|
|
||||||
}
|
|
||||||
|
|
||||||
public <R, S> Children notBetween(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, Object val2) {
|
|
||||||
return maybeDo(condition, () -> appendSqlSegments(columnToSqlSegment(column, false), NOT_BETWEEN,
|
|
||||||
columnToSqlSegment(val1, true), AND, () -> formatParam(null, val2)));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -17,7 +17,7 @@ import com.github.yulichang.toolkit.support.ColumnCache;
|
|||||||
import com.github.yulichang.wrapper.interfaces.Query;
|
import com.github.yulichang.wrapper.interfaces.Query;
|
||||||
import com.github.yulichang.wrapper.interfaces.QueryJoin;
|
import com.github.yulichang.wrapper.interfaces.QueryJoin;
|
||||||
import com.github.yulichang.wrapper.interfaces.QueryLabel;
|
import com.github.yulichang.wrapper.interfaces.QueryLabel;
|
||||||
import com.github.yulichang.wrapper.interfaces.on.OnFunction;
|
import com.github.yulichang.wrapper.interfaces.on.WrapperFunction;
|
||||||
import com.github.yulichang.wrapper.resultmap.MybatisLabel;
|
import com.github.yulichang.wrapper.resultmap.MybatisLabel;
|
||||||
import com.github.yulichang.wrapper.segments.Select;
|
import com.github.yulichang.wrapper.segments.Select;
|
||||||
import com.github.yulichang.wrapper.segments.SelectCache;
|
import com.github.yulichang.wrapper.segments.SelectCache;
|
||||||
@ -27,6 +27,7 @@ import lombok.Getter;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@ -104,7 +105,7 @@ public class MPJLambdaWrapper<T> extends MPJAbstractLambdaWrapper<T, MPJLambdaWr
|
|||||||
MPJLambdaWrapper(T entity, Class<T> entityClass, SharedString sqlSelect, AtomicInteger paramNameSeq,
|
MPJLambdaWrapper(T entity, Class<T> entityClass, SharedString sqlSelect, AtomicInteger paramNameSeq,
|
||||||
Map<String, Object> paramNameValuePairs, MergeSegments mergeSegments,
|
Map<String, Object> paramNameValuePairs, MergeSegments mergeSegments,
|
||||||
SharedString lastSql, SharedString sqlComment, SharedString sqlFirst,
|
SharedString lastSql, SharedString sqlComment, SharedString sqlFirst,
|
||||||
TableList tableList, String keyWord, Class<?> joinClass) {
|
TableList tableList, String index, String keyWord, Class<?> joinClass) {
|
||||||
super.setEntity(entity);
|
super.setEntity(entity);
|
||||||
super.setEntityClass(entityClass);
|
super.setEntityClass(entityClass);
|
||||||
this.paramNameSeq = paramNameSeq;
|
this.paramNameSeq = paramNameSeq;
|
||||||
@ -115,6 +116,7 @@ public class MPJLambdaWrapper<T> extends MPJAbstractLambdaWrapper<T, MPJLambdaWr
|
|||||||
this.sqlComment = sqlComment;
|
this.sqlComment = sqlComment;
|
||||||
this.sqlFirst = sqlFirst;
|
this.sqlFirst = sqlFirst;
|
||||||
this.tableList = tableList;
|
this.tableList = tableList;
|
||||||
|
this.index = index;
|
||||||
this.keyWord = keyWord;
|
this.keyWord = keyWord;
|
||||||
this.joinClass = joinClass;
|
this.joinClass = joinClass;
|
||||||
}
|
}
|
||||||
@ -173,7 +175,7 @@ public class MPJLambdaWrapper<T> extends MPJAbstractLambdaWrapper<T, MPJLambdaWr
|
|||||||
public String getSqlSelect() {
|
public String getSqlSelect() {
|
||||||
if (StringUtils.isBlank(sqlSelect.getStringValue()) && CollectionUtils.isNotEmpty(selectColumns)) {
|
if (StringUtils.isBlank(sqlSelect.getStringValue()) && CollectionUtils.isNotEmpty(selectColumns)) {
|
||||||
String s = selectColumns.stream().map(i -> {
|
String s = selectColumns.stream().map(i -> {
|
||||||
String str = Constant.TABLE_ALIAS + getDefaultSelect(i.getClazz(), (i.getClazz() == getEntityClass() && !i.isLabel())) + StringPool.DOT + i.getColumn();
|
String str = Constant.TABLE_ALIAS + getDefaultSelect(i.getIndex(), i.getClazz(), i) + StringPool.DOT + i.getColumn();
|
||||||
return i.isFunc() ? (String.format(i.getFunc().getSql(), str) + Constant.AS + i.getAlias()) : (i.isHasAlias() ? (str + Constant.AS + i.getAlias()) : str);
|
return i.isFunc() ? (String.format(i.getFunc().getSql(), str) + Constant.AS + i.getAlias()) : (i.isHasAlias() ? (str + Constant.AS + i.getAlias()) : str);
|
||||||
}).collect(Collectors.joining(StringPool.COMMA));
|
}).collect(Collectors.joining(StringPool.COMMA));
|
||||||
sqlSelect.setStringValue(s);
|
sqlSelect.setStringValue(s);
|
||||||
@ -216,13 +218,13 @@ public class MPJLambdaWrapper<T> extends MPJAbstractLambdaWrapper<T, MPJLambdaWr
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
protected MPJLambdaWrapper<T> instance() {
|
protected MPJLambdaWrapper<T> instance() {
|
||||||
return instance(null, null);
|
return instance(index, null, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected MPJLambdaWrapper<T> instance(String keyWord, Class<?> joinClass) {
|
protected MPJLambdaWrapper<T> instance(String index, String keyWord, Class<?> joinClass) {
|
||||||
return new MPJLambdaWrapper<>(getEntity(), getEntityClass(), null, paramNameSeq, paramNameValuePairs,
|
return new MPJLambdaWrapper<>(getEntity(), getEntityClass(), null, paramNameSeq, paramNameValuePairs,
|
||||||
new MergeSegments(), SharedString.emptyString(), SharedString.emptyString(), SharedString.emptyString(),
|
new MergeSegments(), SharedString.emptyString(), SharedString.emptyString(), SharedString.emptyString(),
|
||||||
this.tableList, keyWord, joinClass);
|
this.tableList, index, keyWord, joinClass);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -285,12 +287,21 @@ public class MPJLambdaWrapper<T> extends MPJAbstractLambdaWrapper<T, MPJLambdaWr
|
|||||||
return this.logicSql;
|
return this.logicSql;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 调用此方法 keyword 前后需要带空格 比如 " LEFT JOIN " " RIGHT JOIN "
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public <R> MPJLambdaWrapper<T> join(String keyWord, Class<R> clazz, OnFunction<T> function) {
|
public <R> MPJLambdaWrapper<T> join(String keyWord, Class<R> clazz, WrapperFunction<T> function, WrapperFunction<T> ext) {
|
||||||
MPJLambdaWrapper<T> apply = function.apply(instance(keyWord, clazz));
|
String name = String.valueOf(tableIndex);
|
||||||
tableList.add(clazz, String.valueOf(tableIndex));
|
MPJLambdaWrapper<T> apply = function.apply(instance(name, keyWord, clazz));
|
||||||
|
tableList.add(clazz, name);
|
||||||
onWrappers.add(apply);
|
onWrappers.add(apply);
|
||||||
tableIndex++;
|
tableIndex++;
|
||||||
|
if (Objects.nonNull(ext)) {
|
||||||
|
this.index = name;
|
||||||
|
MPJLambdaWrapper<T> wrapper = ext.apply(typedThis);
|
||||||
|
wrapper.index = null;
|
||||||
|
}
|
||||||
return typedThis;
|
return typedThis;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -91,10 +91,26 @@ public interface Query<Children> extends Serializable {
|
|||||||
default <S> Children selectAs(SFunction<S, ?> column, String alias) {
|
default <S> Children selectAs(SFunction<S, ?> column, String alias) {
|
||||||
Class<?> aClass = LambdaUtils.getEntityClass(column);
|
Class<?> aClass = LambdaUtils.getEntityClass(column);
|
||||||
Map<String, SelectCache> cacheMap = ColumnCache.getMapField(aClass);
|
Map<String, SelectCache> cacheMap = ColumnCache.getMapField(aClass);
|
||||||
|
String index = getIndex();
|
||||||
getSelectColum().add(new SelectAlias(cacheMap.get(LambdaUtils.getName(column)), getIndex(), alias));
|
getSelectColum().add(new SelectAlias(cacheMap.get(LambdaUtils.getName(column)), getIndex(), alias));
|
||||||
return getChildren();
|
return getChildren();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询实体类全部字段
|
||||||
|
*/
|
||||||
|
default Children selectAll(Class<?> clazz) {
|
||||||
|
getSelectColum().addAll(ColumnCache.getListField(clazz).stream().map(i ->
|
||||||
|
new SelectNormal(i, getIndex())).collect(Collectors.toList()));
|
||||||
|
return getChildren();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* select sql 片段
|
||||||
|
*/
|
||||||
|
String getSqlSelect();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 聚合函数查询
|
* 聚合函数查询
|
||||||
* <p>
|
* <p>
|
||||||
@ -131,19 +147,6 @@ public interface Query<Children> extends Serializable {
|
|||||||
return selectFunc(funcEnum, column, LambdaUtils.getName(alias));
|
return selectFunc(funcEnum, column, LambdaUtils.getName(alias));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 查询实体类全部字段
|
|
||||||
*/
|
|
||||||
default Children selectAll(Class<?> clazz) {
|
|
||||||
getSelectColum().addAll(ColumnCache.getListField(clazz).stream().map(i ->
|
|
||||||
new SelectNormal(i, getIndex())).collect(Collectors.toList()));
|
|
||||||
return getChildren();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* select sql 片段
|
|
||||||
*/
|
|
||||||
String getSqlSelect();
|
|
||||||
|
|
||||||
/* 默认聚合函数扩展 */
|
/* 默认聚合函数扩展 */
|
||||||
|
|
||||||
|
@ -4,7 +4,7 @@ import com.baomidou.mybatisplus.core.toolkit.support.SFunction;
|
|||||||
import com.github.yulichang.interfaces.MPJBaseJoin;
|
import com.github.yulichang.interfaces.MPJBaseJoin;
|
||||||
import com.github.yulichang.toolkit.Constant;
|
import com.github.yulichang.toolkit.Constant;
|
||||||
import com.github.yulichang.toolkit.LambdaUtils;
|
import com.github.yulichang.toolkit.LambdaUtils;
|
||||||
import com.github.yulichang.wrapper.interfaces.on.OnFunction;
|
import com.github.yulichang.wrapper.interfaces.on.WrapperFunction;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author yulichang
|
* @author yulichang
|
||||||
@ -41,8 +41,41 @@ public interface QueryJoin<Children, Entity> extends MPJBaseJoin<Entity> {
|
|||||||
* @param clazz 关联实体类
|
* @param clazz 关联实体类
|
||||||
* @param function 条件
|
* @param function 条件
|
||||||
*/
|
*/
|
||||||
default <T> Children leftJoin(Class<T> clazz, OnFunction<Entity> function) {
|
default <T> Children leftJoin(Class<T> clazz, WrapperFunction<Entity> function) {
|
||||||
return join(Constant.LEFT_JOIN, clazz, function);
|
return join(Constant.LEFT_JOIN, clazz, function, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* left join
|
||||||
|
*
|
||||||
|
* @param clazz 关联的实体类
|
||||||
|
* @param left 条件
|
||||||
|
* @param right 条件
|
||||||
|
*/
|
||||||
|
default <T, X> Children leftJoin(Class<T> clazz, SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return leftJoin(clazz, on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* left join
|
||||||
|
*
|
||||||
|
* @param left 条件
|
||||||
|
* @param right 条件
|
||||||
|
*/
|
||||||
|
default <T, X> Children leftJoin(SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return leftJoin(LambdaUtils.getEntityClass(left), on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* left join 多条件
|
||||||
|
* <p>
|
||||||
|
* 例 leftJoin(UserDO.class, on -> on.eq(UserDO::getId,UserAddressDO::getUserId).le().gt()...)
|
||||||
|
*
|
||||||
|
* @param clazz 关联实体类
|
||||||
|
* @param function 条件
|
||||||
|
*/
|
||||||
|
default <T> Children leftJoin(Class<T> clazz, WrapperFunction<Entity> function, WrapperFunction<Entity> ext) {
|
||||||
|
return join(Constant.LEFT_JOIN, clazz, function, ext);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -62,8 +95,29 @@ public interface QueryJoin<Children, Entity> extends MPJBaseJoin<Entity> {
|
|||||||
/**
|
/**
|
||||||
* ignore 参考 left join
|
* ignore 参考 left join
|
||||||
*/
|
*/
|
||||||
default <T> Children rightJoin(Class<T> clazz, OnFunction<Entity> function) {
|
default <T> Children rightJoin(Class<T> clazz, WrapperFunction<Entity> function) {
|
||||||
return join(Constant.RIGHT_JOIN, clazz, function);
|
return join(Constant.RIGHT_JOIN, clazz, function, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children rightJoin(Class<T> clazz, SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return rightJoin(clazz, on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children rightJoin(SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return rightJoin(LambdaUtils.getEntityClass(left), on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T> Children rightJoin(Class<T> clazz, WrapperFunction<Entity> function, WrapperFunction<Entity> ext) {
|
||||||
|
return join(Constant.RIGHT_JOIN, clazz, function, ext);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -83,8 +137,29 @@ public interface QueryJoin<Children, Entity> extends MPJBaseJoin<Entity> {
|
|||||||
/**
|
/**
|
||||||
* ignore 参考 left join
|
* ignore 参考 left join
|
||||||
*/
|
*/
|
||||||
default <T> Children innerJoin(Class<T> clazz, OnFunction<Entity> function) {
|
default <T> Children innerJoin(Class<T> clazz, WrapperFunction<Entity> function) {
|
||||||
return join(Constant.INNER_JOIN, clazz, function);
|
return join(Constant.INNER_JOIN, clazz, function, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children innerJoin(Class<T> clazz, SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return innerJoin(clazz, on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children innerJoin(SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return innerJoin(LambdaUtils.getEntityClass(left), on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T> Children innerJoin(Class<T> clazz, WrapperFunction<Entity> function, WrapperFunction<Entity> ext) {
|
||||||
|
return join(Constant.INNER_JOIN, clazz, function, ext);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -105,16 +180,41 @@ public interface QueryJoin<Children, Entity> extends MPJBaseJoin<Entity> {
|
|||||||
/**
|
/**
|
||||||
* ignore 参考 left join
|
* ignore 参考 left join
|
||||||
*/
|
*/
|
||||||
default <T> Children fullJoin(Class<T> clazz, OnFunction<Entity> function) {
|
default <T> Children fullJoin(Class<T> clazz, WrapperFunction<Entity> function) {
|
||||||
return join(Constant.FULL_JOIN, clazz, function);
|
return join(Constant.FULL_JOIN, clazz, function, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children fullJoin(Class<T> clazz, SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return fullJoin(clazz, on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T, X> Children fullJoin(SFunction<T, ?> left, SFunction<X, ?> right, WrapperFunction<Entity> ext) {
|
||||||
|
return fullJoin(LambdaUtils.getEntityClass(left), on -> on.eq(left, right), ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* ignore 参考 left join
|
||||||
|
*/
|
||||||
|
default <T> Children fullJoin(Class<T> clazz, WrapperFunction<Entity> function, WrapperFunction<Entity> ext) {
|
||||||
|
return join(Constant.FULL_JOIN, clazz, function, ext);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 调用此方法 keyword 前后需要带空格 比如 " LEFT JOIN " " RIGHT JOIN "
|
||||||
|
* <p>
|
||||||
* 查询基类 可以直接调用此方法实现以上所有功能
|
* 查询基类 可以直接调用此方法实现以上所有功能
|
||||||
*
|
*
|
||||||
* @param keyWord 连表关键字
|
* @param keyWord 连表关键字
|
||||||
* @param clazz 连表实体类
|
* @param clazz 连表实体类
|
||||||
* @param function 关联条件
|
* @param function 关联条件
|
||||||
|
* @param ext 扩展 用于关联表的 select 和 where
|
||||||
*/
|
*/
|
||||||
<T> Children join(String keyWord, Class<T> clazz, OnFunction<Entity> function);
|
<T> Children join(String keyWord, Class<T> clazz, WrapperFunction<Entity> function, WrapperFunction<Entity> ext);
|
||||||
}
|
}
|
||||||
|
@ -10,6 +10,7 @@ import com.github.yulichang.wrapper.resultmap.MybatisLabel;
|
|||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
@SuppressWarnings({"unchecked", "unused"})
|
@SuppressWarnings({"unchecked", "unused"})
|
||||||
public interface QueryLabel<Children> {
|
public interface QueryLabel<Children> {
|
||||||
@ -42,18 +43,23 @@ public interface QueryLabel<Children> {
|
|||||||
* @param <F> 包装类集合字段泛型
|
* @param <F> 包装类集合字段泛型
|
||||||
*/
|
*/
|
||||||
default <S, C, Z, F extends java.util.Collection<?>> Children selectCollection(Class<C> child, SFunction<S, F> dtoField) {
|
default <S, C, Z, F extends java.util.Collection<?>> Children selectCollection(Class<C> child, SFunction<S, F> dtoField) {
|
||||||
|
return selectCollection(null, child, dtoField);
|
||||||
|
}
|
||||||
|
|
||||||
|
default <S, C, Z, F extends java.util.Collection<?>> Children selectCollection(Integer index, Class<C> child, SFunction<S, F> dtoField) {
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
||||||
Field field = fieldMap.get(dtoFieldName);
|
Field field = fieldMap.get(dtoFieldName);
|
||||||
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
||||||
MybatisLabel.Builder<C, Z> builder;
|
MybatisLabel.Builder<C, Z> builder;
|
||||||
|
String s = Objects.isNull(index) ? null : index.toString();
|
||||||
if (genericType == null || genericType.isAssignableFrom(child)) {
|
if (genericType == null || genericType.isAssignableFrom(child)) {
|
||||||
//找不到集合泛型 List List<?> List<Object> , 直接查询数据库实体
|
//找不到集合泛型 List List<?> List<Object> , 直接查询数据库实体
|
||||||
builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType());
|
builder = new MybatisLabel.Builder<>(s, dtoFieldName, child, field.getType());
|
||||||
} else {
|
} else {
|
||||||
Class<Z> ofType = (Class<Z>) genericType;
|
Class<Z> ofType = (Class<Z>) genericType;
|
||||||
builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), ofType, true);
|
builder = new MybatisLabel.Builder<>(s, dtoFieldName, child, field.getType(), ofType, true);
|
||||||
}
|
}
|
||||||
addLabel(builder.build());
|
addLabel(builder.build());
|
||||||
return getChildren();
|
return getChildren();
|
||||||
@ -90,13 +96,21 @@ public interface QueryLabel<Children> {
|
|||||||
default <S, C, Z, F extends java.util.Collection<Z>> Children selectCollection(Class<C> child,
|
default <S, C, Z, F extends java.util.Collection<Z>> Children selectCollection(Class<C> child,
|
||||||
SFunction<S, F> dtoField,
|
SFunction<S, F> dtoField,
|
||||||
MFunc<MybatisLabel.Builder<C, Z>> collection) {
|
MFunc<MybatisLabel.Builder<C, Z>> collection) {
|
||||||
|
return selectCollection(null, child, dtoField, collection);
|
||||||
|
}
|
||||||
|
|
||||||
|
default <S, C, Z, F extends java.util.Collection<Z>> Children selectCollection(Integer index,
|
||||||
|
Class<C> child,
|
||||||
|
SFunction<S, F> dtoField,
|
||||||
|
MFunc<MybatisLabel.Builder<C, Z>> collection) {
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
||||||
//获取集合泛型
|
//获取集合泛型
|
||||||
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
||||||
Class<Z> ofType = (Class<Z>) genericType;
|
Class<Z> ofType = (Class<Z>) genericType;
|
||||||
MybatisLabel.Builder<C, Z> builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), ofType, false);
|
MybatisLabel.Builder<C, Z> builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, child, field.getType(), ofType, false);
|
||||||
MybatisLabel.Builder<C, Z> czBuilder = collection.apply(builder);
|
MybatisLabel.Builder<C, Z> czBuilder = collection.apply(builder);
|
||||||
addLabel(czBuilder.build());
|
addLabel(czBuilder.build());
|
||||||
return getChildren();
|
return getChildren();
|
||||||
@ -108,13 +122,18 @@ public interface QueryLabel<Children> {
|
|||||||
* @since 1.3.0
|
* @since 1.3.0
|
||||||
*/
|
*/
|
||||||
default <S, C, F> Children selectAssociation(Class<C> child, SFunction<S, F> dtoField) {
|
default <S, C, F> Children selectAssociation(Class<C> child, SFunction<S, F> dtoField) {
|
||||||
|
return selectAssociation(null, child, dtoField);
|
||||||
|
}
|
||||||
|
|
||||||
|
default <S, C, F> Children selectAssociation(Integer index, Class<C> child, SFunction<S, F> dtoField) {
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
||||||
Field field = fieldMap.get(dtoFieldName);
|
Field field = fieldMap.get(dtoFieldName);
|
||||||
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
||||||
MybatisLabel.Builder<C, F> builder;
|
MybatisLabel.Builder<C, F> builder;
|
||||||
builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), (Class<F>) field.getType(), true);
|
builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, child, field.getType(), (Class<F>) field.getType(), true);
|
||||||
addLabel(builder.build());
|
addLabel(builder.build());
|
||||||
return getChildren();
|
return getChildren();
|
||||||
}
|
}
|
||||||
@ -126,11 +145,17 @@ public interface QueryLabel<Children> {
|
|||||||
*/
|
*/
|
||||||
default <S, C, F> Children selectAssociation(Class<C> child, SFunction<S, F> dtoField,
|
default <S, C, F> Children selectAssociation(Class<C> child, SFunction<S, F> dtoField,
|
||||||
MFunc<MybatisLabel.Builder<C, F>> collection) {
|
MFunc<MybatisLabel.Builder<C, F>> collection) {
|
||||||
|
return selectAssociation(null, child, dtoField, collection);
|
||||||
|
}
|
||||||
|
|
||||||
|
default <S, C, F> Children selectAssociation(Integer index, Class<C> child, SFunction<S, F> dtoField,
|
||||||
|
MFunc<MybatisLabel.Builder<C, F>> collection) {
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<S> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
||||||
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
||||||
MybatisLabel.Builder<C, F> builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), (Class<F>) child, false);
|
MybatisLabel.Builder<C, F> builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, child, field.getType(), (Class<F>) child, false);
|
||||||
MybatisLabel.Builder<C, F> cfBuilder = collection.apply(builder);
|
MybatisLabel.Builder<C, F> cfBuilder = collection.apply(builder);
|
||||||
addLabel(cfBuilder.build());
|
addLabel(cfBuilder.build());
|
||||||
return getChildren();
|
return getChildren();
|
||||||
|
@ -115,40 +115,4 @@ public interface OnCompare<Children> extends Serializable {
|
|||||||
* @return children
|
* @return children
|
||||||
*/
|
*/
|
||||||
<R, S> Children le(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val);
|
<R, S> Children le(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val);
|
||||||
|
|
||||||
/**
|
|
||||||
* ignore
|
|
||||||
*/
|
|
||||||
default <R, S, T> Children between(SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<T, ?> val2) {
|
|
||||||
return between(true, column, val1, val2);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* BETWEEN 值1 AND 值2
|
|
||||||
*
|
|
||||||
* @param condition 执行条件
|
|
||||||
* @param column 字段
|
|
||||||
* @param val1 值1
|
|
||||||
* @param val2 值2
|
|
||||||
* @return children
|
|
||||||
*/
|
|
||||||
<R, S, T> Children between(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<T, ?> val2);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* ignore
|
|
||||||
*/
|
|
||||||
default <R, S, T> Children notBetween(SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<T, ?> val2) {
|
|
||||||
return notBetween(true, column, val1, val2);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* NOT BETWEEN 值1 AND 值2
|
|
||||||
*
|
|
||||||
* @param condition 执行条件
|
|
||||||
* @param column 字段
|
|
||||||
* @param val1 值1
|
|
||||||
* @param val2 值2
|
|
||||||
* @return children
|
|
||||||
*/
|
|
||||||
<R, S, T> Children notBetween(boolean condition, SFunction<R, ?> column, SFunction<S, ?> val1, SFunction<T, ?> val2);
|
|
||||||
}
|
}
|
||||||
|
@ -9,7 +9,7 @@ import com.github.yulichang.wrapper.MPJLambdaWrapper;
|
|||||||
* @since 1.1.8
|
* @since 1.1.8
|
||||||
*/
|
*/
|
||||||
@FunctionalInterface
|
@FunctionalInterface
|
||||||
public interface OnFunction<T> {
|
public interface WrapperFunction<T> {
|
||||||
|
|
||||||
MPJLambdaWrapper<T> apply(MPJLambdaWrapper<T> wrapper);
|
MPJLambdaWrapper<T> apply(MPJLambdaWrapper<T> wrapper);
|
||||||
}
|
}
|
@ -24,7 +24,7 @@ import java.util.stream.Collectors;
|
|||||||
@Getter
|
@Getter
|
||||||
public class MybatisLabel<E, T> {
|
public class MybatisLabel<E, T> {
|
||||||
|
|
||||||
private final String index = null;
|
private String index;
|
||||||
|
|
||||||
private String property;
|
private String property;
|
||||||
|
|
||||||
@ -53,9 +53,10 @@ public class MybatisLabel<E, T> {
|
|||||||
* 自动构建
|
* 自动构建
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public Builder(String property, Class<E> entityClass, Class<?> javaType) {
|
public Builder(String index, String property, Class<E> entityClass, Class<?> javaType) {
|
||||||
this.mybatisLabel = new MybatisLabel<>();
|
this.mybatisLabel = new MybatisLabel<>();
|
||||||
mybatisLabel.property = property;
|
mybatisLabel.property = property;
|
||||||
|
mybatisLabel.index = index;
|
||||||
mybatisLabel.entityClass = entityClass;
|
mybatisLabel.entityClass = entityClass;
|
||||||
mybatisLabel.javaType = javaType;
|
mybatisLabel.javaType = javaType;
|
||||||
mybatisLabel.ofType = (Class<T>) entityClass;
|
mybatisLabel.ofType = (Class<T>) entityClass;
|
||||||
@ -73,9 +74,10 @@ public class MybatisLabel<E, T> {
|
|||||||
* @param ofType 映射类
|
* @param ofType 映射类
|
||||||
* @param auto 自动映射数据库实体对应的字段
|
* @param auto 自动映射数据库实体对应的字段
|
||||||
*/
|
*/
|
||||||
public Builder(String property, Class<E> entityClass, Class<?> javaType, Class<T> ofType, boolean auto) {
|
public Builder(String index, String property, Class<E> entityClass, Class<?> javaType, Class<T> ofType, boolean auto) {
|
||||||
this.mybatisLabel = new MybatisLabel<>();
|
this.mybatisLabel = new MybatisLabel<>();
|
||||||
mybatisLabel.property = property;
|
mybatisLabel.property = property;
|
||||||
|
mybatisLabel.index = index;
|
||||||
mybatisLabel.entityClass = entityClass;
|
mybatisLabel.entityClass = entityClass;
|
||||||
mybatisLabel.javaType = javaType;
|
mybatisLabel.javaType = javaType;
|
||||||
mybatisLabel.ofType = ofType;
|
mybatisLabel.ofType = ofType;
|
||||||
@ -112,67 +114,91 @@ public class MybatisLabel<E, T> {
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public <A, R, B extends Collection<R>> Builder<E, T> collection(Class<A> entityClass, SFunction<T, B> func) {
|
||||||
|
return collection(null, entityClass, func);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 嵌套
|
* 嵌套
|
||||||
*/
|
*/
|
||||||
public <A, R, B extends Collection<R>> Builder<E, T> collection(Class<A> entityClass, SFunction<T, B> func) {
|
public <A, R, B extends Collection<R>> Builder<E, T> collection(Integer index, Class<A> entityClass, SFunction<T, B> func) {
|
||||||
String dtoFieldName = LambdaUtils.getName(func);
|
String dtoFieldName = LambdaUtils.getName(func);
|
||||||
Class<T> dtoClass = LambdaUtils.getEntityClass(func);
|
Class<T> dtoClass = LambdaUtils.getEntityClass(func);
|
||||||
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
||||||
Field field = fieldMap.get(dtoFieldName);
|
Field field = fieldMap.get(dtoFieldName);
|
||||||
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
||||||
MybatisLabel.Builder<A, R> builder;
|
MybatisLabel.Builder<A, R> builder;
|
||||||
|
String s = Objects.isNull(index) ? null : index.toString();
|
||||||
if (genericType == null || genericType.isAssignableFrom(entityClass)) {
|
if (genericType == null || genericType.isAssignableFrom(entityClass)) {
|
||||||
//找不到集合泛型 List List<?> List<Object> , 直接查询数据库实体
|
//找不到集合泛型 List List<?> List<Object> , 直接查询数据库实体
|
||||||
builder = new Builder<>(dtoFieldName, entityClass, field.getType());
|
builder = new Builder<>(s, dtoFieldName, entityClass, field.getType());
|
||||||
} else {
|
} else {
|
||||||
Class<R> ofType = (Class<R>) genericType;
|
Class<R> ofType = (Class<R>) genericType;
|
||||||
builder = new Builder<>(dtoFieldName, entityClass, field.getType(), ofType, true);
|
builder = new Builder<>(s, dtoFieldName, entityClass, field.getType(), ofType, true);
|
||||||
}
|
}
|
||||||
mybatisLabel.mybatisLabels.add(builder.build());
|
mybatisLabel.mybatisLabels.add(builder.build());
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public <A, R, B extends Collection<R>> Builder<E, T> collection(Class<A> entityClass, SFunction<T, B> func, MFunc<Builder<A, R>> mFunc) {
|
||||||
|
return collection(null, entityClass, func, mFunc);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 嵌套
|
* 嵌套
|
||||||
*/
|
*/
|
||||||
public <A, R, B extends Collection<R>> Builder<E, T> collection(Class<A> entityClass, SFunction<T, B> func, MFunc<Builder<A, R>> mFunc) {
|
public <A, R, B extends Collection<R>> Builder<E, T> collection(Integer index,
|
||||||
|
Class<A> entityClass,
|
||||||
|
SFunction<T, B> func,
|
||||||
|
MFunc<Builder<A, R>> mFunc) {
|
||||||
String dtoFieldName = LambdaUtils.getName(func);
|
String dtoFieldName = LambdaUtils.getName(func);
|
||||||
Class<T> dtoClass = LambdaUtils.getEntityClass(func);
|
Class<T> dtoClass = LambdaUtils.getEntityClass(func);
|
||||||
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
||||||
//获取集合泛型
|
//获取集合泛型
|
||||||
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
Class<?> genericType = MPJReflectionKit.getGenericType(field);
|
||||||
Class<R> ofType = (Class<R>) genericType;
|
Class<R> ofType = (Class<R>) genericType;
|
||||||
MybatisLabel.Builder<A, R> builder = new MybatisLabel.Builder<>(dtoFieldName, entityClass, field.getType(), ofType, false);
|
MybatisLabel.Builder<A, R> builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, entityClass, field.getType(), ofType, false);
|
||||||
mybatisLabel.mybatisLabels.add(mFunc.apply(builder).build());
|
mybatisLabel.mybatisLabels.add(mFunc.apply(builder).build());
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public <A, B> Builder<E, T> association(Class<A> child, SFunction<T, B> dtoField) {
|
||||||
|
return association(null, child, dtoField);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 嵌套
|
* 嵌套
|
||||||
*/
|
*/
|
||||||
public <A, B> Builder<E, T> association(Class<A> child, SFunction<T, B> dtoField) {
|
public <A, B> Builder<E, T> association(Integer index, Class<A> child, SFunction<T, B> dtoField) {
|
||||||
Class<T> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<T> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
Map<String, Field> fieldMap = MPJReflectionKit.getFieldMap(dtoClass);
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Field field = fieldMap.get(dtoFieldName);
|
Field field = fieldMap.get(dtoFieldName);
|
||||||
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
||||||
MybatisLabel.Builder<A, B> builder;
|
MybatisLabel.Builder<A, B> builder;
|
||||||
builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), (Class<B>) field.getType(), true);
|
builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, child, field.getType(), (Class<B>) field.getType(), true);
|
||||||
mybatisLabel.mybatisLabels.add(builder.build());
|
mybatisLabel.mybatisLabels.add(builder.build());
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public <A, B> Builder<E, T> selectAssociation(Class<A> child, SFunction<T, B> dtoField,
|
||||||
|
MFunc<MybatisLabel.Builder<A, B>> collection) {
|
||||||
|
return selectAssociation(null, child, dtoField, collection);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 嵌套
|
* 嵌套
|
||||||
*/
|
*/
|
||||||
public <A, B> Builder<E, T> selectAssociation(Class<A> child, SFunction<T, B> dtoField,
|
public <A, B> Builder<E, T> selectAssociation(Integer index, Class<A> child, SFunction<T, B> dtoField,
|
||||||
MFunc<MybatisLabel.Builder<A, B>> collection) {
|
MFunc<MybatisLabel.Builder<A, B>> collection) {
|
||||||
String dtoFieldName = LambdaUtils.getName(dtoField);
|
String dtoFieldName = LambdaUtils.getName(dtoField);
|
||||||
Class<T> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
Class<T> dtoClass = LambdaUtils.getEntityClass(dtoField);
|
||||||
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
Field field = MPJReflectionKit.getFieldMap(dtoClass).get(dtoFieldName);
|
||||||
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
Assert.isFalse(Collection.class.isAssignableFrom(field.getType()), "association 不支持集合类");
|
||||||
MybatisLabel.Builder<A, B> builder = new MybatisLabel.Builder<>(dtoFieldName, child, field.getType(), (Class<B>) child, false);
|
MybatisLabel.Builder<A, B> builder = new MybatisLabel.Builder<>(Objects.isNull(index) ? null : index.toString(),
|
||||||
|
dtoFieldName, child, field.getType(), (Class<B>) child, false);
|
||||||
mybatisLabel.mybatisLabels.add(collection.apply(builder).build());
|
mybatisLabel.mybatisLabels.add(collection.apply(builder).build());
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
@ -14,7 +14,7 @@ import org.apache.ibatis.type.UnknownTypeHandler;
|
|||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 缓存列, 普通列
|
* 缓存
|
||||||
*
|
*
|
||||||
* @author yulichang
|
* @author yulichang
|
||||||
* @since 1.3.10
|
* @since 1.3.10
|
||||||
|
@ -45,6 +45,9 @@ public class UserDO {
|
|||||||
@TableLogic
|
@TableLogic
|
||||||
private Boolean del;
|
private Boolean del;
|
||||||
|
|
||||||
|
@TableField(exist = false)
|
||||||
|
private String alias;
|
||||||
|
|
||||||
@TableField(exist = false)
|
@TableField(exist = false)
|
||||||
private List<UserDO> children;
|
private List<UserDO> children;
|
||||||
}
|
}
|
||||||
|
@ -29,28 +29,29 @@ INSERT INTO area (id, province, city, area, postcode, del) VALUES (10022, '北
|
|||||||
|
|
||||||
DELETE FROM `user`;
|
DELETE FROM `user`;
|
||||||
|
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 1, 1, '张三 1', '{"id": 1,"name":"张三 1"}', 1, 1, 'https://url-01', '2022-01-01 12:00:00', false);
|
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 2, 1, '张三 2', '{"id": 2,"name":"张三 2"}', 1, 0, 'https://url-02', '2022-01-01 12:00:00', false);
|
( 1, 1, '张三 1', '{"id": 1,"name":"张三 1"}', 1, 1, 'https://url-01', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 3, 1, '张三 3', '{"id": 3,"name":"张三 3"}', 1, 0, 'https://url-03', '2022-01-01 12:00:00', false);
|
( 2, 1, '张三 2', '{"id": 2,"name":"张三 2"}', 1, 0, 'https://url-02', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 4, 1, '张三 4', '{"id": 4,"name":"张三 4"}', 1, 0, 'https://url-04', '2022-01-01 12:00:00', false);
|
( 3, 1, '张三 3', '{"id": 3,"name":"张三 3"}', 1, 0, 'https://url-03', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 5, 1, '张三 5', '{"id": 5,"name":"张三 5"}', 1, 0, 'https://url-05', '2022-01-01 12:00:00', false);
|
( 4, 1, '张三 4', '{"id": 4,"name":"张三 4"}', 1, 0, 'https://url-04', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 6, 1, '张三 6', '{"id": 6,"name":"张三 6"}', 1, 0, 'https://url-06', '2022-01-01 12:00:00', false);
|
( 5, 1, '张三 5', '{"id": 5,"name":"张三 5"}', 1, 0, 'https://url-05', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 7, 1, '张三 7', '{"id": 7,"name":"张三 7"}', 1, 0, 'https://url-07', '2022-01-01 12:00:00', false);
|
( 6, 1, '张三 6', '{"id": 6,"name":"张三 6"}', 1, 0, 'https://url-06', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 8, 1, '张三 8', '{"id": 8,"name":"张三 8"}', 1, 0, 'https://url-08', '2022-01-01 12:00:00', false);
|
( 7, 1, '张三 7', '{"id": 7,"name":"张三 7"}', 1, 0, 'https://url-07', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES ( 9, 1, '张三 9', '{"id": 9,"name":"张三 9"}', 1, 0, 'https://url-09', '2022-01-01 12:00:00', false);
|
( 8, 1, '张三 8', '{"id": 8,"name":"张三 8"}', 1, 0, 'https://url-08', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (10, 1, '张三10', '{"id":10,"name":"张三10"}', 1, 0, 'https://url-10', '2022-01-01 12:00:00', true );
|
( 9, 1, '张三 9', '{"id": 9,"name":"张三 9"}', 1, 0, 'https://url-09', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (11, 1, '张三11', '{"id":11,"name":"张三11"}', 1, 0, 'https://url-11', '2022-01-01 12:00:00', true );
|
(10, 1, '张三10', '{"id":10,"name":"张三10"}', 1, 0, 'https://url-10', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (12, 1, '张三12', '{"id":12,"name":"张三12"}', 1, 0, 'https://url-12', '2022-01-01 12:00:00', true );
|
(11, 1, '张三11', '{"id":11,"name":"张三11"}', 1, 0, 'https://url-11', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (13, 1, '张三13', '{"id":13,"name":"张三13"}', 1, 0, 'https://url-13', '2022-01-01 12:00:00', true );
|
(12, 1, '张三12', '{"id":12,"name":"张三12"}', 1, 0, 'https://url-12', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (14, 1, '张三14', '{"id":14,"name":"张三14"}', 1, 0, 'https://url-14', '2022-01-01 12:00:00', true );
|
(13, 1, '张三13', '{"id":13,"name":"张三13"}', 1, 0, 'https://url-13', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (15, 1, '张三15', '{"id":15,"name":"张三15"}', 1, 0, 'https://url-15', '2022-01-01 12:00:00', true );
|
(14, 2, '张三14', '{"id":14,"name":"张三14"}', 1, 0, 'https://url-14', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (16, 1, '张三16', '{"id":16,"name":"张三16"}', 1, 0, 'https://url-16', '2022-01-01 12:00:00', true );
|
(15, 2, '张三15', '{"id":15,"name":"张三15"}', 1, 0, 'https://url-15', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (17, 1, '张三17', '{"id":17,"name":"张三17"}', 1, 0, 'https://url-17', '2022-01-01 12:00:00', true );
|
(16, 2, '张三16', '{"id":16,"name":"张三16"}', 1, 0, 'https://url-16', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (18, 1, '张三18', '{"id":18,"name":"张三18"}', 1, 0, 'https://url-18', '2022-01-01 12:00:00', true );
|
(17, 2, '张三17', '{"id":17,"name":"张三17"}', 1, 0, 'https://url-17', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (19, 1, '张三19', '{"id":19,"name":"张三19"}', 1, 0, 'https://url-19', '2022-01-01 12:00:00', true );
|
(18, 2, '张三18', '{"id":18,"name":"张三18"}', 1, 0, 'https://url-18', '2022-01-01 12:00:00', false),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (20, 1, '张三20', '{"id":20,"name":"张三20"}', 1, 0, 'https://url-20', '2022-01-01 12:00:00', true );
|
(19, 2, '张三19', '{"id":19,"name":"张三19"}', 1, 0, 'https://url-19', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (21, 1, '张三21', '{"id":21,"name":"张三21"}', 1, 0, 'https://url-21', '2022-01-01 12:00:00', true );
|
(20, 2, '张三20', '{"id":20,"name":"张三20"}', 1, 0, 'https://url-20', '2022-01-01 12:00:00', true ),
|
||||||
INSERT INTO `user` (id, pid, `name`, `json`, `address_id`, sex, head_img, create_time, del) VALUES (22, 1, '张三22', '{"id":22,"name":"张三22"}', 1, 0, 'https://url-22', '2022-01-01 12:00:00', true );
|
(21, 2, '张三21', '{"id":21,"name":"张三21"}', 1, 0, 'https://url-21', '2022-01-01 12:00:00', true ),
|
||||||
|
(22, 2, '张三22', '{"id":22,"name":"张三22"}', 1, 0, 'https://url-22', '2022-01-01 12:00:00', true );
|
||||||
|
|
||||||
|
|
||||||
DELETE FROM address;
|
DELETE FROM address;
|
||||||
|
@ -114,21 +114,27 @@ class LambdaWrapperTest {
|
|||||||
void testInner() {
|
void testInner() {
|
||||||
MPJLambdaWrapper<UserDO> wrapper = new MPJLambdaWrapper<UserDO>()
|
MPJLambdaWrapper<UserDO> wrapper = new MPJLambdaWrapper<UserDO>()
|
||||||
// .disableSubLogicDel()//关闭副表逻辑删除
|
// .disableSubLogicDel()//关闭副表逻辑删除
|
||||||
// .disableLogicDel()//关闭主表逻辑删除
|
.disableLogicDel()//关闭主表逻辑删除
|
||||||
.selectAll(UserDO.class)
|
.selectAll(UserDO.class)
|
||||||
.selectCollection(UserDO.class, UserDO::getChildren)
|
.selectCollection(UserDO.class, UserDO::getChildren)
|
||||||
.leftJoin(UserDO.class, UserDO::getPid, UserDO::getId);
|
.leftJoin(UserDO.class, UserDO::getPid, UserDO::getId);
|
||||||
List<UserDO> list = userMapper.selectJoinList(UserDO.class, wrapper);
|
List<UserDO> list = userMapper.selectJoinList(UserDO.class, wrapper);
|
||||||
|
System.out.println(list);
|
||||||
|
|
||||||
MPJLambdaWrapper<UserDO> wrapper1 = new MPJLambdaWrapper<UserDO>()
|
MPJLambdaWrapper<UserDO> wrapper1 = new MPJLambdaWrapper<UserDO>()
|
||||||
.disableSubLogicDel()
|
.disableSubLogicDel()
|
||||||
.disableLogicDel()
|
|
||||||
.selectAll(UserDO.class)
|
.selectAll(UserDO.class)
|
||||||
.selectCollection(UserDO.class, UserDO::getChildren)
|
.selectCollection(1, UserDO.class, UserDO::getChildren, c -> c
|
||||||
.leftJoin(UserDO.class, UserDO::getPid, UserDO::getId);
|
.collection(2, UserDO.class, UserDO::getChildren))
|
||||||
|
.leftJoin(UserDO.class, UserDO::getPid, UserDO::getId, ext -> ext
|
||||||
|
.selectAs(UserDO::getName, UserDO::getAlias)
|
||||||
|
.leftJoin(UserDO.class, UserDO::getPid, UserDO::getId)
|
||||||
|
.le(UserDO::getId, 5))
|
||||||
|
.le(UserDO::getId, 4);
|
||||||
List<UserDO> list1 = userMapper.selectJoinList(UserDO.class, wrapper1);
|
List<UserDO> list1 = userMapper.selectJoinList(UserDO.class, wrapper1);
|
||||||
|
System.out.println(wrapper1.getSqlSegment());
|
||||||
System.out.println(list);
|
assert "(t1.id <= #{ew.paramNameValuePairs.MPGENVAL1} AND t.id <= #{ew.paramNameValuePairs.MPGENVAL2})".equals(wrapper1.getSqlSegment());
|
||||||
|
System.out.println(list1);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -137,13 +143,13 @@ class LambdaWrapperTest {
|
|||||||
@Test
|
@Test
|
||||||
void testLogicDel() {
|
void testLogicDel() {
|
||||||
List<UserDTO> l1 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<>());
|
List<UserDTO> l1 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<>());
|
||||||
assert l1.size() < 10;
|
assert l1.size() < 15;
|
||||||
|
|
||||||
List<UserDTO> l2 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<UserDO>()
|
List<UserDTO> l2 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<UserDO>()
|
||||||
.selectAll(UserDO.class)
|
.selectAll(UserDO.class)
|
||||||
.select(AddressDO::getAddress)
|
.select(AddressDO::getAddress)
|
||||||
.leftJoin(AddressDO.class, AddressDO::getUserId, UserDO::getId));
|
.leftJoin(AddressDO.class, AddressDO::getUserId, UserDO::getId));
|
||||||
assert l2.size() <= 5;
|
assert l2.size() < 11;
|
||||||
|
|
||||||
List<UserDTO> l3 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<UserDO>()
|
List<UserDTO> l3 = userMapper.selectJoinList(UserDTO.class, new MPJLambdaWrapper<UserDO>()
|
||||||
.disableSubLogicDel()
|
.disableSubLogicDel()
|
||||||
@ -207,8 +213,8 @@ class LambdaWrapperTest {
|
|||||||
.selectAll(UserDO.class)
|
.selectAll(UserDO.class)
|
||||||
.select(AddressDO::getAddress)
|
.select(AddressDO::getAddress)
|
||||||
.leftJoin(AddressDO.class, on -> on
|
.leftJoin(AddressDO.class, on -> on
|
||||||
.eq(UserDO::getId, AddressDO::getUserId)
|
.eq(AddressDO::getUserId, UserDO::getId)
|
||||||
.eq(UserDO::getId, AddressDO::getUserId))
|
.eq(AddressDO::getUserId, UserDO::getId))
|
||||||
.eq(UserDO::getId, 1)
|
.eq(UserDO::getId, 1)
|
||||||
.and(i -> i.eq(UserDO::getImg, "er")
|
.and(i -> i.eq(UserDO::getImg, "er")
|
||||||
.or()
|
.or()
|
||||||
|
Loading…
x
Reference in New Issue
Block a user