Question

I have a project that have a modeling like this:

public abstract class Actor{}
public class Person extends Actor {}
public class Organization extends Actor {}

public abstract class Role{ @ManyToOne @JoinColumn(name="ID_ACTOR") }
public class Customer extends Role{}
public class Employee extends Role{}

I would like to get a List<Role> which plays a particular Actor:

public List<Role> getRoles(Actor actor) {
  CriteriaBuilder builder = em.getCriteriaBuilder();
  CriteriaQuery<Role> criteria = builder.createQuery(Role.class);

  //How to do this filter using Criteria API (JPA 2.1)?

  return query.getResultList();
}

The SQL below makes the job:

SELECT 'Customer' as role, c.id as id, c.id_actor as actor
FROM customer c
left join person p on p.id = c.id_actor
left join organization o on o.id = c.id_actor
where c.id_actor = ?

UNION 

SELECT 'Employee' as role, e.id as id, e.id_actor as actor
FROM employee e
left join person p on p.id = e.id_actor
left join organization o on o.id = e.id_actor
where e.id_actor = ?
Was it helpful?

Solution

I resolve the problem making a bidirectional relationship between Actor and Role class:

public abstract class Actor{ @OneToMany(mappedBy="actor") List<Role> roles }
public class Person extends Actor {}
public class Organization extends Actor {}

public abstract class Role{ @ManyToOne @JoinColumn(name="ID_ACTOR") Actor actor }
public class Customer extends Role{}
public class Employee extends Role{}

That way I could get the List<role> which plays a particular Actor:

public List<Role> getRoles(Actor actor) {
    return actor.getRoles();
}

Initially I would like to avoid the bidirectional relationship, but I realized that in this particular case, there are direct benefits

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top