I'm using Hibernate's implementation of JPA and am seeing poor performance as multiple SQL queries are issued for each entity that is fetched. If I use a joined JPA query it generates just one SQL query but doesn't find rows will null relationship.
Example, consider this simple schema. A person lives at an address and is employed by a company. Both address and employer are optional and can thus be null.
@Entity
public class Person {
public name;
@ManyToOne
@Column(nullable=true)
public Address address
@ManyToOne
@Column(nullable=true)
public Company employer
}
@Entity
public class Address {
address attributes ...
}
@Entity
public class Company {
company attributes ...
}
Not shown above is that each JPA entity has some sort of ID (key):
@Id
public Integer id;
The problem I'm seeing is that a single JPA query on Person results in multiple SQL queries on the database. For example, the following JPA query:
select p from Person p where ...
results in the SQL query:
select ... from Person where ...
and also the following pair of SQL queries for each retrieved person:
select ... from Address a where a.id=xxx
select ... from Company c where c.id=yyy
This has a huge impact on performance. If the query result set is 1000 people, then it generates 1+1000+1000=2001 SQL queries.
So I tried optimizing the JPA query by forcing it to join:
select p from Person p join p.address a join p.employer e where ...
or:
select p, a, e from Person p join p.address a join p.employer e where ...
This results in one single SQL query with a bunch of joins. The problem is if address or employer is null, then the joined query won't find it.
So I'm left with either using the join-less query which is slow, or the fast joined query that doesn't retrieve rows will null relationships. I must be missing something here. Surely there's a way for fast and complete querying.