Java EE 中的网关模式

4
我在一个Java EE项目中使用了网关模式,其中我有以下组件:
- 一个具有扩展持久性上下文的有状态会话Bean。 - Bean的事务属性设置为不支持,以防止任何事务提交到数据库中。 - Bean具有保存方法,事务属性设置为需要新的,这将导致一个新的事务,将提交实体的所有更改并反映它们到数据库中。
参考Gateway:adam bein page-67 两天前,我使用GlassFish 3一切正常。我检索一个实体,做出更改,然后调用保存方法而不合并实体。该实体的更改被刷新到数据库中。但是当我切换到GlassFish 4之后,此操作停止了,现在我必须合并实体才能将更改的实体刷新到数据库中。

可能是 网关模式和Glassfish4 的重复问题。 - Nikos Paraskevopoulos
1个回答

1

save方法专门用于插入数据,因此再次调用save将会在数据库中创建另一行记录。

update方法更新会话中的对象。因此,如果对象已经在会话中,它将被更新。 如果对象不在会话中,则应调用merge方法。

因此,如果检索到已存在的实体,则必须调用update/merge而不是save。

JPA规范

合并操作应用于实体X的语义如下: 如果X是一个游离实体,则将X的状态复制到具有相同标识的预先存在的托管实体实例X'上,或者创建一个新的托管副本X'。 如果X是一个新的实体实例,则创建一个新的托管实体实例X',并将X的状态复制到新的托管实体实例X'中。 如果X是一个已删除的实体实例,则合并操作将抛出IllegalArgumentException(或事务提交将失败)。 如果X是托管实体,则合并操作将忽略它,但是,如果这些关系已经使用cascade = MERGE或cascade = ALL注释,那么合并操作会级联到从X引用的关系实体。对于所有由cascade = MERGE或cascade = ALL具有级联元素值的关系从X引用的实体Y,都会递归地将Y合并为Y'。对于所有这样的Y被X引用的Y,X'被设置为引用Y'。(注意,如果X是托管的,则X与X'是同一对象。) 如果将实体X合并到X'中,并且引用另一个实体Y,其中未指定cascade = MERGE或cascade = ALL,则从X'导航到相同的关联会产生一个引用到具有与Y相同持久标识的托管对象Y'。

1
我通过使用unsync实体管理器然后在保存方法中加入事务来解决了这个问题。我相信这是glassfish 4.0.1中的一个错误。 - bob-cac

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接