LazyQueryContainer with JTA transaction

I tried to use the LazyQueryContainer with EJB 3.1 and container managed transaction. it works on loading but when I try to save the changed i got this error

Caused by: javax.persistence.TransactionRequiredException: EntityManager must be access within a transaction
at org.jboss.jpa.deployment.ManagedEntityManagerFactory.verifyInTx(ManagedEntityManagerFactory.java:157) [:1.0.2-alpha-3]

at org.jboss.jpa.deployment.PersistenceUnitDeployment.verifyInTx(PersistenceUnitDeployment.java:318) [:1.0.2-alpha-3]

at org.jboss.jpa.impl.tx.TransactionScopedEntityManager.verifyInTx(TransactionScopedEntityManager.java:105) [:2.0.0]

at org.jboss.jpa.impl.tx.TransactionScopedEntityManager.merge(TransactionScopedEntityManager.java:211) [:2.0.0]

at org.vaadin.addons.lazyquerycontainer.EntityQuery.saveItems(EntityQuery.java:165) [:]

First thought came to my mind was to create a session bean to be extended from LazyQueryContainer and use that instead of an instance of LazyQueryContainer,
but the LazyQueryContainer is a final class so I can not extend it
and the entity manager is passed to the LazyQueryContainer constructor that won’t be available during the session bean constructor.

So is there an alternative solution to this?

Thanks

Farid

I don’t have experience with LazyQueryContainer and CMT transactions but how do you initialize your entity manager? If you’re letting the container to manage the transactions you can initialize the entity manager with the @PersistenceContext annotation in EJBs. With the instructions in this article
Creating JEE6 Vaadin Applications
you might be able to inject container managed entity manager to Vaadin application and pass reference to it for the LazyQueryContainer.

This is probably a terrible hack that shouldn’t be used but you could give it a try anyway.

I initialize the Entity Manager inside the application Servlet like this:

@WebServlet(urlPatterns = “/lazy/*”)
public class LazyServlet extends AbstractApplicationServlet {

@PersistenceContext
EntityManager entityManager;

@Override
protected Application getNewApplication(HttpServletRequest request) throws ServletException {
    return new LazyContainerApplication(entityManager);//bean.getEntityManager());
}

Well i never used entitymanager at the servlet level before. I used to have a session bean with an instance of the entity manager in it, but in this case the constructor of the Lazy query container just gets an instance of the entity manager :

    new EntityContainer<CmsConfig>(entityManager, false, true, true, CmsConfig.class, 100,   sortColumnIDs, sortColumnAscending);

As the reference for the others, i ended up implementing the code like this:

i annotated the application using the @SessionScoped annotation and injected a stateful bean into it:

@SessionScoped
public class LazyContainerApplication extends Application /*implements ClickListener */{
private static final long serialVersionUID = 1L;

@EJB
EntityContainerProviderBean entityContainerProviderBean;

the code for bean is like this:

@Stateful
@TransactionManagement
public class EntityContainerProviderBean {
@PersistenceContext
EntityManager entityManager;

private EntityContainer<MyBean> entityContainer;

public EntityContainer<CmsConfig> createEntityContainer(TableSettings tableSettings){
	entityContainer = new EntityContainer<MyBean>(entityManager, false, true, true, MyBean.class, 100, 
    		tableSettings.getSortColumnIDs().toArray(), tableSettings.getSortColumnAscending());

    return entityContainer;
}

public void commit(){
	entityContainer.commit();
}

}

The bean keeps an instance of the entityManager. Then, createEntityContainer method initializes the container using entityManager.

Then all of the transaction based method calls to the container such as commit need to be done through the session bean.