I have two entities, A and B that are persisted to a relational database via JPA.
public class A {
@Id
private String id;
private String bId;
}
public class B {
@Id
private String id;
private String field;
}
Notice how A does not have a B attribute but rather just its id. In my use case at the time of persisting an A entity the B entity does not currently exist and is written later to the db. However, at read time I would very much like to access A objects with their corresponding B entity if it already exists in the database (or null otherwise) – with a single JPA query.
How could I do this?
Thanks in advance!
Advertisement
Answer
You can use a joined HQL/JPQL query along with an projection in order to achieve what you need. For example consider the following repository, entities and projection classes:
- Repository
@Repository
public interface PersonRepository extends JpaRepository<Person, Long> {
@Query("SELECT P.id AS id, P.detailsId AS detailsId, P.name AS name, PD as detail "
+ "FROM Person P "
+ "JOIN PersonDetails PD "
+ "ON P.detailsId = PD.id")
List<PersonDetailProjection> findJoined();
}
- Entities
@Data
@Entity(name = "Person")
@Table(name = "person")
public class Person {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String name;
private Long detailsId;
}
And
@Data
@Entity(name = "PersonDetails")
@Table(name = "person_details")
public class PersonDetails {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String address;
}
- Projection
public interface PersonDetailProjection {
Long getId();
Long getDetailsId();
String getName();
PersonDetails getDetail();
}
You can modify the query to have a WHERE clause, but the basic gist is what you see. Note that I still fail to see why you would want to do the query like, especially considering the amount of work it takes to set it up.