我们有一些实体带有一堆用Hibernate的@Formula
注释注释的属性。注释中的SQL片段主要运行标量子查询(例如COUNT
个查询)。例如,我们有一个一对多的关系层次结构,其深度为四级:A <- B <- C <- D
(其中<-
标记一对多关联)。通常在提取A
类型的实体时,我们想知道D
类型的关联实体的数量。为此,我们在@Formula
中使用了A
- 带注释的属性。
由于我们每次都不需要这些值,因此我们已将@Formula
属性声明为延迟加载(我们已启用Hibernate的字节码增强功能以实现此功能)。但对于某些查询,我们希望热切地加载这些属性。我们经常在一个查询中加载数百个A
类型的实体,并且动态地控制这些属性的急切/延迟加载在性能方面是很重要的。我们已经使用JPA的实体图来控制哪些属性急切地为某些查询加载,但实体图似乎在这里不起作用。即使我们在实体图中列出了@Formula
属性,它们仍然会被懒惰地加载。
是否可以在每个查询的基础上动态控制@Formula
列的延迟/急切加载?我们目前仅限于JPA Criteria Query API,并且命名查询不是这种可能性。
更新
有问题的属性不是与其他实体的关联,而只是一些计算值。这意味着,例如获取配置文件不适用于此,因为它们仅适用于实体关联(或至少我理解Hibernate manual的方式)。以下是我们@Formula
个属性之一的示例:
@Entity
public class A {
@Basic(fetch = FetchType.LAZY)
@Formula("(select count(*) from entity_D_table where ...)")
private int associatedDCount;
...
}
答案 0 :(得分:1)
您可以使用Critria api使其返回DTO而不是实体。
在条件查询中,使用“投影”仅选择所需的列。
TextView termsText = (TextView)findViewById(R.id.terms_text);
termsText.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse("http://www.yoururl.com"));
startActivity(browserIntent);
}
});
这样,选择查询将只包含您要求的字段,无论映射为EAGER还是LAZY。
答案 1 :(得分:0)
您可以尝试查看Hibernate的抓取配置文件https://docs.jboss.org/hibernate/orm/4.2/manual/en-US/html/ch20.html#performance-fetching-profiles。
例如,您可以注释像这样的实体
@Entity
@FetchProfile(name = "country_states", fetchOverrides = {
@FetchProfile.FetchOverride(entity = Country.class, association = "states", mode = FetchMode.JOIN)
})
public class Country implements Serializable {...
并在查询时激活JOIN模式,如下所示:
session=getSession();
session.beginTransaction();
//enable fetch profile for EAGER fetching
session.enableFetchProfile("country_states");
如http://www.concretepage.com/hibernate/fetchprofile_hibernate_annotation
所示