HHH-7085 Use the in-flight state for naturalId caching
Pass the current state Object[] from the event into the SPC to use for naturalId caching
This commit is contained in:
parent
b5ba7bef42
commit
f1a54aeadf
|
@ -92,7 +92,7 @@ public final class EntityInsertAction extends AbstractEntityInsertAction {
|
|||
throw new AssertionFailure( "possible nonthreadsafe access to session" );
|
||||
}
|
||||
|
||||
entry.postInsert();
|
||||
entry.postInsert( getState() );
|
||||
|
||||
if ( persister.hasInsertGeneratedProperties() ) {
|
||||
persister.processInsertGeneratedProperties( id, instance, getState(), session );
|
||||
|
|
|
@ -1705,54 +1705,53 @@ public class StatefulPersistenceContext implements PersistenceContext {
|
|||
// NATURAL ID RESOLUTION HANDLING ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
@Override
|
||||
public void loadedStateInsertedNotification(EntityEntry entityEntry) {
|
||||
public void loadedStateInsertedNotification(EntityEntry entityEntry, Object[] state) {
|
||||
final EntityPersister persister = entityEntry.getPersister();
|
||||
if ( !persister.hasNaturalIdentifier() ) {
|
||||
// nothing to do
|
||||
return;
|
||||
}
|
||||
|
||||
final Object[] naturalIdValues = getNaturalIdValues( entityEntry, persister );
|
||||
final Object[] naturalIdValues = getNaturalIdValues( state, persister );
|
||||
|
||||
// cache
|
||||
cacheNaturalIdResolution( persister, entityEntry.getId(), naturalIdValues, CachedNaturalIdValueSource.INSERT );
|
||||
}
|
||||
|
||||
@Override
|
||||
public void loadedStateUpdatedNotification(EntityEntry entityEntry) {
|
||||
public void loadedStateUpdatedNotification(EntityEntry entityEntry, Object[] state) {
|
||||
final EntityPersister persister = entityEntry.getPersister();
|
||||
if ( !persister.hasNaturalIdentifier() ) {
|
||||
// nothing to do
|
||||
return;
|
||||
}
|
||||
|
||||
final Object[] naturalIdValues = getNaturalIdValues( entityEntry, persister );
|
||||
final Object[] naturalIdValues = getNaturalIdValues( state, persister );
|
||||
|
||||
// re-cache
|
||||
cacheNaturalIdResolution( persister, entityEntry.getId(), naturalIdValues, CachedNaturalIdValueSource.UPDATE );
|
||||
}
|
||||
|
||||
@Override
|
||||
public void loadedStateDeletedNotification(EntityEntry entityEntry) {
|
||||
public void loadedStateDeletedNotification(EntityEntry entityEntry, Object[] deletedState) {
|
||||
final EntityPersister persister = entityEntry.getPersister();
|
||||
if ( !persister.hasNaturalIdentifier() ) {
|
||||
// nothing to do
|
||||
return;
|
||||
}
|
||||
|
||||
final Object[] naturalIdValues = getNaturalIdValues( entityEntry, persister );
|
||||
final Object[] naturalIdValues = getNaturalIdValues( deletedState, persister );
|
||||
|
||||
// evict from cache
|
||||
evictNaturalIdResolution( persister, entityEntry.getId(), naturalIdValues );
|
||||
}
|
||||
|
||||
private Object[] getNaturalIdValues(EntityEntry entityEntry, EntityPersister persister) {
|
||||
private Object[] getNaturalIdValues(Object[] state, EntityPersister persister) {
|
||||
final int[] naturalIdPropertyIndexes = persister.getNaturalIdentifierProperties();
|
||||
final Object[] naturalIdValues = new Object[naturalIdPropertyIndexes.length];
|
||||
|
||||
final Object[] loadedState = entityEntry.getLoadedState();
|
||||
for ( int i = 0; i < naturalIdPropertyIndexes.length; i++ ) {
|
||||
naturalIdValues[i] = loadedState[naturalIdPropertyIndexes[i]];
|
||||
naturalIdValues[i] = state[naturalIdPropertyIndexes[i]];
|
||||
}
|
||||
|
||||
return naturalIdValues;
|
||||
|
@ -1990,27 +1989,38 @@ public class StatefulPersistenceContext implements PersistenceContext {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void evictNaturalIdResolution(EntityPersister persister, final Serializable pk, Object[] naturalIdValues) {
|
||||
private void evictNaturalIdResolution(EntityPersister persister, final Serializable pk, Object[] deletedNaturalIdValues) {
|
||||
if ( !persister.hasNaturalIdentifier() ) {
|
||||
throw new IllegalArgumentException( "Entity did not define a natural-id" );
|
||||
throw new IllegalArgumentException( "Entity did not define a natrual-id" );
|
||||
}
|
||||
if ( persister.getNaturalIdentifierProperties().length != naturalIdValues.length ) {
|
||||
if ( persister.getNaturalIdentifierProperties().length != deletedNaturalIdValues.length ) {
|
||||
throw new IllegalArgumentException( "Mismatch between expected number of natural-id values and found." );
|
||||
}
|
||||
|
||||
NaturalIdResolutionCache entityNaturalIdResolutionCache = naturalIdResolutionCacheMap.get( persister );
|
||||
Object[] sessionCachedNaturalIdValues = null;
|
||||
if ( entityNaturalIdResolutionCache != null ) {
|
||||
final LocalNaturalIdCacheKey localNaturalIdCacheKey = new LocalNaturalIdCacheKey( persister,
|
||||
naturalIdValues );
|
||||
entityNaturalIdResolutionCache.pkToNaturalIdMap.remove( pk );
|
||||
entityNaturalIdResolutionCache.naturalIdToPkMap.remove( localNaturalIdCacheKey );
|
||||
final LocalNaturalIdCacheKey localNaturalIdCacheKey = entityNaturalIdResolutionCache.pkToNaturalIdMap
|
||||
.remove( pk );
|
||||
if ( localNaturalIdCacheKey != null ) {
|
||||
entityNaturalIdResolutionCache.naturalIdToPkMap.remove( localNaturalIdCacheKey );
|
||||
sessionCachedNaturalIdValues = localNaturalIdCacheKey.getValues();
|
||||
}
|
||||
}
|
||||
|
||||
if ( persister.hasNaturalIdCache() ) {
|
||||
final NaturalIdRegionAccessStrategy naturalIdCacheAccessStrategy = persister.getNaturalIdCacheAccessStrategy();
|
||||
final NaturalIdCacheKey naturalIdCacheKey = new NaturalIdCacheKey( naturalIdValues, persister, session );
|
||||
final NaturalIdRegionAccessStrategy naturalIdCacheAccessStrategy = persister
|
||||
.getNaturalIdCacheAccessStrategy();
|
||||
final NaturalIdCacheKey naturalIdCacheKey = new NaturalIdCacheKey( deletedNaturalIdValues, persister,
|
||||
session );
|
||||
naturalIdCacheAccessStrategy.evict( naturalIdCacheKey );
|
||||
|
||||
if ( sessionCachedNaturalIdValues != null
|
||||
&& !Arrays.equals( sessionCachedNaturalIdValues, deletedNaturalIdValues ) ) {
|
||||
final NaturalIdCacheKey sessionNaturalIdCacheKey = new NaturalIdCacheKey( sessionCachedNaturalIdValues,
|
||||
persister, session );
|
||||
naturalIdCacheAccessStrategy.evict( sessionNaturalIdCacheKey );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -241,7 +241,7 @@ public final class EntityEntry implements Serializable {
|
|||
.getCustomEntityDirtinessStrategy()
|
||||
.resetDirty( entity, getPersister(), (Session) persistenceContext.getSession() );
|
||||
|
||||
notifyLoadedStateUpdated();
|
||||
notifyLoadedStateUpdated( updatedState );
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -253,17 +253,17 @@ public final class EntityEntry implements Serializable {
|
|||
status = Status.GONE;
|
||||
existsInDatabase = false;
|
||||
|
||||
notifyLoadedStateDeleted();
|
||||
notifyLoadedStateDeleted( deletedState );
|
||||
}
|
||||
|
||||
/**
|
||||
* After actually inserting a row, record the fact that the instance exists on the
|
||||
* database (needed for identity-column key generation)
|
||||
*/
|
||||
public void postInsert() {
|
||||
public void postInsert(Object[] insertedState) {
|
||||
existsInDatabase = true;
|
||||
|
||||
notifyLoadedStateInserted();
|
||||
notifyLoadedStateInserted( insertedState );
|
||||
}
|
||||
|
||||
public boolean isNullifiable(boolean earlyInsert, SessionImplementor session) {
|
||||
|
@ -360,7 +360,7 @@ public final class EntityEntry implements Serializable {
|
|||
}
|
||||
setStatus( Status.MANAGED );
|
||||
loadedState = getPersister().getPropertyValues( entity );
|
||||
notifyLoadedStateUpdated();
|
||||
notifyLoadedStateUpdated( loadedState );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -374,28 +374,28 @@ public final class EntityEntry implements Serializable {
|
|||
return loadedWithLazyPropertiesUnfetched;
|
||||
}
|
||||
|
||||
private void notifyLoadedStateUpdated() {
|
||||
private void notifyLoadedStateUpdated(Object[] state) {
|
||||
if ( persistenceContext == null ) {
|
||||
throw new HibernateException( "PersistenceContext was null on attempt to update loaded state" );
|
||||
}
|
||||
|
||||
persistenceContext.loadedStateUpdatedNotification( this );
|
||||
persistenceContext.loadedStateUpdatedNotification( this, state );
|
||||
}
|
||||
|
||||
private void notifyLoadedStateInserted() {
|
||||
private void notifyLoadedStateInserted(Object[] state) {
|
||||
if ( persistenceContext == null ) {
|
||||
throw new HibernateException( "PersistenceContext was null on attempt to insert loaded state" );
|
||||
}
|
||||
|
||||
persistenceContext.loadedStateInsertedNotification( this );
|
||||
persistenceContext.loadedStateInsertedNotification( this, state );
|
||||
}
|
||||
|
||||
private void notifyLoadedStateDeleted() {
|
||||
private void notifyLoadedStateDeleted(Object[] deletedState) {
|
||||
if ( persistenceContext == null ) {
|
||||
throw new HibernateException( "PersistenceContext was null on attempt to delete loaded state" );
|
||||
}
|
||||
|
||||
persistenceContext.loadedStateDeletedNotification( this );
|
||||
persistenceContext.loadedStateDeletedNotification( this, deletedState );
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -683,11 +683,11 @@ public interface PersistenceContext {
|
|||
*/
|
||||
public boolean wasInsertedDuringTransaction(EntityPersister persister, Serializable id);
|
||||
|
||||
public void loadedStateUpdatedNotification(EntityEntry entityEntry);
|
||||
public void loadedStateUpdatedNotification(EntityEntry entityEntry, Object[] state);
|
||||
|
||||
public void loadedStateInsertedNotification(EntityEntry entityEntry);
|
||||
public void loadedStateInsertedNotification(EntityEntry entityEntry, Object[] state);
|
||||
|
||||
public void loadedStateDeletedNotification(EntityEntry entityEntry);
|
||||
public void loadedStateDeletedNotification(EntityEntry entityEntry, Object[] deletedState);
|
||||
|
||||
public Object[] findCachedNaturalId(EntityPersister persister, Serializable pk);
|
||||
|
||||
|
@ -704,5 +704,4 @@ public interface PersistenceContext {
|
|||
|
||||
public void cacheNaturalIdResolution(EntityPersister persister, Serializable pk, Object[] naturalId, CachedNaturalIdValueSource valueSource);
|
||||
|
||||
public void evictNaturalIdResolution(EntityPersister persister, final Serializable pk, Object[] naturalIdValues );
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue