简体   繁体   中英

How to join two entities with ManyToMany relationship in the jpa query

I have two entities User and Role . Each user can have multiple roles.

User class

@Entity
public class User {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id", updatable = false, nullable = false)
    private Long id;

    @ManyToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
    @JoinTable(
            name = "user_role",
            joinColumns = @JoinColumn(name = "user_id"),
            inverseJoinColumns = @JoinColumn(name = "role_id")
    )
    private Set<Role> roles = new HashSet<>();
}

Role class:

@Entity
public class Role {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id", updatable = false, nullable = false)
    private Long id;

    private String name;
}

So a new joined table is being created called: user_role 在此处输入图像描述

I want to create a query for returning a list of users with role_id of 4, for example. The query that I already tried:

@Override
public List<User> getArtists() {
   return em.createQuery(
      "from User u, Role r where u.roles='4'",
      User.class
   ).getResultList();
}

How can I fix this query in order to retrieve a list of users with role_id of 4?

You can do something like this:

List<User> users = em.createQuery(
   "select distinct u from User u join fetch u.roles rl where rl.id = :id",
    User.class)
.setHint( QueryHints.HINT_PASS_DISTINCT_THROUGH, false )
.setParameter("id", 1L)
.getResultList();

The QueryHints.HINT_PASS_DISTINCT_THROUGH is added as an additional performance optimization . But please note that this optimization will work only with hibernate 5.2.2.Final... 5.2.11.Final. It was broken in the 5.2.12.Final.

If I were you, I will get the benfit of using SpringdataJpa with hibernate and just use this statment: If you don't want to use query:

List<User> findByRoles_Id(Long id);

In your User Repository:

    public interface UserRepository extends JpaRepository<User, Long> {

    List<User> findByRoles_Id(Long id);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM