2010-06-05 1 views
1

У меня возникли проблемы с попыткой сохранить объект, идентификатор которого является сгенерированным значением. Эта сущность (A) в течение продолжительности сохраняется в каскаде другого объекта (B). Связь между A и B является OneToMany, а свойство, связанное с B, является частью составного ключа.Не удалось синхронизировать состояние базы данных с сеансом

Я использую Eclipse, JBoss выполнения, JPA/Hibernate

Вот мой код:

Entity A:

@Entity 
public class Cambios implements Serializable { 
    private static final long serialVersionUID = 1L; 

    @SequenceGenerator(name="CAMBIOS_GEN",sequenceName="CAMBIOS_SEQ",allocationSize=1) 
    @Id @GeneratedValue(strategy=GenerationType.SEQUENCE, generator="CAMBIOS_GEN") 
    @Column(name="ID_CAMBIO") 
    private Long idCambio; 

    //bi-directional many-to-one association to ObjetosCambio 
    @OneToMany(cascade={CascadeType.PERSIST},mappedBy="cambios") 
    private List<ObjetosCambio> objetosCambioList; 

    public Cambios() { 
    } 

    ... 
} 

Entity B:

@Entity 
@Table(name="OBJETOS_CAMBIO") 
public class ObjetosCambio implements Serializable { 
    private static final long serialVersionUID = 1L; 

    @EmbeddedId 
    private ObjetosCambioPK id; 

    //bi-directional many-to-one association to Cambios 
    @ManyToOne 
    @JoinColumn(name="ID_CAMBIO", insertable=false, updatable=false) 
    private Cambios cambios; 

    //bi-directional many-to-one association to Objetos 
    @ManyToOne 
    @JoinColumn(name="ID_OBJETO", insertable=false, updatable=false) 
    private Objetos objetos; 

    public ObjetosCambio() { 
    } 

... 

Entity B PK:

@Embeddable 
public class ObjetosCambioPK implements Serializable { 
    //default serial version id, required for serializable classes. 
    private static final long serialVersionUID = 1L; 

    @Column(name="ID_OBJETO") 
    private Long idObjeto; 

    @Column(name="ID_CAMBIO") 
    private Long idCambio; 

    public ObjetosCambioPK() { 
    } 

Клиент:

public String generarCambio(){ 

     ServiceLocator serviceLocator = null; 
     try {   
      serviceLocator = serviceLocator.getInstance(); 
      FachadaLocal tcLocal; 
      tcLocal = (FachadaLocal)serviceLocator.getFacadeService("java:comp/env/negocio/Fachada"); 

      Cambios cambio = new Cambios(); 

      Iterator it = objetosLocal.iterator(); //OBJETOSLOCAL IS ALREADY POPULATED OUTSIDE OF THIS METHOD    
      List<ObjetosCambio> ocList = new ArrayList();    
      while (it.hasNext()){ 
        Objetos objeto = (Objetos)it.next(); 
        ObjetosCambio objetosCambio = new ObjetosCambio(); 
        objetosCambio.setCambios(cambio); //AT THIS TIME THIS "CAMBIO" DOES NOT HAVE ITS ID, ITS SUPPOSED TO BE GENERATED AT PERSISTENCE TIME 

        ObjetosCambioPK ocPK = new ObjetosCambioPK(); 
        ocPK.setIdObjeto(objeto.getIdObjeto()); 

        objetosCambio.setId(ocPK); 
        ocList.add(objetosCambio); 
           } 

      cambio.setObjetosCambioList(ocList); 

      tcLocal.persistEntity(cambio); 
      return "exito";    
       } catch (NamingException e) { 
        // TODO     
        e.printStackTrace();      
              } 
     return null; 
    } 


ERROR: 

15:23:25,717 WARN [JDBCExceptionReporter] SQL Error: 1400, SQLState: 23000 
15:23:25,717 ERROR [JDBCExceptionReporter] ORA-01400: no se puede realizar una inserción NULL en ("CDC"."OBJETOS_CAMBIO"."ID_CAMBIO") 

15:23:25,717 WARN [JDBCExceptionReporter] SQL Error: 1400, SQLState: 23000 
15:23:25,717 ERROR [JDBCExceptionReporter] ORA-01400: no se puede realizar una inserción NULL en ("CDC"."OBJETOS_CAMBIO"."ID_CAMBIO") 

15:23:25,717 ERROR [AbstractFlushingEventListener] 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:94) 
    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:266) 
    at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:167) 
    at org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:321) 
    at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:50) 
    at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1027) 
    at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:365) 
    at org.hibernate.ejb.AbstractEntityManagerImpl$1.beforeCompletion(AbstractEntityManagerImpl.java:504) 
    at com.arjuna.ats.internal.jta.resources.arjunacore.SynchronizationImple.beforeCompletion(SynchronizationImple.java:101) 
    at com.arjuna.ats.arjuna.coordinator.TwoPhaseCoordinator.beforeCompletion(TwoPhaseCoordinator.java:269) 
    at com.arjuna.ats.arjuna.coordinator.TwoPhaseCoordinator.end(TwoPhaseCoordinator.java:89) 
    at com.arjuna.ats.arjuna.AtomicAction.commit(AtomicAction.java:177) 
    at com.arjuna.ats.internal.jta.transaction.arjunacore.TransactionImple.commitAndDisassociate(TransactionImple.java:1423) 
    at com.arjuna.ats.internal.jta.transaction.arjunacore.BaseTransaction.commit(BaseTransaction.java:137) 
    at com.arjuna.ats.jbossatx.BaseTransactionManagerDelegate.commit(BaseTransactionManagerDelegate.java:75) 
    at org.jboss.aspects.tx.TxPolicy.endTransaction(TxPolicy.java:170) 
    at org.jboss.aspects.tx.TxPolicy.invokeInOurTx(TxPolicy.java:87) 
    at org.jboss.aspects.tx.TxInterceptor$Required.invoke(TxInterceptor.java:190) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.aspects.tx.TxPropagationInterceptor.invoke(TxPropagationInterceptor.java:76) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.ejb3.tx.NullInterceptor.invoke(NullInterceptor.java:42) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.ejb3.security.Ejb3AuthenticationInterceptorv2.invoke(Ejb3AuthenticationInterceptorv2.java:186) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.ejb3.ENCPropagationInterceptor.invoke(ENCPropagationInterceptor.java:41) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.ejb3.BlockContainerShutdownInterceptor.invoke(BlockContainerShutdownInterceptor.java:67) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.aspects.currentinvocation.CurrentInvocationInterceptor.invoke(CurrentInvocationInterceptor.java:67) 
    at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:102) 
    at org.jboss.ejb3.session.SessionSpecContainer.invoke(SessionSpecContainer.java:176) 
    at org.jboss.ejb3.session.SessionSpecContainer.invoke(SessionSpecContainer.java:216) 
    at org.jboss.ejb3.proxy.impl.handler.session.SessionProxyInvocationHandlerBase.invoke(SessionProxyInvocationHandlerBase.java:207) 
    at org.jboss.ejb3.proxy.impl.handler.session.SessionProxyInvocationHandlerBase.invoke(SessionProxyInvocationHandlerBase.java:164) 
    at $Proxy298.persistEntity(Unknown Source) 
    at backing.SolicitudCambio.generarCambio(SolicitudCambio.java:521) 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) 
    at java.lang.reflect.Method.invoke(Unknown Source) 
    at com.sun.faces.el.MethodBindingImpl.invoke(MethodBindingImpl.java:146) 
    at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:92) 
    at javax.faces.component.UICommand.broadcast(UICommand.java:332) 
    at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:287) 
    at javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:401) 
    at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:95) 
    at com.sun.faces.lifecycle.LifecycleImpl.phase(LifecycleImpl.java:245) 
    at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:110) 
    at javax.faces.webapp.FacesServlet.service(FacesServlet.java:213) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
    at org.apache.myfaces.webapp.filter.ExtensionsFilter.doFilter(ExtensionsFilter.java:301) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
    at org.jboss.web.tomcat.filters.ReplyHeaderFilter.doFilter(ReplyHeaderFilter.java:96) 
    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:235) 
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) 
    at org.jboss.web.tomcat.security.SecurityAssociationValve.invoke(SecurityAssociationValve.java:190) 
    at org.jboss.web.tomcat.security.JaccContextValve.invoke(JaccContextValve.java:92) 
    at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.process(SecurityContextEstablishmentValve.java:126) 
    at org.jboss.web.tomcat.security.SecurityContextEstablishmentValve.invoke(SecurityContextEstablishmentValve.java:70) 
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) 
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 
    at org.jboss.web.tomcat.service.jca.CachedConnectionValve.invoke(CachedConnectionValve.java:158) 
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:330) 
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:829) 
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:598) 
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447) 
    at java.lang.Thread.run(Unknown Source) 
Caused by: java.sql.BatchUpdateException: ORA-01400: no se puede realizar una inserción NULL en ("CDC"."OBJETOS_CAMBIO"."ID_CAMBIO") 

Заранее спасибо! JM.-


Я попытался установить cambios.idCambio вручную, но я все еще получаю ту же ошибку. Hibernate должен выполнять какое-то сопоставление между объектамиCambioPK.idCambio и objetosCambio.cambios. Возможно, это то, что мне здесь не хватает, и я не знаю, как его реализовать.

Кто-нибудь?

ответ

1

Я не думаю, что приведенный выше код может работать, idCambio вашего встраиваемого ObjetosCambioPK просто никогда не назначается, следовательно, ошибка базы данных. На самом деле я не знаю, как добиться того, что вы хотите, «полностью автоматизированным» способом (я не думаю, что это выполнимо), и тогда я бы и flush() новый Cambios, а затем установил назначенный Id на составном ключе каждый экземпляр ObjetosCambio.

+0

Спасибо за ваш ответ, я когда-то добился этого, но это было с другой архитектурой (EJB3, Jdeveloper, Toplink), поэтому я знаю, что это может сработать. В то время я использовал аннотацию @ @ IdClass вместо '@ EmbeddedId', но я читал, что это не лучший подход в наши дни, похоже, что этот @IdClass был реализован только в Hibernate из-за совместимости EJB2. Кроме того, у меня также проблемы с '@ idClass' ... поэтому я предпочитаю продолжать поиск решения для этого. Что касается вашего совета: – Steppen

+0

«Я бы так упорствовал() и запустил() новый Cambios, а затем установил назначенный идентификатор в составном ключе каждого экземпляра ObjetosCambio». Если я сделаю так, как вы говорите, разве я не рискну оставить БД в противоречивом состоянии? (при условии, что исключение происходит в режиме «ObjetosCambio») – Steppen

+0

@Steppen В случае, если исключение происходит в режиме «ObjetosCambio», транзакция будет отменена, и вы не будете в противоречивом состоянии. –