hibernate Spring Data 休眠:如何使用实体中指定的提取类型进行自定义查询?

uajslkp6  于 2023-02-04  发布在  Spring
关注(0)|答案(1)|浏览(109)

我正在使用Spring Data和Hibernate 6.x开发一个Sping Boot 3.x应用程序。我有一个实体类,如下所示:

@Entity
public class User {

    @Id
    private UUID id = UUID.randomUUID();

    @Column
    private String country;

    @ManyToMany(fetchType = FetchType.EAGER)
    private Set<Role> roles;

    // constructors, getters, setters, equals/hashcode based on id
}

当我在存储库中执行这样的自定义查询时:

@Query("""
   FROM User user
   WHERE user.country = ?1
""")
public Set<User> getUserByCountry(String country);

...我得到了一个Set<User>,但是他们的roles属性是由Hibernate延迟加载的;我可以从SQL查询日志中清楚地看到这一点。一个角色查询被发送到每个用户的数据库。
现在,我已经有一段时间了,我清楚地记得FetchType.EAGER是不受欢迎的,因为它影响了所有查询,而且您不能选择退出它。即使roles引用被标记为EAGER,也会执行延迟提取。这种行为在Hibernate的最新(主要)版本中是否发生了变化?我可以告诉Hibernate总是在默认情况下为所有定制查询提取渴望关联吗?
我试着使用@EntityGraph显式地告诉自定义查询急切地获取roles引用,这很好用,但是如果没有提供@EntityGraph注解,我强烈希望hib从实体的注解中推断出这个信息。
编辑:我昨天验证了 Boot 和hib5.x的获取行为 * 实际上是 * 不同的。这似乎是hib6.x的事情。

szqfcxe2

szqfcxe21#

生成的SQL查询应该包含一个join来获取roles作为主查询的一部分。在您的真实的模型中,当您有多个这样的渴望收集时,Hibernate必须发出单独的查询以避免多个包获取,这将改变结果的基数。但是,如果您只有一个渴望收集,请在问题跟踪器(https://hibernate.atlassian.net)中创建一个问题,并使用一个重现该问题的测试用例(https://github.com/hibernate/hibernate-test-case-templates/blob/master/orm/hibernate-orm-6/src/test/java/org/hibernate/bugs/JPAUnitTestCase.java)。

相关问题