Search in sources :

Example 1 with AggregateAttributeChangeListener

use of org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener in project eclipselink by eclipse-ee4j.

the class SimpleTypes_AggregateObject method verifyChangTracking.

@Test
public void verifyChangTracking() {
    persistSimpleA();
    DynamicType simpleTypeA = dynamicHelper.getType("SimpleA");
    Assert.assertNotNull(simpleTypeA);
    UnitOfWork uow = session.acquireUnitOfWork();
    ReadObjectQuery roq = dynamicHelper.newReadObjectQuery("SimpleA");
    roq.setSelectionCriteria(roq.getExpressionBuilder().get("id").equal(1));
    DynamicEntityImpl sharedA = (DynamicEntityImpl) session.executeQuery(roq);
    assertNotNull(sharedA);
    assertNull(sharedA._persistence_getPropertyChangeListener());
    DynamicEntityImpl a = (DynamicEntityImpl) uow.executeQuery(roq);
    assertNotNull(a);
    assertNotNull(a._persistence_getPropertyChangeListener());
    DynamicEntityImpl c = a.<DynamicEntityImpl>get("c");
    assertNotNull(c);
    assertNotNull(c._persistence_getPropertyChangeListener());
    assertTrue(c._persistence_getPropertyChangeListener() instanceof AggregateAttributeChangeListener);
    uow.release();
}
Also used : UnitOfWork(org.eclipse.persistence.sessions.UnitOfWork) DynamicEntityImpl(org.eclipse.persistence.internal.dynamic.DynamicEntityImpl) ReadObjectQuery(org.eclipse.persistence.queries.ReadObjectQuery) DynamicType(org.eclipse.persistence.dynamic.DynamicType) AggregateAttributeChangeListener(org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener) Test(org.junit.Test)

Example 2 with AggregateAttributeChangeListener

use of org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener in project eclipselink by eclipse-ee4j.

the class AggregateMapping method updateChangeRecord.

/**
 * INTERNAL:
 * Either create a new change record or update the change record with the new value.
 * This is used by attribute change tracking.
 */
@Override
public void updateChangeRecord(Object sourceClone, Object newValue, Object oldValue, ObjectChangeSet objectChangeSet, UnitOfWorkImpl uow) throws DescriptorException {
    // This method will be called when either the referenced aggregate has
    // been changed or a component of the referenced aggregate has been changed
    // this case is determined by the value of the sourceClone
    boolean isNewRecord = false;
    AggregateChangeRecord changeRecord = (AggregateChangeRecord) objectChangeSet.getChangesForAttributeNamed(this.getAttributeName());
    if (changeRecord == null) {
        changeRecord = new AggregateChangeRecord(objectChangeSet);
        changeRecord.setAttribute(this.getAttributeName());
        changeRecord.setMapping(this);
        objectChangeSet.addChange(changeRecord);
        isNewRecord = true;
    }
    if (sourceClone.getClass().equals(objectChangeSet.getClassType(uow))) {
        if (isNewRecord) {
            changeRecord.setOldValue(oldValue);
        }
        // event was fired on the parent to the aggregate, the attribute value changed.
        ClassDescriptor referenceDescriptor = getReferenceDescriptor(newValue, uow);
        if (newValue == null) {
            // attribute set to null
            changeRecord.setChangedObject(null);
            if (referenceDescriptor.getObjectChangePolicy().isAttributeChangeTrackingPolicy()) {
                if (((ChangeTracker) oldValue)._persistence_getPropertyChangeListener() != null) {
                    // need to detach listener
                    ((AggregateAttributeChangeListener) ((ChangeTracker) oldValue)._persistence_getPropertyChangeListener()).setParentListener(null);
                }
            }
            return;
        } else {
            // attribute set to new aggregate
            UnitOfWorkChangeSet uowChangeSet = (UnitOfWorkChangeSet) objectChangeSet.getUOWChangeSet();
            // force comparison change detection to build changeset.
            ObjectChangeSet aggregateChangeSet = (ObjectChangeSet) uowChangeSet.getObjectChangeSetForClone(newValue);
            if (aggregateChangeSet != null && aggregateChangeSet.getDescriptor() == referenceDescriptor) {
                // old differences must be thrown away because difference is between old value and new value
                aggregateChangeSet.clear(true);
            }
            // make sure the listener is initialized
            if (referenceDescriptor.getObjectChangePolicy().isAttributeChangeTrackingPolicy()) {
                if (oldValue != null && ((ChangeTracker) oldValue)._persistence_getPropertyChangeListener() != null) {
                    // need to detach listener
                    ((AggregateAttributeChangeListener) ((ChangeTracker) oldValue)._persistence_getPropertyChangeListener()).setParentListener(null);
                }
                // need to attach new listener.
                AggregateAttributeChangeListener newListener = (AggregateAttributeChangeListener) ((ChangeTracker) newValue)._persistence_getPropertyChangeListener();
                if (newListener == null) {
                    newListener = new AggregateAttributeChangeListener(referenceDescriptor, uow, ((AttributeChangeListener) ((ChangeTracker) sourceClone)._persistence_getPropertyChangeListener()), this.getAttributeName(), newValue);
                    ((ChangeTracker) newValue)._persistence_setPropertyChangeListener(newListener);
                }
                newListener.setParentListener((AttributeChangeListener) ((ChangeTracker) sourceClone)._persistence_getPropertyChangeListener());
                if (changeRecord.getChangedObject() != null && changeRecord.getChangedObject().hasChanges()) {
                    // the oldValue has been already changed - get the original oldValue.
                    oldValue = changeRecord.getOldValue();
                }
                if (oldValue != null) {
                    if (referenceDescriptor != getReferenceDescriptor(oldValue, uow)) {
                        // oldValue and newValue belong to different types - have to start from scratch.
                        oldValue = null;
                    }
                }
            }
            // force comparison change detection to build changeset.
            changeRecord.setChangedObject(referenceDescriptor.getObjectChangePolicy().createObjectChangeSetThroughComparison(newValue, oldValue, uowChangeSet, (oldValue == null), uow, referenceDescriptor));
            // process nested aggregates
            for (DatabaseMapping mapping : referenceDescriptor.getMappings()) {
                if (mapping.isAggregateObjectMapping()) {
                    Object nestedNewValue = mapping.getAttributeValueFromObject(newValue);
                    Object nestedOldValue = null;
                    if (oldValue != null) {
                        nestedOldValue = mapping.getAttributeValueFromObject(oldValue);
                    }
                    // bug #413120 - update nested change record only if the value is different
                    if (nestedNewValue != nestedOldValue) {
                        mapping.updateChangeRecord(newValue, nestedNewValue, nestedOldValue, (org.eclipse.persistence.internal.sessions.ObjectChangeSet) changeRecord.getChangedObject(), uow);
                    }
                }
            }
            referenceDescriptor.getObjectChangePolicy().setChangeSetOnListener((ObjectChangeSet) changeRecord.getChangedObject(), newValue);
        }
    } else {
        // a value was set on the aggregate but the aggregate was not changed.
        if (referenceDescriptor.getObjectChangePolicy().isAttributeChangeTrackingPolicy()) {
            // The aggregate that is referenced is Attribute Change Tracked as well.
            changeRecord.setChangedObject(((AggregateAttributeChangeListener) ((ChangeTracker) sourceClone)._persistence_getPropertyChangeListener()).getObjectChangeSet());
        } else {
            // not tracked at attribute level, lets force build a changeset then.
            changeRecord.setChangedObject(referenceDescriptor.getObjectChangePolicy().createObjectChangeSetThroughComparison(sourceClone, null, (UnitOfWorkChangeSet) objectChangeSet.getUOWChangeSet(), true, uow, referenceDescriptor));
        }
    }
}
Also used : org.eclipse.persistence.internal.sessions(org.eclipse.persistence.internal.sessions) ClassDescriptor(org.eclipse.persistence.descriptors.ClassDescriptor) AggregateAttributeChangeListener(org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener) ChangeTracker(org.eclipse.persistence.descriptors.changetracking.ChangeTracker)

Example 3 with AggregateAttributeChangeListener

use of org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener in project eclipselink by eclipse-ee4j.

the class SimpleTypes_AggregateObject method verifyChangTracking.

@Test
public void verifyChangTracking() {
    persistSimpleA();
    DynamicTypeImpl simpleTypeA = (DynamicTypeImpl) helper.getType("SimpleA");
    assertNotNull(simpleTypeA);
    EntityManager em = emf.createEntityManager();
    em.getTransaction().begin();
    DynamicEntityImpl a = (DynamicEntityImpl) em.find(simpleTypeA.getJavaClass(), 1);
    assertNotNull(a);
    assertNotNull(a._persistence_getPropertyChangeListener());
    DynamicEntityImpl c = a.<DynamicEntityImpl>get("c");
    assertNotNull(c);
    assertNotNull(c._persistence_getPropertyChangeListener());
    assertTrue(c._persistence_getPropertyChangeListener() instanceof AggregateAttributeChangeListener);
    em.getTransaction().rollback();
    em.close();
}
Also used : EntityManager(jakarta.persistence.EntityManager) DynamicEntityImpl(org.eclipse.persistence.internal.dynamic.DynamicEntityImpl) AggregateAttributeChangeListener(org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener) DynamicTypeImpl(org.eclipse.persistence.internal.dynamic.DynamicTypeImpl) Test(org.junit.Test)

Aggregations

AggregateAttributeChangeListener (org.eclipse.persistence.internal.descriptors.changetracking.AggregateAttributeChangeListener)3 DynamicEntityImpl (org.eclipse.persistence.internal.dynamic.DynamicEntityImpl)2 Test (org.junit.Test)2 EntityManager (jakarta.persistence.EntityManager)1 ClassDescriptor (org.eclipse.persistence.descriptors.ClassDescriptor)1 ChangeTracker (org.eclipse.persistence.descriptors.changetracking.ChangeTracker)1 DynamicType (org.eclipse.persistence.dynamic.DynamicType)1 DynamicTypeImpl (org.eclipse.persistence.internal.dynamic.DynamicTypeImpl)1 org.eclipse.persistence.internal.sessions (org.eclipse.persistence.internal.sessions)1 ReadObjectQuery (org.eclipse.persistence.queries.ReadObjectQuery)1 UnitOfWork (org.eclipse.persistence.sessions.UnitOfWork)1