Open zhangzhenhuajack opened 3 years ago
解决办法是把 // @EntityGraph(attributePaths = {"thirdPartyTpusers","teacher","parent"}, type = EntityGraph.EntityGraphType.LOAD) 这个注解注释掉之后就会产生N+1的sql问题
注释去掉变成如下:
public interface TpuserRepository extends GenericUserRepository<Tpuser> {
@EntityGraph(attributePaths = {"thirdPartyTpusers","teacher","parent"}, type = EntityGraph.EntityGraphType.LOAD)
List<Tpuser> findAllByIdIn(Iterable<Long> ids);
}
我们再执行上面的测试用例,而打印的SQL就会变成一个SQL,如下:
2021-09-17 16:46:02.102 DEBUG [-,,,] 40625 --- [ main] org.hibernate.SQL :
select tpuser0_.id as id1_24_0_,
parent1_.id as id1_13_1_,
thirdparty2_.id as id1_18_2_,
teacher3_.id as id1_15_3_,
tpuser0_.created_at as created_2_24_0_,
tpuser0_.updated_at as updated_3_24_0_,
tpuser0_.lock_version as lock_ver4_24_0_,
tpuser0_.auto_generate as auto_gen5_24_0_,
tpuser0_.email as email6_24_0_,
tpuser0_.gender as gender7_24_0_,
tpuser0_.invitation_code_group as invitati8_24_0_,
tpuser0_.invited_by_code as invited_9_24_0_,
tpuser0_.mobile_phone as mobile_10_24_0_,
tpuser0_.mobile_phone_validated as mobile_11_24_0_,
tpuser0_.name as name12_24_0_,
tpuser0_.password_hash as passwor13_24_0_,
tpuser0_.password_updated_at as passwor14_24_0_,
tpuser0_.state as state15_24_0_,
tpuser0_.uuid as uuid16_24_0_,
parent1_.created_at as created_2_13_1_,
parent1_.updated_at as updated_3_13_1_,
parent1_.lock_version as lock_ver4_13_1_,
parent1_.deleted as deleted5_13_1_,
parent1_.deleted_at as deleted_6_13_1_,
parent1_.address as address7_13_1_,
parent1_.state as state8_13_1_,
parent1_.tpuser_id as tpuser_i9_13_1_,
thirdparty2_.created_at as created_2_18_2_,
thirdparty2_.updated_at as updated_3_18_2_,
thirdparty2_.lock_version as lock_ver4_18_2_,
thirdparty2_.avatar_url as avatar_u5_18_2_,
thirdparty2_.city as city6_18_2_,
thirdparty2_.country as country7_18_2_,
thirdparty2_.nickname as nickname8_18_2_,
thirdparty2_.openid as openid9_18_2_,
thirdparty2_.platform as platfor10_18_2_,
thirdparty2_.province as provinc11_18_2_,
thirdparty2_.sex as sex12_18_2_,
thirdparty2_.uid as uid15_18_2_,
thirdparty2_.unionid as unionid13_18_2_,
thirdparty2_.uuid as uuid14_18_2_,
thirdparty2_.uid as uid15_18_0__,
thirdparty2_.id as id1_18_0__,
teacher3_.created_at as created_2_15_3_,
teacher3_.updated_at as updated_3_15_3_,
teacher3_.lock_version as lock_ver4_15_3_,
teacher3_.deleted as deleted5_15_3_,
teacher3_.deleted_at as deleted_6_15_3_,
teacher3_.address as address7_15_3_,
teacher3_.area_id as area_id8_15_3_,
teacher3_.last_login_date as last_log9_15_3_,
teacher3_.state as state10_15_3_,
teacher3_.tpuser_id as tpuser_12_15_3_,
teacher3_.type as type11_15_3_
from tpusers tpuser0_
left outer join parents parent1_ on tpuser0_.id = parent1_.tpuser_id and (parent1_.deleted = 0)
left outer join third_party_tpusers thirdparty2_ on tpuser0_.id = thirdparty2_.uid
left outer join teachers teacher3_ on tpuser0_.id = teacher3_.tpuser_id and (teacher3_.deleted = 0)
where tpuser0_.id in (?, ?)
从而解决了问题。
不过建议对JPA不熟悉的,建议实体上都不要用关联关系。用mysql的思路解决问题即可;
出现N+1的SQL的场景,我们有如下四个实体,核心内容如下:
2021-09-17 16:42:03.480 TRACE [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] o.h.type.descriptor.sql.BasicExtractor : extracted value ([uuid1624] : [VARCHAR]) - [81164fff-4184-47c3-84a5-d44e71400bd4] 2021-09-17 16:42:03.500 DEBUG [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] org.hibernate.SQL : select parent0_.id as id1_130, parent0_.created_at as created_2_130, parent0_.updated_at as updated_3_130, parent0_.lock_version as lock_ver4_130, parent0_.deleted as deleted5_130, parent0_.deleted_at as deleted_6_130, parent0_.address as address7_130, parent0_.state as state8_130, parent0_.tpuser_id as tpuser_i9_130 from parents parent0 where parent0.tpuserid=? and ( parent0.deleted = 0)
2021-09-17 16:42:03.545 DEBUG [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] org.hibernate.SQL : select teacher0_.id as id1_150, teacher0_.created_at as created_2_150, teacher0_.updated_at as updated_3_150, teacher0_.lock_version as lock_ver4_150, teacher0_.deleted as deleted5_150, teacher0_.deleted_at as deleted_6_150, teacher0_.address as address7_150, teacher0_.area_id as area_id8_150, teacher0_.last_login_date as last_log9_150, teacher0_.state as state10_150, teacher0_.tpuser_id as tpuser_12_150, teacher0_.type as type11_150 from teachers teacher0 where teacher0.tpuserid=? and ( teacher0.deleted = 0)
2021-09-17 16:42:03.581 DEBUG [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] org.hibernate.SQL : select parent0_.id as id1_130, parent0_.created_at as created_2_130, parent0_.updated_at as updated_3_130, parent0_.lock_version as lock_ver4_130, parent0_.deleted as deleted5_130, parent0_.deleted_at as deleted_6_130, parent0_.address as address7_130, parent0_.state as state8_130, parent0_.tpuser_id as tpuser_i9_130 from parents parent0 where parent0.tpuserid=? and ( parent0.deleted = 0) 2021-09-17 16:42:03.622 DEBUG [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] org.hibernate.SQL : select teacher0_.id as id1_150, teacher0_.created_at as created_2_150, teacher0_.updated_at as updated_3_150, teacher0_.lock_version as lock_ver4_150, teacher0_.deleted as deleted5_150, teacher0_.deleted_at as deleted_6_150, teacher0_.address as address7_150, teacher0_.area_id as area_id8_150, teacher0_.last_login_date as last_log9_150, teacher0_.state as state10_150, teacher0_.tpuser_id as tpuser_12_150, teacher0_.type as type11_150 from teachers teacher0 where teacher0.tpuserid=? and ( teacher0.deleted = 0) 2021-09-17 16:42:03.623 TRACE [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] o.h.type.descriptor.sql.BasicBinder : binding parameter [1] as [BIGINT] - [8991696] 2021-09-17 16:42:03.768 DEBUG [-,cebfb5f6a6b6a1c9,cebfb5f6a6b6a1c9,true] 40539 --- [nio-9000-exec-1] org.hibernate.SQL : select thirdparty0_.uid as uid15_181, thirdparty0_.id as id1_181, thirdparty0_.id as id1_180, thirdparty0_.created_at as created_2_180, thirdparty0_.updated_at as updated_3_180, thirdparty0_.lock_version as lock_ver4_180, thirdparty0_.avatar_url as avatar_u5_180, thirdparty0_.city as city6_180, thirdparty0_.country as country7_180, thirdparty0_.nickname as nickname8_180, thirdparty0_.openid as openid9_180, thirdparty0_.platform as platfor10_180, thirdparty0_.province as provinc11_180, thirdparty0_.sex as sex12_180, thirdparty0_.uid as uid15_180, thirdparty0_.unionid as unionid13_180, thirdparty0_.uuid as uuid14_180 from third_partytpusers thirdparty0 where thirdparty0_.uid in (?, ?)