如何在JOOQ中动态生成Condition条件,支持多表查询场景
通用动态条件封装实现
你可以直接基于参数类型的无效值判断实现泛型工具方法,无需额外传入类型参数,避免类型转换错误:
import org.jooq.Condition; import org.jooq.Field; import org.jooq.impl.DSL; import org.apache.commons.lang3.StringUtils; public class DynamicConditionUtils { public static <T> Condition eqIfValid(Field<T> field, T value) { // 空值直接返回恒真条件,不影响查询逻辑 if (value == null) { return DSL.trueCondition(); } // 字符串类型单独判断非空 if (value instanceof String str && StringUtils.isBlank(str)) { return DSL.trueCondition(); } // 数字类型判断是否为正(适配原有id>0的判断逻辑) if (value instanceof Number num && num.longValue() <= 0) { return DSL.trueCondition(); } return field.eq(value); } }
多表查询场景使用方式
jOOQ的Field实例本身已绑定所属表元信息,多表场景下直接传入对应表的字段即可,不会出现字段歧义:
Condition queryCondition = DSL.trueCondition(); // 拼接BOOK表动态条件 queryCondition = queryCondition .and(DynamicConditionUtils.eqIfValid(BOOK.NAME, book.getName())) .and(DynamicConditionUtils.eqIfValid(BOOK.ID, book.getId())); // 拼接AUTHOR表动态条件 queryCondition = queryCondition .and(DynamicConditionUtils.eqIfValid(AUTHOR.NAME, author.getName())) .and(DynamicConditionUtils.eqIfValid(AUTHOR.AGE, author.getAge())); // 执行多表关联查询 Result<Record> result = dslContext.select() .from(BOOK) .leftJoin(AUTHOR).on(BOOK.AUTHOR_ID.eq(AUTHOR.ID)) .where(queryCondition) .fetch();
扩展功能实现
如果需要支持更多查询逻辑,可以在工具类中新增对应方法:
- 模糊查询方法
public static Condition likeIfValid(Field<String> field, String value) { if (StringUtils.isBlank(value)) { return DSL.trueCondition(); } return field.like("%" + value + "%"); }
- 范围查询方法
public static <T extends Comparable<T>> Condition rangeIfValid(Field<T> field, T minValue, T maxValue) { Condition condition = DSL.trueCondition(); if (minValue != null) { condition = condition.and(field.ge(minValue)); } if (maxValue != null) { condition = condition.and(field.le(maxValue)); } return condition; }
内容的提问来源于stack exchange,提问作者einherjar
相关产品推荐
相关产品推荐

