JPA和JPQL MEMBER OF查询始终返回空结果

时间:2013-08-21 14:19:33

标签: hibernate jpa persistence jpql criteriaquery

我遇到了JPA2 / Hibernate 4.2 / MySQL 5.1 / Java 6

的问题

我有以下类User,它有一个属性Set<Role>,其中Role是一个枚举。这是班级:

@Entity
public class User
{
  private static final long serialVersionUID = 1L;

  @ElementCollection(fetch=FetchType.EAGER)
  @Enumerated(value=EnumType.STRING)
  protected Set<Role> roles;

  // .. other stuff
}

public enum Role { ADMIN, OPERATOR, ... }

我已尝试为此创建CriteriaQuery和JPQL查询但由于某种原因,每次都返回一个空列表,即使该角色存在。

以下是条件查询的代码:

CriteriaBuilder builder = getEntityManager().getCriteriaBuilder();
CriteriaQuery<User> query = builder.createQuery(User.class);
Root<User> root = query.from(User.class);

query.where(builder.isMember( Role.ADMIN, root.<Set<Role>>get( "roles" ) ) );

List<User> result = getEntityManager().createQuery(query).getResultList();

这是我正在创建的JPQL:

String jpql = "SELECT * FROM com.mypackage.user.User WHERE (:roles1 MEMBER OF roles))";
Query query = em.createQuery(jpql);
query.setParameter( "roles1", Role.ADMIN );
List result = em.getResultList();

users表包含具有所有角色的单个用户,但这些用户都没有返回任何结果。我需要为我正在进行的工作提供JPA和JPQL版本。请帮忙!

1 个答案:

答案 0 :(得分:1)

好的,对于有类似问题的人,我有 解决方案,但这不是很好。感谢JB Nizet指导,因为他们帮助诊断了问题。

问题是由于JPA和/或Hibernate在处理非String数据时的限制。在这里,我使用了一个枚举,它在一个Role对象和它在数据库中的字符串表示之间进行了相等的测试,而不是将我传入的角色转换为它的db表示(正如你所期望的那样)然后做比较。

为了获得JPQL版本,我做了:

String jpql = "SELECT * FROM com.mypackage.user.User WHERE (:roles1 MEMBER OF roles))";
Query query = em.createQuery(jpql);
query.setParameter( "roles1", Role.ADMIN.toString() );
List result = em.getResultList();

要修复JPA版本,我做了:

CriteriaBuilder builder = getEntityManager().getCriteriaBuilder();
CriteriaQuery<User> query = builder.createQuery(User.class);
Root<User> root = query.from(User.class);

query.where(builder.isMember( Role.ADMIN.toString(), root.<Set<String>>get( "roles" ) ) );

List<User> result = getEntityManager().createQuery(query).getResultList();

如果任何人都可以更正此代码并使其成为所以toString是不必要的(我没有排除我没有正确设置它的想法)如果你能把我说得对,我将不胜感激。 :)