6 Replies Latest reply on Aug 16, 2014 10:45 AM by Rafael Peres dos Santos

    javax.persistence.TransactionRequiredException

    psilos panipsilos Newbie

      Hi guys,

       

      For an app I m using JSF managed beans and JPA. However when I m trying to persist an entity I m getting the following error:

      : javax.persistence.TransactionRequiredException: JBAS011469: Transaction is required to perform this operation (either use a transaction or extended persistence context):

       

      My bean is:

       

       

      package org.tutorial;
      
      import java.util.ArrayList;
      import java.util.List;
      
      import javax.ejb.Stateful;
      import javax.ejb.Stateless;
      import javax.enterprise.inject.Model;
      import javax.faces.application.FacesMessage;
      import javax.faces.context.FacesContext;
      import javax.persistence.EntityManager;
      import javax.persistence.PersistenceContext;
      import javax.persistence.Query;
      
      import org.Entities.*;
      import org.Handlers.*;
      
      
      
      
      @Statefull
      @model
      public class ProjectEntityHandlerBean
      {
        private String projectName;
        private String description;
        private String duration;
        private  List<Project> projectList;
      
        @PersistenceContext
        private EntityManager em;
      
      public ProjectEntityHandlerBean()
      {
      
      }
      
      
      
      
      
      
          public String getProjectName() {
          return projectName;
      }
      
      public void setProjectName(final String projectName) {
          this.projectName = projectName;
      }
      
          public String getDescription() {
          return description;
      }
      
      public void setDescription(final String description) {
          this.description = description;
      }
      
      public String getDuration() {
          return duration;
      }
      
      public void setDuration(final String duration) {
          this.duration = duration;
      }
      
      public List<Project> getProjectList() {  
          return projectList;  
      } 
      
          public String insertNewProject()
          {   
              System.out.println("Enter insert method");
              Project project = new Project();
              project.setProjectName(this.projectName);
              project.setDescription(this.description);
              project.setDuration(this.duration);        
              em.persist(project);  <----------  At this line I get the error
              return "viewid?faces-redirect=true";
          }    
          public String getAllProjects()
          {
              Query query = em.createQuery("SELECT p FROM Project p");
              projectList = query.getResultList();
              return "true";        
          }    
      }
      

      The full stack of the server is:

       

      16:03:56,686 WARNING [javax.enterprise.resource.webcontainer.jsf.lifecycle] (http--0.0.0.0-8080-2) #{ProjectEntityHandlerBean.insertNewProject}: javax.persistence.TransactionRequiredException: JBAS011469: Transaction is required to perform this operation (either use a transaction or extended persistence context): javax.faces.FacesException: #{ProjectEntityHandlerBean.insertNewProject}: javax.persistence.TransactionRequiredException: JBAS011469: Transaction is required to perform this operation (either use a transaction or extended persistence context)

          at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:118) [jsf-impl-2.1.7-jbossorg-2.jar:]

          at javax.faces.component.UICommand.broadcast(UICommand.java:315) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at javax.faces.component.UIData.broadcast(UIData.java:1093) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at javax.faces.component.UIData.broadcast(UIData.java:1093) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:794) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1259) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:81) [jsf-impl-2.1.7-jbossorg-2.jar:]

          at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101) [jsf-impl-2.1.7-jbossorg-2.jar:]

          at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:118) [jsf-impl-2.1.7-jbossorg-2.jar:]

          at javax.faces.webapp.FacesServlet.service(FacesServlet.java:593) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:329) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:248) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:275) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:161) [jbossweb-7.0.13.Final.jar:]

          at org.jboss.as.jpa.interceptor.WebNonTxEmCloserValve.invoke(WebNonTxEmCloserValve.java:50) [jboss-as-jpa-7.1.1.Final.jar:7.1.1.Final]

          at org.jboss.as.web.security.SecurityContextAssociationValve.invoke(SecurityContextAssociationValve.java:153) [jboss-as-web-7.1.1.Final.jar:7.1.1.Final]

          at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:155) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) [jbossweb-7.0.13.Final.jar:]

          at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:368) [jbossweb-7.0.13.Final.jar:]

          at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:877) [jbossweb-7.0.13.Final.jar:]

          at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:671) [jbossweb-7.0.13.Final.jar:]

          at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:930) [jbossweb-7.0.13.Final.jar:]

          at java.lang.Thread.run(Unknown Source) [rt.jar:1.6.0_32]

      Caused by: javax.faces.el.EvaluationException: javax.persistence.TransactionRequiredException: JBAS011469: Transaction is required to perform this operation (either use a transaction or extended persistence context)

          at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:102) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102) [jsf-impl-2.1.7-jbossorg-2.jar:]

          ... 23 more

      Caused by: javax.persistence.TransactionRequiredException: JBAS011469: Transaction is required to perform this operation (either use a transaction or extended persistence context)

          at org.jboss.as.jpa.container.AbstractEntityManager.transactionIsRequired(AbstractEntityManager.java:692) [jboss-as-jpa-7.1.1.Final.jar:7.1.1.Final]

          at org.jboss.as.jpa.container.AbstractEntityManager.persist(AbstractEntityManager.java:562) [jboss-as-jpa-7.1.1.Final.jar:7.1.1.Final]

          at org.tutorial.ProjectEntityHandlerBean.insertNewProject(ProjectEntityHandlerBean.java:90) [classes:]

          at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) [rt.jar:1.6.0_32]

          at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) [rt.jar:1.6.0_32]

          at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) [rt.jar:1.6.0_32]

          at java.lang.reflect.Method.invoke(Unknown Source) [rt.jar:1.6.0_32]

          at org.apache.el.parser.AstValue.invoke(AstValue.java:262) [jbossweb-7.0.13.Final.jar:]

          at org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:278) [jbossweb-7.0.13.Final.jar:]

          at com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:105) [jsf-impl-2.1.7-jbossorg-2.jar:]

          at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:88) [jboss-jsf-api_2.1_spec-2.0.1.Final.jar:2.0.1.Final]

          ... 24 more

       

      Anybody could tell me what I m doing wrong? The bean is request scoped and ve also tried with @stateless.

        • 1. Re: javax.persistence.TransactionRequiredException
          Wolf-Dieter Fink Master

          The access to a database, query persist, must have a transaction. you might add the transaction annotation to the method or you might use an extended EntityManager scope

          • 2. Re: javax.persistence.TransactionRequiredException
            psilos panipsilos Newbie

            Well I think that @transaction is available in Spring. I m using JSF and managed beans so  @Transaction is not available.

            I tried to use the extended EntityManager scope but again this is not valid for managed beans.

            • 3. Re: javax.persistence.TransactionRequiredException
              Dmitry K Newbie

              I have the same problem, did anybody solve it?

              • 4. Re: javax.persistence.TransactionRequiredException
                Stephen Coy Master

                The original poster mis-spelt @Stateful, so his bean would not have been transactional.

                 

                Dmitry, you should probably start a new discussion and describe your exact scenario.

                • 5. Re: javax.persistence.TransactionRequiredException
                  Rafael Peres dos Santos Newbie

                  Wich version of jboss, if is 7.x or after versions like jboss eap 6.2.0 i found this bug, if you use @TransactionAttribute(TransactionAttributeType.SUPPORTS) at class level,

                  the container ignore a method declaration of @TransactionAttribute(TransactionAttributeType.REQUIRED) and throw  javax.persistence.TransactionRequiredException

                  Other way to avoid  javax.persistence.TransactionRequiredException in bugged versions of jboss is using a interface that don't use generics

                   

                  In jboss 6 versions @TransactionAttribute(TransactionAttributeType.SUPPORTS) at class level works as ejb-spec.

                  ( I don't know how to relate this bug to jboss please anyone relate this it's a very worst bug )

                  About me i'm a SCJP 6, SCWD 5 and OCPBCD 5 and 6 years working with Java, this is not my code error, it's a bug of jboss.

                   

                  Example:

                   

                   

                  
                  @Stateless
                  @Local(BO.class)
                  @TransactionManagement(TransactionManagementType.CONTAINER)
                  @TransactionAttribute(TransactionAttributeType.SUPPORTS)
                  public class BOImpl implements BO {
                      @PersistenceContext(unitName = "sgenEjbTestPU")
                      private EntityManager em;
                  
                      @Override
                      @TransactionAttribute(TransactionAttributeType.REQUIRED)
                      public AppParam saveOrUpdate(AppParam param) {
                          em.persist(param);
                          return param;
                      }
                  }
                  
                  import br.com.pegasus.sgen.domain.AppParam;
                  public interface BO extends BOGeneric<AppParam, Integer> {
                  }
                  
                  public interface BOGeneric<T, Id> {
                      T saveOrUpdate(T param);
                  }
                  
                  import br.com.pegasus.sgen.domain.AppParam;
                  public interface BOInterfaceWithoutGenerics {
                      AppParam saveOrUpdate(AppParam param);
                  }
                  
                  @Entity
                  @Table(name = "tb_app_param")
                  @XmlRootElement
                  public class AppParam implements Serializable {
                      private static final long serialVersionUID = 4818981684503640410L;
                  
                      @Id
                      @GeneratedValue(strategy = GenerationType.IDENTITY)
                      @Basic(optional = false)
                      @Column(name = "id_app_param")
                      private Integer id;
                  
                      @Basic(optional = false)
                      @Column(name = "name")
                      private String name;
                  
                      @Basic(optional = false)
                      @Column(name = "js_value")
                       private String jsValue;
                  
                      public AppParam() {
                      }
                  
                      public AppParam(Integer id) {
                          this.id = id;
                      }
                  
                      public AppParam(String name) {
                          this.name = name;
                      }
                  
                      public AppParam(Integer id, String name, String jsValue) {
                          this.id = id;
                          this.name = name;
                          this.jsValue = jsValue;
                      }
                  
                      public Integer getId() {
                          return this.id;
                      }
                  
                      public void setId(Integer id) {
                          this.id = id;
                      }
                  
                      public String getName() {
                          return this.name;
                      }
                  
                      public void setName(String name) {
                          this.name = name;
                      }
                  
                      public String getJsValue() {
                          return this.jsValue;
                      }
                  
                      public void setJsValue(String jsValue) {
                          this.jsValue = jsValue;
                      }
                  
                      public int hashCode() {
                          int hash = 0;
                          hash += (this.id != null ? this.id.hashCode() : 0);
                          return hash;
                      }
                  
                      public boolean equals(Object object) {
                          if (!(object instanceof AppParam)) {
                              return false;
                          }
                          AppParam other = (AppParam) object;
                          if (((this.id == null) && (other.id != null)) || ((this.id != null) && (!this.id.equals(other.id)))) {
                              return false;
                          }
                          return true;
                      }
                  
                    }
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  

                   

                  in persistence.xml
                  <persistence-unit name="sgenEjbTestPU" transaction-type="JTA">
                          <provider>org.hibernate.ejb.HibernatePersistence</provider>
                          <jta-data-source>java:/sgenXAMysqlDS</jta-data-source>
                          <jar-file>lib/sgen-domain-1.0.0.jar</jar-file>
                          <properties>
                              <property name="hibernate.show_sql" value="true" />
                              <property name="hibernate.format_sql" value="true" />
                              <property name="hibernate.use_sql_comments" value="false" />
                              <property name="hibernate.dialect" value="org.hibernate.dialect.MySQLInnoDBDialect" />
                          </properties>
                  </persistence-unit>
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  

                   

                  in com/mysql/main/modules.xml
                  <?xml version="1.0" encoding="UTF-8"?>
                  <module xmlns="urn:jboss:module:1.0" name="com.mysql">
                    <resources>
                      <resource-root path="mysql-connector-java-5.1.22-bin.jar"/>
                    </resources>
                    <dependencies>
                      <module name="javax.api"/>
                      <module name="javax.transaction.api"/>
                    </dependencies>
                  </module>
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  

                   

                  in <drivers> section of standalone.xml
                  <driver name="xa.mysql" module="com.mysql">
                        <xa-datasource-class>com.mysql.jdbc.jdbc2.optional.MysqlXADataSource</xa-datasource-class>
                  </driver>
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  

                   

                  in ds file named: testJboss-ds.xml in deployments dir folder
                  <?xml version="1.0" encoding="UTF-8"?>
                  <datasources>
                  <xa-datasource jndi-name="java:/sgenXAMysqlDS" pool-name="MySqlPool" enabled="true" jta="true" use-java-context="true" use-ccm="true">
                      <xa-datasource-property name="ServerName">ip</xa-datasource-property>
                      <xa-datasource-property name="PortNumber">databaseport</xa-datasource-property>
                      <xa-datasource-property name="DatabaseName">databasename</xa-datasource-property>
                      <xa-datasource-property name="User">username</xa-datasource-property>
                      <xa-datasource-property name="Password">password</xa-datasource-property>
                      <driver>xa.mysql</driver>
                      <transaction-isolation>TRANSACTION_READ_COMMITTED</transaction-isolation>
                  </xa-datasource>
                  </datasources>
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  
                  • 6. Re: javax.persistence.TransactionRequiredException
                    Rafael Peres dos Santos Newbie

                    I think you are not using a persistence unit with JTA in this case you must open a transaction manually with BMT.

                    the default @TransactionManagement(TransactionManagementType.CONTAINER) you must change it to @TransactionManagement(TransactionManagementType.BEAN) if you are not using a JTA persistence unit( why i think this,

                    in your code there is no error just a configuration makes javax.persistence.TransactionRequiredException occur because the default @TransactionAttribute when none is specified is @TransactionAttribute(TransactionAttributeType.REQUIRED)).

                     

                    in the caller use something like this:

                     

                    @EJB

                    private YourStatefulInterface sf;

                     

                    @Resource

                    UserTransaction tx;

                     

                    tx.begin();

                    sf.yourMethodThatPersist();
                    tx.commit();

                    // if an exception occur

                    tx.rollback();