我需要从另一个 Web 应用程序调用远程无状态 EJB,使用相同的 glassfish( 3.1 最终版本),返回 Entity Bean(JPA 2/Eclipselink)。我正在通过依赖注入(@EJB)在Web应用程序中获得ejb引用,但实体变为空。我用谷歌搜索它,发现它可能是可序列化的问题。我在某处找到了这个
TopLink 要么修改实体类 ("编织"它们)在负载或替代品 运行时的集合访问为 能够检测延迟访问或 修改后的关系(没有 在没有这个的情况下支持延迟加载的方法 或子类化或使用代理 运行时)。这给我们带来了一个非常 重要提示:你不应该使用 反射以访问实体,但 只能通过其业务方法。当一个 编织实体在 服务器并在客户端上反序列化 没有相应的 实体编织,串行版本UID 将不匹配,因为计算 值包括类字段和 方法。
那么我是否需要在我的应用程序???上进行DTO转换
"但实体变为空"是什么意思? 您是在远程 SessionBean 上调用方法并返回 null,还是返回关系为 null 的实体?
如果它是一个空关系,则可能是懒惰问题,如果你的关系是懒惰的,并且尚未被获取或访问,那么它将为空。 您需要获取它,访问它或使其成为EAGER。
如果您返回 null,则还有其他问题。
也许您受到 Glassfish bug 16164 的影响。
建议的解决方法是将此属性添加到持久性.xml:
<property name="eclipselink.weaving" value="false"/>
这解决了我的问题。
当您尝试返回实体时,带有 EclipseLink 和 Glassfish 的远程 EJB 无法正常工作。
与休眠相同,您需要在返回响应之前删除所有代理。使用 Hibernate,您需要在删除代理之前刷新并清除持久性上下文。如果未加载,请将 null 设置为属性。您可以使其与 Java EE 拦截器一起使用。
但是,EclipseLink 不像 Hibernate 那样工作。即使您清除了持久性上下文,获取/设置在惰性属性上也会尝试获取。即使是外部交易。
如果您设置属性名称="eclipselink.weaving" value="false",它将起作用,因为 EclipseLink 不会更改 POJO 类的字节码,但 ManyToOne 将始终被获取。因此,它可以在内存中加载数据库。
我解决此问题的唯一方法是使用 DTO 或将 Hibernate 与拦截器一起使用。
编辑:您始终可以使用外部化接口覆盖实体序列化。按字段获取对象,以确保延迟获取不适用。
Openjpa似乎也默认使用编织方法。 http://openjpa.apache.org/entity-enhancement.html