All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.baomidou.mybatisplus.extension.conditions.query.QueryJoinWrapper Maven / Gradle / Ivy

/*
 * Copyright (c) 2011-2022, baomidou ([email protected]).
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.baomidou.mybatisplus.extension.conditions.query;

import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;

import org.apache.ibatis.reflection.property.PropertyNamer;

import com.baomidou.mybatisplus.core.conditions.AbstractJoinWrapper;
import com.baomidou.mybatisplus.core.conditions.SharedString;
import com.baomidou.mybatisplus.core.conditions.query.Query;
import com.baomidou.mybatisplus.core.conditions.segments.MergeSegments;
import com.baomidou.mybatisplus.core.enums.BaseFuncEnum;
import com.baomidou.mybatisplus.core.metadata.TableInfo;
import com.baomidou.mybatisplus.core.metadata.TableInfoHelper;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.Constants;
import com.baomidou.mybatisplus.core.toolkit.ExceptionUtils;
import com.baomidou.mybatisplus.core.toolkit.LambdaUtils;
import com.baomidou.mybatisplus.core.toolkit.StringPool;
import com.baomidou.mybatisplus.core.toolkit.support.LambdaMeta;
import com.baomidou.mybatisplus.core.toolkit.support.SFunction;
import com.baomidou.mybatisplus.extension.conditions.query.interfaces.QueryJoinFunc;


/**
 * 本类使用String来构造多表查询条件
 * demo:--需要注意的是 如果要添加其他表的过滤条件或者排序字段,请在调用了join方法后直接调用类似下面这种写法,否则不会别名添加可能会出错
 *  QueryJoinWrapper wrapper = new QueryJoinWrapper<>(LambdaJoinQueryWrapperTest.TableOne.class);
 *             wrapper.leftJoin(TableTwo.class)
 *                 .eq("table_two_id", 1)
 *                 .select("name")
 * @author mahuibo
 * @since 2022-12-16
 */
public class QueryJoinWrapper extends AbstractJoinWrapper>
    implements QueryJoinFunc>, Query, T, String> {

    /**
     * 主表model的class
     */
    private Class mainClass;

    /**
     * 当前使用的class
     */
    private Class thisUseClass;

    public QueryJoinWrapper(Class mainClass) {
        super(mainClass);
        this.mainClass = mainClass;
        super.initNeed();
    }


    /**
     * 非对外公开的构造方法,只用于生产嵌套 sql
     *
     * @param entityClass 本不应该需要的
     */
    private QueryJoinWrapper(Class mainClass, T entity, Class entityClass, AtomicInteger paramNameSeq, Map paramNameValuePairs,
                             MergeSegments mergeSegments, SharedString paramAlias, SharedString lastSql, SharedString sqlComment,
                             SharedString sqlFirst, StringBuilder joinFroms,Map, String> aliasMap) {
        super(mainClass);
        super.setEntity(entity);
        super.setEntityClass(entityClass);
        this.mainClass = mainClass;
        this.paramNameSeq = paramNameSeq;
        this.paramNameValuePairs = paramNameValuePairs;
        this.expression = mergeSegments;
        this.paramAlias = paramAlias;
        this.lastSql = lastSql;
        this.sqlComment = sqlComment;
        this.sqlFirst = sqlFirst;
        this.joinFroms = joinFroms;
        this.aliasMap = aliasMap;
    }

    @Override
    protected QueryJoinWrapper instance() {
        return new QueryJoinWrapper<>(mainClass, getEntity(), getEntityClass(), paramNameSeq, paramNameValuePairs, new MergeSegments(), paramAlias,
            SharedString.emptyString(), SharedString.emptyString(), SharedString.emptyString(), this.joinFroms,this.aliasMap);
    }

    public  QueryJoinWrapper end(Class clz) {
        return (QueryJoinWrapper) this;
    }

    @Override
    protected  String customBuildJoin(LEFT leftProperty, RIGHT rightProperty) {
        LambdaMeta leftMeta = LambdaUtils.extract((SFunction) leftProperty);
        LambdaMeta rightMeta = LambdaUtils.extract((SFunction) rightProperty);

        // 关联表别名
        String leftAlias = aliasMap.get(leftMeta.getInstantiatedClass());
        // 关联表别名
        String rightAlias = aliasMap.get(rightMeta.getInstantiatedClass());

        getCache(leftMeta.getInstantiatedClass(), PropertyNamer.methodToProperty(leftMeta.getImplMethodName()));

        return Constants.SPACE + leftAlias + Constants.DOT + getCache(leftMeta.getInstantiatedClass(), PropertyNamer.methodToProperty(leftMeta.getImplMethodName())).getColumn() + Constants.EQUALS + rightAlias + Constants.DOT + getCache(rightMeta.getInstantiatedClass(), PropertyNamer.methodToProperty(rightMeta.getImplMethodName())).getColumn();
    }

    /**
     * 软删除字段处理
     *
     * @param joinClass
     */
    @Override
    protected void initLogicDelete(Class joinClass, String joinType) {
        TableInfo tableInfo = TableInfoHelper.getTableInfo(joinClass);
        // 不是left join的时候
        if (tableInfo.getLogicDeleteFieldInfo() != null) {
            this.joinFroms.append(Constants.SPACE + Constants.AND + Constants.SPACE + aliasMap.get(joinClass)
                + Constants.DOT + tableInfo.getLogicDeleteFieldInfo().getColumn() + Constants.SPACE + Constants.EQUALS
                + Constants.SPACE + parseLogicNotDeleteValue(tableInfo.getLogicDeleteFieldInfo()));
        }
        //如果没有join其他的表,需要把主表的软删除字段放到on上
        if (this.aliasMap.size() == 2) {
            tableInfo = TableInfoHelper.getTableInfo(this.mainClass);
            if (tableInfo.getLogicDeleteFieldInfo() != null) {
                this.joinFroms.append(Constants.SPACE + Constants.AND + Constants.SPACE + aliasMap.get(this.mainClass)
                    + Constants.DOT + tableInfo.getLogicDeleteFieldInfo().getColumn() + Constants.SPACE + Constants.EQUALS
                    + Constants.SPACE + parseLogicNotDeleteValue(tableInfo.getLogicDeleteFieldInfo()));
            }
        }
    }


    @Override
    public MergeSegments getExpression() {
        //如果没有join其他的表,需要把主表的软删除字段放到where上
        if (this.aliasMap.size() == 1 && !isAppendMainLogicDelete) {
            isAppendMainLogicDelete = true;
            TableInfo tableInfo = TableInfoHelper.getTableInfo(this.mainClass);
            if (tableInfo.getLogicDeleteFieldInfo() != null) {
                eq(tableInfo.getLogicDeleteFieldInfo().getProperty(), parseLogicNotDeleteValue(tableInfo.getLogicDeleteFieldInfo()));
            }
        }
        return expression;
    }

    @Override
    protected String columnToString(String column) {
        if (!super.aliasMap.containsKey(thisUseClass)) {
            throw ExceptionUtils.mpe("not join class: \"%s\".", thisUseClass.getName());
        }
        return super.aliasMap.get(thisUseClass) + StringPool.DOT + column;
    }

    @Override
    @SafeVarargs
    public final QueryJoinWrapper select(String... columns) {
        return select(Arrays.asList(columns));
    }

    public QueryJoinWrapper select(List columns) {
        if (CollectionUtils.isNotEmpty(columns)) {
            for (String column : columns) {
                selectColumns.add(SelectColumn.of(thisUseClass, column));
            }
        }
        return typedThis;
    }

    /**
     * 查询函数列,如果column不指定,则查询 *
     * 

select xx(column) as alias

*/ @Override public final QueryJoinWrapper selectFun(BaseFuncEnum fun, String alias, String column) { String columnStr = column == null ? "*" : aliasMap.get(thisUseClass) + Constants.DOT + column; String funStr = String.format(fun.getSql(), columnStr); this.funSqlSelect.add(new SharedString(funStr + Constants.AS + alias)); return typedThis; } @Override public QueryJoinWrapper join(Class joinClass, String joinType) { this.thisUseClass = joinClass; pubJoin(joinClass, null, null, joinType); return typedThis; } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy