소스 검색

改进分层结构

hubin 7 년 전
부모
커밋
10e2cf8050

+ 97 - 56
mybatis-plus-adapter/src/main/java/com/baomidou/mybatisplus/mapper/Wrapper.java

@@ -25,14 +25,14 @@ import java.util.concurrent.atomic.AtomicInteger;
 import com.baomidou.mybatisplus.core.conditions.SqlPlus;
 import com.baomidou.mybatisplus.core.enums.SqlLike;
 import com.baomidou.mybatisplus.core.exceptions.MybatisPlusException;
+import com.baomidou.mybatisplus.core.metadata.Column;
+import com.baomidou.mybatisplus.core.metadata.Columns;
 import com.baomidou.mybatisplus.core.toolkit.ArrayUtils;
 import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
 import com.baomidou.mybatisplus.core.toolkit.MapUtils;
 import com.baomidou.mybatisplus.core.toolkit.SerializationUtils;
 import com.baomidou.mybatisplus.core.toolkit.StringUtils;
-import com.baomidou.mybatisplus.core.toolkit.TableInfoHelper;
 import com.baomidou.mybatisplus.core.toolkit.sql.SqlUtils;
-import com.baomidou.mybatisplus.core.toolkit.support.Property;
 
 
 /**
@@ -63,6 +63,10 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
     private final Map<String, Object> paramNameValuePairs = new HashMap<>();
     private final AtomicInteger paramNameSeq = new AtomicInteger(0);
     protected String paramAlias = null;
+    /**
+     * SQL 查询字段内容,例如:id,name,age
+     */
+    protected String sqlSelect = null;
     /**
      * 自定义是否输出sql为 WHERE OR AND OR OR
      */
@@ -102,6 +106,92 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
         return !isEmptyOfWhere();
     }
 
+    public String getSqlSelect() {
+        return StringUtils.isEmpty(sqlSelect) ? null : SqlUtils.stripSqlInjection(sqlSelect);
+    }
+
+    public Wrapper<T> setSqlSelect(String sqlSelect) {
+        if (StringUtils.isNotEmpty(sqlSelect)) {
+            this.sqlSelect = sqlSelect;
+        }
+        return this;
+    }
+
+    /**
+     * <p>
+     * 使用字符串数组封装sqlSelect,便于在不需要指定 AS 的情况下通过实体类自动生成的列静态字段快速组装 sqlSelect,<br/>
+     * 减少手动录入的错误率
+     * </p>
+     *
+     * @param columns 字段
+     * @return
+     */
+    public Wrapper<T> setSqlSelect(String... columns) {
+        StringBuilder builder = new StringBuilder();
+        for (String column : columns) {
+            if (StringUtils.isNotEmpty(column)) {
+                if (builder.length() > 0) {
+                    builder.append(",");
+                }
+                builder.append(column);
+            }
+        }
+        this.sqlSelect = builder.toString();
+        return this;
+    }
+
+    /**
+     * <p>
+     * 使用对象封装的setsqlselect
+     * </p>
+     *
+     * @param column 字段
+     * @return
+     */
+    public Wrapper<T> setSqlSelect(Column... column) {
+        if (ArrayUtils.isNotEmpty(column)) {
+            StringBuilder builder = new StringBuilder();
+            for (int i = 0; i < column.length; i++) {
+                if (column[i] != null) {
+                    String col = column[i].getColumn();
+                    String as = column[i].getAs();
+                    if (StringUtils.isEmpty(col)) {
+                        continue;
+                    }
+                    builder.append(col).append(as);
+                    if (i < column.length - 1) {
+                        builder.append(",");
+                    }
+                }
+            }
+            this.sqlSelect = builder.toString();
+        }
+        return this;
+    }
+
+    /**
+     * <p>
+     * 使用对象封装的setsqlselect
+     * </p>
+     *
+     * @param columns 字段
+     * @return
+     */
+    public Wrapper<T> setSqlSelect(Columns columns) {
+        Column[] columnArray = columns.getColumns();
+        if (ArrayUtils.isNotEmpty(columnArray)) {
+            setSqlSelect(columnArray);
+        }
+        return this;
+    }
+
+    /**
+     * <p>
+     * SQL 片段 (子类实现)
+     * </p>
+     */
+    public abstract String getSqlSegment();
+
     @Override
     public String toString() {
         StringBuilder sb = new StringBuilder("Wrapper<T>:");
@@ -213,31 +303,6 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
         return eq(true, column, params);
     }
 
-    public Wrapper<T> eq(boolean condition, Property<T, ?> func, Object params) {
-        if (condition) {
-            sql.WHERE(formatSql(String.format("%s = {0}", toCol(func)), params));
-        }
-        return this;
-    }
-
-    /**
-     * 为了支持字段重构做出的修改
-     * <p>
-     * 你可以在指定 Wrapper<T> 泛型的前提下这么使用:
-     * <p>
-     * Wrapper<User> wrapper = new EntityWrapper<User>();
-     * wrapper.eq(User::getUserName, "baomidou")
-     * <p>
-     * 改方法会根据规则(比如配置的字段映射、或者下划线规则)将 User::getUserName 转换为对应的数据库字段信息
-     *
-     * @param func   需要转换的 function
-     * @param params 参数信息
-     * @return 返回自身
-     */
-    public Wrapper<T> eq(Property<T, ?> func, Object params) {
-        return eq(true, func, params);
-    }
-
     /**
      * <p>
      * 等同于SQL的"field <> value"表达式
@@ -887,7 +952,7 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
      */
     public Wrapper<T> like(boolean condition, String column, String value) {
         if (condition) {
-            handlerLike(column, value, SqlLike.DEFAULT, false);
+            handerLike(column, value, SqlLike.DEFAULT, false);
         }
         return this;
     }
@@ -917,7 +982,7 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
      */
     public Wrapper<T> notLike(boolean condition, String column, String value) {
         if (condition) {
-            handlerLike(column, value, SqlLike.DEFAULT, true);
+            handerLike(column, value, SqlLike.DEFAULT, true);
         }
         return this;
     }
@@ -944,7 +1009,7 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
      * @param value  like匹配值
      * @param isNot  是否为NOT LIKE操作
      */
-    private void handlerLike(String column, String value, SqlLike type, boolean isNot) {
+    private void handerLike(String column, String value, SqlLike type, boolean isNot) {
         if (StringUtils.isNotEmpty(column) && StringUtils.isNotEmpty(value)) {
             StringBuilder inSql = new StringBuilder();
             inSql.append(column);
@@ -969,7 +1034,7 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
      */
     public Wrapper<T> like(boolean condition, String column, String value, SqlLike type) {
         if (condition) {
-            handlerLike(column, value, type, false);
+            handerLike(column, value, type, false);
         }
         return this;
     }
@@ -1001,7 +1066,7 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
      */
     public Wrapper<T> notLike(boolean condition, String column, String value, SqlLike type) {
         if (condition) {
-            handlerLike(column, value, type, true);
+            handerLike(column, value, type, true);
         }
         return this;
     }
@@ -1547,22 +1612,6 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
         return this;
     }
 
-    /**
-     * 是否为空
-     */
-    public boolean isEmpty() {
-        return sql.isEmptyOfWhere();
-    }
-
-    public static <T> Wrapper<T> getInstance() {
-        return new Wrapper<T>() {
-            @Override
-            public String getSqlSegment() {
-                return null;
-            }
-        };
-    }
-
     /**
      * <p>
      * 克隆本身 fixed github issues/241
@@ -1572,13 +1621,5 @@ public abstract class Wrapper<T> extends com.baomidou.mybatisplus.core.condition
     public Wrapper<T> clone() {
         return SerializationUtils.clone(this);
     }
-
-    /**
-     * @param func function
-     * @return 返回从 function 中解析出的 column
-     */
-    protected String toCol(Property<T, ?> func) {
-        return TableInfoHelper.toColumn(func);
-    }
 }
 

+ 1 - 1
mybatis-plus-core/src/main/java/com/baomidou/mybatisplus/core/conditions/EntityWrapper.java

@@ -27,7 +27,7 @@ import com.baomidou.mybatisplus.core.toolkit.sql.SqlUtils;
  * @author hubin
  * @Date 2018-05-25
  */
-public class EntityWrapper<T> extends QueryWrapper<T> {
+public class EntityWrapper<T> extends QueryWrapper<T, EntityWrapper<T>> {
 
     /**
      * 数据库表映射实体类

+ 384 - 5
mybatis-plus-core/src/main/java/com/baomidou/mybatisplus/core/conditions/QueryWrapper.java

@@ -15,9 +15,39 @@
  */
 package com.baomidou.mybatisplus.core.conditions;
 
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.AND;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.BETWEEN;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.EQ;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.EXISTS;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GE;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GROUP_BY;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GT;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.HAVING;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IN;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IS_NOT_NULL;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IS_NULL;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LE;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LIKE;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LT;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.NE;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.NOT;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.OR;
+import static com.baomidou.mybatisplus.core.enums.SqlKeyword.ORDER_BY;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicInteger;
 import java.util.function.Function;
+import java.util.stream.Collectors;
 
 import com.baomidou.mybatisplus.core.enums.SqlKeyword;
+import com.baomidou.mybatisplus.core.toolkit.ArrayUtils;
+import com.baomidou.mybatisplus.core.toolkit.StringUtils;
+import com.baomidou.mybatisplus.core.toolkit.TableInfoHelper;
+import com.baomidou.mybatisplus.core.toolkit.support.Property;
 
 
 /**
@@ -28,19 +58,368 @@ import com.baomidou.mybatisplus.core.enums.SqlKeyword;
  * @author hubin
  * @since 2017-05-26
  */
-public class QueryWrapper<T> extends Wrapper<T, QueryWrapper<T>> {
+public class QueryWrapper<T, Q extends QueryWrapper<T, Q>> extends Wrapper<T> {
+
+    private List<ISqlSegment> expression = new ArrayList<>();
+    private static final String MP_GENERAL_PARAMNAME = "MPGENVAL";
+    private final AtomicInteger paramNameSeq = new AtomicInteger(0);
+    private final Map<String, Object> paramNameValuePairs = new HashMap<>();
+    protected String paramAlias = null;
+    private static final String DEFAULT_PARAM_ALIAS = "ew";
+
+    /**
+     * 占位符
+     */
+    private static final String PLACE_HOLDER = "{%s}";
+
+    private static final String MYBATIS_PLUS_TOKEN = "#{%s.paramNameValuePairs.%s}";
+
+    public Q apply(String condition) {
+        expression.add(() -> condition);
+        return typedThis();
+    }
+
+    public Q notIn(String condition) {
+        return not().in(condition);
+    }
+
+    /**
+     * LIKE '%值%'
+     */
+    public Q like(String column, Object val) {
+        return like(true, column, val);
+    }
+
+    /**
+     * LIKE '%值%'
+     */
+    public Q like(boolean condition, String column, Object val) {
+        return doIt(condition, () -> column, LIKE, () -> "'%", () -> formatSql("{0}", val), () -> "%'");
+    }
+
+    /**
+     * LIKE '%值'
+     */
+    public Q likeLeft(String column, Object val) {
+        return likeLeft(true, column, val);
+    }
+
+    /**
+     * LIKE '%值'
+     */
+    public Q likeLeft(boolean condition, String column, Object val) {
+        return doIt(condition, () -> column, LIKE, () -> "'%", () -> formatSql("{0}", val), () -> "'");
+    }
+
+    /**
+     * LIKE '值%'
+     */
+    public Q likeRight(String column, Object val) {
+        return likeRight(true, column, val);
+    }
+
+    /**
+     * LIKE '值%'
+     */
+    public Q likeRight(boolean condition, String column, Object val) {
+        return doIt(condition, () -> column, LIKE, () -> "'", () -> formatSql("{0}", val), () -> "%'");
+    }
+
+    /**
+     * 等于 =
+     */
+    public Q eq(Property<T, ?> property, Object val) {
+        return eq(true, property, val);
+    }
+
+    /**
+     * 等于 =
+     */
+    public Q eq(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, EQ, val);
+    }
+
+    /**
+     * 不等于 <>
+     */
+    public Q ne(Property<T, ?> property, Object val) {
+        return ne(true, property, val);
+    }
+
+    /**
+     * 不等于 <>
+     */
+    public Q ne(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, NE, val);
+    }
+
+    /**
+     * 大于 >
+     */
+    public Q gt(Property<T, ?> property, Object val) {
+        return gt(true, property, val);
+    }
+
+    /**
+     * 大于 >
+     */
+    public Q gt(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, GT, val);
+    }
+
+    /**
+     * 大于等于 >=
+     */
+    public Q ge(Property<T, ?> property, Object val) {
+        return ge(true, property, val);
+    }
+
+    /**
+     * 大于等于 >=
+     */
+    public Q ge(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, GE, val);
+    }
+
+    /**
+     * 小于 <
+     */
+    public Q lt(Property<T, ?> property, Object val) {
+        return lt(true, property, val);
+    }
+
+    /**
+     * 小于 <
+     */
+    public Q lt(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, LT, val);
+    }
+
+    /**
+     * 小于等于 <=
+     */
+    public Q le(Property<T, ?> property, Object val) {
+        return le(true, property, val);
+    }
+
+    /**
+     * 小于等于 <=
+     */
+    public Q le(boolean condition, Property<T, ?> property, Object val) {
+        return addCondition(condition, property, LE, val);
+    }
+
+    /**
+     * BETWEEN 值1 AND 值2
+     */
+    public Q between(String column, Object val1, Object val2) {
+        return between(true, column, "val1", "val2");
+    }
+
+    /**
+     * BETWEEN 值1 AND 值2
+     */
+    public Q between(boolean condition, String column, Object val1, Object val2) {
+        return doIt(condition, () -> column, BETWEEN, () -> "val1", AND, () -> "val2");
+    }
+
+    /**
+     * 字段 IS NULL
+     */
+    public Q isNull(String column) {
+        return isNull(true, column);
+    }
+
+    /**
+     * 字段 IS NULL
+     */
+    public Q isNull(boolean condition, String column) {
+        return doIt(condition, () -> column, IS_NULL);
+    }
+
+    /**
+     * 字段 IS NOT NULL
+     */
+    public Q isNotNull(String column) {
+        return isNotNull(true, column);
+    }
+
+    /**
+     * 字段 IS NOT NULL
+     */
+    public Q isNotNull(boolean condition, String column) {
+        return doIt(condition, () -> column, IS_NOT_NULL);
+    }
+
+    /**
+     * 分组:GROUP BY 字段, ...
+     */
+    public Q groupBy(String column) {
+        return doIt(true, GROUP_BY, () -> column);
+    }
+
+    /**
+     * 排序:ORDER BY 字段, ...
+     */
+    public Q orderBy(String column) {//todo 产生的sql有bug
+        return doIt(true, ORDER_BY, () -> column);
+    }
+
+    /**
+     * HAVING 关键词
+     */
+    public Q having() {
+        return doIt(true, HAVING);
+    }
+
+    /**
+     * exists ( sql 语句 )
+     */
+    public Q exists(String condition) {
+        return this.addNestedCondition(condition, EXISTS);
+    }
+
+    /**
+     * LAST 拼接在 SQL 末尾
+     */
+    public Q last(String condition) {
+        return doIt(true, () -> condition);
+    }
+
+    /**
+     * NOT 关键词
+     */
+    protected Q not() {//todo 待考虑
+        return doIt(true, NOT);
+    }
+
+    public Q and() {
+        expression.add(AND);
+        return typedThis();
+    }
+
+    public Q and(Function<Q, Q> func) {
+        return addNestedCondition(func, AND);
+    }
+
+    public Q or(Function<Q, Q> func) {
+        return addNestedCondition(func, OR);
+    }
+
+    public Q in(String condition) {//todo 待动
+        return addNestedCondition(condition, IN);
+    }
+
+    public Q or(Property<T, ?> property, Object val) {
+        //todo 待动
+        return addCondition(true, property, OR, val);
+    }
+
+    /**
+     * <p>
+     * 嵌套查询条件
+     * </p>
+     *
+     * @param val        查询条件值
+     * @param sqlKeyword SQL 关键词
+     * @return this
+     */
+    protected Q addNestedCondition(Object val, SqlKeyword sqlKeyword) {
+        return doIt(true, sqlKeyword, () -> this.formatSql("({0})", val));
+    }
 
     /**
      * <p>
-     * 多重嵌套查询条件
+     * 普通查询条件
      * </p>
      *
-     * @param condition  查询条件值
+     * @param condition  是否执行
+     * @param property   属性
      * @param sqlKeyword SQL 关键词
+     * @param val        条件值
+     * @return this
+     */
+    protected Q addCondition(boolean condition, Property<T, ?> property, SqlKeyword sqlKeyword, Object val) {
+        return doIt(condition, () -> TableInfoHelper.toColumn(property),
+            sqlKeyword, () -> this.formatSql("{0}", val));
+    }
+
+    /**
+     * <p>
+     * 格式化SQL
+     * </p>
+     *
+     * @param sqlStr SQL语句部分
+     * @param params 参数集
      * @return this
      */
-    protected QueryWrapper addNestedCondition(Function<QueryWrapper, QueryWrapper> condition, SqlKeyword sqlKeyword) {
-        return doIt(true, sqlKeyword, () -> "(", condition.apply(new QueryWrapper<T>()), () -> ")");
+    protected String formatSql(String sqlStr, Object... params) {
+        return formatSqlIfNeed(true, sqlStr, params);
+    }
+
+    /**
+     * <p>
+     * 根据需要格式化SQL<BR>
+     * <BR>
+     * Format SQL for methods: EntityQ<T>.where/and/or...("name={0}", value);
+     * ALL the {<b>i</b>} will be replaced with #{MPGENVAL<b>i</b>}<BR>
+     * <BR>
+     * ew.where("sample_name=<b>{0}</b>", "haha").and("sample_age &gt;<b>{0}</b>
+     * and sample_age&lt;<b>{1}</b>", 18, 30) <b>TO</b>
+     * sample_name=<b>#{MPGENVAL1}</b> and sample_age&gt;#<b>{MPGENVAL2}</b> and
+     * sample_age&lt;<b>#{MPGENVAL3}</b><BR>
+     * </p>
+     *
+     * @param need   是否需要格式化
+     * @param sqlStr SQL语句部分
+     * @param params 参数集
+     * @return this
+     */
+    protected String formatSqlIfNeed(boolean need, String sqlStr, Object... params) {
+        if (!need || StringUtils.isEmpty(sqlStr)) {
+            return null;
+        }
+        if (ArrayUtils.isNotEmpty(params)) {
+            for (int i = 0; i < params.length; ++i) {
+                String genParamName = MP_GENERAL_PARAMNAME + paramNameSeq.incrementAndGet();
+                sqlStr = sqlStr.replace(String.format(PLACE_HOLDER, i),
+                    String.format(MYBATIS_PLUS_TOKEN, getParamAlias(), genParamName));
+                paramNameValuePairs.put(genParamName, params[i]);
+            }
+        }
+        return sqlStr;
+    }
+
+    /**
+     * <p>
+     * 对sql片段进行组装
+     * </p>
+     *
+     * @param condition   是否执行
+     * @param sqlSegments sql片段数组
+     * @return this
+     */
+    protected Q doIt(boolean condition, ISqlSegment... sqlSegments) {
+        if (condition) {
+            expression.addAll(Arrays.asList(sqlSegments));
+        }
+        return typedThis();
+    }
+
+    public String getParamAlias() {
+        return StringUtils.isEmpty(paramAlias) ? DEFAULT_PARAM_ALIAS : paramAlias;
+    }
+
+    @SuppressWarnings("unchecked")
+    protected Q typedThis() {
+        return (Q) this;
+    }
+
+    @Override
+    public String getSqlSegment() {
+        return String.join(" ", expression.stream()
+            .map(ISqlSegment::getSqlSegment)
+            .collect(Collectors.toList()));
     }
 
 }

+ 1 - 1
mybatis-plus-core/src/main/java/com/baomidou/mybatisplus/core/conditions/UpdateWrapper.java

@@ -24,7 +24,7 @@ package com.baomidou.mybatisplus.core.conditions;
  * @author hubin , yanghu , Dyang , Caratacus
  * @Date 2016-11-7
  */
-public class UpdateWrapper<T> extends Wrapper<T, UpdateWrapper<T>> {
+public class UpdateWrapper<T> extends QueryWrapper<T, UpdateWrapper<T>> {
 
     /**
      * 数据库表映射实体类

+ 1 - 392
mybatis-plus-core/src/main/java/com/baomidou/mybatisplus/core/conditions/Wrapper.java

@@ -15,40 +15,6 @@
  */
 package com.baomidou.mybatisplus.core.conditions;
 
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.AND;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.BETWEEN;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.EQ;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.EXISTS;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GE;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GROUP_BY;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.GT;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.HAVING;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IN;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IS_NOT_NULL;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.IS_NULL;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LE;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LIKE;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.LT;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.NE;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.NOT;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.OR;
-import static com.baomidou.mybatisplus.core.enums.SqlKeyword.ORDER_BY;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicInteger;
-import java.util.function.Function;
-import java.util.stream.Collectors;
-
-import com.baomidou.mybatisplus.core.enums.SqlKeyword;
-import com.baomidou.mybatisplus.core.toolkit.ArrayUtils;
-import com.baomidou.mybatisplus.core.toolkit.StringUtils;
-import com.baomidou.mybatisplus.core.toolkit.TableInfoHelper;
-import com.baomidou.mybatisplus.core.toolkit.support.Property;
-
 /**
  * <p>
  * 条件构造抽象类
@@ -57,21 +23,7 @@ import com.baomidou.mybatisplus.core.toolkit.support.Property;
  * @author hubin
  * @Date 2018-05-25
  */
-public abstract class Wrapper<T, WRAPPER extends Wrapper<T, WRAPPER>> implements ISqlSegment {
-
-    private List<ISqlSegment> expression = new ArrayList<>();
-    private static final String MP_GENERAL_PARAMNAME = "MPGENVAL";
-    private final AtomicInteger paramNameSeq = new AtomicInteger(0);
-    private final Map<String, Object> paramNameValuePairs = new HashMap<>();
-    protected String paramAlias = null;
-    private static final String DEFAULT_PARAM_ALIAS = "ew";
-
-    /**
-     * 占位符
-     */
-    private static final String PLACE_HOLDER = "{%s}";
-
-    private static final String MYBATIS_PLUS_TOKEN = "#{%s.paramNameValuePairs.%s}";
+public abstract class Wrapper<T> implements ISqlSegment {
 
     /**
      * 实体对象(子类实现)
@@ -87,348 +39,5 @@ public abstract class Wrapper<T, WRAPPER extends Wrapper<T, WRAPPER>> implements
         return null;
     }
 
-    public WRAPPER apply(String condition) {
-        expression.add(() -> condition);
-        return typedThis();
-    }
-
-    public WRAPPER notIn(String condition) {
-        return not().in(condition);
-    }
-
-    /**
-     * LIKE '%值%'
-     */
-    public WRAPPER like(String column, Object val) {
-        return like(true, column, val);
-    }
-
-    /**
-     * LIKE '%值%'
-     */
-    public WRAPPER like(boolean condition, String column, Object val) {
-        return doIt(condition, () -> column, LIKE, () -> "'%", () -> formatSql("{0}", val), () -> "%'");
-    }
-
-    /**
-     * LIKE '%值'
-     */
-    public WRAPPER likeLeft(String column, Object val) {
-        return likeLeft(true, column, val);
-    }
-
-    /**
-     * LIKE '%值'
-     */
-    public WRAPPER likeLeft(boolean condition, String column, Object val) {
-        return doIt(condition, () -> column, LIKE, () -> "'%", () -> formatSql("{0}", val), () -> "'");
-    }
-
-    /**
-     * LIKE '值%'
-     */
-    public WRAPPER likeRight(String column, Object val) {
-        return likeRight(true, column, val);
-    }
-
-    /**
-     * LIKE '值%'
-     */
-    public WRAPPER likeRight(boolean condition, String column, Object val) {
-        return doIt(condition, () -> column, LIKE, () -> "'", () -> formatSql("{0}", val), () -> "%'");
-    }
-
-    /**
-     * 等于 =
-     */
-    public WRAPPER eq(Property<T, ?> property, Object val) {
-        return eq(true, property, val);
-    }
-
-    /**
-     * 等于 =
-     */
-    public WRAPPER eq(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, EQ, val);
-    }
-
-    /**
-     * 不等于 <>
-     */
-    public WRAPPER ne(Property<T, ?> property, Object val) {
-        return ne(true, property, val);
-    }
-
-    /**
-     * 不等于 <>
-     */
-    public WRAPPER ne(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, NE, val);
-    }
-
-    /**
-     * 大于 >
-     */
-    public WRAPPER gt(Property<T, ?> property, Object val) {
-        return gt(true, property, val);
-    }
-
-    /**
-     * 大于 >
-     */
-    public WRAPPER gt(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, GT, val);
-    }
-
-    /**
-     * 大于等于 >=
-     */
-    public WRAPPER ge(Property<T, ?> property, Object val) {
-        return ge(true, property, val);
-    }
-
-    /**
-     * 大于等于 >=
-     */
-    public WRAPPER ge(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, GE, val);
-    }
-
-    /**
-     * 小于 <
-     */
-    public WRAPPER lt(Property<T, ?> property, Object val) {
-        return lt(true, property, val);
-    }
-
-    /**
-     * 小于 <
-     */
-    public WRAPPER lt(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, LT, val);
-    }
-
-    /**
-     * 小于等于 <=
-     */
-    public WRAPPER le(Property<T, ?> property, Object val) {
-        return le(true, property, val);
-    }
-
-    /**
-     * 小于等于 <=
-     */
-    public WRAPPER le(boolean condition, Property<T, ?> property, Object val) {
-        return addCondition(condition, property, LE, val);
-    }
-
-    /**
-     * BETWEEN 值1 AND 值2
-     */
-    public WRAPPER between(String column, Object val1, Object val2) {
-        return between(true, column, "val1", "val2");
-    }
-
-    /**
-     * BETWEEN 值1 AND 值2
-     */
-    public WRAPPER between(boolean condition, String column, Object val1, Object val2) {
-        return doIt(condition, () -> column, BETWEEN, () -> "val1", AND, () -> "val2");
-    }
-
-    /**
-     * 字段 IS NULL
-     */
-    public WRAPPER isNull(String column) {
-        return isNull(true, column);
-    }
-
-    /**
-     * 字段 IS NULL
-     */
-    public WRAPPER isNull(boolean condition, String column) {
-        return doIt(condition, () -> column, IS_NULL);
-    }
-
-    /**
-     * 字段 IS NOT NULL
-     */
-    public WRAPPER isNotNull(String column) {
-        return isNotNull(true, column);
-    }
-
-    /**
-     * 字段 IS NOT NULL
-     */
-    public WRAPPER isNotNull(boolean condition, String column) {
-        return doIt(condition, () -> column, IS_NOT_NULL);
-    }
-
-    /**
-     * 分组:GROUP BY 字段, ...
-     */
-    public WRAPPER groupBy(String column) {
-        return doIt(true, GROUP_BY, () -> column);
-    }
-
-    /**
-     * 排序:ORDER BY 字段, ...
-     */
-    public WRAPPER orderBy(String column) {//todo 产生的sql有bug
-        return doIt(true, ORDER_BY, () -> column);
-    }
-
-    /**
-     * HAVING 关键词
-     */
-    public WRAPPER having() {
-        return doIt(true, HAVING);
-    }
-
-    /**
-     * exists ( sql 语句 )
-     */
-    public WRAPPER exists(String condition) {
-        return this.addNestedCondition(condition, EXISTS);
-    }
-
-    /**
-     * LAST 拼接在 SQL 末尾
-     */
-    public WRAPPER last(String condition) {
-        return doIt(true, () -> condition);
-    }
-
-    /**
-     * NOT 关键词
-     */
-    protected WRAPPER not() {//todo 待考虑
-        return doIt(true, NOT);
-    }
-
-    public WRAPPER and(Function<WRAPPER, WRAPPER> func) {
-        return addNestedCondition(func, AND);
-    }
-
-    public WRAPPER or(Function<WRAPPER, WRAPPER> func) {
-        return addNestedCondition(func, OR);
-    }
-
-    public WRAPPER in(String condition) {//todo 待动
-        return addNestedCondition(condition, IN);
-    }
-
-    public WRAPPER or(Property<T, ?> property, Object val) {
-        //todo 待动
-        return addCondition(true, property, OR, val);
-    }
-
-    /**
-     * <p>
-     * 嵌套查询条件
-     * </p>
-     *
-     * @param val        查询条件值
-     * @param sqlKeyword SQL 关键词
-     * @return this
-     */
-    protected WRAPPER addNestedCondition(Object val, SqlKeyword sqlKeyword) {
-        return doIt(true, sqlKeyword, () -> this.formatSql("({0})", val));
-    }
-
-    /**
-     * <p>
-     * 普通查询条件
-     * </p>
-     *
-     * @param condition  是否执行
-     * @param property   属性
-     * @param sqlKeyword SQL 关键词
-     * @param val        条件值
-     * @return this
-     */
-    protected WRAPPER addCondition(boolean condition, Property<T, ?> property, SqlKeyword sqlKeyword, Object val) {
-        return doIt(condition, () -> TableInfoHelper.toColumn(property),
-            sqlKeyword, () -> this.formatSql("{0}", val));
-    }
-
-    /**
-     * <p>
-     * 格式化SQL
-     * </p>
-     *
-     * @param sqlStr SQL语句部分
-     * @param params 参数集
-     * @return this
-     */
-    protected String formatSql(String sqlStr, Object... params) {
-        return formatSqlIfNeed(true, sqlStr, params);
-    }
-
-    /**
-     * <p>
-     * 根据需要格式化SQL<BR>
-     * <BR>
-     * Format SQL for methods: EntityWrapper<T>.where/and/or...("name={0}", value);
-     * ALL the {<b>i</b>} will be replaced with #{MPGENVAL<b>i</b>}<BR>
-     * <BR>
-     * ew.where("sample_name=<b>{0}</b>", "haha").and("sample_age &gt;<b>{0}</b>
-     * and sample_age&lt;<b>{1}</b>", 18, 30) <b>TO</b>
-     * sample_name=<b>#{MPGENVAL1}</b> and sample_age&gt;#<b>{MPGENVAL2}</b> and
-     * sample_age&lt;<b>#{MPGENVAL3}</b><BR>
-     * </p>
-     *
-     * @param need   是否需要格式化
-     * @param sqlStr SQL语句部分
-     * @param params 参数集
-     * @return this
-     */
-    protected String formatSqlIfNeed(boolean need, String sqlStr, Object... params) {
-        if (!need || StringUtils.isEmpty(sqlStr)) {
-            return null;
-        }
-        if (ArrayUtils.isNotEmpty(params)) {
-            for (int i = 0; i < params.length; ++i) {
-                String genParamName = MP_GENERAL_PARAMNAME + paramNameSeq.incrementAndGet();
-                sqlStr = sqlStr.replace(String.format(PLACE_HOLDER, i),
-                    String.format(MYBATIS_PLUS_TOKEN, getParamAlias(), genParamName));
-                paramNameValuePairs.put(genParamName, params[i]);
-            }
-        }
-        return sqlStr;
-    }
-
-    /**
-     * <p>
-     * 对sql片段进行组装
-     * </p>
-     *
-     * @param condition   是否执行
-     * @param sqlSegments sql片段数组
-     * @return this
-     */
-    protected WRAPPER doIt(boolean condition, ISqlSegment... sqlSegments) {
-        if (condition) {
-            expression.addAll(Arrays.asList(sqlSegments));
-        }
-        return typedThis();
-    }
-
-    public String getParamAlias() {
-        return StringUtils.isEmpty(paramAlias) ? DEFAULT_PARAM_ALIAS : paramAlias;
-    }
-
-    @SuppressWarnings("unchecked")
-    protected WRAPPER typedThis() {
-        return (WRAPPER) this;
-    }
-
-    @Override
-    public String getSqlSegment() {
-        return String.join(" ", expression.stream()
-            .map(ISqlSegment::getSqlSegment)
-            .collect(Collectors.toList()));
-    }
-
 }
 

+ 2 - 1
mybatis-plus-core/src/test/java/com/baomidou/mybatisplus/core/test/QueryWrapperTest.java

@@ -13,7 +13,8 @@ public class QueryWrapperTest {
 
     @Test
     public void test() {
-        Wrapper wrapper = new EntityWrapper().eq(User::getName, 123);
+        Wrapper wrapper = new EntityWrapper<User>().eq(User::getName, 123)
+            .and().eq(User::getId, 1);
         log(wrapper.getSqlSegment());
     }