Skip to main content

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [List Home]
RE: [eclipselink-users] RE: Strange issue in merging changes.

Hello Chris,

 

Also,

 

>>Also, are you saying that the entity returned from em.merge doesn't have the changes that are in the entity passed in, or do the changes revert later on? 

 

Yes, the entity returned from em.merge doesn’t have the changes that are in the entity passed in. And while debugging I noticed that the changes are maintained until the child which has ManyToOne (Cascade=CascadeType.REFRESH) with parent is being merged for changes in ObjectBuilder. As soon as the execution starts to merge the changes in the child, after the control comes back to the parent merging, the changes are lost.

 

 

>>Also, what other settings are you using (customizers, event listeners, properties that change cache behavior etc)?  If something you do causes a refresh on Child, this will force a refresh on the parent >>as well (with the cascade refresh option), causing you to loose the changes. 

 

I am not using any event listeners, however using session customizer to add a custom logger to the EL but I don’t suspect this would affect cache behavior. I have observed that if child getter is called and child is accessed or children are loaded in EAGER fashion in OneToMany relation, this issue occurs.

 

>>Are you able to see why the Child is referencing a different instance  of the Parent than is referencing it?  This shouldn't happen, but depending on how you are managing your entities and setting >>relations though, its not disallowed. 

 

In the debug mode, I see that the entity hashcode for the parent is same as that of the referred parent instance from within child. Also before merge if I inspect the parent reference from within child I see all the data intact. However after merge i.e. ObjectBuilder class execution, the changes to the parent are lost.

 

>>Can you set the eclipselink.logging.level property to Finest and show the log generated up to where you check the merged parent for the changes.

I have generated the log, however the log created is huge since our entity structure is deep in hierarchy. Hence I would create a simple use case with which I can simulate the issue and I will share the generated log. Still for your reference I have attached two log files with the real entities, one with log statements after service is invoked and before em.merge is called and the other after merge is called.

 

Also is there any way I can show you the issue simulation, that would certainly help me to reduce the time in resolving it.

 

Thanks for your help,

Shashi

 

 

 

From: eclipselink-users-bounces@xxxxxxxxxxx [mailto:eclipselink-users-bounces@xxxxxxxxxxx] On Behalf Of Shashikant Kale
Sent: Thursday, July 29, 2010 11:27 AM
To: EclipseLink User Discussions
Subject: RE: [eclipselink-users] RE: Strange issue in merging changes.

 

Hello Chris,

 

I didn’t get the Tim’s mail you referred below. Not sure if it didn’t reach me somehow.

 

However what difference I find using @Transactional(readOnly=false) (this doesn’t work i.e. parent entity changes are lost) and @Transactional (readOnly=true) (This works all fine) is that the former way the early transaction is started on the UnitOfWork. The following code is getting executed in the first case. This is EL specific code which is called in the EclipseLink integration code in spring orm.

 

                  UnitOfWork uow = (UnitOfWork) getSession(entityManager);

                  uow.beginEarlyTransaction();

 

Due to beginEarlyTransaction call on the UoW I find that if a child entity is accessed meanwhile (or loaded due to EAGER fetchType set on the OneToMany relation) which has relation with parent as

 

ManyToOne with cascade type as REFRESH the changes are lost when the execution reaches in ObjectBuilder for merging the changes in the child entity.

 

I will try out your suggestion for debugging and answer your queries below and will also provide log set at Finer level in some time.

 

Thanks so much for your help,

Shashi

 

From: eclipselink-users-bounces@xxxxxxxxxxx [mailto:eclipselink-users-bounces@xxxxxxxxxxx] On Behalf Of Christopher Delahunt
Sent: Wednesday, July 28, 2010 7:31 PM
To: EclipseLink User Discussions
Subject: Re: [eclipselink-users] RE: Strange issue in merging changes.

 

Hello Shashi,

I'm not all that familiar with Spring, so I don't know if this could be something to do with its interactions, but you might try the suggestion Tim made about using propagation on your transaction. 

Looking at EclipseLink though, it seems you are able to debug the EclipseLink-Spring integration code and the application.  Are you able to see why the Child is referencing a different instance
of the Parent than is referencing it?  This shouldn't happen, but depending on how you are managing your entities and setting relations though, its not disallowed.  Also, are you saying that the entity
returned from em.merge doesn't have the changes that are in the entity passed in, or do the changes revert later on?  Does the collection of children include new ones?

Also, what other settings are you using (customizers, event listeners, properties that change cache behavior etc)?  If something you do causes a refresh on Child, this will force a refresh on the parent as well (with the cascade refresh option), causing you to loose the changes. 
Can you set the eclipselink.logging.level property to Finest and show the log generated up to where you check the merged parent for the changes.

Best Regards,
Chris


On 28/07/2010 9:10 AM, Shashikant Kale wrote:

Can an EL dev team member please share thought on why this would be happening. This has come as a critical issue for us and we are struggling to get an alternative to make it work.

 

Regards,
Shashi

 

From: eclipselink-users-bounces@xxxxxxxxxxx [mailto:eclipselink-users-bounces@xxxxxxxxxxx] On Behalf Of Shashikant Kale
Sent: Tuesday, July 27, 2010 4:35 PM
To: EclipseLink User Discussions
Subject: [eclipselink-users] RE: Strange issue in merging changes.

 

Also,

 

Figured out that, in spring, if a transaction is writable, i.e. readOnly=false, an early transaction is started on the current UoW. The code is

 

            if (!definition.isReadOnly() && !this.lazyDatabaseTransaction) {

                  // This is the magic bit. As with the existing Spring TopLink integration,

                  // begin an early transaction to force EclipseLink to get a JDBC Connection

                  // so that Spring can manage transactions with JDBC as well as EclipseLink.

                  UnitOfWork uow = (UnitOfWork) getSession(entityManager);

                  uow.beginEarlyTransaction();

            }

And it is writable, an early transaction is started and the changes done to the parent are lost during merge. I couldn’t figure out how this changes the behavior, but looks like it does.

 

Can somebody please throw some light on this?

 

Thanks,

Shashi

 

From: eclipselink-users-bounces@xxxxxxxxxxx [mailto:eclipselink-users-bounces@xxxxxxxxxxx] On Behalf Of Shashikant Kale
Sent: Tuesday, July 27, 2010 2:34 PM
To: EclipseLink User Discussions
Subject: [eclipselink-users] Strange issue in merging changes.

 

Hi,

 

We have been using Eclipselink 1.2.0 with Spring.

 

We have configured Spring transaction interceptor (Using @Transactional(readOnly=false)) to manage the transactions in our Service code.

 

Parent  {

      @OneToMany(mappedBy="parent", cascade={CascadeType.ALL},  fetch=FetchType.EAGER)

      @org.eclipse.persistence.annotations.PrivateOwned

protected List<Child> children = new ArrayList<Child>();

}

 

Child {

      @ManyToOne(cascade={CascadeType.REFRESH}) @JoinColumn(name="SOME_CHILD_ID")

      protected Parent parent;

}

 

Service {

                @Transactional (readOnly=false)

                public void serviceMethod (Parent parent){

 

                                parent.setData(“data”);

                                ……

                                ……

                                Parent merged = em.merge(parent);

 

                                // Here the merged parent has lost the changes i.e. data

}

}

 

However I am seeing a strange issue in merging the changes for an entity which has a child entity with OneToMany relation. The changes done to the entity are getting lost. When I debugged into EL code, I went inside merge code where changes are calculated for an entity, however in org.eclipse.persistence.internal.descriptors.ObjectBuilder class I find that when the OneToMany mapping is being merged in the method while traversing through the DatabaseMapping, it calls further to merge changes in the Child, the target entity instance i.e. child entity instance doesn’t contain the latest parent entity with the changes. Hence the changes of the parent are getting lost.

 

public void mergeIntoObject(Object target, boolean isUnInitialized, Object source, MergeManager mergeManager, boolean cascadeOnly, boolean isTargetCloneOfOriginal)

 

However if I remove CascadeType.REFRESH in the ManyToOne mapping inside Child it works fine. Also if I mark the service method as @Transactional (readOnly=true) it works fine either.

 

Is there anything wrong in the entity relationship setup?

 

Kindly let me know.

 

TIA,
Shashi

 
 
 


 
 
 
_______________________________________________
eclipselink-users mailing list
eclipselink-users@xxxxxxxxxxx
https://dev.eclipse.org/mailman/listinfo/eclipselink-users
  

Back to the top