I have a tables with One-Many Relationships as follows
City->School->Teacher->Children
and my JPQL for retrieving children from a city is as below
@Query("Select c from Children c where c.teacher.school.city=:city")
Set<Children> findChildrenFromCity(@Param("city") City city);
This reference here about Where clause says that
"Compound path expressions make the where clause extremely powerful."
However, upon observing the logs I realise that the above query is doing strange things like
Generate multiple Selects instead of one Select
Some cross joins can be seen in the logs
I am trying to understand if I am defining my query correctly and if the compound Where is indeed so powerful, why is my query so inefficient.
You can use the following method:
Set<Children> findAllByTeacherSchoolCity(String city);
assuming, that your class Children
has field Teacher teacher
, Teacher
has School school
and School
has String city
.
In case there are differences, please ask in comments for clarification.
Try this
@Query("Select c from City city join city.schools s join s.teachers t join t.childrens c where city = :city")
Set<Children> findChildrenFromCity(@Param("city") City city);
This query is running exactly one Select
query to fetch the Children
entities. Check the below mentioned logs.
HIBERNATE: SELECT childrens3_.id AS id1_0_, childrens3_.date_created AS date_cre2_0_, childrens3_.date_updated AS date_upd3_0_, childrens3_.NAME AS name4_0_, childrens3_.teacher_id AS teacher_5_0_ FROM city city0_ INNER JOIN school schools1_ ON city0_.id = schools1_.city_id INNER JOIN teacher teachers2_ ON schools1_.id = teachers2_.school_id INNER JOIN children childrens3_ ON teachers2_.id = childrens3_.teacher_id WHERE city0_.id = ?
Now what you have is an n+1
issue. To fix such issue you can use join fetch
instead of simple joins.
如果你想使用查询注释试试这个方法
@Query("Select c from Children c join fetch c.teacher t join fetch t.school s join fetch s.city ct where ct.id = :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.