gpt4 book ai didi

java - 防止 Hibernate 加载惰性 ManyToOne

转载 作者:行者123 更新时间:2023-11-30 09:05:46 27 4
gpt4 key购买 nike

我将模型中的问题减少到 3 个实体:

  • 车站。
  • 位置(每个站几个)。
  • 位置组(每个站几个)。

Location 类:

@Entity
@Table(name = "***")
public class Location {

@ManyToOne
@JoinColumn(name = "s_id")
private Station s;

@ManyToOne
@JoinColumn(name = "g_id")
private GroupOfLocations group;

}

GroupOfLocation 类:

@Entity
@Table(name = "***")
public class GroupOfLocation {

@ManyToOne(fetch = FetchType.LAZY) //I do not want the Station to be loaded
@JoinColumn(name = "s_id")
private Station s;

}

当我通过 ID 获取位置时:

  1. 它的站已加载
  2. 位置组已加载
  3. 组站已加载我不需要它。

问题: 该组包含电台,但我不想加载它。我预计 fetch = FetchType.LAZY 会阻止 Station 完全加载,但它不起作用。

我在 SO 上搜索过,有时问题出在声明为 final 的类,但此模型中没有 final 类。

有什么想法吗?

这是通过 ID 搜索实体 ID 的方式:

public Location getById(Integer id) {
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaQuery<Location> query = cb.createQuery(Location.class);
Root<Location> entity = query.from(Location.class);
Predicate whereClause = cb.equal(entity.get(Location_.id), id);
query.where(whereClause);
return em.createQuery(query).getSingleResult();
}

最佳答案

任何 JPQL 或 Criteria 查询都将转到 override the default获取计划(您在实体映射中定义的计划)。

默认查询计划仅在使用 find 或 getReference 加载实体时有效

entityManager.find(GroupOfLocation.class, 1L);

默认的@ManyToOne 抓取是 EAGER,但由于您还没有发出联合抓取,这些抓取将通过一些额外的选择来提取。

location.group.station 不会通过额外的选择获取,但代理仍会存在。

如果 location.station 恰好与 location.group.station 匹配,那么 Hibernate 将使用已经加载的 location.station,因为在 Hibernate Session 对象内部相等性匹配实例相等性(意味着只能有一个具有给定实体标识符的实体类型的对象)。

因此,如果 location.group.stationlocation.station 引用同一个实体,您将看到一个已初始化的代理,否则代理将保持未初始化状态。

如果 session 关闭并且代理未初始化,您将在访问它时遇到延迟异常。

关于java - 防止 Hibernate 加载惰性 ManyToOne,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24758459/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com