我在Java EE项目中使用网关模式:
具有扩展存在上下文的有状态会话bean。
bean将事务属性设置为不支持 停止将任何事务提交到数据库中。
bean有一个save方法,其transaction属性设置为require new将导致新的事务将提交所有 实体的变化并将它们反映到数据库中。
请参阅Gateway:adam bein page-67
直到两天前我才使用GlassFish 3并且一切正常。我检索一个实体,进行更改,然后在不合并实体的情况下调用save方法。实体更改将刷新到数据库。但当我将GlassFish更改为GlassFish 4时,此操作已停止,现在我必须合并实体才能将更改的实体刷新到数据库。
答案 0 :(得分:1)
特别保存插入。因此,再次调用save将导致db中的另一行。
更新更新会话中的对象。因此,如果对象在会话中,它将更新。 如果对象不在会话中,则应调用merge。
因此,如果您检索已存在的实体,则必须调用update / merge而不是save。
应用于实体X的合并操作的语义如下: 如果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'。对于由X,X'引用的所有这样的Y.设置为引用Y'。 (注意,如果管理X,则X与X'是相同的对象。)
如果X是合并到X'的实体,引用另一个实体Y,其中未指定cascade = MERGE或cascade = ALL,则从X'中导航相同的关联。产生对托管对象Y'具有与Y相同的持久性身份。