2012-08-01 3 views
0

감사 목적으로 Hibernate Envar를 사용하고 있습니다. 여기 Hibernate Envers - org.hibernate.exception.ConstraintViolationException : JDBC 배치 업데이트를 수행 할 수 없음

내 코드 및 구성

있는 hibernate.cfg.xml 파일 구성입니다

<!-- Audit --> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="post-insert"/> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="post-update"/> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="post-delete"/> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="pre-collection-update"/> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="pre-collection-remove"/> 
     <listener class="org.hibernate.envers.event.AuditEventListener" type="post-collection-recreate"/> 

한 샘플 법인 Annoted와 나는 감사를 기록하는 RevistionEntity을 만든 @Audited

@Entity 
@Table(name = "Users") 
@Audited 
public class User extends GenericDomain implements Serializable { 

    @Id 
    @GeneratedValue(strategy = GenerationType.AUTO) 
    private Long id; 
    @Column(length=100) 
    private String name; 
    @Column(length=60) 
    private String username; 
    @Column(length=130) 
    private String password; 
    // Getter and setter with more fields 
} 

로그인 한 사용자에 대해 감사를 로깅하는 사람

@Entity 
@Table(name = "REVISIONS") 
@RevisionEntity(CustomRevisionListener.class) 
public class CustomRevisionEntity { 

    @Id 
    @GeneratedValue 
    @RevisionNumber 
    private int id; 
    @RevisionTimestamp 
    private long audit_timestamp; 
    private String username; 
    private Long userid; 
    // Getter and Setter 
} 

여기에 삽입 /가 잘 작동 삭제를 들어 내 리스너 클래스

public class CustomRevisionListener implements RevisionListener { 

    public void newRevision(Object revisionEntity) { 
     CustomRevisionEntity revision = (CustomRevisionEntity) revisionEntity; 
     revision.setUsername("username"); //for testing 
    } 
} 

입니다.

그러나

업데이트

[ERROR] [http-8080-1 06:05:26] (JDBCExceptionReporter.java:logExceptions:101) Duplicate entry '1085-3' for key 1 
[ERROR] [http-8080-1 06:05:26] (AbstractFlushingEventListener.java:performExecutions:324) Could not synchronize database state with session 
org.hibernate.exception.ConstraintViolationException: Could not execute JDBC batch update 
     at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:96) 
     at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:66) 
     at org.hibernate.jdbc.AbstractBatcher.executeBatch(AbstractBatcher.java:275) 
     at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:263) 
     at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:179) 
     at org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:321) 
     at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:51) 
     at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1206) 
     at org.hibernate.envers.synchronization.AuditProcess.doBeforeTransactionCompletion(AuditProcess.java:157) 
     at org.hibernate.envers.synchronization.AuditProcess.beforeCompletion(AuditProcess.java:164) 
     at org.hibernate.transaction.JDBCTransaction.notifyLocalSynchsBeforeTransactionCompletion(JDBCTransaction.java:274) 
     at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:140) 
     at org.springframework.orm.hibernate3.HibernateTransactionManager.doCommit(HibernateTransactionManager.java:656) 
     at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:754) 
     at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:723) 
     at org.springframework.transaction.interceptor.TransactionAspectSupport.commitTransactionAfterReturning(TransactionAspectSupport.java:393) 
     at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:120) 
     at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172) 
     at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:202) 
     at $Proxy106.deleteSaleRecord(Unknown Source) 
     at org.commission.controller.salerecord.SaleRecordController.delete(SaleRecordController.java:753) 
     at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
     at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
     at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
     at java.lang.reflect.Method.invoke(Method.java:597) 
     at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.invokeHandlerMethod(HandlerMethodInvoker.java:176) 
     at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.invokeHandlerMethod(AnnotationMethodHandlerAdapter.java:426) 
     at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(AnnotationMethodHandlerAdapter.java:414) 
     at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:790) 
     at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:719) 
     at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:644) 
     at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:549) 
     at javax.servlet.http.HttpServlet.service(HttpServlet.java:690) 
     at javax.servlet.http.HttpServlet.service(HttpServlet.java:803) 
     at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
     at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
     at org.commission.util.SessionFilter.doFilter(SessionFilter.java:71) 
     at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
     at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
     at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233) 
     at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175) 
     at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128) 
     at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 
     at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 
     at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:286) 
     at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:844) 
     at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583) 
     at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447) 
     at java.lang.Thread.run(Thread.java:619) 
Caused by: java.sql.BatchUpdateException: Duplicate entry '1085-3' for key 1 
     at com.mysql.jdbc.PreparedStatement.executeBatchSerially(PreparedStatement.java:2018) 
     at com.mysql.jdbc.PreparedStatement.executeBatch(PreparedStatement.java:1449) 
     at com.mchange.v2.c3p0.impl.NewProxyPreparedStatement.executeBatch(NewProxyPreparedStatement.java:1723) 
     at org.hibernate.jdbc.BatchingBatcher.doExecuteBatch(BatchingBatcher.java:70) 
     at org.hibernate.jdbc.AbstractBatcher.executeBatch(AbstractBatcher.java:268) 
     ... 46 more 

로는 다음과 같은 예외를주고 조회를 위해 여기에서 모든 엔티티

불행하게도 전체 스택 트레이스와 테이블의 SQL 정의없이
public E update(E entity) { 
     getSession().update(entity); 
     return entity; 
    } 
+0

@Teinacher, 업데이트 코드를 게시했는지 확인하십시오. 이는 감사의 경우에만 발생합니다. 감사 기능이 없다면 CRUD 기능이 완벽하게 작동합니다. –

답변

1

내 일반적인 업데이트 코드입니다, 여기에서 무슨 일이 일어나고 있는지 말하기가 어렵습니다. 다음과 같이 점검 할 사항입니다.

  1. 감사 테이블의 제약 조건/PK는 무엇입니까? - 기본 키에 개정 번호와 개정 유형이 누락되었을 가능성이 있습니다 - 특정 엔터티에 대해 동일한 세션에서 업데이트 및 삭제가 발생했기 때문에 발생했습니다 (나는 계단식 조작과 관련이 있다고 생각하지만 지금은 기억할 수 없다.) 엔티티 테이블의 개정 번호 + PK가 감사 테이블의 각 행을 고유하게 식별하기에 충분할 것으로 예상했다.

  2. 기본적으로 삭제 된 엔티티는 원래 엔티티의 리비전 번호, 수정 유형 및 ID/PK 만 포함합니다. 감사 테이블에 NOT NULL 제약 조건이 있으면 오류가 발생할 수 있습니다. org.hibernate.envers.store_data_at_delete 속성을 true으로 설정하면이 문제를 해결할 수 있습니다.

+0

안녕하세요, 귀하의 # 1과 동일한 문제가 있습니다. 내 감사 테이블은'@ JoinTable'과 두 개의 PK 컬럼이있는 다 대일 (many to many) 테이블로, 감사 테이블에서 총 4 개가됩니다. 그러나 PK의 네 열 모두를 업그레이드 한 후에도 최대 절전 모드에서 오류가 발생합니다. org.hibernate.NonUniqueObjectException : 같은 식별자 값을 가진 다른 객체가 이미 세션과 연관되어있다. # 2도 나에게 '사실'입니다. 최대 절전 모드가 동일한 신원을 가지고 있다고 생각하는 이유는 무엇입니까? – Andreas

+0

오래전에, 이제는 테이블 정의로 새로운 질문을 게시 할 수 있습니다. 필자는 결국 감사 테이블에서 키를 삭제했다고 생각합니다. 그렇지 않으면 관리하기가 너무 어려워졌습니다. – ifx

+0

필자는 이런 일이 일어나지 않도록보기 코드를 다시 작성하는 일이 많았습니다. 많은 번거 로움이있었습니다. – Andreas

관련 문제