使用bean的entityListener中的无限循环

osc*_*car 1 java spring hibernate jpa listener

我创建一个 EntityListener 来审核特定实体。存储状态更改的历史记录。我使用 AutowireHelper 注入 Bean。我在这里得到它https://guylabs.ch/2014/02/22/autowiring-pring-beans-in-hibernate-jpa-entity-listeners/comment-page-1/

这可以很好地注入存储库,但要调用任何存储库的任何函数,请返回 AutowireHelper.autowire 行。

这是我的代码,EntityListener 执行 AutowireHelper.autowire ,当涉及到“find”方法时返回到 autowire 行:

public class AuditListener {

    @Inject
    private UserRepository userRepository;

    @Inject
    private ConfigurationRepository configurationRepository;

    @PreUpdate
    public void preUpdate(Object object) {
        //TODO: pre update
        AutowireHelper.autowire(this, this.userRepository, this.configurationRepository);

        //I need get bbdd entities
        List<Configuracion> config = this.configurationRepository.findAll();

        Foo foo = (Foo) object;
        System.out.println("Foo updated: " + foo.getId());
    }
}
Run Code Online (Sandbox Code Playgroud)

我的错误:

无法提交 JPA 事务;嵌套异常是 javax.persistence.RollbackException:提交事务时出错 12:43:25,291 INFO [stdout] (http-/0.0.0.0:8080-1) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 12:43 :25,291 信息 [stdout] (http-/0.0.0.0:8080-1) 在 sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) 12:43:25,291 信息 [stdout] (http-/0.0.0.0: 8080-1)在sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)12:43:25,291信息[stdout](http-/0.0.0.0:8080-1)在java.lang.reflect.Method.invoke (Method.java:601)12:43:25,291信息[stdout](http-/0.0.0.0:8080-1)在org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:221)12 :43:25,291信息[标准输出](http-/0.0.0.0:8080-1)在org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:137)12:43:25,291信息[标准输出] (http-/0.0.0.0:8080-1)在org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:110)12:43:25,291信息[stdout](http-/ 0.0.0.0:8080-1) 在 org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver.doResolveHandlerMethodException(ExceptionHandlerExceptionResolver.java:362)|

完整轨迹:

14:01:35,393 错误 [stderr] (http-/0.0.0.0:8080-1) org.springframework.transaction.TransactionSystemException:无法提交 JPA 事务;嵌套异常是 javax.persistence.RollbackException: 提交事务时出错 14:01:35,398 ERROR [stderr] (http-/0.0.0.0:8080-1) at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager. java:526) 14:01:35,401 错误 [stderr] (http-/0.0.0.0:8080-1) 在 org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:757) 14:01:35,405 错误[stderr] (http-/0.0.0.0:8080-1) 在 org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:726) 14:01:35,408 错误 [stderr] (http-/0.0.0.0 :8080-1)在org.springframework.transaction.interceptor.TransactionAspectSupport.commitTransactionAfterReturning(TransactionAspectSupport.java:521)14:01:35,412错误[stderr](http-/0.0.0.0:8080-1)在org.springframework。 transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:291) 14:01:35,415 错误 [stderr] (http-/0.0.0.0:8080-1) 在 org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor. java:96) 14:01:35,419 错误 [stderr] (http-/0.0.0.0:8080-1) 在 org.springframework.aop.framework.ReflectiveMethodInvocau.proceed(ReflectiveMethodInitation.java:179) 14:01:35,422 错误[stderr] (http-/0.0.0.0:8080-1) 在 org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:207) 14:01:35,425 错误 [stderr] (http-/0.0.0.0 :8080-1)在com.sun.proxy.$Proxy195.save(来源未知)14:01:35,428错误[stderr](http-/0.0.0.0:8080-1)在es.company.project.web。 controller.foo.FooController.save(FooController.java:395) 14:01:35,431 错误 [stderr] (http-/0.0.0.0:8080-1) 在 sun.reflect.NativeMethodAccessorImpl.invoke0(本机方法) 14:01 :35,434错误[stderr](http-/0.0.0.0:8080-1)在sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)14:01:35,436错误[stderr](http-/0.0.0.0: 8080-1)在sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)14:01:35,437错误[stderr](http-/0.0.0.0:8080-1)在java.lang.reflect.Method.invoke (Method.java:601)14:01:35,438错误[stderr](http-/0.0.0.0:8080-1)在org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:221)14 :01:35,439错误[stderr](http-/0.0.0.0:8080-1)在org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:137)14:01:35,441错误[stderr] (http-/0.0.0.0:8080-1)在org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:110)14:01:35,442错误[stderr](http-/ 0.0.0.0:

Pra*_*ras 5

您在这里遇到交易问题:

1 - 你的

AuditListener.preUpdate
Run Code Online (Sandbox Code Playgroud)

叫做。

2 - 你这么称呼

this.configurationRepository.findAll()
Run Code Online (Sandbox Code Playgroud)

在那里。

3 - spring进入其存储库以获取元素,您可以在堆栈跟踪中看到它:

org.springframework.data.jpa.repository.support.SimpleJpaRepository.findAll
Run Code Online (Sandbox Code Playgroud)

4 - 获取元素并从存储库返回后,这次休眠,尝试flush元素,您可以再次在堆栈中看到它:

org.hibernate.internal.SessionImpl.autoFlushIfRequired(SessionImpl.java:1166)
Run Code Online (Sandbox Code Playgroud)

5 - 刷新元素时,hibernate 再次调用您的AuditListener.preUpdate方法 --> 回到数字 1

这就是解释。现在,为什么需要在 PreUpdate 事件中调用某些 Repository 方法?你不能用其他方式做到这一点吗?