动态QueryDSL查询构建器

时间:2019-06-06 15:08:05

标签: hibernate spring-data-jpa querydsl

我正在尝试编写一个接受动态谓词的通用DAO类。

在我的BaseDAO类中,我创建PathBuilder来使用以下构造函数添加一些谓词:PathBuilder<Q> entityPath = new PathBuilder<Q>(clazz, "entity");

执行时,出现以下异常:

  

2019-06-06 17:55:11.779错误11212 --- [http-nio-8080-exec-2]   o.a.c.c.C。[。[。[/]。[dispatcherServlet]:的Servlet.service()   路径[]中的servlet [dispatcherServlet]抛出异常   [请求处理失败;嵌套异常为   org.springframework.dao.InvalidDataAccessApiUsageException:   org.hibernate.hql.internal.ast.QuerySyntaxException:无效的路径:   'entity.id' [从com.example.clientcachedemo.Member中选择member1   member1,其中entity.id =?1];嵌套异常为   java.lang.IllegalArgumentException:   org.hibernate.hql.internal.ast.QuerySyntaxException:无效的路径:   'entity.id'[从com.example.clientcachedemo.Member中选择member1   member1,其中entity.id =?1]]的根本原因

     

org.hibernate.hql.internal.ast.QuerySyntaxException:无效的路径:   'entity.id'[从com.example.clientcachedemo.Member中选择member1   member1,其中entity.id =吗?1]


在构造HQL时,休眠似乎使用了“ member1”作为表别名。 如果我将PathBuilder的创建更改为PathBuilder<Q> entityPath = new PathBuilder<Q>(clazz, "member1");,则一切正常,但这应该是通用代码。

如何推断休眠使用的表的别名?

如何强制休眠使用其他别名(“实体”)?

基本实体:

public abstract class BaseEntity implements Serializable {

    private static final long serialVersionUID = -5322749711870322616L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "id", nullable = false, columnDefinition = "BIGINT UNSIGNED")
    protected Long id;

    @UpdateTimestamp
    public Timestamp timestamp;

    @Version
    Long version;
}

成员实体

@Data
@Entity
@Cacheable
@org.hibernate.annotations.Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
@Table(name = "MEMBERS", indexes = { @Index(name = "ix1", unique = false, columnList = "timestamp") })
public class Member extends BaseEntity {

    private static final long serialVersionUID = -3641904361081907333L;
    private String name;
    private String city;
    private String email;
    private String gender;
    private String hour;
    private String title;
}

BaseDAO

public class BaseDAO<E extends BaseEntity, Q extends EntityPath<?>> {

    @Autowired
    BaseQDSLRepository<E, Q> repository;

    public Iterable<E> query(RestCriteria criteria) {

        Class<E> clazz = getEntityClass();
        PathBuilder<E> entityPath = new PathBuilder<E>(clazz, "entity");
        Predicate p = entityPath.get("id").eq(1L); // TODO Parse criteria to predicate...
        return repository.findAll(p);
    }

    @SuppressWarnings({ "unchecked" })
    protected Class<E> getEntityClass() {
        Class<E> clazz = null;
        Type[] genericTypes = ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments();
        if (genericTypes[0] instanceof ParameterizedType) {
            clazz = (Class<E>) ((ParameterizedType) genericTypes[1]).getRawType();
        } else {
            clazz = (Class<E>) genericTypes[0];
        }
        return clazz;
    }

}

BaseQDSLRepository

@NoRepositoryBean
public interface BaseQDSLRepository<E extends BaseEntity, Q extends EntityPath<?>>
        extends BaseJpaRepository<E>, QuerydslPredicateExecutor<E>, BinderCustomizer<Q> {

}

控制器

@PostMapping
@ResponseBody
public Iterable<Member> query(@RequestBody RestCriteria criteria) {
    Iterable<Member> mems = dao.query(criteria);
    return mems;
}

0 个答案:

没有答案