Search in sources :

Example 1 with Stage

use of org.hibernate.reactive.stage.Stage in project hibernate-reactive by hibernate.

the class ReactiveAbstractEntityPersister method updateReactive.

default CompletionStage<Void> updateReactive(final Serializable id, final Object[] fields, int[] paramDirtyFields, final boolean hasDirtyCollection, final Object[] oldFields, final Object oldVersion, final Object object, final Object rowId, final SharedSessionContractImplementor session) {
    CompletionStage<Void> stage = voidFuture();
    CompletionStage<int[]> dirtyFieldsStage = completedFuture(paramDirtyFields);
    // apply any pre-update in-memory value generation
    if (delegate().getEntityMetamodel().hasPreUpdateGeneratedValues()) {
        final InMemoryValueGenerationStrategy[] valueGenerationStrategies = delegate().getEntityMetamodel().getInMemoryValueGenerationStrategies();
        int valueGenerationStrategiesSize = valueGenerationStrategies.length;
        if (valueGenerationStrategiesSize != 0) {
            int[] fieldsPreUpdateNeeded = new int[valueGenerationStrategiesSize];
            int count = 0;
            for (int i = 0; i < valueGenerationStrategiesSize; i++) {
                final int index = i;
                if (valueGenerationStrategies[i] != null && valueGenerationStrategies[i].getGenerationTiming().includesUpdate()) {
                    stage = stage.thenCompose(v -> generateValue(object, session, valueGenerationStrategies[index]).thenAccept(value -> setFieldValue(fields, object, index, value)));
                    fieldsPreUpdateNeeded[count++] = i;
                }
            }
            final int finalCount = count;
            dirtyFieldsStage = stage.thenApply(v -> paramDirtyFields != null ? join(paramDirtyFields, trim(fieldsPreUpdateNeeded, finalCount)) : null);
        }
    }
    return dirtyFieldsStage.thenCompose(dirtyFields -> {
        // note: dirtyFields==null means we had no snapshot, and we couldn't get one using select-before-update
        // oldFields==null just means we had no snapshot to begin with (we might have used select-before-update to get the dirtyFields)
        final boolean[] tableUpdateNeeded = delegate().getTableUpdateNeeded(dirtyFields, hasDirtyCollection);
        final int span = delegate().getTableSpan();
        final boolean[] propsToUpdate;
        final String[] updateStrings;
        EntityEntry entry = session.getPersistenceContextInternal().getEntry(object);
        // in the process of being deleted.
        if (entry == null && !delegate().isMutable()) {
            throw log.updatingImmutableEntityThatsNotInTheSession();
        }
        if ((delegate().getEntityMetamodel().isDynamicUpdate() && dirtyFields != null)) {
            // We need to generate the UPDATE SQL when dynamic-update="true"
            propsToUpdate = delegate().getPropertiesToUpdate(dirtyFields, hasDirtyCollection);
            // don't need to check laziness (dirty checking algorithm handles that)
            updateStrings = new String[span];
            for (int j = 0; j < span; j++) {
                final boolean useRowId = j == 0 && rowId != null;
                updateStrings[j] = tableUpdateNeeded[j] ? delegate().generateUpdateString(propsToUpdate, j, oldFields, useRowId) : null;
            }
        } else if (!delegate().isModifiableEntity(entry)) {
            // We need to generate UPDATE SQL when a non-modifiable entity (e.g., read-only or immutable)
            // needs:
            // - to have references to transient entities set to null before being deleted
            // - to have version incremented do to a "dirty" association
            // If dirtyFields == null, then that means that there are no dirty properties to
            // to be updated; an empty array for the dirty fields needs to be passed to
            // getPropertiesToUpdate() instead of null.
            propsToUpdate = delegate().getPropertiesToUpdate(dirtyFields == null ? ArrayHelper.EMPTY_INT_ARRAY : dirtyFields, hasDirtyCollection);
            // don't need to check laziness (dirty checking algorithm handles that)
            updateStrings = new String[span];
            for (int j = 0; j < span; j++) {
                final boolean useRowId = j == 0 && rowId != null;
                updateStrings[j] = tableUpdateNeeded[j] ? delegate().generateUpdateString(propsToUpdate, j, oldFields, useRowId) : null;
            }
        } else {
            // For the case of dynamic-update="false", or no snapshot, we use the static SQL
            boolean hasUninitializedLazy = delegate().hasUninitializedLazyProperties(object);
            updateStrings = getUpdateStrings(rowId != null, hasUninitializedLazy);
            propsToUpdate = delegate().getPropertyUpdateability(object);
        }
        // Now update only the tables with dirty properties (and the table with the version number)
        return loop(0, span, i -> tableUpdateNeeded[i], table -> updateOrInsertReactive(id, fields, oldFields, table == 0 ? rowId : null, propsToUpdate, table, oldVersion, updateStrings[table], session));
    });
}
Also used : Arrays(java.util.Arrays) CompletionStages.completedFuture(org.hibernate.reactive.util.impl.CompletionStages.completedFuture) ReactiveDynamicBatchingEntityLoaderBuilder(org.hibernate.reactive.loader.entity.impl.ReactiveDynamicBatchingEntityLoaderBuilder) Expectations.appropriateExpectation(org.hibernate.jdbc.Expectations.appropriateExpectation) EventSource(org.hibernate.event.spi.EventSource) Log(org.hibernate.reactive.logging.impl.Log) PersistenceContext(org.hibernate.engine.spi.PersistenceContext) LoggerFactory(org.hibernate.reactive.logging.impl.LoggerFactory) ReactiveConnectionSupplier(org.hibernate.reactive.session.ReactiveConnectionSupplier) NonIdentifierAttribute(org.hibernate.tuple.NonIdentifierAttribute) PersistentCollection(org.hibernate.collection.spi.PersistentCollection) JDBCException(org.hibernate.JDBCException) PersistentAttributeInterceptor(org.hibernate.engine.spi.PersistentAttributeInterceptor) ResultSet(java.sql.ResultSet) SessionFactoryImpl(org.hibernate.internal.SessionFactoryImpl) CompletionStages.voidFuture(org.hibernate.reactive.util.impl.CompletionStages.voidFuture) SessionFactoryImplementor(org.hibernate.engine.spi.SessionFactoryImplementor) Mutiny(org.hibernate.reactive.mutiny.Mutiny) LockOptions(org.hibernate.LockOptions) Attribute(javax.persistence.metamodel.Attribute) PersistentAttributeInterceptable(org.hibernate.engine.spi.PersistentAttributeInterceptable) MethodHandles(java.lang.invoke.MethodHandles) StaleObjectStateException(org.hibernate.StaleObjectStateException) LazyAttributeDescriptor(org.hibernate.bytecode.enhance.spi.interceptor.LazyAttributeDescriptor) Set(java.util.Set) ReactiveEntityLoader(org.hibernate.reactive.loader.entity.impl.ReactiveEntityLoader) MutinyValueGenerator(org.hibernate.reactive.tuple.MutinyValueGenerator) PreparedStatement(java.sql.PreparedStatement) Serializable(java.io.Serializable) LoadQueryInfluencers(org.hibernate.engine.spi.LoadQueryInfluencers) ArrayHelper(org.hibernate.internal.util.collections.ArrayHelper) Lockable(org.hibernate.persister.entity.Lockable) MessageHelper.infoString(org.hibernate.pretty.MessageHelper.infoString) List(java.util.List) CompletionStage(java.util.concurrent.CompletionStage) Expectation(org.hibernate.jdbc.Expectation) Dialect(org.hibernate.dialect.Dialect) CompletionStages.loop(org.hibernate.reactive.util.impl.CompletionStages.loop) AbstractEntityPersister(org.hibernate.persister.entity.AbstractEntityPersister) SessionImplementor(org.hibernate.engine.spi.SessionImplementor) Update(org.hibernate.sql.Update) HibernateException(org.hibernate.HibernateException) PreparedStatementAdaptor(org.hibernate.reactive.adaptor.impl.PreparedStatementAdaptor) SharedSessionContractImplementor(org.hibernate.engine.spi.SharedSessionContractImplementor) AbstractEntityPersister.determineValueNullness(org.hibernate.persister.entity.AbstractEntityPersister.determineValueNullness) OptimisticLockStyle(org.hibernate.engine.OptimisticLockStyle) AssertionFailure(org.hibernate.AssertionFailure) CompletionStages.logSqlException(org.hibernate.reactive.util.impl.CompletionStages.logSqlException) Session(org.hibernate.Session) StageSessionFactoryImpl(org.hibernate.reactive.stage.impl.StageSessionFactoryImpl) InMemoryValueGenerationStrategy(org.hibernate.tuple.InMemoryValueGenerationStrategy) EntityType(org.hibernate.type.EntityType) UniqueEntityLoader(org.hibernate.loader.entity.UniqueEntityLoader) MultiLoadOptions(org.hibernate.persister.entity.MultiLoadOptions) SQLException(java.sql.SQLException) PreparedStatementAdaptor.bind(org.hibernate.reactive.adaptor.impl.PreparedStatementAdaptor.bind) StageValueGenerator(org.hibernate.reactive.tuple.StageValueGenerator) ArrayHelper.trim(org.hibernate.internal.util.collections.ArrayHelper.trim) StageSessionImpl(org.hibernate.reactive.stage.impl.StageSessionImpl) ReactiveSession(org.hibernate.reactive.session.ReactiveSession) ArrayHelper.join(org.hibernate.internal.util.collections.ArrayHelper.join) MutinySessionFactoryImpl(org.hibernate.reactive.mutiny.impl.MutinySessionFactoryImpl) LockMode(org.hibernate.LockMode) Iterator(java.util.Iterator) Parameters(org.hibernate.reactive.pool.impl.Parameters) Versioning(org.hibernate.engine.internal.Versioning) SimpleSelect(org.hibernate.sql.SimpleSelect) MutinySessionImpl(org.hibernate.reactive.mutiny.impl.MutinySessionImpl) ValueGenerator(org.hibernate.tuple.ValueGenerator) CompletionStages.returnOrRethrow(org.hibernate.reactive.util.impl.CompletionStages.returnOrRethrow) EntityKey(org.hibernate.engine.spi.EntityKey) Delete(org.hibernate.sql.Delete) IdentifierGeneration.castToIdentifierType(org.hibernate.reactive.id.impl.IdentifierGeneration.castToIdentifierType) AbstractEntityPersister.isValueGenerationRequired(org.hibernate.persister.entity.AbstractEntityPersister.isValueGenerationRequired) Stage(org.hibernate.reactive.stage.Stage) GenerationTiming(org.hibernate.tuple.GenerationTiming) VERSION_COLUMN_ALIAS(org.hibernate.persister.entity.AbstractEntityPersister.VERSION_COLUMN_ALIAS) OuterJoinLoadable(org.hibernate.persister.entity.OuterJoinLoadable) VersionType(org.hibernate.type.VersionType) EntityEntry(org.hibernate.engine.spi.EntityEntry) Type(org.hibernate.type.Type) ReactiveConnection(org.hibernate.reactive.pool.ReactiveConnection) InMemoryValueGenerationStrategy(org.hibernate.tuple.InMemoryValueGenerationStrategy) MessageHelper.infoString(org.hibernate.pretty.MessageHelper.infoString) EntityEntry(org.hibernate.engine.spi.EntityEntry)

Example 2 with Stage

use of org.hibernate.reactive.stage.Stage in project hibernate-reactive by hibernate.

the class ReactiveAbstractEntityPersister method reactivePreInsertInMemoryValueGeneration.

default CompletionStage<Void> reactivePreInsertInMemoryValueGeneration(Object[] fields, Object object, SharedSessionContractImplementor session) {
    CompletionStage<Void> stage = voidFuture();
    if (getEntityMetamodel().hasPreInsertGeneratedValues()) {
        final InMemoryValueGenerationStrategy[] strategies = getEntityMetamodel().getInMemoryValueGenerationStrategies();
        for (int i = 0; i < strategies.length; i++) {
            final int index = i;
            final InMemoryValueGenerationStrategy strategy = strategies[i];
            if (strategy != null && strategy.getGenerationTiming().includesInsert()) {
                stage = stage.thenCompose(v -> generateValue(object, session, strategy).thenAccept(value -> {
                    fields[index] = value;
                    setPropertyValue(object, index, value);
                }));
            }
        }
    }
    return stage;
}
Also used : Arrays(java.util.Arrays) CompletionStages.completedFuture(org.hibernate.reactive.util.impl.CompletionStages.completedFuture) ReactiveDynamicBatchingEntityLoaderBuilder(org.hibernate.reactive.loader.entity.impl.ReactiveDynamicBatchingEntityLoaderBuilder) Expectations.appropriateExpectation(org.hibernate.jdbc.Expectations.appropriateExpectation) EventSource(org.hibernate.event.spi.EventSource) Log(org.hibernate.reactive.logging.impl.Log) PersistenceContext(org.hibernate.engine.spi.PersistenceContext) LoggerFactory(org.hibernate.reactive.logging.impl.LoggerFactory) ReactiveConnectionSupplier(org.hibernate.reactive.session.ReactiveConnectionSupplier) NonIdentifierAttribute(org.hibernate.tuple.NonIdentifierAttribute) PersistentCollection(org.hibernate.collection.spi.PersistentCollection) JDBCException(org.hibernate.JDBCException) PersistentAttributeInterceptor(org.hibernate.engine.spi.PersistentAttributeInterceptor) ResultSet(java.sql.ResultSet) SessionFactoryImpl(org.hibernate.internal.SessionFactoryImpl) CompletionStages.voidFuture(org.hibernate.reactive.util.impl.CompletionStages.voidFuture) SessionFactoryImplementor(org.hibernate.engine.spi.SessionFactoryImplementor) Mutiny(org.hibernate.reactive.mutiny.Mutiny) LockOptions(org.hibernate.LockOptions) Attribute(javax.persistence.metamodel.Attribute) PersistentAttributeInterceptable(org.hibernate.engine.spi.PersistentAttributeInterceptable) MethodHandles(java.lang.invoke.MethodHandles) StaleObjectStateException(org.hibernate.StaleObjectStateException) LazyAttributeDescriptor(org.hibernate.bytecode.enhance.spi.interceptor.LazyAttributeDescriptor) Set(java.util.Set) ReactiveEntityLoader(org.hibernate.reactive.loader.entity.impl.ReactiveEntityLoader) MutinyValueGenerator(org.hibernate.reactive.tuple.MutinyValueGenerator) PreparedStatement(java.sql.PreparedStatement) Serializable(java.io.Serializable) LoadQueryInfluencers(org.hibernate.engine.spi.LoadQueryInfluencers) ArrayHelper(org.hibernate.internal.util.collections.ArrayHelper) Lockable(org.hibernate.persister.entity.Lockable) MessageHelper.infoString(org.hibernate.pretty.MessageHelper.infoString) List(java.util.List) CompletionStage(java.util.concurrent.CompletionStage) Expectation(org.hibernate.jdbc.Expectation) Dialect(org.hibernate.dialect.Dialect) CompletionStages.loop(org.hibernate.reactive.util.impl.CompletionStages.loop) AbstractEntityPersister(org.hibernate.persister.entity.AbstractEntityPersister) SessionImplementor(org.hibernate.engine.spi.SessionImplementor) Update(org.hibernate.sql.Update) HibernateException(org.hibernate.HibernateException) PreparedStatementAdaptor(org.hibernate.reactive.adaptor.impl.PreparedStatementAdaptor) SharedSessionContractImplementor(org.hibernate.engine.spi.SharedSessionContractImplementor) AbstractEntityPersister.determineValueNullness(org.hibernate.persister.entity.AbstractEntityPersister.determineValueNullness) OptimisticLockStyle(org.hibernate.engine.OptimisticLockStyle) AssertionFailure(org.hibernate.AssertionFailure) CompletionStages.logSqlException(org.hibernate.reactive.util.impl.CompletionStages.logSqlException) Session(org.hibernate.Session) StageSessionFactoryImpl(org.hibernate.reactive.stage.impl.StageSessionFactoryImpl) InMemoryValueGenerationStrategy(org.hibernate.tuple.InMemoryValueGenerationStrategy) EntityType(org.hibernate.type.EntityType) UniqueEntityLoader(org.hibernate.loader.entity.UniqueEntityLoader) MultiLoadOptions(org.hibernate.persister.entity.MultiLoadOptions) SQLException(java.sql.SQLException) PreparedStatementAdaptor.bind(org.hibernate.reactive.adaptor.impl.PreparedStatementAdaptor.bind) StageValueGenerator(org.hibernate.reactive.tuple.StageValueGenerator) ArrayHelper.trim(org.hibernate.internal.util.collections.ArrayHelper.trim) StageSessionImpl(org.hibernate.reactive.stage.impl.StageSessionImpl) ReactiveSession(org.hibernate.reactive.session.ReactiveSession) ArrayHelper.join(org.hibernate.internal.util.collections.ArrayHelper.join) MutinySessionFactoryImpl(org.hibernate.reactive.mutiny.impl.MutinySessionFactoryImpl) LockMode(org.hibernate.LockMode) Iterator(java.util.Iterator) Parameters(org.hibernate.reactive.pool.impl.Parameters) Versioning(org.hibernate.engine.internal.Versioning) SimpleSelect(org.hibernate.sql.SimpleSelect) MutinySessionImpl(org.hibernate.reactive.mutiny.impl.MutinySessionImpl) ValueGenerator(org.hibernate.tuple.ValueGenerator) CompletionStages.returnOrRethrow(org.hibernate.reactive.util.impl.CompletionStages.returnOrRethrow) EntityKey(org.hibernate.engine.spi.EntityKey) Delete(org.hibernate.sql.Delete) IdentifierGeneration.castToIdentifierType(org.hibernate.reactive.id.impl.IdentifierGeneration.castToIdentifierType) AbstractEntityPersister.isValueGenerationRequired(org.hibernate.persister.entity.AbstractEntityPersister.isValueGenerationRequired) Stage(org.hibernate.reactive.stage.Stage) GenerationTiming(org.hibernate.tuple.GenerationTiming) VERSION_COLUMN_ALIAS(org.hibernate.persister.entity.AbstractEntityPersister.VERSION_COLUMN_ALIAS) OuterJoinLoadable(org.hibernate.persister.entity.OuterJoinLoadable) VersionType(org.hibernate.type.VersionType) EntityEntry(org.hibernate.engine.spi.EntityEntry) Type(org.hibernate.type.Type) ReactiveConnection(org.hibernate.reactive.pool.ReactiveConnection) InMemoryValueGenerationStrategy(org.hibernate.tuple.InMemoryValueGenerationStrategy)

Aggregations

Serializable (java.io.Serializable)2 MethodHandles (java.lang.invoke.MethodHandles)2 PreparedStatement (java.sql.PreparedStatement)2 ResultSet (java.sql.ResultSet)2 SQLException (java.sql.SQLException)2 Arrays (java.util.Arrays)2 Iterator (java.util.Iterator)2 List (java.util.List)2 Set (java.util.Set)2 CompletionStage (java.util.concurrent.CompletionStage)2 Attribute (javax.persistence.metamodel.Attribute)2 AssertionFailure (org.hibernate.AssertionFailure)2 HibernateException (org.hibernate.HibernateException)2 JDBCException (org.hibernate.JDBCException)2 LockMode (org.hibernate.LockMode)2 LockOptions (org.hibernate.LockOptions)2 Session (org.hibernate.Session)2 StaleObjectStateException (org.hibernate.StaleObjectStateException)2 LazyAttributeDescriptor (org.hibernate.bytecode.enhance.spi.interceptor.LazyAttributeDescriptor)2 PersistentCollection (org.hibernate.collection.spi.PersistentCollection)2