Mar*_*ark 5 java querydsl spring-data-jpa
我希望 spring 数据返回一个较小的 dto 类来代替我的完整实体。
在 QueryDsl 和 Spring Data JPA 的帮助下,我尝试构建一个查询 EntityPath 的服务,但返回了一个兼容的数据传输对象。我想以动态方式构建此查询。
<!-- language: java -->
/**
* @param type The dto class you want to query
* @param ep The entitypath for the full class (generated QClass)
* @param pageRequest The spring data jpa domain pagerequest instance
* @param predicate predicate generated by .getValue() on a BooleanExpression
*/
@Override
public Page<? extends DtoMarker> getPagedResultsForDto(Class<? extends DtoMarker> type, EntityPath<?> ep , PageRequest pageRequest, Predicate predicate) throws NoSuchFieldException, SecurityException{
List<Expression<?>> expressions = getExpressions(type, ep);
JPAQuery query = new JPAQuery(em);
query = query.from(ep).where(predicate);
if (pageRequest != null) {
query = query.limit(pageRequest.getPageSize()).offset(pageRequest.getOffset());
}
if (pageRequest.getSort() != null) {
for (Sort.Order o : pageRequest.getSort()) {
query = query.orderBy(toOrderSpecifier(o, ep));
}
}
List<? extends DtoMarker> tuples = query.list(Projections.bean(type, expressions.toArray(new Expression[expressions.size()])));
return new PageImpl<>(tuples, pageRequest, getCountTotalSizeForDto(type, ep, pageRequest, predicate));
}
private List<Expression<?>> getExpressions(Class<? extends DtoMarker> type,
EntityPath<?> ep) {
List<Expression<?>> expressions = new ArrayList<Expression<?>>();
List<Field> fields = new ArrayList<Field>();
for (Field field : type.getDeclaredFields()){
fields.add(field);
}
for (Field field : type.getSuperclass().getDeclaredFields()){
fields.add(field);
}
for (Field field : fields) {
String generictype = field.getType().getSimpleName();
if (generictype.equals("String")){
expressions.add(new StringPath(ep, field.getName()));
}
if (generictype.equals("Boolean")) {
expressions.add(new BooleanPath(ep, field.getName()));
}
if (generictype.equals("Long")) {
expressions.add(new NumberPath<Long>(Long.class, ep, field.getName()));
}
}
return expressions;
}
Run Code Online (Sandbox Code Playgroud)
这很有效,唯一的问题是我实现排序的方式。我通过以下方式将 spring 数据 jpa 排序转换为 querydsl:
<!-- language: java -->
@SuppressWarnings({ "rawtypes", "unchecked" })
private OrderSpecifier<?> toOrderSpecifier(Order order, EntityPath<?> ep) {
ComparablePath<?> sortPropertyExpression = new ComparablePath(Comparable.class, ep, order.getProperty());
com.mysema.query.types.Order orderExpression = order.isAscending() ? com.mysema.query.types.Order.ASC
: com.mysema.query.types.Order.DESC;
return new OrderSpecifier(orderExpression, sortPropertyExpression);
}
Run Code Online (Sandbox Code Playgroud)
但这有一个问题,即字符串不会按忽略大小写(= 要求)排序!
也许这可能是通往解决方案的道路?:
<!-- language: java -->
sortPropertyExpression = order.isIgnoreCase() ? Expressions.stringPath(order.getProperty()).lower() : Expressions.stringPath(order.getProperty());
Run Code Online (Sandbox Code Playgroud)
但它仅适用于 stringPaths 并为 numberpath 等提供例外。
任何我可以用来进行动态排序的其他想法?
| 归档时间: |
|
| 查看次数: |
3699 次 |
| 最近记录: |