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

org.zodiac.mybatisplus.binding.parser.MiddleTable Maven / Gradle / Ivy

There is a newer version: 1.6.8
Show newest version
package org.zodiac.mybatisplus.binding.parser;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import org.apache.ibatis.jdbc.SQL;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.zodiac.commons.constants.DatabaseConstants;
import org.zodiac.commons.util.Colls;
import org.zodiac.commons.util.lang.Strings;
import org.zodiac.core.exception.IllegalUsageException;
import org.zodiac.mybatis.util.MyBatisSqlExecutor;
import org.zodiac.mybatisplus.binding.binder.BaseBinder;
import org.zodiac.mybatisplus.binding.cache.BindingCacheManager;
import org.zodiac.mybatisplus.binding.helper.ResultAssembler;
import org.zodiac.mybatisplus.util.MyBatisPlusSpringBootUtil;
import org.zodiac.sdk.toolkit.util.lang.ObjUtil;
import org.zodiac.sdk.toolkit.util.lang.StrUtil;

import java.util.*;
import java.util.stream.Collectors;

/**
 * 中间表。
 * 
 */
public class MiddleTable {

    private static final Logger log = LoggerFactory.getLogger(MiddleTable.class);

    /**
     * 中间表
     */
    private String table;
    /**
     * 主干对象列映射
     */
    private Map trunkObjColMapping;
    /**
     * 枝干对象列映射
     */
    private Map branchObjColMapping;
    /**
     * 附加条件
     */
    private List additionalConditions;

    public MiddleTable(String table) {
        this.table = table;
    }

    public String getTable() {
        return this.table;
    }

    public Map getTrunkObjColMapping() {
        return this.trunkObjColMapping;
    }

    public Map getBranchObjColMapping() {
        return this.branchObjColMapping;
    }

    /**
     * 与主对象的关联。
     * 
     * @param middleTableCol 中间表列
     * @param trunkObjCol 主干对象列
     * @return {@link MiddleTable}对象
     */
    public MiddleTable connectTrunkObj(String middleTableCol, String trunkObjCol) {
        if (trunkObjColMapping == null) {
            trunkObjColMapping = new LinkedHashMap<>(8);
        }
        trunkObjColMapping.put(trunkObjCol, middleTableCol);
        return this;
    }

    /**
     * 与枝对象的关联。
     * 
     * @param middleTableCol 中间表列
     * @param branchObjCol 分支对象列
     * @return {@link MiddleTable}对象
     */
    public MiddleTable connectBranchObj(String middleTableCol, String branchObjCol) {
        if (branchObjColMapping == null) {
            branchObjColMapping = new LinkedHashMap<>(8);
        } else if (branchObjColMapping.size() >= 1) {
            throw new IllegalUsageException(BaseBinder.NOT_SUPPORT_MSG);
        }
        branchObjColMapping.put(middleTableCol, branchObjCol);
        return this;
    }

    /**
     * 添加中间表查询所需的附加条件。
     * 
     * @param additionalCondition 附件条件
     * @return {@link MiddleTable}对象
     */
    public MiddleTable addAdditionalCondition(String additionalCondition) {
        if (this.additionalConditions == null) {
            this.additionalConditions = new ArrayList<>();
        }
        this.additionalConditions.add(additionalCondition);
        return this;
    }

    /**
     * 执行1-1关联查询,得到关联映射Map。
     * 
     * @param trunkObjCol2ValuesMap 主对象列映射值map
     * @return 结果
     */
    public Map executeOneToOneQuery(Map trunkObjCol2ValuesMap) {
        if (Colls.emptyMap(trunkObjCol2ValuesMap)) {
            log.warn("不合理的中间表查询:无过滤条件!");
            return Collections.emptyMap();
        }
        /*id //org_id*/
        EntityInfoCache linkage = BindingCacheManager.getEntityInfoByTable(table);
        /*有定义mapper,首选mapper。*/
        if (linkage != null) {
            List> resultSetMapList = queryByMapper(linkage, trunkObjCol2ValuesMap);
            return ResultAssembler.convertToOneToOneResult(resultSetMapList, trunkObjColMapping, branchObjColMapping);
        } else {
            /*提取中间表查询SQL: SELECT id, org_id FROM department WHERE id IN(?) 。*/
            List paramValueList = new ArrayList();
            String sql = toSQL(trunkObjCol2ValuesMap, paramValueList);
            /*执行查询并合并结果。*/
            try {
                List> resultSetMapList = MyBatisSqlExecutor.executeQuery(sql, paramValueList);
                return ResultAssembler.convertToOneToOneResult(resultSetMapList, trunkObjColMapping,
                    branchObjColMapping);
            } catch (Exception e) {
                log.error("中间表查询异常: " + sql, e);
                return Collections.emptyMap();
            }
        }
    }

    /**
     * 执行1-N关联查询,得到关联映射Map。
     * 
     * @param trunkObjCol2ValuesMap 主干对象列映射值map
     * @return 结果
     */
    public Map executeOneToManyQuery(Map trunkObjCol2ValuesMap) {
        if (Colls.emptyMap(trunkObjCol2ValuesMap)) {
            throw new IllegalUsageException("不合理的中间表查询:无过滤条件!");
        }
        /*user_id //role_id*/
        EntityInfoCache linkage = BindingCacheManager.getEntityInfoByTable(table);
        /*有定义mapper,首选mapper。*/
        if (linkage != null) {
            List> resultSetMapList = queryByMapper(linkage, trunkObjCol2ValuesMap);
            return ResultAssembler.convertToOneToManyResult(resultSetMapList, trunkObjColMapping, branchObjColMapping);
        } else {
            /*提取中间表查询SQL: SELECT user_id, role_id FROM user_role WHERE user_id IN(?) 。*/
            List paramValueList = new ArrayList();
            String sql = toSQL(trunkObjCol2ValuesMap, paramValueList);
            /*执行查询并合并结果。*/
            try {
                List> resultSetMapList = MyBatisSqlExecutor.executeQuery(sql, paramValueList);
                return ResultAssembler.convertToOneToManyResult(resultSetMapList, trunkObjColMapping,
                    branchObjColMapping);
            } catch (Exception e) {
                log.error("中间表查询异常: " + sql, e);
                return Collections.emptyMap();
            }
        }
    }

    /**
     * 通过定义的Mapper查询结果。
     * 
     * @param linkage 实体缓存
     * @param trunkObjCol2ValuesMap 主干对象列映射值map
     * @return 结果
     */
    private List> queryByMapper(EntityInfoCache linkage, Map trunkObjCol2ValuesMap) {
        QueryWrapper queryWrapper = new QueryWrapper<>();
        queryWrapper.setEntityClass(linkage.getEntityClass());
        /*select所需字段。*/
        queryWrapper.select(getSelectColumns());
        for (Map.Entry entry : trunkObjCol2ValuesMap.entrySet()) {
            String column = entry.getKey();
            if (column != null && ObjUtil.isNotEmptyObject(entry.getValue())) {
                queryWrapper.in(column, entry.getValue());
            }
        }
        if (additionalConditions != null) {
            for (String condition : additionalConditions) {
                queryWrapper.apply(condition);
            }
        }
        /*查询条件为空时不进行查询。*/
        if (queryWrapper.isEmptyOfNormal()) {
            return Collections.emptyList();
        }
        BaseMapper mapper = linkage.getBaseMapper();
        List> resultSetMapList = mapper.selectMaps(queryWrapper);
        return resultSetMapList;
    }

    /**
     * 转换查询SQL。
     * 
     * @param trunkObjCol2ValuesMap 注解外键值的列表,用于拼接SQL查询
     * @param paramValueList 参数列表
     * @return 结果
     */
    private String toSQL(Map trunkObjCol2ValuesMap, List paramValueList) {
        if (Colls.emptyMap(trunkObjCol2ValuesMap)) {
            return null;
        }
        /*select所需字段。*/
        String selectColumns = ObjUtil.join(getSelectColumns());

        return new SQL() {
            {
                SELECT(selectColumns);
                FROM(table);
                for (Map.Entry entry : trunkObjCol2ValuesMap.entrySet()) {
                    String column = entry.getKey();
                    if (column != null && ObjUtil.isNotEmptyObject(entry.getValue())) {
                        List values = (List)entry.getValue().stream().distinct().collect(Collectors.toList());
                        String params = StrUtil.repeat("?", ",", values.size());
                        WHERE(column + " IN (" + params + ")");
                        paramValueList.addAll(values);
                    }
                }
                /*添加删除标记。*/
                boolean appendDeleteFlag = true;
                if (additionalConditions != null) {
                    for (String condition : additionalConditions) {
                        WHERE(condition);
//                        if (Strings.containsIgnoreCase(condition, DatabaseConstants.COLUMN_IS_DELETED)) {
//                            appendDeleteFlag = false;
//                        }
                        if (StrUtil.containsAnyIgnoreCase(condition, DatabaseConstants.COLUMN_IS_DELETED, DatabaseConstants.COLUMN_DELETE_FLAG)) {
                            appendDeleteFlag = false;
                        }
                    }
                }
                /*如果需要删除。*/
                if (appendDeleteFlag) {
                    String deletedCol = ParserCache.getDeletedColumn(table);
                    if (deletedCol != null) {
                        WHERE(deletedCol + " = " + MyBatisPlusSpringBootUtil.getActiveFlagValue());
                    }
                }
            }
        }.toString();
    }

    private String[] getSelectColumns() {
        List columns = new ArrayList<>(8);
        /*select所需字段。*/
        if (Colls.notEmptyMap(trunkObjColMapping)) {
            for (Map.Entry entry : trunkObjColMapping.entrySet()) {
                columns.add(entry.getValue());
            }
        }
        if (Colls.notEmptyMap(branchObjColMapping)) {
            for (Map.Entry entry : branchObjColMapping.entrySet()) {
                columns.add(entry.getKey());
            }
        }
        return Strings.toStringArray(columns);
    }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy