HHH-18610 ColumnReferenceKey for discriminator

This commit is contained in:
Andrea Boriero 2024-11-13 13:10:57 +01:00
parent bfaf3c5931
commit 691604dbfb
3 changed files with 53 additions and 8 deletions

View File

@ -4,6 +4,7 @@
*/ */
package org.hibernate.query.results.internal; package org.hibernate.query.results.internal;
import org.hibernate.metamodel.mapping.EntityDiscriminatorMapping;
import org.hibernate.metamodel.mapping.EntityIdentifierMapping; import org.hibernate.metamodel.mapping.EntityIdentifierMapping;
import org.hibernate.metamodel.mapping.ModelPart; import org.hibernate.metamodel.mapping.ModelPart;
import org.hibernate.metamodel.mapping.SelectableMapping; import org.hibernate.metamodel.mapping.SelectableMapping;
@ -19,6 +20,7 @@ import org.hibernate.sql.results.graph.basic.BasicFetch;
import org.hibernate.sql.results.jdbc.spi.JdbcValuesMetadata; import org.hibernate.sql.results.jdbc.spi.JdbcValuesMetadata;
import static org.hibernate.sql.ast.spi.SqlExpressionResolver.createColumnReferenceKey; import static org.hibernate.sql.ast.spi.SqlExpressionResolver.createColumnReferenceKey;
import static org.hibernate.sql.ast.spi.SqlExpressionResolver.createDiscriminatorColumnReferenceKey;
/** /**
* @author Steve Ebersole * @author Steve Ebersole
@ -65,6 +67,25 @@ public class ResultsHelper {
); );
} }
public static Expression resolveSqlExpression(
DomainResultCreationStateImpl resolver,
JdbcValuesMetadata jdbcValuesMetadata,
TableReference tableReference,
EntityDiscriminatorMapping discriminatorMapping,
String columnAlias) {
return resolver.resolveSqlExpression(
createDiscriminatorColumnReferenceKey(
tableReference,
discriminatorMapping
),
processingState -> {
final int jdbcPosition = jdbcValuesMetadata.resolveColumnPosition( columnAlias );
final int valuesArrayPosition = jdbcPositionToValuesArrayPosition( jdbcPosition );
return new ResultSetMappingSqlSelection( valuesArrayPosition, discriminatorMapping.getJdbcMapping() );
}
);
}
public static Expression resolveSqlExpression( public static Expression resolveSqlExpression(
DomainResultCreationStateImpl resolver, DomainResultCreationStateImpl resolver,
TableReference tableReference, TableReference tableReference,

View File

@ -7,6 +7,7 @@ package org.hibernate.query.results.internal.dynamic;
import org.hibernate.LockMode; import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming; import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.CollectionPart; import org.hibernate.metamodel.mapping.CollectionPart;
import org.hibernate.metamodel.mapping.EntityDiscriminatorMapping;
import org.hibernate.metamodel.mapping.EntityMappingType; import org.hibernate.metamodel.mapping.EntityMappingType;
import org.hibernate.metamodel.mapping.ModelPart; import org.hibernate.metamodel.mapping.ModelPart;
import org.hibernate.metamodel.mapping.PluralAttributeMapping; import org.hibernate.metamodel.mapping.PluralAttributeMapping;
@ -259,7 +260,7 @@ public class DynamicResultBuilderEntityStandard
} }
if ( discriminatorColumnName != null ) { if ( discriminatorColumnName != null ) {
resolveSqlSelection( resolveDiscriminatorSqlSelection(
discriminatorColumnName, discriminatorColumnName,
tableReference, tableReference,
entityMapping.getDiscriminatorMapping(), entityMapping.getDiscriminatorMapping(),
@ -284,6 +285,25 @@ public class DynamicResultBuilderEntityStandard
} }
} }
private static void resolveDiscriminatorSqlSelection(String columnAlias, TableReference tableReference, EntityDiscriminatorMapping discriminatorMapping, JdbcValuesMetadata jdbcResultsMetadata, DomainResultCreationState domainResultCreationState) {
final DomainResultCreationStateImpl creationStateImpl = impl( domainResultCreationState );
creationStateImpl.resolveSqlSelection(
ResultsHelper.resolveSqlExpression(
creationStateImpl,
jdbcResultsMetadata,
tableReference,
discriminatorMapping,
columnAlias
),
discriminatorMapping.getJdbcMapping().getJdbcJavaType(),
null,
domainResultCreationState.getSqlAstCreationState()
.getCreationContext()
.getSessionFactory()
.getTypeConfiguration()
);
}
private FetchBuilder findIdFetchBuilder() { private FetchBuilder findIdFetchBuilder() {
return findFetchBuilder( entityMapping.getIdentifierMapping() ); return findFetchBuilder( entityMapping.getIdentifierMapping() );
} }

View File

@ -6,10 +6,10 @@ package org.hibernate.sql.ast.spi;
import java.util.function.Function; import java.util.function.Function;
import org.hibernate.metamodel.mapping.EntityDiscriminatorMapping;
import org.hibernate.metamodel.mapping.JdbcMapping; import org.hibernate.metamodel.mapping.JdbcMapping;
import org.hibernate.metamodel.mapping.SelectableMapping; import org.hibernate.metamodel.mapping.SelectableMapping;
import org.hibernate.metamodel.mapping.SelectablePath; import org.hibernate.metamodel.mapping.SelectablePath;
import org.hibernate.metamodel.mapping.internal.DiscriminatorTypeImpl;
import org.hibernate.sql.ast.tree.expression.ColumnReference; import org.hibernate.sql.ast.tree.expression.ColumnReference;
import org.hibernate.sql.ast.tree.expression.Expression; import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.NestedColumnReference; import org.hibernate.sql.ast.tree.expression.NestedColumnReference;
@ -91,6 +91,15 @@ public interface SqlExpressionResolver {
return createColumnReferenceKey( tableReference, selectable.getSelectablePath(), selectable.getJdbcMapping() ); return createColumnReferenceKey( tableReference, selectable.getSelectablePath(), selectable.getJdbcMapping() );
} }
/**
* Convenience form for creating a key from TableReference and EntityDiscriminatorMapping
*/
static ColumnReferenceKey createDiscriminatorColumnReferenceKey(TableReference tableReference, EntityDiscriminatorMapping discriminatorMapping) {
assert tableReference.containsAffectedTableName( discriminatorMapping.getContainingTableExpression() )
: String.format( ROOT, "Expecting tables to match between TableReference (%s) and SelectableMapping (%s)", tableReference.getTableId(), discriminatorMapping.getContainingTableExpression() );
return createColumnReferenceKey( tableReference, discriminatorMapping.getSelectablePath(), discriminatorMapping.getUnderlyingJdbcMapping() );
}
default Expression resolveSqlExpression(TableReference tableReference, SelectableMapping selectableMapping) { default Expression resolveSqlExpression(TableReference tableReference, SelectableMapping selectableMapping) {
return resolveSqlExpression( return resolveSqlExpression(
createColumnReferenceKey( tableReference, selectableMapping ), createColumnReferenceKey( tableReference, selectableMapping ),
@ -127,12 +136,7 @@ public interface SqlExpressionResolver {
public ColumnReferenceKey(String tableQualifier, SelectablePath selectablePath, JdbcMapping jdbcMapping) { public ColumnReferenceKey(String tableQualifier, SelectablePath selectablePath, JdbcMapping jdbcMapping) {
this.tableQualifier = tableQualifier; this.tableQualifier = tableQualifier;
this.selectablePath = selectablePath; this.selectablePath = selectablePath;
if ( jdbcMapping instanceof DiscriminatorTypeImpl discriminatorType ) { this.jdbcMapping = jdbcMapping;
this.jdbcMapping = discriminatorType.getUnderlyingJdbcMapping();
}
else {
this.jdbcMapping = jdbcMapping;
}
} }
@Override @Override