public enum NullabilityCheckType { CREATE, UPDATE, DELETE }
/** * make sure user didn't mangle the id */ public void checkId(Object object, EntityPersister persister, Serializable id, SessionImplementor session) throws HibernateException { if ( id != null && id instanceof DelayedPostInsertIdentifier ) { // this is a situation where the entity id is assigned by a post-insert generator // and was saved outside the transaction forcing it to be delayed return; } if ( persister.canExtractIdOutOfEntity() ) { Serializable oid = persister.getIdentifier( object, session ); if ( id == null ) { throw new AssertionFailure( "null id in " + persister.getEntityName() + " entry (don't flush the Session after an exception occurs)" ); } if ( !persister.getIdentifierType().isEqual( id, oid, session.getFactory() ) ) { throw new HibernateException( "identifier of an instance of " + persister.getEntityName() + " was altered from " + id + " to " + oid ); } } }
protected void evictEntityData(EntityPersister entityDescriptor) { EntityPersister rootEntityDescriptor = entityDescriptor; if ( entityDescriptor.isInherited() && ! entityDescriptor.getEntityName().equals( entityDescriptor.getRootEntityName() ) ) { rootEntityDescriptor = getSessionFactory().getMetamodel().entityPersister( entityDescriptor.getRootEntityName() ); } evictEntityData( rootEntityDescriptor.getNavigableRole(), rootEntityDescriptor.getCacheAccessStrategy() ); }
private int generateHashCode() { int result = 17; final String rootEntityName = persister.getRootEntityName(); result = 37 * result + ( rootEntityName != null ? rootEntityName.hashCode() : 0 ); result = 37 * result + persister.getIdentifierType().getHashCode( identifier, persister.getFactory() ); return result; }
private boolean sameIdentifier(final EntityKey otherKey) { return persister.getIdentifierType().isEqual( otherKey.identifier, this.identifier, persister.getFactory() ); }
public NavigableRole getRootEntityRole(EntityPersister entityDescriptor) { final String rootEntityName = entityDescriptor.getRootEntityName(); if ( entityDescriptor.getEntityName().equals( rootEntityName ) ) { return entityDescriptor.getNavigableRole(); } else { final EntityPersister rootEntityDescriptor = entityDescriptor.getFactory() .getMetamodel() .entityPersister( rootEntityName ); return rootEntityDescriptor.getNavigableRole(); } }
protected boolean checkModified(SessionImplementor session, Object newObj, Object oldObj) { if ( nonInsertableFake ) { return false; } if ( newObj == null || oldObj == null || newObj.getClass().equals( oldObj.getClass() ) ) { return !EntityTools.entitiesEqual( session, referencedEntityName, newObj, oldObj ); } // There is a chance that oldObj may reference the identifier of the old entity rather // than the entity instance itself. This happens under Session#update with a detached // entity because the database snapshot that is used to derive the prior state doesn't // return the entity instances of the to-one associations but only the identifier. // // So here we assume the method was supplied the id and we ask the persister to verify // if the value is the identifier type. If not, we assume its the entity type and // therefore resolve the identifier from the entity directly prior to simply then // doing the identifier comparison. final EntityPersister persister = session.getFactory().getMetamodel().entityPersister( referencedEntityName ); Object resolvedNewObjectId = newObj; if ( !persister.getIdentifierType().getReturnedClass().isInstance( newObj ) ) { resolvedNewObjectId = EntityTools.getIdentifier( session, referencedEntityName, newObj ); } Object resolvedOldObjectId = oldObj; if ( !persister.getIdentifierType().getReturnedClass().isInstance( oldObj ) ) { resolvedOldObjectId = EntityTools.getIdentifier( session, referencedEntityName, oldObj ); } return !Objects.deepEquals( resolvedNewObjectId, resolvedOldObjectId ); }
private static void processDereferencedCollection(PersistentCollection coll, SessionImplementor session) { final PersistenceContext persistenceContext = session.getPersistenceContext(); final CollectionEntry entry = persistenceContext.getCollectionEntry( coll ); final CollectionPersister loadedPersister = entry.getLoadedPersister(); Serializable ownerId = loadedPersister.getOwnerEntityPersister().getIdentifier( coll.getOwner(), session ); if ( ownerId == null ) { if ( session.getFactory().getSessionFactoryOptions().isIdentifierRollbackEnabled() ) { final EntityEntry ownerEntry = persistenceContext.getEntry( coll.getOwner() ); if ( ownerEntry != null ) { ownerId = ownerEntry.getId(); final EntityKey key = session.generateEntityKey( ownerId, loadedPersister.getOwnerEntityPersister() ); final Object owner = persistenceContext.getEntity( key ); if ( owner == null ) { throw new AssertionFailure(
final EventSource source = event.getSession(); final EntityPersister persister = source.getEntityPersister( event.getEntityName(), entity ); final String entityName = persister.getEntityName(); id = persister.getIdentifier( entity, source ); Serializable entityId = persister.getIdentifier( entity, source ); if ( !persister.getIdentifierType().isEqual( id, entityId, source.getFactory() ) ) { throw new HibernateException( "merge requested with id not matching id of passed entity" ); String previousFetchProfile = source.getLoadQueryInfluencers().getInternalFetchProfile(); source.getLoadQueryInfluencers().setInternalFetchProfile( "merge" ); final Serializable clonedIdentifier = (Serializable) persister.getIdentifierType() .deepCopy( id, source.getFactory() ); final Object result = source.get( entityName, clonedIdentifier ); source.getLoadQueryInfluencers().setInternalFetchProfile( previousFetchProfile ); ( (MergeContext) copyCache ).put( entity, result, true ); //before cascade! final Object target = source.getPersistenceContext().unproxy( result ); if ( target == entity ) { throw new AssertionFailure( "entity was not detached" ); if ( source.getFactory().getStatistics().isStatisticsEnabled() ) { source.getFactory().getStatistics().optimisticFailure( entityName );
private Object[] getDatabaseSnapshot(SessionImplementor session, EntityPersister persister, Serializable id) { if ( persister.isSelectBeforeUpdateRequired() ) { Object[] snapshot = session.getPersistenceContext() .getDatabaseSnapshot( id, persister ); if ( snapshot == null ) { //do we even really need this? the update will fail anyway.... if ( session.getFactory().getStatistics().isStatisticsEnabled() ) { session.getFactory().getStatistics() .optimisticFailure( persister.getEntityName() ); } throw new StaleObjectStateException( persister.getEntityName(), id ); } return snapshot; } // TODO: optimize away this lookup for entities w/o unsaved-value="undefined" final EntityKey entityKey = session.generateEntityKey( id, persister ); return session.getPersistenceContext().getCachedDatabaseSnapshot( entityKey ); } }
private void addParentChildEntityNameByPropertyAndValue(AbstractEntityInsertAction action, BatchIdentifier batchIdentifier, Type type, Object value) { if ( type.isEntityType() ) { final EntityType entityType = (EntityType) type; final String entityName = entityType.getName(); final String rootEntityName = action.getSession().getFactory().getMetamodel().entityPersister( entityName ).getRootEntityName(); else if ( type.isCollectionType() ) { CollectionType collectionType = (CollectionType) type; final SessionFactoryImplementor sessionFactory = ( (SessionImplementor) action.getSession() ) .getSessionFactory(); if ( collectionType.getElementType( sessionFactory ).isEntityType() && !sessionFactory.getMetamodel().collectionPersister( collectionType.getRole() ).isManyToMany() ) { String entityName = collectionType.getAssociatedEntityName( sessionFactory ); String rootEntityName = action.getSession().getFactory().getMetamodel().entityPersister( entityName ).getRootEntityName(); batchIdentifier.getChildEntityNames().add( entityName ); if ( !rootEntityName.equals( entityName ) ) {
private void assertEnumProperty(Class<?> entityClass, Class<?> typeClass, String propertyName, EnumType expectedType) { doInJPA( this::entityManagerFactory, entityManager -> { final SessionFactoryImplementor sessionFactory = entityManager.unwrap( SessionImplementor.class ).getSessionFactory(); final EntityPersister entityPersister = sessionFactory.getMetamodel().entityPersister( entityClass ); final EnversService enversService = sessionFactory.getServiceRegistry().getService( EnversService.class ); final String entityName = entityPersister.getEntityName(); final String auditEntityName = enversService.getAuditEntitiesConfiguration().getAuditEntityName( entityName ); final EntityPersister auditedEntityPersister = sessionFactory.getMetamodel().entityPersister( auditEntityName ); final org.hibernate.type.Type propertyType = auditedEntityPersister.getPropertyType( propertyName ); assertTyping( CustomType.class, propertyType ); final UserType userType = ( (CustomType) propertyType ).getUserType(); assertTyping( typeClass, userType ); assertTyping( org.hibernate.type.EnumType.class, userType ); switch ( expectedType ) { case STRING: assertTrue( !( (org.hibernate.type.EnumType) userType ).isOrdinal() ); break; default: assertTrue( ( (org.hibernate.type.EnumType) userType ).isOrdinal() ); break; } } ); } }
protected boolean invokeInterceptor( SessionImplementor session, Object entity, EntityEntry entry, final Object[] values, EntityPersister persister) { boolean isDirty = false; if ( entry.getStatus() != Status.DELETED ) { if ( callbackRegistry.preUpdate( entity ) ) { isDirty = copyState( entity, persister.getPropertyTypes(), values, session.getFactory() ); } } final boolean answerFromInterceptor = session.getInterceptor().onFlushDirty( entity, entry.getId(), values, entry.getLoadedState(), persister.getPropertyNames(), persister.getPropertyTypes() ); return answerFromInterceptor || isDirty; }
log.tracev( "Reassociating transient instance: {0}", MessageHelper.infoString( persister, id, event.getSession().getFactory() ) ); final EntityKey key = source.generateEntityKey( id, persister ); source.getPersistenceContext().checkUniqueness( key, object ); Object[] values = persister.getPropertyValues( object ); TypeHelper.deepCopy( values, persister.getPropertyTypes(), persister.getPropertyUpdateability(), values, source Object version = Versioning.getVersion( values, persister ); EntityEntry newEntry = source.getPersistenceContext().addEntity( object, ( persister.isMutable() ? Status.MANAGED : Status.READ_ONLY ), values, key, persister.afterReassociate( object, source );
@Override public void noCascade( EventSource session, Object parent, EntityPersister persister, Type propertyType, int propertyIndex) { if ( propertyType.isEntityType() ) { Object child = persister.getPropertyValue( parent, propertyIndex ); String childEntityName = ((EntityType) propertyType).getAssociatedEntityName( session.getFactory() ); if ( child != null && !isInManagedState( child, session ) && !(child instanceof HibernateProxy) //a proxy cannot be transient and it breaks ForeignKeys.isTransient && ForeignKeys.isTransient( childEntityName, child, null, session ) ) { String parentEntityName = persister.getEntityName(); String propertyName = persister.getPropertyNames()[propertyIndex]; throw new TransientPropertyValueException( "object references an unsaved transient instance - save the transient instance before flushing", childEntityName, parentEntityName, propertyName ); } } }
@Test @SuppressWarnings("unchecked") public void testPropertyAccessIgnoresStaticFields() { // verify that the entity persister is configured with property intValue as an Integer rather than // using the static field reference and determining the type to be String. assertTrue( sessionFactory() .getMetamodel() .entityPersister( FooEntity.class ) .getPropertyType( "intValue" ) .getReturnedClass() .isAssignableFrom( Integer.class ) ); } }
EntityKey entityKey, Object entityInstance) { final Object version = session.getPersistenceContext().getEntry( entityInstance ).getVersion(); VersionType versionType = persister.getVersionType(); final Object currentVersion; try { throw session.getFactory().getServiceRegistry().getService( JdbcServices.class ).getSqlExceptionHelper().convert( e, "Could not read version value from result set" if ( session.getFactory().getStatistics().isStatisticsEnabled() ) { session.getFactory().getStatistics().optimisticFailure( persister.getEntityName() ); throw new StaleObjectStateException( persister.getEntityName(), entityKey.getIdentifier() );
public AddWorkUnit( SessionImplementor sessionImplementor, String entityName, EnversService enversService, Serializable id, Map<String, Object> data) { super( sessionImplementor, entityName, enversService, id, RevisionType.ADD ); this.data = data; final String[] propertyNames = sessionImplementor.getFactory().getMetamodel() .entityPersister( getEntityName() ) .getPropertyNames(); this.state = ArraysTools.mapToArray( data, propertyNames ); }
SoftLock lock = null; final Object ck; final EntityDataAccess cache = persister.getCacheAccessStrategy(); if ( persister.canWriteToCache() ) { ck = cache.generateCacheKey( event.getEntityId(), persister, source.getFactory(), source.getTenantIdentifier() ); lock = persister.getCacheAccessStrategy().lockItem( source, ck, null ); if ( persister.canWriteToCache() ) { cache.unlockItem( source, ck, lock ); return event.getSession().getPersistenceContext().proxyFor( persister, keyToLoad, entity );
public CachedNaturalId(EntityPersister persister, Object[] values) { this.persister = persister; this.values = values; final int prime = 31; int hashCodeCalculation = 1; hashCodeCalculation = prime * hashCodeCalculation + persister.hashCode(); final int[] naturalIdPropertyIndexes = persister.getNaturalIdentifierProperties(); naturalIdTypes = new Type[ naturalIdPropertyIndexes.length ]; int i = 0; for ( int naturalIdPropertyIndex : naturalIdPropertyIndexes ) { final Type type = persister.getPropertyType( persister.getPropertyNames()[ naturalIdPropertyIndex ] ); naturalIdTypes[i] = type; final int elementHashCode = values[i] == null ? 0 :type.getHashCode( values[i], persister.getFactory() ); hashCodeCalculation = prime * hashCodeCalculation + elementHashCode; i++; } this.hashCode = hashCodeCalculation; }