Camunda Spring启动事务问题

Posted

技术标签:

【中文标题】Camunda Spring启动事务问题【英文标题】:Camunda Spring boot transaction issues 【发布时间】:2018-10-17 14:59:01 【问题描述】:

我有 camunda 进程实例,它检查数据库中的某些内容(只读),并且随机我得到各种与事务相关的异常。

代码是从 Camunda JavaDelegate 调用的,当我通过常规 REST api 调用调用它时,它工作正常。

我使用默认的 camunda spring boot 配置,我所做的唯一适配是针对 oracle:

   @Component
    @Order(Ordering.DEFAULT_ORDER - 1)
    public class CmcConfig extends AbstractCamundaConfiguration 
        @Override
        public void preInit(ProcessEngineConfigurationImpl processEngineConfiguration) 
            processEngineConfiguration.setJdbcBatchProcessing(false);
            super.preInit(processEngineConfiguration);
        
    

例外:

org.springframework.dao.InvalidDataAccessApiUsageException: detached entity passed to persist: xxxx.xxx.Entity1; nested exception is org.hibernate.PersistentObjectException: detached entity passed to persist: xxxx.xxx.Entity1
    at org.springframework.orm.jpa.vendor.HibernateJpaDialect.convertHibernateAccessException(HibernateJpaDialect.java:299) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.orm.jpa.vendor.HibernateJpaDialect.translateExceptionIfPossible(HibernateJpaDialect.java:244) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:521) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:761) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:730) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.TransactionTemplate.execute(TransactionTemplate.java:150) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.camunda.bpm.engine.spring.SpringTransactionInterceptor.execute(SpringTransactionInterceptor.java:40) ~[camunda-engine-spring-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.interceptor.ProcessApplicationContextInterceptor.execute(ProcessApplicationContextInterceptor.java:66) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.interceptor.LogInterceptor.execute(LogInterceptor.java:30) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobHelper.executeJob(ExecuteJobHelper.java:36) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobHelper.executeJob(ExecuteJobHelper.java:29) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobsRunnable.executeJob(ExecuteJobsRunnable.java:88) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobsRunnable.run(ExecuteJobsRunnable.java:57) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.springframework.security.concurrent.DelegatingSecurityContextRunnable.run(DelegatingSecurityContextRunnable.java:83) [spring-security-core-4.2.4.RELEASE.jar:4.2.4.RELEASE]
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) [na:1.8.0_152]
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) [na:1.8.0_152]
    at java.lang.Thread.run(Thread.java:748) [na:1.8.0_152]
Caused by: org.hibernate.PersistentObjectException: detached entity passed to persist: xxxx.xxx.Entity1
    at org.hibernate.event.internal.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:124) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.firePersistOnFlush(SessionImpl.java:802) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.persistOnFlush(SessionImpl.java:795) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.spi.CascadingActions$8.cascade(CascadingActions.java:340) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeToOne(Cascade.java:398) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeAssociation(Cascade.java:323) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeProperty(Cascade.java:162) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeCollectionElements(Cascade.java:431) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeCollection(Cascade.java:363) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeAssociation(Cascade.java:326) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascadeProperty(Cascade.java:162) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.internal.Cascade.cascade(Cascade.java:111) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.AbstractFlushingEventListener.cascadeOnFlush(AbstractFlushingEventListener.java:150) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.AbstractFlushingEventListener.prepareEntityFlushes(AbstractFlushingEventListener.java:141) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:74) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:38) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.flush(SessionImpl.java:1282) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.managedFlush(SessionImpl.java:465) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.flushBeforeTransactionCompletion(SessionImpl.java:2963) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.beforeTransactionCompletion(SessionImpl.java:2339) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.jdbc.internal.JdbcCoordinatorImpl.beforeTransactionCompletion(JdbcCoordinatorImpl.java:485) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.beforeCompletionCallback(JdbcResourceLocalTransactionCoordinatorImpl.java:147) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.access$100(JdbcResourceLocalTransactionCoordinatorImpl.java:38) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl$TransactionDriverControlImpl.commit(JdbcResourceLocalTransactionCoordinatorImpl.java:231) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.transaction.internal.TransactionImpl.commit(TransactionImpl.java:65) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.jpa.internal.TransactionImpl.commit(TransactionImpl.java:61) ~[hibernate-entitymanager-5.0.12.Final.jar:5.0.12.Final]
    at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:517) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    ... 14 common frames omitted

org.springframework.transaction.TransactionSystemException: Could not commit JPA transaction; nested exception is javax.persistence.RollbackException: Error while committing the transaction
    at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:526) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:761) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:730) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.springframework.transaction.support.TransactionTemplate.execute(TransactionTemplate.java:150) ~[spring-tx-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    at org.camunda.bpm.engine.spring.SpringTransactionInterceptor.execute(SpringTransactionInterceptor.java:40) ~[camunda-engine-spring-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.interceptor.ProcessApplicationContextInterceptor.execute(ProcessApplicationContextInterceptor.java:66) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.interceptor.LogInterceptor.execute(LogInterceptor.java:30) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobHelper.executeJob(ExecuteJobHelper.java:36) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobHelper.executeJob(ExecuteJobHelper.java:29) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobsRunnable.executeJob(ExecuteJobsRunnable.java:88) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.camunda.bpm.engine.impl.jobexecutor.ExecuteJobsRunnable.run(ExecuteJobsRunnable.java:57) ~[camunda-engine-7.8.0.jar:7.8.0]
    at org.springframework.security.concurrent.DelegatingSecurityContextRunnable.run(DelegatingSecurityContextRunnable.java:83) [spring-security-core-4.2.4.RELEASE.jar:4.2.4.RELEASE]
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) [na:1.8.0_152]
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) [na:1.8.0_152]
    at java.lang.Thread.run(Thread.java:748) [na:1.8.0_152]
Caused by: javax.persistence.RollbackException: Error while committing the transaction
    at org.hibernate.jpa.internal.TransactionImpl.commit(TransactionImpl.java:87) ~[hibernate-entitymanager-5.0.12.Final.jar:5.0.12.Final]
    at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:517) ~[spring-orm-4.3.14.RELEASE.jar:4.3.14.RELEASE]
    ... 14 common frames omitted
Caused by: java.lang.NullPointerException: null
    at org.hibernate.event.internal.AbstractFlushingEventListener.prepareCollectionFlushes(AbstractFlushingEventListener.java:178) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:78) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.event.internal.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:38) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.flush(SessionImpl.java:1282) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.managedFlush(SessionImpl.java:465) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.flushBeforeTransactionCompletion(SessionImpl.java:2963) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.internal.SessionImpl.beforeTransactionCompletion(SessionImpl.java:2339) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.jdbc.internal.JdbcCoordinatorImpl.beforeTransactionCompletion(JdbcCoordinatorImpl.java:485) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.beforeCompletionCallback(JdbcResourceLocalTransactionCoordinatorImpl.java:147) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl.access$100(JdbcResourceLocalTransactionCoordinatorImpl.java:38) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.resource.transaction.backend.jdbc.internal.JdbcResourceLocalTransactionCoordinatorImpl$TransactionDriverControlImpl.commit(JdbcResourceLocalTransactionCoordinatorImpl.java:231) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.engine.transaction.internal.TransactionImpl.commit(TransactionImpl.java:65) ~[hibernate-core-5.0.12.Final.jar:5.0.12.Final]
    at org.hibernate.jpa.internal.TransactionImpl.commit(TransactionImpl.java:61) ~[hibernate-entitymanager-5.0.12.Final.jar:5.0.12.Final]
    ... 15 common frames omitted

【问题讨论】:

【参考方案1】:

您需要让 Camunda 使用外部事务管理器(Spring 事务管理器)

我在我的 Spring Boot 项目中使用了旧的 spring 方式。我必须在配置文件(main/resources/spring/camunda-workflow-config.xml)中将事务管理器和数据源名称传递给 camunda。

像这样:

<property name="transactionManager" ref="transactionManager" />
<property name="dataSource" ref="dataSource" />
<property name="transactionsExternallyManaged" value="true" />

【讨论】:

以上是关于Camunda Spring启动事务问题的主要内容,如果未能解决你的问题,请参考以下文章

如何使用Java在camunda流程引擎上获取扩展属性

将 REST-Call 从 Angular 发送到 Camunda Rest-Engine 时出现 CORS 错误

在spring cloud中加入camunda rest接口时的一个坑

使用 Spring Boot 和 mongodb 运行 camunda

如何在 Spring Boot 中实现 Camunda SendTask

在挂起状态下启动camunda进程