JPA当前没有交易活动

时间:2017-05-08 15:52:56

标签: java spring jpa transactions

目标: 要触发多个删除操作,如果两者之间发生任何异常,则应删除删除操作。例如:

  • dao.deleteQMap(id)已成功执行。
  • dao.deleteAVersion(id)函数发生异常,因此 dao.deleteQMap(id)应该回滚。

以下是代码:

/ **在服务类** /

@Transactional
 public void deleteExistingData(List<A> aL) {
        Long abyId;
        String aID;
        List<AV> avList;
        for (A a1 : aL) {
            aID = a1.getAIId();
            for (AVersion aV : avList) {
                dao.deleteQMap(id)  /** delete #1 **/
            }
            dao.deleteAVersion(id);    /** delete #2**/
            dao.deleteADetails(id);    /** delete #3 **/
        }
    }

/ **在dao class ** /

public void deleteQMap (Long aVId) {
        Query query = getEntityManager().createQuery("DELETE FROM AQ a WHERE a.Id = : aVId ");
        query.setParameter("aVId ", aVId).executeUpdate();
    }

在服务类的函数上方声明了Transactional注释,但是当控件进入dao.deleteQMap(id)时,它会抛出以下异常。想要使用@Transactional,因为它自己处理回滚功能。

javax.persistence.TransactionRequiredException: 
Exception Description: No transaction is currently active
    at org.eclipse.persistence.internal.jpa.transaction.EntityTransactionWrapper.throwCheckTransactionFailedException(EntityTransactionWrapper.java:109)
    at org.eclipse.persistence.internal.jpa.transaction.EntityTransactionWrapper.checkForTransaction(EntityTransactionWrapper.java:50)
    at org.eclipse.persistence.internal.jpa.EntityManagerImpl.checkForTransaction(EntityManagerImpl.java:1272)
    at org.eclipse.persistence.internal.jpa.EJBQueryImpl.executeUpdate(EJBQueryImpl.java:417)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at org.springframework.orm.jpa.SharedEntityManagerCreator$DeferredQueryInvocationHandler.invoke(SharedEntityManagerCreator.java:311)
    at com.sun.proxy.$Proxy122.executeUpdate(Unknown Source)
    at com.dsths.cmt.persistence.CmtDao.deleteQuestionMap(CmtDao.java:117)
    at com.dsths.cmt.services.ImportServiceImpl.deleteExistingData(ImportServiceImpl.java:145)
    at com.dsths.cmt.services.ImportServiceImpl.readExcel(ImportServiceImpl.java:70)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:198)
    at com.sun.proxy.$Proxy55.readExcel(Unknown Source)
    at com.dsths.cmt.resources.ExportResource.uploadFile(ExportResource.java:104)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at com.sun.jersey.spi.container.JavaMethodInvokerFactory$1.invoke(JavaMethodInvokerFactory.java:60)
    at com.sun.jersey.server.impl.model.method.dispatch.AbstractResourceMethodDispatchProvider$ResponseOutInvoker._dispatch(AbstractResourceMethodDispatchProvider.java:205)
    at com.sun.jersey.server.impl.model.method.dispatch.ResourceJavaMethodDispatcher.dispatch(ResourceJavaMethodDispatcher.java:75)
    at com.sun.jersey.server.impl.uri.rules.HttpMethodRule.accept(HttpMethodRule.java:288)
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147)
    at com.sun.jersey.server.impl.uri.rules.ResourceClassRule.accept(ResourceClassRule.java:108)
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147)
    at com.sun.jersey.server.impl.uri.rules.RootResourceClassesRule.accept(RootResourceClassesRule.java:84)
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1483)
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1414)
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1363)
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1353)
    at com.sun.jersey.spi.container.servlet.WebComponent.service(WebComponent.java:414)
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:537)
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:708)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:848)
    at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:648)
    at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1336)
    at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:106)
    at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1307)
    at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:186)
    at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:160)
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:343)
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:260)
    at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1307)
    at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:453)
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:137)
    at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:559)
    at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:231)
    at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1072)
    at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:382)
    at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:193)
    at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1006)
    at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:135)
    at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(ContextHandlerCollection.java:255)
    at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerCollection.java:154)
    at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116)
    at org.eclipse.jetty.server.handler.StatisticsHandler.handle(StatisticsHandler.java:126)
    at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116)
    at org.eclipse.jetty.server.Server.handle(Server.java:365)
    at org.eclipse.jetty.server.AbstractHttpConnection.handleRequest(AbstractHttpConnection.java:485)
    at org.eclipse.jetty.server.AbstractHttpConnection.content(AbstractHttpConnection.java:937)
    at org.eclipse.jetty.server.AbstractHttpConnection$RequestHandler.content(AbstractHttpConnection.java:998)
    at org.eclipse.jetty.http.HttpParser.parseNext(HttpParser.java:856)
    at org.eclipse.jetty.http.HttpParser.parseAvailable(HttpParser.java:240)
    at org.eclipse.jetty.server.AsyncHttpConnection.handle(AsyncHttpConnection.java:82)
    at org.eclipse.jetty.io.nio.SelectChannelEndPoint.handle(SelectChannelEndPoint.java:627)
    at org.eclipse.jetty.io.nio.SelectChannelEndPoint$1.run(SelectChannelEndPoint.java:51)
    at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:608)
    at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:543)
    at java.lang.Thread.run(Thread.java:745)

任何建议都非常感谢。

用于访问本地数据库的Entity Manager Factory

<bean id="entityManagerFactory"
      class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
    <property name="persistenceUnitName" value="persistenceUnit"/>
    <property name="jpaVendorAdapter">
        <bean class="org.springframework.orm.jpa.vendor.EclipseLinkJpaVendorAdapter">
            <property name="showSql" value="true"/>
            <property name="generateDdl" value="false"/>
        </bean>
    </property>
    <property name="jpaPropertyMap">
        <map>
            <entry key="eclipselink.jdbc.native-sql" value="true"/>
            <!-- do not allow sharing of cache between sessions -->
            <entry key="eclipselink.cache.shared.default" value="false"/>
            <!-- Enable a custom logger implementation to allow Eclipselink to use Log4j for logging. -->
            <entry key="eclipselink.logging.logger" value="org.eclipse.persistence.logging.Log4jSessionLog"/>
            <!-- Enable batch writing for performance  -->
            <entry key="eclipselink.jdbc.batch-writing" value="${persistence.batchWriting}"/>

            <!--
              When set to true, all Eclipselink exceptions are logged before being returned to the
              caller.
            -->
            <entry key="eclipselink.logging.exceptions" value="true"/>

            <entry key="eclipselink.weaving" value="false"/>
            <entry key="eclipselink.session.customizer"
                   value="com.dst.hps.persistence.dao.eclipselink.HistoryAndUUIDSequenceAndLog4j"/>
        </map>
    </property>
    <property name="packagesToScan">
        <list>
            <value>com.dst.hps.persistence.entities</value>
            <value>com.dsths.cmt.entities</value>
        </list>
    </property>
    <property name="dataSource" ref="dataSource"/>
</bean>

使用@Transactional注释

启用交易
<tx:annotation-driven/>

<bean id="eclipselinkDialect" class="org.springframework.orm.jpa.vendor.EclipseLinkJpaDialect"/>

<!-- For info Refer to spring framework manual 7.9.2 - using metatdata-driven autoproxying -->

<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
    <property name="entityManagerFactory" ref="entityManagerFactory"/>
    <property name="jpaDialect" ref="eclipselinkDialect"/>
    <!--
      Uncommenting the following line will result in
      'org.springframework.dao.InvalidDataAccessApiUsageException: Query delete from Target, query
      hint javax.persistence.lock.timeout is not valid for this type of query'
    -->
    <!-- <property name="defaultTimeout" value="1200" /> -->

    <!-- TODO: This might need to be set to false -->
    <property name="nestedTransactionAllowed" value="true"/>
</bean>

1 个答案:

答案 0 :(得分:0)

我的功能实现了:

public boolean registrar(Country c) {
    final EntityTransaction transaction = em.getTransaction();
    transaction.begin();
    boolean resultado;
    try {

        Query q = em
                .createNativeQuery("INSERT INTO Countries (COUNTRY_ID, COUNTRY_NAME, REGION_ID) VALUES (?,?,?)");
        q.setParameter(1, c.getCountryId());
        q.setParameter(2, c.getCountryName());
        q.setParameter(3, c.getRegion().getRegionId());
        q.executeUpdate();

        transaction.commit();
        resultado = true;
    } catch (PersistenceException e) {
        transaction.rollback();
        resultado = false;
    }
    return resultado;
}