2011-10-02 18 views
0

我试图在JBoss7中运行由maven archetype groupId生成的简单JEE6应用程序:org.fluttercode.knappsack,artifactID:jee6-sandbox-archetype。 (通过这个turial去了,对不起,德语)通过@ConversationScoped方法提供EntityManager

但是,调用的欢迎JSF的时候,我得到了以下错误消息:

org.jboss.weld.exceptions.IllegalProductException: WELD-000053 Producers 
    cannot declare passivating scope and return a non-serializable class: 
    [method] @Produces @DataRepository @ConversationScoped 
    public org.rap.jee6project.bean.DataRepositoryProducer.getEntityManager() 
org.jboss.weld.bean.AbstractProducerBean.checkReturnValue(AbstractProducerBean.java:264) 
org.jboss.weld.bean.AbstractProducerBean.create(AbstractProducerBean.java:362) 
org.jboss.weld.context.AbstractContext.get(AbstractContext.java:122) 

事实上,它应该返回一个EntityManager的DataRepositoyProducer类实例,被定义为如下注释:

@Stateless 
public class DataRepositoryProducer { 


private EntityManager entityManager; 

@Produces @DataRepository @ConversationScoped 
public EntityManager getEntityManager() { 
    return entityManager; 
} 

@PersistenceContext 
public void setEntityManager(EntityManager entityManager) { 
    this.entityManager = entityManager; 
} 

} 

如果我使用@RequestScoped,应用程序按照承诺运行。我想知道为什么其他人通过本教程没有遇到这个问题?以及如何正确地修复它(使用@RequestScoped意味着豆为每个用户请求重新创建,对吧?,我预计效率不高)

官方JEE6教程说:“使用会话,应用程序或会话范围必须是可序列化的,但使用请求范围的bean不必是可序列化的“”。然而,这似乎并不是问题,因为服务器不是关于不可序列化的bean,而是生产者bean的产品。

+0

使得DataRepositoryProducer一个状态bean和注释全班同学为@ConversationScoped时,它的工作原理。不知道我是否应该对这个解决方案感到满意。 也许,生产者的概念并不是容器提供的对象(如EntityManager)的最佳实践。 – rainer198

回答

1

应该..

@Stateful 
@ConversationScoped 
public class ProducerCreator implements Serializable{ 
    @PersistenceConText 
    private EntityManager entityManager; 
    .... 
} 

,如果你想使用相同的实体上下文中每个会话的应该是

@PersistenceContex(type = PersistenceContextType.EXTENDED) 

最后,如果你想拥有的服务层,应创建有状态并注入对话bean

+0

谢谢,这就像我在我的评论中提到的解决方案。我想知道是否应该使用生产者来获取EntityManager实例,因为要记住有状态的EJB会影响可伸缩性。为什么不以JEE5方式注入它,直接使用@PersistenceContext而不是使用专用的生产者bean。 – rainer198

+0

默认情况下EntityManager是事务范围。我认为,将entityManager更改为对话作用域是没有意义的。让我们看看Seam持久化模块http://www.seamframework.org/Seam3/PersistenceModule,如果你真的想制作EntityManager。 – Udonake

1

我在jboss7上运行演示程序时遇到了同样的问题。

只需在getEntityManager()中删除@ConversationScoped就可以让我部署它。

即使有一些缺陷:

javax.servlet.ServletException: javax.faces.component.StateHolderSaver cannot be cast to [Ljava.lang.Object;  
javax.faces.webapp.FacesServlet.service(FacesServlet.java:606) 
org.jboss.weld.servlet.ConversationPropagationFilter.doFilter(ConversationPropagationFilter.java:62) 

我不知道到底,如果是相关的,但我猜是这样。

1

记住:EntityManager不是序列化的,所以它不能被储存在ConversationScope

相关问题