[英]How to improve performance in Hibernate polymorphic query when using table per class strategy?
When using table per class strategy, polymorphic query looks like this:按 class 策略使用表时,多态查询如下所示:
SELECT <some cols>
FROM
(
SELECT
parent_id,
entity1_col,
entity2_col,
1 as clazz_
FROM
entity_table1
UNION
SELECT
parent_id,
entity1_col,
entity2_col,
2 as clazz_
FROM
entity_table2
) abstract_entity
WHERE
abstract_entity.parent_id = X
We can see that if we have a lot of rows in entity_table1 and entity_table2, this query can lead to performance issue.我们可以看到,如果 entity_table1 和 entity_table2 中有很多行,则此查询可能会导致性能问题。
I am using Spring-data & Hibernate and this request is generated when fetching a OneToMany relation on a parent entity.我正在使用 Spring-data 和 Hibernate 并且在获取父实体上的 OneToMany 关系时会生成此请求。
My question is: why Hibernate generates such request though it is restricting selected rows on parent_id that is common to entity_table1 & entity_table2?我的问题是:为什么 Hibernate 会生成这样的请求,尽管它限制了 entity_table1 和 entity_table2 共有的 parent_id 上的选定行?
Is there a way to have Hibernate generating a SQL request that look like this:有没有办法让 Hibernate 生成一个 SQL 请求,如下所示:
SELECT <some cols>
FROM
(
SELECT
parent_id,
entity1_col,
entity2_col,
1 as clazz_
FROM
entity_table1
WHERE
parent_id=X
UNION
SELECT
parent_id,
entity1_col,
entity2_col,
2 as clazz_
FROM
entity_table2
WHERE
parent_id=X
) abstract_entity
Having "WHERE parent_id=X" in each request in FROM? FROM 中的每个请求中都有“WHERE parent_id=X”? This way no performance issue when fetching relation on parent entity.这样在获取父实体上的关系时不会出现性能问题。
Thanks !谢谢 !
I made a modification based on hibernate 5.6.3 to pushdown the predict for polymorphic query when using table per class strategy.我根据 hibernate 5.6.3 进行了修改,以在使用每个 class 策略的表时下推多态查询的预测。 Please refer to https://github.com/kerler/hibernate-orm/tree/main_5.6.3-open-care .请参考https://github.com/kerler/hibernate-orm/tree/main_5.6.3-open-care 。
After modification, for code “Query q = s.createQuery( "from Being h where h.identity =:name1 or h.identity =:name2 or h.identity =:name2" );”修改后,对于代码“Query q = s.createQuery("from Being h where h.identity =:name1 or h.identity =:name2 or h.identity =:name2" );” in hibernate UT case UnionSubclassTest.java::testNestedUnionedSubclasses(), the SQL generated by hibernate is like: in hibernate UT case UnionSubclassTest.java::testNestedUnionedSubclasses(), the SQL generated by hibernate is like:
00:37:43,945 DEBUG SQL:144 -
select
being0_.bid as bid1_2_,
being0_.ident as ident2_2_,
being0_.location as location3_2_,
being0_.sex as sex1_6_,
being0_.salary as salary1_4_,
being0_.species as species1_0_,
being0_.hive as hive2_0_,
being0_.clazz_ as clazz_
from
( select
bid,
ident,
location,
sex,
salary,
null as species,
null as hive,
2 as clazz_
from
employees
where
ident=?
or ident=?
or ident=?
union
all select
bid,
ident,
location,
sex,
null as salary,
null as species,
null as hive,
1 as clazz_
from
humans
where
ident=?
or ident=?
or ident=?
union
all select
bid,
ident,
location,
null as sex,
null as salary,
species,
hive,
3 as clazz_
from
aliens
where
ident=?
or ident=?
or ident=?
) being0_
where
being0_.ident=?
or being0_.ident=?
or being0_.ident=?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.