Search in sources :

Example 1 with BindQuery

use of com.diboot.core.binding.query.BindQuery in project diboot by dibo-software.

the class ParserCache method getBindQueryAnnos.

/**
 * 获取dto类中定义的BindQuery注解
 * @param dtoClass
 * @return
 */
public static List<AnnoJoiner> getBindQueryAnnos(Class<?> dtoClass) {
    String dtoClassName = dtoClass.getName();
    if (dtoClassBindQueryCacheMap.containsKey(dtoClassName)) {
        return dtoClassBindQueryCacheMap.get(dtoClassName);
    }
    // 初始化
    List<AnnoJoiner> annos = new ArrayList<>();
    AtomicInteger index = new AtomicInteger(1);
    Map<String, String> joinOn2Alias = new HashMap<>(8);
    // 构建AnnoJoiner
    BiConsumer<Field, BindQuery> buildAnnoJoiner = (field, query) -> {
        AnnoJoiner annoJoiner = new AnnoJoiner(field, query);
        // 关联对象,设置别名
        if (V.notEmpty(annoJoiner.getJoin())) {
            String key = annoJoiner.getJoin() + ":" + annoJoiner.getCondition();
            String alias = joinOn2Alias.get(key);
            if (alias == null) {
                alias = "r" + index.getAndIncrement();
                annoJoiner.setAlias(alias);
                joinOn2Alias.put(key, alias);
            } else {
                annoJoiner.setAlias(alias);
            }
            annoJoiner.parse();
        }
        annos.add(annoJoiner);
    };
    for (Field field : BeanUtils.extractFields(dtoClass, BindQuery.class)) {
        BindQuery query = field.getAnnotation(BindQuery.class);
        // 不可能为null
        if (query.ignore()) {
            continue;
        }
        buildAnnoJoiner.accept(field, query);
    }
    for (Field field : BeanUtils.extractFields(dtoClass, BindQuery.List.class)) {
        BindQuery.List queryList = field.getAnnotation(BindQuery.List.class);
        for (BindQuery bindQuery : queryList.value()) {
            buildAnnoJoiner.accept(field, bindQuery);
        }
    }
    dtoClassBindQueryCacheMap.put(dtoClassName, annos);
    return annos;
}
Also used : AnnoJoiner(com.diboot.core.binding.query.dynamic.AnnoJoiner) InvalidUsageException(com.diboot.core.exception.InvalidUsageException) java.util(java.util) ProtectField(com.diboot.core.data.annotation.ProtectField) ContextHelper(com.diboot.core.util.ContextHelper) TableName(com.baomidou.mybatisplus.annotation.TableName) BindingCacheManager(com.diboot.core.binding.cache.BindingCacheManager) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) BiConsumer(java.util.function.BiConsumer) BeanUtils(com.diboot.core.util.BeanUtils) NonNull(lombok.NonNull) AnnotationUtils(org.springframework.core.annotation.AnnotationUtils) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) Field(java.lang.reflect.Field) IMaskStrategy(com.diboot.core.data.mask.IMaskStrategy) IEncryptStrategy(com.diboot.core.data.encrypt.IEncryptStrategy) Slf4j(lombok.extern.slf4j.Slf4j) ParameterizedType(java.lang.reflect.ParameterizedType) S(com.diboot.core.util.S) Type(java.lang.reflect.Type) BaseMapper(com.baomidou.mybatisplus.core.mapper.BaseMapper) V(com.diboot.core.util.V) Annotation(java.lang.annotation.Annotation) com.diboot.core.binding.annotation(com.diboot.core.binding.annotation) BindQuery(com.diboot.core.binding.query.BindQuery) ProtectField(com.diboot.core.data.annotation.ProtectField) Field(java.lang.reflect.Field) AnnoJoiner(com.diboot.core.binding.query.dynamic.AnnoJoiner) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) BindQuery(com.diboot.core.binding.query.BindQuery)

Example 2 with BindQuery

use of com.diboot.core.binding.query.BindQuery in project diboot by dibo-software.

the class QueryBuilder method dtoToWrapper.

/**
 * 转换具体实现
 *
 * @param dto
 * @return
 */
private static <DTO> QueryWrapper<?> dtoToWrapper(DTO dto, Collection<String> fields) {
    QueryWrapper<?> wrapper;
    // 转换
    LinkedHashMap<String, FieldAndValue> fieldValuesMap = extractNotNullValues(dto, fields);
    if (V.isEmpty(fieldValuesMap)) {
        return new QueryWrapper<>();
    }
    // 只解析有值的
    fields = fieldValuesMap.keySet();
    // 是否有join联表查询
    boolean hasJoinTable = ParserCache.hasJoinTable(dto, fields);
    if (hasJoinTable) {
        wrapper = new DynamicJoinQueryWrapper<>(dto.getClass(), fields);
    } else {
        wrapper = new ExtQueryWrapper<>();
    }
    // 构建 ColumnName
    List<AnnoJoiner> annoJoinerList = ParserCache.getBindQueryAnnos(dto.getClass());
    BiFunction<BindQuery, Field, String> buildColumnName = (bindQuery, field) -> {
        if (bindQuery != null) {
            String key = field.getName() + bindQuery;
            for (AnnoJoiner annoJoiner : annoJoinerList) {
                if (key.equals(annoJoiner.getKey())) {
                    if (V.notEmpty(annoJoiner.getJoin())) {
                        // 获取注解Table
                        return annoJoiner.getAlias() + "." + annoJoiner.getColumnName();
                    } else {
                        return (hasJoinTable ? "self." : "") + annoJoiner.getColumnName();
                    }
                }
            }
        }
        return (hasJoinTable ? "self." : "") + BeanUtils.getColumnName(field);
    };
    // 忽略空字符串"",空集合等
    BiFunction<Object, BindQuery, Boolean> ignoreEmpty = (value, bindQuery) -> bindQuery != null && // 忽略空字符串"",空集合等
    bindQuery.strategy().equals(Strategy.IGNORE_EMPTY) && (// 字符串""
    value instanceof String && S.isEmpty((String) value) || // 空集合
    (value instanceof Collection && ((Collection<?>) value).size() == 0));
    // 查找加密策略
    BiFunction<BindQuery, String, IEncryptStrategy> findEncryptStrategy = (bindQuery, defFieldName) -> {
        if (ENABLE_DATA_PROTECT) {
            Class<?> clazz = bindQuery == null || bindQuery.entity() == NullType.class ? dto.getClass() : bindQuery.entity();
            String fieldName = bindQuery == null || S.isEmpty(bindQuery.field()) ? defFieldName : bindQuery.field();
            return ParserCache.getFieldEncryptorMap(clazz).get(fieldName);
        }
        return null;
    };
    // 构建QueryWrapper
    for (Map.Entry<String, FieldAndValue> entry : fieldValuesMap.entrySet()) {
        FieldAndValue fieldAndValue = entry.getValue();
        Field field = fieldAndValue.getField();
        // 忽略注解 @TableField(exist = false) 的字段
        TableField tableField = field.getAnnotation(TableField.class);
        if (tableField != null && !tableField.exist()) {
            continue;
        }
        // 忽略字段
        BindQuery query = field.getAnnotation(BindQuery.class);
        if (query != null && query.ignore()) {
            continue;
        }
        BindQuery.List queryList = field.getAnnotation(BindQuery.List.class);
        Object value = fieldAndValue.getValue();
        // 构建Query
        if (queryList != null) {
            wrapper.and(queryWrapper -> {
                for (BindQuery bindQuery : queryList.value()) {
                    if (ignoreEmpty.apply(value, bindQuery)) {
                        continue;
                    }
                    IEncryptStrategy encryptor = findEncryptStrategy.apply(bindQuery, entry.getKey());
                    Comparison comparison = encryptor == null ? bindQuery.comparison() : Comparison.EQ;
                    String columnName = buildColumnName.apply(bindQuery, field);
                    buildQuery(queryWrapper.or(), comparison, columnName, encryptor == null ? value : encryptor.encrypt(value.toString()));
                }
            });
        } else {
            if (ignoreEmpty.apply(value, query)) {
                continue;
            }
            IEncryptStrategy encryptor = findEncryptStrategy.apply(query, entry.getKey());
            Comparison comparison = query != null && encryptor == null ? query.comparison() : Comparison.EQ;
            String columnName = buildColumnName.apply(query, field);
            buildQuery(wrapper, comparison, columnName, encryptor == null ? value : encryptor.encrypt(value.toString()));
        }
    }
    return wrapper;
}
Also used : AnnoJoiner(com.diboot.core.binding.query.dynamic.AnnoJoiner) Comparison(com.diboot.core.binding.query.Comparison) java.util(java.util) BiFunction(java.util.function.BiFunction) Cons(com.diboot.core.config.Cons) LoggerFactory(org.slf4j.LoggerFactory) ExtQueryWrapper(com.diboot.core.binding.query.dynamic.ExtQueryWrapper) LambdaQueryWrapper(com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper) PropertiesUtils(com.diboot.core.util.PropertiesUtils) Method(java.lang.reflect.Method) BeanUtils(com.diboot.core.util.BeanUtils) QueryWrapper(com.baomidou.mybatisplus.core.conditions.query.QueryWrapper) Logger(org.slf4j.Logger) NullType(javax.lang.model.type.NullType) TableLogic(com.baomidou.mybatisplus.annotation.TableLogic) Field(java.lang.reflect.Field) TableField(com.baomidou.mybatisplus.annotation.TableField) IEncryptStrategy(com.diboot.core.data.encrypt.IEncryptStrategy) InvocationTargetException(java.lang.reflect.InvocationTargetException) DynamicJoinQueryWrapper(com.diboot.core.binding.query.dynamic.DynamicJoinQueryWrapper) S(com.diboot.core.util.S) V(com.diboot.core.util.V) Modifier(java.lang.reflect.Modifier) ISqlSegment(com.baomidou.mybatisplus.core.conditions.ISqlSegment) NormalSegmentList(com.baomidou.mybatisplus.core.conditions.segments.NormalSegmentList) BindQuery(com.diboot.core.binding.query.BindQuery) ParserCache(com.diboot.core.binding.parser.ParserCache) Strategy(com.diboot.core.binding.query.Strategy) Field(java.lang.reflect.Field) TableField(com.baomidou.mybatisplus.annotation.TableField) BindQuery(com.diboot.core.binding.query.BindQuery) Comparison(com.diboot.core.binding.query.Comparison) IEncryptStrategy(com.diboot.core.data.encrypt.IEncryptStrategy) ExtQueryWrapper(com.diboot.core.binding.query.dynamic.ExtQueryWrapper) LambdaQueryWrapper(com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper) QueryWrapper(com.baomidou.mybatisplus.core.conditions.query.QueryWrapper) DynamicJoinQueryWrapper(com.diboot.core.binding.query.dynamic.DynamicJoinQueryWrapper) TableField(com.baomidou.mybatisplus.annotation.TableField) AnnoJoiner(com.diboot.core.binding.query.dynamic.AnnoJoiner) NullType(javax.lang.model.type.NullType)

Aggregations

BindQuery (com.diboot.core.binding.query.BindQuery)2 AnnoJoiner (com.diboot.core.binding.query.dynamic.AnnoJoiner)2 IEncryptStrategy (com.diboot.core.data.encrypt.IEncryptStrategy)2 BeanUtils (com.diboot.core.util.BeanUtils)2 S (com.diboot.core.util.S)2 V (com.diboot.core.util.V)2 Field (java.lang.reflect.Field)2 java.util (java.util)2 TableField (com.baomidou.mybatisplus.annotation.TableField)1 TableLogic (com.baomidou.mybatisplus.annotation.TableLogic)1 TableName (com.baomidou.mybatisplus.annotation.TableName)1 ISqlSegment (com.baomidou.mybatisplus.core.conditions.ISqlSegment)1 LambdaQueryWrapper (com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper)1 QueryWrapper (com.baomidou.mybatisplus.core.conditions.query.QueryWrapper)1 NormalSegmentList (com.baomidou.mybatisplus.core.conditions.segments.NormalSegmentList)1 BaseMapper (com.baomidou.mybatisplus.core.mapper.BaseMapper)1 com.diboot.core.binding.annotation (com.diboot.core.binding.annotation)1 BindingCacheManager (com.diboot.core.binding.cache.BindingCacheManager)1 ParserCache (com.diboot.core.binding.parser.ParserCache)1 Comparison (com.diboot.core.binding.query.Comparison)1