我刚刚开始使用Hibernate,我想知道如何将一个新元素插入到oneToMany关系中,而不用首先加载容器。
考虑以下示例:
@Entity
@Table(name="orders")
class Order {
@Id @GeneratedId
public Long id;
@OneToMany(mappedBy="order")
public List<Item> items = new ArrayList<Item>();
}
@Entity
@Table(name="items")
class Item {
@Id @GeneratedId
public Long id;
@ManyToOne
public Order order;
}
我想在订单中插入一个新商品(我知道订单的ID并且它有效),但我不想先加载订单。显然,这应该是可能的,因为SQL只需要插入的id而不是整个Order对象。
答案 0 :(得分:2)
你应该可以在Hibernate中轻松完成这项工作。
Item item - new Item();
Order order = new Order();
order.setId(order_id);
item.setOrder(order);
em.persist(item);
确保在Item实体的订单属性中正确设置了级联属性。如果不这样做,您最终可能无意中更改了Order中的值。
@ManyToOne(cascade=CascadeType.PERSIST)
应该没问题。如果订单不存在,它将仅允许从项目侧更改订单。
顺便说一下,您可能想要将此关系视为ManyToMany,因为在多个订单上设置项目是有意义的。
答案 1 :(得分:1)
我认为你不能,Hibernate需要在会话/上下文中使用Order才能添加项目。即Hibernate将需要“知道”项目顺序。
答案 2 :(得分:1)
“幸运的是”你没有任何级联策略,并且依赖项设置在Item侧。
您可以使用session.load()来加载具有所需ID的用户。 load()方法将返回一个代理,以防在会话中找不到它。当你想设置依赖而不去db来获取实体时,这很有用。
它看起来像:
Order order = session.load(Order.class, orderId); // no DB call
Item item = new Item();
item.setOrder(order);
// set other attributes of item
session.save(item);
对于load()和get()的差异,请参阅 Hibernate: Difference between session.get and session.load
答案 3 :(得分:0)
您可以通过创建没有Item
的新Order
来执行此操作,并将其保留,然后使用本机查询从新order_id
更新Item
值。< / p>