implement @Formula
This commit is contained in:
parent
e10992e4fc
commit
40575125f1
|
@ -99,7 +99,7 @@ class DatabaseSnapshotExecutor {
|
|||
final List<DomainResult> domainResults = new ArrayList<>();
|
||||
|
||||
entityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(tab, col, jdbcMapping) -> {
|
||||
(tab, col, isColFormula, jdbcMapping) -> {
|
||||
final TableReference tableReference = rootTableGroup.resolveTableReference( tab );
|
||||
|
||||
final JdbcParameter jdbcParameter = new JdbcParameterImpl( jdbcMapping );
|
||||
|
@ -111,6 +111,7 @@ class DatabaseSnapshotExecutor {
|
|||
s -> new ColumnReference(
|
||||
tableReference,
|
||||
col,
|
||||
isColFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -145,7 +146,7 @@ class DatabaseSnapshotExecutor {
|
|||
contributorMapping -> {
|
||||
rootPath.append( contributorMapping.getAttributeName() );
|
||||
contributorMapping.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final TableReference tableReference = rootTableGroup.resolveTableReference(
|
||||
containingTableExpression );
|
||||
|
||||
|
@ -158,6 +159,7 @@ class DatabaseSnapshotExecutor {
|
|||
s -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -327,6 +327,7 @@ public class LoaderSelectBuilder {
|
|||
p -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -356,7 +357,7 @@ public class LoaderSelectBuilder {
|
|||
final List<ColumnReference> columnReferences = new ArrayList<>( numberOfKeyColumns );
|
||||
|
||||
keyPart.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final TableReference tableReference = rootTableGroup.resolveTableReference( containingTableExpression );
|
||||
columnReferences.add(
|
||||
(ColumnReference) sqlExpressionResolver.resolveSqlExpression(
|
||||
|
@ -364,6 +365,7 @@ public class LoaderSelectBuilder {
|
|||
p -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -683,6 +685,7 @@ public class LoaderSelectBuilder {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableGroup.resolveTableReference( simpleFkDescriptor.getContainingTableExpression() ),
|
||||
simpleFkDescriptor.getMappedColumnExpression(),
|
||||
false,
|
||||
simpleFkDescriptor.getJdbcMapping(),
|
||||
this.creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -691,13 +694,14 @@ public class LoaderSelectBuilder {
|
|||
else {
|
||||
final List<ColumnReference> columnReferences = new ArrayList<>( jdbcTypeCount );
|
||||
fkDescriptor.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) ->
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) ->
|
||||
columnReferences.add(
|
||||
(ColumnReference) sqlAstCreationState.getSqlExpressionResolver().resolveSqlExpression(
|
||||
createColumnReferenceKey( containingTableExpression, columnExpression ),
|
||||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableGroup.resolveTableReference( containingTableExpression ),
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
this.creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -747,7 +751,7 @@ public class LoaderSelectBuilder {
|
|||
|
||||
final MutableInteger count = new MutableInteger();
|
||||
fkDescriptor.visitTargetColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
// for each column, resolve a SqlSelection and add it to the sub-query select-clause
|
||||
final TableReference tableReference = ownerTableGroup.resolveTableReference( containingTableExpression );
|
||||
final Expression expression = sqlExpressionResolver.resolveSqlExpression(
|
||||
|
@ -755,6 +759,7 @@ public class LoaderSelectBuilder {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -24,6 +24,10 @@ public interface BasicValuedModelPart extends BasicValuedMapping, ModelPart, Fet
|
|||
*/
|
||||
String getMappedColumnExpression();
|
||||
|
||||
default boolean isMappedColumnExpressionFormula() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
default MappingType getPartMappingType() {
|
||||
return this::getJavaTypeDescriptor;
|
||||
|
|
|
@ -15,5 +15,6 @@ public interface ColumnConsumer {
|
|||
void accept(
|
||||
String containingTableExpression,
|
||||
String columnExpression,
|
||||
boolean isColumnExpressionFormula,
|
||||
JdbcMapping jdbcMapping);
|
||||
}
|
||||
|
|
|
@ -177,6 +177,7 @@ public class EmbeddableMappingType implements ManagedMappingType {
|
|||
(BasicType) subtype,
|
||||
containingTableExpression,
|
||||
mappedColumnExpressions.get( columnPosition++ ),
|
||||
false,
|
||||
representationStrategy.resolvePropertyAccess( bootPropertyDescriptor ),
|
||||
compositeType.getCascadeStyle( attributeIndex ),
|
||||
creationProcess
|
||||
|
|
|
@ -34,6 +34,7 @@ public class MappingModelHelper {
|
|||
return new ColumnReference(
|
||||
basicPart.getContainingTableExpression(),
|
||||
basicPart.getMappedColumnExpression(),
|
||||
basicPart.isMappedColumnExpressionFormula(),
|
||||
basicPart.getJdbcMapping(),
|
||||
sessionFactory
|
||||
);
|
||||
|
@ -44,6 +45,7 @@ public class MappingModelHelper {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
basicPart.getContainingTableExpression(),
|
||||
basicPart.getMappedColumnExpression(),
|
||||
basicPart.isMappedColumnExpressionFormula(),
|
||||
basicPart.getJdbcMapping(),
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -53,12 +55,13 @@ public class MappingModelHelper {
|
|||
else {
|
||||
final List<ColumnReference> columnReferences = new ArrayList<>( jdbcTypeCount );
|
||||
modelPart.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final ColumnReference colRef;
|
||||
if ( sqlExpressionResolver == null ) {
|
||||
colRef = new ColumnReference(
|
||||
containingTableExpression,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
);
|
||||
|
@ -69,6 +72,7 @@ public class MappingModelHelper {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
containingTableExpression,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -125,7 +125,7 @@ public class BasicEntityIdentifierMappingImpl implements BasicEntityIdentifierMa
|
|||
|
||||
@Override
|
||||
public void visitColumns(ColumnConsumer consumer) {
|
||||
consumer.accept( getContainingTableExpression(), getMappedColumnExpression(), getJdbcMapping() );
|
||||
consumer.accept( getContainingTableExpression(), getMappedColumnExpression(), false, getJdbcMapping() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -190,6 +190,7 @@ public class BasicEntityIdentifierMappingImpl implements BasicEntityIdentifierMa
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableReference.getIdentificationVariable(),
|
||||
pkColumnName,
|
||||
false,
|
||||
( (BasicValuedMapping) entityPersister.getIdentifierType() ).getJdbcMapping(),
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -224,6 +225,7 @@ public class BasicEntityIdentifierMappingImpl implements BasicEntityIdentifierMa
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTable,
|
||||
pkColumnName,
|
||||
false,
|
||||
( (BasicValuedModelPart) entityPersister.getIdentifierType() ).getJdbcMapping(),
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -131,6 +131,7 @@ public class BasicValuedCollectionPart
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableGroup.getPrimaryTableReference().getIdentificationVariable(),
|
||||
columnExpression,
|
||||
false,
|
||||
mapper,
|
||||
creationState.getSqlAstCreationState().getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -9,9 +9,11 @@ package org.hibernate.metamodel.mapping.internal;
|
|||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.LockMode;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.engine.FetchStrategy;
|
||||
import org.hibernate.engine.FetchTiming;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
import org.hibernate.metamodel.mapping.BasicValuedModelPart;
|
||||
import org.hibernate.metamodel.mapping.ColumnConsumer;
|
||||
import org.hibernate.metamodel.mapping.ConvertibleModelPart;
|
||||
|
@ -24,6 +26,7 @@ import org.hibernate.metamodel.model.convert.spi.BasicValueConverter;
|
|||
import org.hibernate.metamodel.model.domain.NavigableRole;
|
||||
import org.hibernate.property.access.spi.PropertyAccess;
|
||||
import org.hibernate.query.NavigablePath;
|
||||
import org.hibernate.sql.Template;
|
||||
import org.hibernate.sql.ast.Clause;
|
||||
import org.hibernate.sql.ast.spi.SqlAstCreationState;
|
||||
import org.hibernate.sql.ast.spi.SqlExpressionResolver;
|
||||
|
@ -50,6 +53,7 @@ public class BasicValuedSingularAttributeMapping
|
|||
private final NavigableRole navigableRole;
|
||||
private final String tableExpression;
|
||||
private final String mappedColumnExpression;
|
||||
private final boolean isMappedColumnExpressionFormula;
|
||||
|
||||
private final JdbcMapping jdbcMapping;
|
||||
private final BasicValueConverter valueConverter;
|
||||
|
@ -65,6 +69,7 @@ public class BasicValuedSingularAttributeMapping
|
|||
FetchStrategy mappedFetchStrategy,
|
||||
String tableExpression,
|
||||
String mappedColumnExpression,
|
||||
boolean isMappedColumnExpressionFormula,
|
||||
BasicValueConverter valueConverter,
|
||||
JdbcMapping jdbcMapping,
|
||||
ManagedMappingType declaringType,
|
||||
|
@ -73,6 +78,7 @@ public class BasicValuedSingularAttributeMapping
|
|||
this.navigableRole = navigableRole;
|
||||
this.tableExpression = tableExpression;
|
||||
this.mappedColumnExpression = mappedColumnExpression;
|
||||
this.isMappedColumnExpressionFormula = isMappedColumnExpressionFormula;
|
||||
this.valueConverter = valueConverter;
|
||||
this.jdbcMapping = jdbcMapping;
|
||||
|
||||
|
@ -104,6 +110,11 @@ public class BasicValuedSingularAttributeMapping
|
|||
return mappedColumnExpression;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isMappedColumnExpressionFormula() {
|
||||
return isMappedColumnExpressionFormula;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getContainingTableExpression() {
|
||||
return tableExpression;
|
||||
|
@ -142,15 +153,18 @@ public class BasicValuedSingularAttributeMapping
|
|||
|
||||
final TableReference tableReference = tableGroup.resolveTableReference( getContainingTableExpression() );
|
||||
|
||||
final String tableAlias = tableReference.getIdentificationVariable();
|
||||
final String columnExpression = getMappedColumnExpression();
|
||||
return expressionResolver.resolveSqlSelection(
|
||||
expressionResolver.resolveSqlExpression(
|
||||
SqlExpressionResolver.createColumnReferenceKey(
|
||||
tableReference,
|
||||
getMappedColumnExpression()
|
||||
columnExpression
|
||||
),
|
||||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
getMappedColumnExpression(),
|
||||
tableAlias,
|
||||
columnExpression,
|
||||
isMappedColumnExpressionFormula(),
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState().getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
@ -179,6 +193,7 @@ public class BasicValuedSingularAttributeMapping
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
getMappedColumnExpression(),
|
||||
isMappedColumnExpressionFormula(),
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState().getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
@ -246,6 +261,6 @@ public class BasicValuedSingularAttributeMapping
|
|||
|
||||
@Override
|
||||
public void visitColumns(ColumnConsumer consumer) {
|
||||
consumer.accept( tableExpression, mappedColumnExpression, jdbcMapping );
|
||||
consumer.accept( tableExpression, mappedColumnExpression, isMappedColumnExpressionFormula, jdbcMapping );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -138,6 +138,7 @@ public class CollectionIdentifierDescriptorImpl implements CollectionIdentifierD
|
|||
p -> new ColumnReference(
|
||||
tableGroup.getPrimaryTableReference().getIdentificationVariable(),
|
||||
columnName,
|
||||
false,
|
||||
type,
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -176,6 +177,7 @@ public class CollectionIdentifierDescriptorImpl implements CollectionIdentifierD
|
|||
p -> new ColumnReference(
|
||||
tableGroup.getPrimaryTableReference().getIdentificationVariable(),
|
||||
columnName,
|
||||
false,
|
||||
type,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -217,6 +217,7 @@ public class EmbeddedAttributeMapping
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
attrColumnExpr,
|
||||
false,
|
||||
jdbcMapping,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -177,7 +177,7 @@ public class EmbeddedCollectionPart implements CollectionPart, EmbeddableValuedF
|
|||
|
||||
final List<Expression> expressions = new ArrayList<>();
|
||||
getEmbeddableTypeDescriptor().visitColumns(
|
||||
(tableExpression, columnExpression, jdbcMapping) ->{
|
||||
(tableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) ->{
|
||||
assert containingTableExpression.equals( tableExpression );
|
||||
assert columnExpressions.contains( columnExpression );
|
||||
expressions.add(
|
||||
|
@ -186,6 +186,7 @@ public class EmbeddedCollectionPart implements CollectionPart, EmbeddableValuedF
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableGroup.resolveTableReference( tableExpression ),
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -118,6 +118,7 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor, Model
|
|||
new ColumnReference(
|
||||
identificationVariable,
|
||||
columnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState()
|
||||
.getCreationContext()
|
||||
|
@ -169,6 +170,7 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor, Model
|
|||
new ColumnReference(
|
||||
identificationVariable,
|
||||
columnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState()
|
||||
.getCreationContext()
|
||||
|
@ -260,6 +262,7 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor, Model
|
|||
new ColumnReference(
|
||||
lhs,
|
||||
lhsExpressions.get( i ),
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
),
|
||||
|
@ -267,6 +270,7 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor, Model
|
|||
new ColumnReference(
|
||||
rhs,
|
||||
rhsColumnExpressions.get( i ),
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -312,14 +316,14 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor, Model
|
|||
@Override
|
||||
public void visitReferringColumns(ColumnConsumer consumer) {
|
||||
for ( int i = 0; i < keyColumnExpressions.size(); i++ ) {
|
||||
consumer.accept( keyColumnContainingTable, keyColumnExpressions.get( i ), jdbcMappings.get( i ) );
|
||||
consumer.accept( keyColumnContainingTable, keyColumnExpressions.get( i ), false, jdbcMappings.get( i ) );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitTargetColumns(ColumnConsumer consumer) {
|
||||
for ( int i = 0; i < keyColumnExpressions.size(); i++ ) {
|
||||
consumer.accept( targetColumnContainingTable, targetColumnExpressions.get( i ), jdbcMappings.get( i ) );
|
||||
consumer.accept( targetColumnContainingTable, targetColumnExpressions.get( i ), false, jdbcMappings.get( i ) );
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -227,6 +227,7 @@ public class EmbeddedIdentifierMappingImpl
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
attrColumnExpr,
|
||||
false,
|
||||
jdbcMapping,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -49,6 +49,7 @@ public class EntityDiscriminatorMappingImpl extends AbstractEntityDiscriminatorM
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
getMappedColumnExpression(),
|
||||
false,
|
||||
getJdbcMapping(),
|
||||
creationState.getSqlAstCreationState().getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -87,6 +87,7 @@ public class EntityRowIdMappingImpl implements EntityRowIdMapping {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
columnTableReference,
|
||||
rowIdName,
|
||||
false,
|
||||
JavaObjectType.INSTANCE,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -142,6 +142,7 @@ public class EntityVersionMappingImpl implements EntityVersionMapping, FetchOpti
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
columnTableReference,
|
||||
columnExpression,
|
||||
false,
|
||||
versionBasicType,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
@ -179,6 +180,7 @@ public class EntityVersionMappingImpl implements EntityVersionMapping, FetchOpti
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
columnTableReference,
|
||||
columnExpression,
|
||||
false,
|
||||
versionBasicType,
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -204,6 +204,7 @@ public class MappingModelCreationHelper {
|
|||
(BasicType) idSubPropertyType,
|
||||
rootTableName,
|
||||
rootTableKeyColumnNames[columnsConsumedSoFar],
|
||||
false,
|
||||
entityPersister.getRepresentationStrategy().resolvePropertyAccess( bootIdSubProperty ),
|
||||
CascadeStyles.ALL,
|
||||
creationProcess
|
||||
|
@ -272,6 +273,7 @@ public class MappingModelCreationHelper {
|
|||
BasicType attrType,
|
||||
String tableExpression,
|
||||
String attrColumnName,
|
||||
boolean isAttrFormula,
|
||||
PropertyAccess propertyAccess,
|
||||
CascadeStyle cascadeStyle,
|
||||
MappingModelCreationProcess creationProcess) {
|
||||
|
@ -333,6 +335,15 @@ public class MappingModelCreationHelper {
|
|||
: FetchStrategy.IMMEDIATE_JOIN;
|
||||
|
||||
if ( valueConverter != null ) {
|
||||
|
||||
if ( isAttrFormula ) {
|
||||
throw new MappingException( String.format(
|
||||
"Value converter should not be set for column [%s] annotated with @Formula [%s]",
|
||||
attrName,
|
||||
attrColumnName
|
||||
) );
|
||||
}
|
||||
|
||||
// we want to "decompose" the "type" into its various pieces as expected by the mapping
|
||||
assert valueConverter.getRelationalJavaDescriptor() == resolution.getRelationalJavaDescriptor();
|
||||
|
||||
|
@ -354,6 +365,7 @@ public class MappingModelCreationHelper {
|
|||
fetchStrategy,
|
||||
tableExpression,
|
||||
attrColumnName,
|
||||
false,
|
||||
valueConverter,
|
||||
mappingBasicType.getJdbcMapping(),
|
||||
declaringType,
|
||||
|
@ -369,6 +381,7 @@ public class MappingModelCreationHelper {
|
|||
fetchStrategy,
|
||||
tableExpression,
|
||||
attrColumnName,
|
||||
isAttrFormula,
|
||||
null,
|
||||
attrType,
|
||||
declaringType,
|
||||
|
|
|
@ -89,6 +89,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
identificationVariable,
|
||||
targetColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState()
|
||||
.getCreationContext()
|
||||
|
@ -139,6 +140,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
identificationVariable,
|
||||
keyColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationState.getSqlAstCreationState().getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
@ -167,6 +169,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
lhs,
|
||||
keyColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
),
|
||||
|
@ -174,6 +177,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
rhs,
|
||||
targetColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -184,6 +188,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
lhs,
|
||||
targetColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
),
|
||||
|
@ -191,6 +196,7 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
new ColumnReference(
|
||||
rhs,
|
||||
keyColumnExpression,
|
||||
false,
|
||||
jdbcMapping,
|
||||
creationContext.getSessionFactory()
|
||||
)
|
||||
|
@ -285,12 +291,12 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
|
|||
|
||||
@Override
|
||||
public void visitReferringColumns(ColumnConsumer consumer) {
|
||||
consumer.accept( keyColumnContainingTable, keyColumnExpression, jdbcMapping );
|
||||
consumer.accept( keyColumnContainingTable, keyColumnExpression, false, jdbcMapping );
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitTargetColumns(ColumnConsumer consumer) {
|
||||
consumer.accept( targetColumnContainingTable, targetColumnExpression, jdbcMapping );
|
||||
consumer.accept( targetColumnContainingTable, targetColumnExpression, false, jdbcMapping );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -26,10 +26,12 @@ import org.hibernate.sql.ast.tree.select.SortSpecification;
|
|||
*/
|
||||
public class ColumnReference implements OrderingExpression, SequencePart {
|
||||
private final String columnExpression;
|
||||
private final boolean isColumnExpressionFormula;
|
||||
private final NavigablePath rootPath;
|
||||
|
||||
public ColumnReference(String columnExpression, NavigablePath rootPath) {
|
||||
public ColumnReference(String columnExpression, boolean isColumnExpressionFormula, NavigablePath rootPath) {
|
||||
this.columnExpression = columnExpression;
|
||||
this.isColumnExpressionFormula = isColumnExpressionFormula;
|
||||
this.rootPath = rootPath;
|
||||
}
|
||||
|
||||
|
@ -37,6 +39,10 @@ public class ColumnReference implements OrderingExpression, SequencePart {
|
|||
return columnExpression;
|
||||
}
|
||||
|
||||
public boolean isColumnExpressionFormula() {
|
||||
return isColumnExpressionFormula;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SequencePart resolvePathPart(
|
||||
String name,
|
||||
|
@ -63,6 +69,7 @@ public class ColumnReference implements OrderingExpression, SequencePart {
|
|||
sqlAstProcessingState -> new org.hibernate.sql.ast.tree.expression.ColumnReference(
|
||||
tableGroup.getPrimaryTableReference(),
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
// because these ordering fragments are only ever part of the order-by clause, there
|
||||
// is no need for the JdbcMapping
|
||||
null,
|
||||
|
|
|
@ -58,6 +58,7 @@ public interface DomainPath extends OrderingExpression, SequencePart {
|
|||
new ColumnReference(
|
||||
tableReference,
|
||||
basicValuedPart.getMappedColumnExpression(),
|
||||
basicValuedPart.isMappedColumnExpressionFormula(),
|
||||
basicValuedPart.getJdbcMapping(),
|
||||
creationState.getCreationContext().getSessionFactory()
|
||||
),
|
||||
|
@ -68,7 +69,7 @@ public interface DomainPath extends OrderingExpression, SequencePart {
|
|||
}
|
||||
else {
|
||||
getReferenceModelPart().visitColumns(
|
||||
(tableExpression, columnExpression, jdbcMapping) -> {
|
||||
(tableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final TableReference tableReference = tableGroup.resolveTableReference( tableExpression );
|
||||
ast.addSortSpecification(
|
||||
new SortSpecification(
|
||||
|
@ -80,6 +81,7 @@ public interface DomainPath extends OrderingExpression, SequencePart {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -37,7 +37,7 @@ public class RootSequencePart implements SequencePart {
|
|||
|
||||
if ( isTerminal ) {
|
||||
// assume a column-reference
|
||||
return new ColumnReference( name, pluralAttributePath.getNavigablePath() );
|
||||
return new ColumnReference( name, false, pluralAttributePath.getNavigablePath() );
|
||||
}
|
||||
|
||||
throw new PathResolutionException(
|
||||
|
|
|
@ -122,7 +122,6 @@ import org.hibernate.loader.entity.CacheEntityLoaderHelper;
|
|||
import org.hibernate.mapping.BasicValue;
|
||||
import org.hibernate.mapping.Column;
|
||||
import org.hibernate.mapping.Component;
|
||||
import org.hibernate.mapping.Formula;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.mapping.RootClass;
|
||||
|
@ -824,7 +823,8 @@ public abstract class AbstractEntityPersister
|
|||
colAliases[k] = thing.getAlias( dialect, prop.getValue().getTable() );
|
||||
if ( thing.isFormula() ) {
|
||||
foundFormula = true;
|
||||
( (Formula) thing ).setFormula( substituteBrackets( ( (Formula) thing ).getFormula() ) );
|
||||
// ( (Formula) thing ).setFormula( substituteBrackets( ( (Formula) thing ).getFormula() ) );
|
||||
// TODO: uncomment the above statement when this#substituteBrackets(String) is implemented
|
||||
formulaTemplates[k] = thing.getTemplate( dialect, factory.getQueryEngine().getSqmFunctionRegistry() );
|
||||
}
|
||||
else {
|
||||
|
@ -1406,6 +1406,7 @@ public abstract class AbstractEntityPersister
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableReference.getIdentificationVariable(),
|
||||
rootPkColumnName,
|
||||
false,
|
||||
jdbcMapping,
|
||||
getFactory()
|
||||
)
|
||||
|
@ -1420,6 +1421,7 @@ public abstract class AbstractEntityPersister
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
joinedTableReference.getIdentificationVariable(),
|
||||
fkColumnName,
|
||||
false,
|
||||
jdbcMapping,
|
||||
getFactory()
|
||||
)
|
||||
|
@ -6143,6 +6145,7 @@ public abstract class AbstractEntityPersister
|
|||
(BasicType) attrType,
|
||||
tableExpression,
|
||||
attrColumnNames[0],
|
||||
false,
|
||||
propertyAccess,
|
||||
tupleAttrDefinition.getCascadeStyle(),
|
||||
creationProcess
|
||||
|
@ -6150,6 +6153,17 @@ public abstract class AbstractEntityPersister
|
|||
}
|
||||
|
||||
if ( attrType instanceof BasicType ) {
|
||||
final String attrColumnExpression;
|
||||
final boolean isAttrColumnExpressionFormula;
|
||||
if ( attrColumnNames[0] != null ) {
|
||||
attrColumnExpression = attrColumnNames[0];
|
||||
isAttrColumnExpressionFormula = false;
|
||||
}
|
||||
else {
|
||||
final String[] attrColumnFormulaTemplate = propertyColumnFormulaTemplates[ propertyIndex ];
|
||||
attrColumnExpression = attrColumnFormulaTemplate[0];
|
||||
isAttrColumnExpressionFormula = true;
|
||||
}
|
||||
return MappingModelCreationHelper.buildBasicAttributeMapping(
|
||||
attrName,
|
||||
getNavigableRole().append( bootProperty.getName() ),
|
||||
|
@ -6158,7 +6172,8 @@ public abstract class AbstractEntityPersister
|
|||
this,
|
||||
(BasicType) attrType,
|
||||
tableExpression,
|
||||
attrColumnNames[0],
|
||||
attrColumnExpression,
|
||||
isAttrColumnExpressionFormula,
|
||||
propertyAccess,
|
||||
tupleAttrDefinition.getCascadeStyle(),
|
||||
creationProcess
|
||||
|
|
|
@ -33,6 +33,7 @@ import org.hibernate.engine.spi.ExecuteUpdateResultCheckStyle;
|
|||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.internal.DynamicFilterAliasGenerator;
|
||||
import org.hibernate.internal.FilterAliasGenerator;
|
||||
import org.hibernate.internal.TableGroupFilterAliasGenerator;
|
||||
import org.hibernate.internal.util.MarkerObject;
|
||||
import org.hibernate.internal.util.MutableInteger;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
|
@ -1272,7 +1273,7 @@ public class JoinedSubclassEntityPersister extends AbstractEntityPersister {
|
|||
() -> columnConsumer -> {
|
||||
final String[] keyColumnNames = constraintOrderedKeyColumnNames[tablePosition];
|
||||
for ( String column : keyColumnNames ) {
|
||||
columnConsumer.accept( tableName, column, null );
|
||||
columnConsumer.accept( tableName, column, false, null );
|
||||
}
|
||||
}
|
||||
);
|
||||
|
@ -1343,6 +1344,7 @@ public class JoinedSubclassEntityPersister extends AbstractEntityPersister {
|
|||
return new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
discriminatorColumnNameByTableName.get( tableReference.getTableExpression() ),
|
||||
false,
|
||||
jdbcMappings.get( 0 ),
|
||||
getFactory()
|
||||
);
|
||||
|
|
|
@ -928,6 +928,7 @@ public class SingleTableEntityPersister extends AbstractEntityPersister {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableGroup.getPrimaryTableReference().getIdentificationVariable(),
|
||||
getDiscriminatorColumnName(),
|
||||
false,
|
||||
( (BasicType) getDiscriminatorType() ).getJdbcMapping(),
|
||||
getFactory()
|
||||
)
|
||||
|
@ -952,7 +953,7 @@ public class SingleTableEntityPersister extends AbstractEntityPersister {
|
|||
() -> columnConsumer -> {
|
||||
final String[] keyColumnNames = constraintOrderedKeyColumnNames[tablePosition];
|
||||
for ( String column : keyColumnNames ) {
|
||||
columnConsumer.accept( tableName, column, null );
|
||||
columnConsumer.accept( tableName, column, false,null );
|
||||
}
|
||||
}
|
||||
);
|
||||
|
|
|
@ -389,7 +389,7 @@ public class UnionSubclassEntityPersister extends AbstractEntityPersister {
|
|||
() -> columnConsumer -> {
|
||||
final String[] keyColumnNames = constraintOrderedKeyColumnNames[tablePosition];
|
||||
for ( String column : keyColumnNames ) {
|
||||
columnConsumer.accept( tableName, column, null );
|
||||
columnConsumer.accept( tableName, column, false, null );
|
||||
}
|
||||
}
|
||||
);
|
||||
|
|
|
@ -80,7 +80,7 @@ public class MatchingIdSelectionHelper {
|
|||
final List<DomainResult> domainResults = new ArrayList<>();
|
||||
final MutableInteger i = new MutableInteger();
|
||||
targetEntityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final int position = i.getAndIncrement();
|
||||
final TableReference tableReference = mutatingTableGroup.resolveTableReference( containingTableExpression );
|
||||
final Expression expression = sqmConverter.getSqlExpressionResolver().resolveSqlExpression(
|
||||
|
@ -88,6 +88,7 @@ public class MatchingIdSelectionHelper {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -141,7 +142,7 @@ public class MatchingIdSelectionHelper {
|
|||
|
||||
final MutableInteger i = new MutableInteger();
|
||||
targetEntityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final int position = i.getAndIncrement();
|
||||
final TableReference tableReference = mutatingTableGroup.resolveTableReference( containingTableExpression );
|
||||
final Expression expression = sqmConverter.getSqlExpressionResolver().resolveSqlExpression(
|
||||
|
@ -149,6 +150,7 @@ public class MatchingIdSelectionHelper {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -221,10 +221,11 @@ public class CteDeleteHandler extends AbstractCteMutationHandler implements Dele
|
|||
final List<ColumnReference> columnsToMatchReferences = new ArrayList<>();
|
||||
|
||||
columnsToMatchVisitationSupplier.get().accept(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> columnsToMatchReferences.add(
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> columnsToMatchReferences.add(
|
||||
new ColumnReference(
|
||||
targetTableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -76,7 +76,7 @@ public final class ExecuteWithIdTableHelper {
|
|||
for ( int i = 0; i < idTable.getIdTableColumns().size(); i++ ) {
|
||||
final IdTableColumn column = idTable.getIdTableColumns().get( i );
|
||||
idTableInsert.addTargetColumnReferences(
|
||||
new ColumnReference( idTableReference, column.getColumnName(), column.getJdbcMapping(), factory )
|
||||
new ColumnReference( idTableReference, column.getColumnName(), false, column.getJdbcMapping(), factory )
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -88,7 +88,7 @@ public final class ExecuteWithIdTableHelper {
|
|||
final MutableInteger positionWrapper = new MutableInteger();
|
||||
|
||||
mutatingEntityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final int jdbcPosition = positionWrapper.getAndIncrement();
|
||||
final TableReference tableReference = mutatingTableGroup.resolveTableReference( containingTableExpression );
|
||||
matchingIdSelection.getSelectClause().addSqlSelection(
|
||||
|
@ -100,6 +100,7 @@ public final class ExecuteWithIdTableHelper {
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
tableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
factory
|
||||
)
|
||||
|
@ -190,6 +191,7 @@ public final class ExecuteWithIdTableHelper {
|
|||
new ColumnReference(
|
||||
tableReference,
|
||||
idTableColumn.getColumnName(),
|
||||
false,
|
||||
idTableColumn.getJdbcMapping(),
|
||||
executionContext.getSession().getFactory()
|
||||
)
|
||||
|
@ -211,6 +213,7 @@ public final class ExecuteWithIdTableHelper {
|
|||
new ColumnReference(
|
||||
idTableReference,
|
||||
idTable.getSessionUidColumn().getColumnName(),
|
||||
false,
|
||||
idTable.getSessionUidColumn().getJdbcMapping(),
|
||||
executionContext.getSession().getFactory()
|
||||
),
|
||||
|
|
|
@ -53,12 +53,13 @@ public final class ExecuteWithoutIdTableHelper {
|
|||
matchingIdSelect.getFromClause().addRoot( matchingIdSelectTableGroup );
|
||||
|
||||
rootEntityPersister.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final ColumnReference columnReference = (ColumnReference) sqlExpressionResolver.resolveSqlExpression(
|
||||
SqlExpressionResolver.createColumnReferenceKey( rootTableReference, columnExpression ),
|
||||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableReference,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -34,7 +34,7 @@ public class IdTable implements Exportable {
|
|||
);
|
||||
|
||||
entityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> columns.add(
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> columns.add(
|
||||
new IdTableColumn(
|
||||
this,
|
||||
columnExpression,
|
||||
|
|
|
@ -285,7 +285,7 @@ public class RestrictedDeleteExecutionDelegate implements TableBasedDeleteHandle
|
|||
*/
|
||||
final List<ColumnReference> deletingTableColumnRefs = new ArrayList<>();
|
||||
tableKeyColumnVisitationSupplier.get().accept(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
assert targetTableReference.getTableExpression().equals( containingTableExpression );
|
||||
|
||||
final Expression expression = sqlExpressionResolver.resolveSqlExpression(
|
||||
|
@ -293,6 +293,7 @@ public class RestrictedDeleteExecutionDelegate implements TableBasedDeleteHandle
|
|||
sqlAstProcessingState -> new ColumnReference(
|
||||
rootTableGroup.getPrimaryTableReference(),
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
@ -456,12 +457,13 @@ public class RestrictedDeleteExecutionDelegate implements TableBasedDeleteHandle
|
|||
final TableKeyExpressionCollector keyColumnCollector = new TableKeyExpressionCollector( entityDescriptor );
|
||||
|
||||
tableKeyColumnVisitationSupplier.get().accept(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
assert containingTableExpression.equals( tableExpression );
|
||||
keyColumnCollector.apply(
|
||||
new ColumnReference(
|
||||
(String) null,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
factory
|
||||
)
|
||||
|
|
|
@ -236,12 +236,13 @@ public class UpdateExecutionDelegate implements TableBasedUpdateHandler.Executio
|
|||
final TableKeyExpressionCollector keyColumnCollector = new TableKeyExpressionCollector( entityDescriptor );
|
||||
|
||||
tableKeyColumnVisitationSupplier.get().accept(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
assert containingTableExpression.equals( tableExpression );
|
||||
keyColumnCollector.apply(
|
||||
new ColumnReference(
|
||||
(String) null,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -67,6 +67,7 @@ public class DisjunctionRestrictionProducer implements MatchingIdRestrictionProd
|
|||
final ColumnReference idColumnReference = new ColumnReference(
|
||||
mutatingTableReference,
|
||||
idColumn,
|
||||
false,
|
||||
basicIdMapping.getJdbcMapping(),
|
||||
sessionFactory
|
||||
);
|
||||
|
@ -88,8 +89,8 @@ public class DisjunctionRestrictionProducer implements MatchingIdRestrictionProd
|
|||
final List<ColumnReference> columnReferences = new ArrayList<>( idColumnCount );
|
||||
final List<JdbcMapping> jdbcMappings = new ArrayList<>( idColumnCount );
|
||||
identifierMapping.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
columnReferences.add( new ColumnReference( mutatingTableReference, columnExpression, jdbcMapping, sessionFactory ) );
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
columnReferences.add( new ColumnReference( mutatingTableReference, columnExpression, isColumnExpressionFormula, jdbcMapping, sessionFactory ) );
|
||||
jdbcMappings.add( jdbcMapping );
|
||||
}
|
||||
);
|
||||
|
|
|
@ -69,6 +69,7 @@ public class InPredicateRestrictionProducer implements MatchingIdRestrictionProd
|
|||
final Expression inFixture = new ColumnReference(
|
||||
mutatingTableReference,
|
||||
idColumn,
|
||||
false,
|
||||
basicIdMapping.getJdbcMapping(),
|
||||
sessionFactory
|
||||
);
|
||||
|
@ -83,8 +84,8 @@ public class InPredicateRestrictionProducer implements MatchingIdRestrictionProd
|
|||
final List<ColumnReference> columnReferences = new ArrayList<>( idColumnCount );
|
||||
final List<JdbcMapping> jdbcMappings = new ArrayList<>( idColumnCount );
|
||||
identifierMapping.visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
columnReferences.add( new ColumnReference( mutatingTableReference, columnExpression, jdbcMapping, sessionFactory ) );
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
columnReferences.add( new ColumnReference( mutatingTableReference, columnExpression, isColumnExpressionFormula, jdbcMapping, sessionFactory ) );
|
||||
jdbcMappings.add( jdbcMapping );
|
||||
}
|
||||
);
|
||||
|
|
|
@ -62,6 +62,7 @@ public class BasicValuedPathInterpretation<T> implements AssignableSqmPathInterp
|
|||
sacs -> new ColumnReference(
|
||||
tableReference.getIdentificationVariable(),
|
||||
mapping.getMappedColumnExpression(),
|
||||
mapping.isMappedColumnExpressionFormula(),
|
||||
mapping.getJdbcMapping(),
|
||||
sqlAstCreationState.getCreationContext().getSessionFactory()
|
||||
)
|
||||
|
|
|
@ -237,7 +237,7 @@ public class StandardSqmUpdateTranslator
|
|||
|
||||
// create one JdbcParameter for each column in the assigned path
|
||||
assignedPathInterpretation.getExpressionType().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> {
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> {
|
||||
final JdbcParameter jdbcParameter = new JdbcParameterImpl( jdbcMapping );
|
||||
jdbcParametersForSqm.add( jdbcParameter );
|
||||
assignments.add(
|
||||
|
@ -246,6 +246,7 @@ public class StandardSqmUpdateTranslator
|
|||
// we do not want a qualifier (table alias) here
|
||||
(String) null,
|
||||
columnExpression,
|
||||
isColumnExpressionFormula,
|
||||
jdbcMapping,
|
||||
getCreationContext().getSessionFactory()
|
||||
),
|
||||
|
|
|
@ -277,6 +277,9 @@ public class SqmSelectStatement<T> extends AbstractSqmSelectQuery<T> implements
|
|||
|
||||
@Override
|
||||
public SqmSelectStatement<T> orderBy(Order... orders) {
|
||||
if ( getQuerySpec().getOrderByClause() == null ) {
|
||||
getQuerySpec().setOrderByClause( new SqmOrderByClause() );
|
||||
}
|
||||
for ( Order order : orders ) {
|
||||
getQuerySpec().getOrderByClause().addSortSpecification( (SqmSortSpecification) order );
|
||||
}
|
||||
|
@ -285,6 +288,9 @@ public class SqmSelectStatement<T> extends AbstractSqmSelectQuery<T> implements
|
|||
|
||||
@Override
|
||||
public SqmSelectStatement<T> orderBy(List<Order> orders) {
|
||||
if ( getQuerySpec().getOrderByClause() == null ) {
|
||||
getQuerySpec().setOrderByClause( new SqmOrderByClause() );
|
||||
}
|
||||
for ( Order order : orders ) {
|
||||
getQuerySpec().getOrderByClause().addSortSpecification( (SqmSortSpecification) order );
|
||||
}
|
||||
|
|
|
@ -492,11 +492,7 @@ public abstract class AbstractSqlAstWalker
|
|||
|
||||
@Override
|
||||
public void visitColumnReference(ColumnReference columnReference) {
|
||||
if ( columnReference.getQualifier() != null ) {
|
||||
appendSql( columnReference.getQualifier() );
|
||||
appendSql( "." );
|
||||
}
|
||||
appendSql( columnReference.getColumnExpression() );
|
||||
appendSql( columnReference.getExpressionText() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -46,7 +46,7 @@ public class CteTable {
|
|||
final int numberOfColumns = entityDescriptor.getIdentifierMapping().getJdbcTypeCount( sessionFactory.getTypeConfiguration() );
|
||||
cteColumns = new ArrayList<>( numberOfColumns );
|
||||
entityDescriptor.getIdentifierMapping().visitColumns(
|
||||
(containingTableExpression, columnExpression, jdbcMapping) -> cteColumns.add(
|
||||
(containingTableExpression, columnExpression, isColumnExpressionFormula, jdbcMapping) -> cteColumns.add(
|
||||
new CteColumn(
|
||||
"cte_" + columnExpression,
|
||||
jdbcMapping
|
||||
|
@ -183,6 +183,7 @@ public class CteTable {
|
|||
new ColumnReference(
|
||||
tableReference,
|
||||
cteColumn.getColumnExpression(),
|
||||
false,
|
||||
cteColumn.getJdbcMapping(),
|
||||
sessionFactory
|
||||
)
|
||||
|
|
|
@ -4,19 +4,18 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
|
||||
package org.hibernate.sql.ast.tree.expression;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
import org.hibernate.metamodel.mapping.JdbcMapping;
|
||||
import org.hibernate.metamodel.mapping.MappingModelExpressable;
|
||||
import org.hibernate.sql.Template;
|
||||
import org.hibernate.sql.ast.SqlAstWalker;
|
||||
import org.hibernate.sql.ast.tree.from.TableReference;
|
||||
import org.hibernate.sql.ast.tree.update.Assignable;
|
||||
|
@ -25,32 +24,43 @@ import org.hibernate.sql.ast.tree.update.Assignable;
|
|||
* Models a reference to a Column in a SQL AST
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
public class ColumnReference implements Expression, Assignable {
|
||||
private final String qualifier;
|
||||
private final String columnExpression;
|
||||
private final boolean isColumnExpressionFormula;
|
||||
private final String referenceExpression;
|
||||
private final JdbcMapping jdbcMapping;
|
||||
|
||||
public ColumnReference(
|
||||
String qualifier,
|
||||
String columnExpression,
|
||||
boolean isColumnExpressionFormula,
|
||||
JdbcMapping jdbcMapping,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
this.qualifier = StringHelper.nullIfEmpty( qualifier );
|
||||
this.columnExpression = columnExpression;
|
||||
this.referenceExpression = this.qualifier == null
|
||||
? columnExpression
|
||||
: this.qualifier + "." + columnExpression;
|
||||
if ( isColumnExpressionFormula ) {
|
||||
assert qualifier != null;
|
||||
this.columnExpression = StringHelper.replace( columnExpression, Template.TEMPLATE, qualifier );
|
||||
}
|
||||
else {
|
||||
this.columnExpression = columnExpression;
|
||||
}
|
||||
this.isColumnExpressionFormula = isColumnExpressionFormula;
|
||||
this.referenceExpression = this.qualifier == null || isColumnExpressionFormula
|
||||
? this.columnExpression
|
||||
: this.qualifier + "." + this.columnExpression;
|
||||
this.jdbcMapping = jdbcMapping;
|
||||
}
|
||||
|
||||
public ColumnReference(
|
||||
TableReference tableReference,
|
||||
String columnExpression,
|
||||
boolean isColumnExpressionFormula,
|
||||
JdbcMapping jdbcMapping,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
this( tableReference.getIdentificationVariable(), columnExpression, jdbcMapping, sessionFactory );
|
||||
this( tableReference.getIdentificationVariable(), columnExpression, isColumnExpressionFormula, jdbcMapping, sessionFactory );
|
||||
}
|
||||
|
||||
public String getQualifier() {
|
||||
|
@ -61,6 +71,10 @@ public class ColumnReference implements Expression, Assignable {
|
|||
return columnExpression;
|
||||
}
|
||||
|
||||
public boolean isColumnExpressionFormula() {
|
||||
return isColumnExpressionFormula;
|
||||
}
|
||||
|
||||
public String getExpressionText() {
|
||||
return referenceExpression;
|
||||
}
|
||||
|
@ -103,7 +117,7 @@ public class ColumnReference implements Expression, Assignable {
|
|||
}
|
||||
|
||||
final ColumnReference that = (ColumnReference) o;
|
||||
return Objects.equals( referenceExpression, that.referenceExpression );
|
||||
return referenceExpression.equals( that.referenceExpression );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -0,0 +1,131 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.orm.test.formula;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Root;
|
||||
|
||||
import org.hibernate.annotations.Formula;
|
||||
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.junit.Assert.assertThat;
|
||||
|
||||
/**
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
FormulaBasicsTest.Account.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
public class FormulaBasicsTest {
|
||||
|
||||
@BeforeEach
|
||||
void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Account account = new Account( );
|
||||
account.setId( 1L );
|
||||
account.setCredit( 5000d );
|
||||
account.setRate( 1.25 / 100 );
|
||||
session.persist( account );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testLoader(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Account account = session.find( Account.class, 1L );
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHQL(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Account account = session.createQuery( "select a from Account a where a.id = :id", Account.class )
|
||||
.setParameter( "id", 1L ).uniqueResult();
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCriteria(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final CriteriaBuilder criteriaBuilder = scope.getSessionFactory().getCriteriaBuilder();
|
||||
final CriteriaQuery<Account> criteria = criteriaBuilder.createQuery( Account.class );
|
||||
final Root<Account> root = criteria.from( Account.class );
|
||||
criteria.select( root );
|
||||
criteria.where( criteriaBuilder.equal( root.get( "id" ), criteriaBuilder.literal( 1L ) ) );
|
||||
final Account account = session.createQuery( criteria ).uniqueResult();
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from Account" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "Account")
|
||||
public static class Account {
|
||||
|
||||
@Id
|
||||
private Long id;
|
||||
|
||||
private Double credit;
|
||||
|
||||
private Double rate;
|
||||
|
||||
@Formula(value = "credit * rate")
|
||||
private Double interest;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Double getCredit() {
|
||||
return credit;
|
||||
}
|
||||
|
||||
public void setCredit(Double credit) {
|
||||
this.credit = credit;
|
||||
}
|
||||
|
||||
public Double getRate() {
|
||||
return rate;
|
||||
}
|
||||
|
||||
public void setRate(Double rate) {
|
||||
this.rate = rate;
|
||||
}
|
||||
|
||||
public Double getInterest() {
|
||||
return interest;
|
||||
}
|
||||
|
||||
public void setInterest(Double interest) {
|
||||
this.interest = interest;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,122 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.orm.test.formula;
|
||||
|
||||
import java.util.List;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.Table;
|
||||
|
||||
import org.hibernate.annotations.Formula;
|
||||
import org.hibernate.query.Query;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.FailureExpected;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hibernate.testing.hamcrest.CollectionMatchers.hasSize;
|
||||
import static org.junit.Assert.assertThat;
|
||||
|
||||
/**
|
||||
* @author Алексей Макаров
|
||||
* @author Gail Badner
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel( annotatedClasses = FormulaNativeQueryTest.Foo.class )
|
||||
@SessionFactory
|
||||
@TestForIssue(jiraKey = "HHH-7525")
|
||||
public class FormulaNativeQueryTest {
|
||||
|
||||
@BeforeEach
|
||||
void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.persist( new Foo( 1, 1 ) );
|
||||
session.persist( new Foo( 1, 2 ) );
|
||||
session.persist( new Foo( 2, 1 ) );
|
||||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> session.createQuery( "delete from Foo" ).executeUpdate() );
|
||||
}
|
||||
|
||||
@Test
|
||||
@FailureExpected( jiraKey = "HHH-7525", reason = "native query not implemented yet")
|
||||
void testNativeQuery(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Query<Foo> query = session.createNativeQuery( "SELECT ft.* FROM foo_table ft", Foo.class );
|
||||
final List<Foo> list = query.getResultList();
|
||||
assertThat( list, hasSize( 3 ) );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHql(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Query<Foo> query = session.createQuery( "SELECT ft FROM Foo ft", Foo.class );
|
||||
final List<Foo> list = query.getResultList();
|
||||
assertThat( list, hasSize( 3 ) );
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "Foo")
|
||||
@Table(name = "foo_table")
|
||||
public static class Foo {
|
||||
|
||||
private int id;
|
||||
private int locationStart;
|
||||
private int locationEnd;
|
||||
private int distance;
|
||||
|
||||
public Foo() {
|
||||
}
|
||||
|
||||
public Foo(int locationStart, int locationEnd) {
|
||||
this.locationStart = locationStart;
|
||||
this.locationEnd = locationEnd;
|
||||
}
|
||||
|
||||
@Id
|
||||
@GeneratedValue
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
private void setId(int id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public int getLocationStart() {
|
||||
return locationStart;
|
||||
}
|
||||
public void setLocationStart(int locationStart) {
|
||||
this.locationStart = locationStart;
|
||||
}
|
||||
|
||||
public int getLocationEnd() {
|
||||
return locationEnd;
|
||||
}
|
||||
public void setLocationEnd(int locationEnd) {
|
||||
this.locationEnd = locationEnd;
|
||||
}
|
||||
|
||||
@Formula("abs(locationEnd - locationStart)")
|
||||
public int getDistance() {
|
||||
return distance;
|
||||
}
|
||||
|
||||
public void setDistance(int distance) {
|
||||
this.distance = distance;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -4,74 +4,59 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.test.annotations.formula;
|
||||
|
||||
import static org.hibernate.testing.transaction.TransactionUtil.doInHibernate;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
package org.hibernate.orm.test.formula;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.math.BigDecimal;
|
||||
import java.util.List;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.GenerationType;
|
||||
import javax.persistence.Id;
|
||||
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.Transaction;
|
||||
import org.hibernate.annotations.Formula;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.Configuration;
|
||||
import org.hibernate.cfg.Environment;
|
||||
import org.hibernate.dialect.H2Dialect;
|
||||
import org.hibernate.query.Query;
|
||||
import org.hibernate.test.annotations.formula.FormulaWithColumnTypesTest.ExtendedDialect;
|
||||
import org.hibernate.test.locking.A;
|
||||
import org.hibernate.testing.RequiresDialect;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
|
||||
import org.junit.Test;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.RequiresDialect;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
/**
|
||||
* @author Yanming Zhou*
|
||||
* @author Yanming Zhou
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel( annotatedClasses = FormulaWithAliasTest.Customer.class )
|
||||
@SessionFactory
|
||||
@RequiresDialect(H2Dialect.class)
|
||||
public class FormulaWithAliasTest extends BaseCoreFunctionalTestCase {
|
||||
public class FormulaWithAliasTest {
|
||||
|
||||
@Override
|
||||
protected Class<?>[] getAnnotatedClasses() {
|
||||
return new Class[] { Customer.class };
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void configure(Configuration configuration) {
|
||||
configuration.setProperty(
|
||||
Environment.DIALECT,
|
||||
ExtendedDialect.class.getName()
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestForIssue(jiraKey = "HHH-12280")
|
||||
public void testFormulaWithAlias() throws Exception {
|
||||
doInHibernate( this::sessionFactory, session -> {
|
||||
Customer company1 = new Customer();
|
||||
@BeforeEach
|
||||
void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final Customer company1 = new Customer();
|
||||
company1.setBalance(new BigDecimal(100));
|
||||
company1.setVip(true);
|
||||
session.persist(company1);
|
||||
|
||||
Customer company2 = new Customer();
|
||||
final Customer company2 = new Customer();
|
||||
company2.setBalance(new BigDecimal(1000));
|
||||
company2.setVip(false);
|
||||
session.persist(company2);
|
||||
} );
|
||||
|
||||
doInHibernate( this::sessionFactory, session -> {
|
||||
List<Customer> customers = session.createQuery(
|
||||
"select c " +
|
||||
"from Customer c ", Customer.class)
|
||||
.getResultList();
|
||||
}
|
||||
@Test
|
||||
@TestForIssue(jiraKey = "HHH-12280")
|
||||
void testFormulaWithAlias(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final List<Customer> customers = session.createQuery( "select c from Customer c ", Customer.class ).getResultList();
|
||||
|
||||
assertEquals(2, customers.size());
|
||||
assertEquals(1d, customers.get(0).getPercentage().doubleValue(), 0);
|
||||
|
@ -79,6 +64,11 @@ public class FormulaWithAliasTest extends BaseCoreFunctionalTestCase {
|
|||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> session.createQuery( "delete from Customer" ).executeUpdate() );
|
||||
}
|
||||
|
||||
@Entity(name = "Customer")
|
||||
public static class Customer implements Serializable{
|
||||
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.test.annotations.formula;
|
||||
package org.hibernate.orm.test.formula;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
|
@ -49,89 +49,89 @@ public class FormulaWithColumnTypesTest extends BaseCoreFunctionalTestCase {
|
|||
@TestForIssue(jiraKey = "HHH-9951")
|
||||
public void testFormulaAnnotationWithTypeNames() {
|
||||
|
||||
inTransaction(
|
||||
session -> {
|
||||
DisplayItem displayItem20 = new DisplayItem();
|
||||
displayItem20.setDisplayCode( "20" );
|
||||
inTransaction( session -> {
|
||||
session.getSessionFactory().getQueryEngine().getInterpretationCache().close();
|
||||
|
||||
DisplayItem displayItem03 = new DisplayItem();
|
||||
displayItem03.setDisplayCode( "03" );
|
||||
final DisplayItem displayItem20 = new DisplayItem();
|
||||
displayItem20.setDisplayCode( "20" );
|
||||
|
||||
DisplayItem displayItem100 = new DisplayItem();
|
||||
displayItem100.setDisplayCode( "100" );
|
||||
final DisplayItem displayItem03 = new DisplayItem();
|
||||
displayItem03.setDisplayCode( "03" );
|
||||
|
||||
session.persist( displayItem20 );
|
||||
session.persist( displayItem03 );
|
||||
session.persist( displayItem100 );
|
||||
}
|
||||
);
|
||||
final DisplayItem displayItem100 = new DisplayItem();
|
||||
displayItem100.setDisplayCode( "100" );
|
||||
|
||||
session.persist( displayItem20 );
|
||||
session.persist( displayItem03 );
|
||||
session.persist( displayItem100 );
|
||||
} );
|
||||
|
||||
// 1. Default sorting by display code natural ordering (resulting in 3-100-20).
|
||||
inTransaction(
|
||||
session -> {
|
||||
CriteriaBuilder criteriaBuilder = session.getCriteriaBuilder();
|
||||
CriteriaQuery<DisplayItem> criteria = criteriaBuilder.createQuery( DisplayItem.class );
|
||||
Root<DisplayItem> root = criteria.from( DisplayItem.class );
|
||||
criteria.orderBy( criteriaBuilder.asc( root.get( "displayCode" ) ) );
|
||||
inTransaction( session -> {
|
||||
session.getSessionFactory().getQueryEngine().getInterpretationCache().close();
|
||||
|
||||
List displayItems = session.createQuery( criteria ).list();
|
||||
final CriteriaBuilder criteriaBuilder = session.getCriteriaBuilder();
|
||||
final CriteriaQuery<DisplayItem> criteria = criteriaBuilder.createQuery( DisplayItem.class );
|
||||
final Root<DisplayItem> root = criteria.from( DisplayItem.class );
|
||||
criteria.orderBy( criteriaBuilder.asc( root.get( "displayCode" ) ) );
|
||||
|
||||
final List<DisplayItem> displayItems = session.createQuery( criteria ).getResultList();
|
||||
|
||||
// List displayItems = session.createCriteria( DisplayItem.class )
|
||||
// .addOrder( Order.asc( "displayCode" ) )
|
||||
// .list();
|
||||
|
||||
assertNotNull( displayItems );
|
||||
assertEquals( displayItems.size(), 3 );
|
||||
assertEquals(
|
||||
"03",
|
||||
( (DisplayItem) displayItems.get( 0 ) ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"100",
|
||||
( (DisplayItem) displayItems.get( 1 ) ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"20",
|
||||
( (DisplayItem) displayItems.get( 2 ) ).getDisplayCode()
|
||||
);
|
||||
}
|
||||
);
|
||||
assertNotNull( displayItems );
|
||||
assertEquals( 3, displayItems.size() );
|
||||
assertEquals(
|
||||
"03",
|
||||
displayItems.get( 0 ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"100",
|
||||
displayItems.get( 1 ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"20",
|
||||
displayItems.get( 2 ).getDisplayCode()
|
||||
);
|
||||
} );
|
||||
|
||||
// 2. Sorting by the casted type (resulting in 3-20-100).
|
||||
inTransaction(
|
||||
session -> {
|
||||
CriteriaBuilder criteriaBuilder = session.getCriteriaBuilder();
|
||||
CriteriaQuery<DisplayItem> criteria = criteriaBuilder.createQuery( DisplayItem.class );
|
||||
Root<DisplayItem> root = criteria.from( DisplayItem.class );
|
||||
criteria.orderBy( criteriaBuilder.asc( root.get( "displayCodeAsInteger" ) ) );
|
||||
inTransaction( session -> {
|
||||
session.getSessionFactory().getQueryEngine().getInterpretationCache().close();
|
||||
|
||||
List displayItemsSortedByInteger = session.createQuery( criteria ).list();
|
||||
final CriteriaBuilder criteriaBuilder = session.getCriteriaBuilder();
|
||||
final CriteriaQuery<DisplayItem> criteria = criteriaBuilder.createQuery( DisplayItem.class );
|
||||
final Root<DisplayItem> root = criteria.from( DisplayItem.class );
|
||||
criteria.orderBy( criteriaBuilder.asc( root.get( "displayCodeAsInteger" ) ) );
|
||||
|
||||
final List<DisplayItem> displayItemsSortedByInteger = session.createQuery( criteria ).getResultList();
|
||||
|
||||
// List displayItemsSortedByInteger = session.createCriteria( DisplayItem.class )
|
||||
// .addOrder( Order.asc( "displayCodeAsInteger" ) )
|
||||
// .list();
|
||||
|
||||
assertNotNull( displayItemsSortedByInteger );
|
||||
assertEquals( displayItemsSortedByInteger.size(), 3 );
|
||||
assertEquals(
|
||||
"03",
|
||||
( (DisplayItem) displayItemsSortedByInteger.get( 0 ) ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"20",
|
||||
( (DisplayItem) displayItemsSortedByInteger.get( 1 ) ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"100",
|
||||
( (DisplayItem) displayItemsSortedByInteger.get( 2 ) ).getDisplayCode()
|
||||
);
|
||||
}
|
||||
);
|
||||
assertNotNull( displayItemsSortedByInteger );
|
||||
assertEquals( 3, displayItemsSortedByInteger.size() );
|
||||
assertEquals(
|
||||
"03",
|
||||
displayItemsSortedByInteger.get( 0 ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"20",
|
||||
displayItemsSortedByInteger.get( 1 ).getDisplayCode()
|
||||
);
|
||||
assertEquals(
|
||||
"100",
|
||||
displayItemsSortedByInteger.get( 2 ).getDisplayCode()
|
||||
);
|
||||
} );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?>[] getAnnotatedClasses() {
|
||||
return new Class<?>[] {DisplayItem.class};
|
||||
return new Class<?>[] { DisplayItem.class };
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -200,8 +200,8 @@ public class FormulaWithColumnTypesTest extends BaseCoreFunctionalTestCase {
|
|||
|
||||
public ExtendedDialect() {
|
||||
super();
|
||||
registerKeyword( "FLOAT" );
|
||||
registerKeyword( "INTEGER" );
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -0,0 +1,130 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.orm.test.formula;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
import javax.persistence.Column;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
|
||||
import org.hibernate.annotations.Formula;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.orm.junit.DialectFeatureChecks;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.RequiresDialectFeature;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
||||
/**
|
||||
* @author Vlad Mihalcea
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel( annotatedClasses = FormulaWithPartitionByTest.DisplayItem.class )
|
||||
@SessionFactory
|
||||
@RequiresDialectFeature( jiraKey = "HHH-10754", feature = DialectFeatureChecks.SupportPartitionBy.class )
|
||||
public class FormulaWithPartitionByTest {
|
||||
|
||||
@BeforeEach
|
||||
void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final DisplayItem displayItem20_1 = new DisplayItem();
|
||||
displayItem20_1.setId( 1 );
|
||||
displayItem20_1.setDiscountCode( "20" );
|
||||
displayItem20_1.setDiscountValue( 12.34d );
|
||||
|
||||
final DisplayItem displayItem20_2 = new DisplayItem();
|
||||
displayItem20_2.setId( 2 );
|
||||
displayItem20_2.setDiscountCode( "20" );
|
||||
displayItem20_2.setDiscountValue( 15.89 );
|
||||
|
||||
final DisplayItem displayItem100 = new DisplayItem();
|
||||
displayItem100.setId( 3 );
|
||||
displayItem100.setDiscountCode( "100" );
|
||||
displayItem100.setDiscountValue( 12.5 );
|
||||
|
||||
session.persist( displayItem20_1 );
|
||||
session.persist( displayItem20_2 );
|
||||
session.persist( displayItem100 );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestForIssue( jiraKey = "HHH-10754" )
|
||||
void testFormulaAnnotationWithPartitionBy(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final List<DisplayItem> displayItems = session.createQuery( "select di from DisplayItem di order by di.id", DisplayItem.class).getResultList();
|
||||
|
||||
assertNotNull( displayItems );
|
||||
assertEquals( 3, displayItems.size() );
|
||||
|
||||
assertEquals( 1, displayItems.get( 0 ).getItemsByCode().intValue() );
|
||||
assertEquals( 2, displayItems.get( 1 ).getItemsByCode().intValue() );
|
||||
assertEquals( 1, displayItems.get( 2 ).getItemsByCode().intValue() );
|
||||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> session.createQuery( "delete from DisplayItem" ).executeUpdate() );
|
||||
}
|
||||
|
||||
@Entity(name = "DisplayItem")
|
||||
public static class DisplayItem implements Serializable {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
@Column(name = "DISCOUNT_CODE")
|
||||
private String discountCode;
|
||||
|
||||
@Column(name = "DISCOUNT_VALUE")
|
||||
private Double discountValue;
|
||||
|
||||
@Formula("ROW_NUMBER() OVER( PARTITION BY DISCOUNT_CODE ORDER BY SIGN(DISCOUNT_VALUE) DESC )")
|
||||
private Integer itemsByCode;
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Integer id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getDiscountCode() {
|
||||
return discountCode;
|
||||
}
|
||||
|
||||
public void setDiscountCode(String discountCode) {
|
||||
this.discountCode = discountCode;
|
||||
}
|
||||
|
||||
public Integer getItemsByCode() {
|
||||
return itemsByCode;
|
||||
}
|
||||
|
||||
public void setItemsByCode(Integer itemsByCode) {
|
||||
this.itemsByCode = itemsByCode;
|
||||
}
|
||||
|
||||
public Double getDiscountValue() {
|
||||
return discountValue;
|
||||
}
|
||||
|
||||
public void setDiscountValue(Double discountValue) {
|
||||
this.discountValue = discountValue;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,133 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.metamodel.mapping.formula;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.criteria.CriteriaBuilder;
|
||||
import javax.persistence.criteria.CriteriaQuery;
|
||||
import javax.persistence.criteria.Root;
|
||||
|
||||
import org.hibernate.annotations.Formula;
|
||||
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertThat;
|
||||
|
||||
/**
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
FormulaTests.Account.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
public class FormulaTests {
|
||||
|
||||
@BeforeEach
|
||||
void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
Account account = new Account( );
|
||||
account.setId( 1L );
|
||||
account.setCredit( 5000d );
|
||||
account.setRate( 1.25 / 100 );
|
||||
session.persist( account );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testLoader(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
Account account = session.find( Account.class, 1L );
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHQL(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
Account account = session.createQuery( "select a from Account a where a.id = :id", Account.class )
|
||||
.setParameter( "id", 1L ).uniqueResult();
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCriteria(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
final CriteriaBuilder criteriaBuilder = scope.getSessionFactory().getCriteriaBuilder();
|
||||
final CriteriaQuery<Account> criteria = criteriaBuilder.createQuery( Account.class );
|
||||
Root<Account> root = criteria.from( Account.class );
|
||||
criteria.select( root );
|
||||
criteria.where( criteriaBuilder.equal( root.get( "id" ), criteriaBuilder.literal( 1L ) ) );
|
||||
Account account = session.createQuery( criteria ).uniqueResult();
|
||||
assertThat( account.getInterest(), is( 62.5d ));
|
||||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from Account" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "Account")
|
||||
public static class Account {
|
||||
|
||||
@Id
|
||||
private Long id;
|
||||
|
||||
private Double credit;
|
||||
|
||||
private Double rate;
|
||||
|
||||
@Formula(value = "credit * rate")
|
||||
private Double interest;
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Double getCredit() {
|
||||
return credit;
|
||||
}
|
||||
|
||||
public void setCredit(Double credit) {
|
||||
this.credit = credit;
|
||||
}
|
||||
|
||||
public Double getRate() {
|
||||
return rate;
|
||||
}
|
||||
|
||||
public void setRate(Double rate) {
|
||||
this.rate = rate;
|
||||
}
|
||||
|
||||
public Double getInterest() {
|
||||
return interest;
|
||||
}
|
||||
|
||||
public void setInterest(Double interest) {
|
||||
this.interest = interest;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -56,12 +56,12 @@ public class ManyToOneJoinTableTest {
|
|||
final ToOneAttributeMapping simpleAttributeMapping = (ToOneAttributeMapping) simpleEntityAssociation;
|
||||
|
||||
ForeignKeyDescriptor foreignKeyDescriptor = simpleAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "other_simple" ) );
|
||||
assertThat( keyColumn, is( "RHS_ID" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "simple_entity" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
@ -73,12 +73,12 @@ public class ManyToOneJoinTableTest {
|
|||
final ToOneAttributeMapping anotherAttributeMapping = (ToOneAttributeMapping) anotherEntityAssociation;
|
||||
|
||||
foreignKeyDescriptor = anotherAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "other_another" ) );
|
||||
assertThat( keyColumn, is( "RHS_ID" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "another_entity" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
@ -95,12 +95,12 @@ public class ManyToOneJoinTableTest {
|
|||
ToOneAttributeMapping otherAttributeMapping = (ToOneAttributeMapping) otherEntityEntityAssociation;
|
||||
|
||||
foreignKeyDescriptor = otherAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "other_simple" ) );
|
||||
assertThat( keyColumn, is( "LHS_ID" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "other_entity" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
@ -117,12 +117,12 @@ public class ManyToOneJoinTableTest {
|
|||
otherAttributeMapping = (ToOneAttributeMapping) otherEntityEntityAssociation;
|
||||
|
||||
foreignKeyDescriptor = otherAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "another_entity" ) );
|
||||
assertThat( keyColumn, is( "other_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "other_entity" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -53,12 +53,12 @@ public class ManyToOneTest {
|
|||
final ToOneAttributeMapping childAttributeMapping = (ToOneAttributeMapping) simpleEntityAssociation;
|
||||
|
||||
ForeignKeyDescriptor foreignKeyDescriptor = childAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormua, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "other_entity" ) );
|
||||
assertThat( keyColumn, is( "simple_entity_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "simple_entity" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -51,12 +51,12 @@ public class EntityWithBidirectionalAssociationTest {
|
|||
final ToOneAttributeMapping childAttributeMapping = (ToOneAttributeMapping) childAssociation;
|
||||
|
||||
ForeignKeyDescriptor foreignKeyDescriptor = childAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "PARENT" ) );
|
||||
assertThat( keyColumn, is( "child_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "CHILD" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
@ -72,12 +72,12 @@ public class EntityWithBidirectionalAssociationTest {
|
|||
final ToOneAttributeMapping parentAttributeMapping = (ToOneAttributeMapping) parentAssociation;
|
||||
|
||||
foreignKeyDescriptor = parentAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "PARENT" ) );
|
||||
assertThat( keyColumn, is( "child_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "CHILD" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -53,12 +53,12 @@ public class EntityWithOneBidirectionalJoinTableAssociationTest {
|
|||
final ToOneAttributeMapping childAttributeMapping = (ToOneAttributeMapping) childAssociation;
|
||||
|
||||
ForeignKeyDescriptor foreignKeyDescriptor = childAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "PARENT_CHILD" ) );
|
||||
assertThat( keyColumn, is( "child_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "CHILD" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
@ -74,12 +74,12 @@ public class EntityWithOneBidirectionalJoinTableAssociationTest {
|
|||
final ToOneAttributeMapping parentAttributeMapping = (ToOneAttributeMapping) parentAssociation;
|
||||
|
||||
foreignKeyDescriptor = parentAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "PARENT_CHILD" ) );
|
||||
assertThat( keyColumn, is( "parent_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "PARENT" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -47,12 +47,12 @@ public class EntityWithOneToOneJoinTableTest {
|
|||
final ToOneAttributeMapping otherAttributeMapping = (ToOneAttributeMapping) other;
|
||||
|
||||
final ForeignKeyDescriptor foreignKeyDescriptor = otherAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "Entity_SimpleEntity" ) );
|
||||
assertThat( keyColumn, is( "other_id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "SIMPLE_ENTITY" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -48,12 +48,12 @@ public class EntityWithOneToOneSharingPrimaryKeyTest {
|
|||
final ToOneAttributeMapping otherAttributeMapping = (ToOneAttributeMapping) otherAssociation;
|
||||
|
||||
ForeignKeyDescriptor foreignKeyDescriptor = otherAttributeMapping.getForeignKeyDescriptor();
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitReferringColumns( (keyTable, keyColumn, isKeyColumnFormula, jdbcMapping) -> {
|
||||
assertThat( keyTable, is( "EntityWithOneToOneSharingPrimaryKey" ) );
|
||||
assertThat( keyColumn, is( "id" ) );
|
||||
} );
|
||||
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, jdbcMapping) -> {
|
||||
foreignKeyDescriptor.visitTargetColumns( (targetTable, targetColumn, isTargetColumnFormula, jdbcMapping) -> {
|
||||
assertThat( targetTable, is( "SIMPLE_ENTITY" ) );
|
||||
assertThat( targetColumn, is( "id" ) );
|
||||
} );
|
||||
|
|
|
@ -1,143 +0,0 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.test.annotations.formula;
|
||||
|
||||
import org.hibernate.annotations.Formula;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.Configuration;
|
||||
|
||||
import org.hibernate.testing.FailureExpected;
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import javax.persistence.*;
|
||||
import java.util.List;
|
||||
|
||||
import static org.hibernate.testing.transaction.TransactionUtil.doInHibernate;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
|
||||
/**
|
||||
* @author Алексей Макаров
|
||||
* @author Gail Badner
|
||||
*/
|
||||
@TestForIssue(jiraKey = "HHH-7525")
|
||||
public class FormulaNativeQueryTest extends BaseCoreFunctionalTestCase {
|
||||
|
||||
// Add your entities here.
|
||||
@Override
|
||||
protected Class[] getAnnotatedClasses() {
|
||||
return new Class[]{
|
||||
Foo.class
|
||||
};
|
||||
}
|
||||
|
||||
// Add in any settings that are specific to your test. See resources/hibernate.properties for the defaults.
|
||||
@Override
|
||||
protected void configure(Configuration configuration) {
|
||||
super.configure(configuration);
|
||||
|
||||
configuration.setProperty(AvailableSettings.SHOW_SQL, Boolean.TRUE.toString());
|
||||
configuration.setProperty(AvailableSettings.FORMAT_SQL, Boolean.TRUE.toString());
|
||||
}
|
||||
|
||||
@Before
|
||||
public void prepare() {
|
||||
doInHibernate(
|
||||
this::sessionFactory, session -> {
|
||||
session.persist( new Foo( 1, 1 ) );
|
||||
session.persist( new Foo( 1, 2 ) );
|
||||
session.persist( new Foo( 2, 1 ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@After
|
||||
public void cleanup() {
|
||||
doInHibernate(
|
||||
this::sessionFactory, session -> {
|
||||
session.createQuery( "delete from Foo" ).executeUpdate();
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
@FailureExpected( jiraKey = "HHH-7525" )
|
||||
public void testNativeQuery() throws Exception {
|
||||
doInHibernate(
|
||||
this::sessionFactory, session -> {
|
||||
Query query = session.createNativeQuery( "SELECT ft.* FROM foo_table ft", Foo.class );
|
||||
List<Foo> list = query.getResultList();
|
||||
assertEquals( 3, list.size() );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHql() throws Exception {
|
||||
// Show that HQL does work
|
||||
doInHibernate(
|
||||
this::sessionFactory, session -> {
|
||||
Query query = session.createQuery( "SELECT ft FROM Foo ft", Foo.class );
|
||||
List<Foo> list = query.getResultList();
|
||||
assertEquals(3, list.size());
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Entity(name = "Foo")
|
||||
@Table(name = "foo_table")
|
||||
public static class Foo {
|
||||
|
||||
private int id;
|
||||
private int locationStart;
|
||||
private int locationEnd;
|
||||
private int distance;
|
||||
|
||||
public Foo() {
|
||||
}
|
||||
|
||||
public Foo(int locationStart, int locationEnd) {
|
||||
this.locationStart = locationStart;
|
||||
this.locationEnd = locationEnd;
|
||||
}
|
||||
|
||||
@Id
|
||||
@GeneratedValue
|
||||
public int getId() {
|
||||
return id;
|
||||
}
|
||||
private void setId(int id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public int getLocationStart() {
|
||||
return locationStart;
|
||||
}
|
||||
public void setLocationStart(int locationStart) {
|
||||
this.locationStart = locationStart;
|
||||
}
|
||||
|
||||
public int getLocationEnd() {
|
||||
return locationEnd;
|
||||
}
|
||||
public void setLocationEnd(int locationEnd) {
|
||||
this.locationEnd = locationEnd;
|
||||
}
|
||||
|
||||
@Formula("abs(locationEnd - locationStart)")
|
||||
public int getDistance() {
|
||||
return distance;
|
||||
}
|
||||
|
||||
public void setDistance(int distance) {
|
||||
this.distance = distance;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,138 +0,0 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
*/
|
||||
package org.hibernate.test.annotations.formula;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
import javax.persistence.Column;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.GeneratedValue;
|
||||
import javax.persistence.Id;
|
||||
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.Transaction;
|
||||
import org.hibernate.annotations.Formula;
|
||||
import org.hibernate.dialect.Oracle8iDialect;
|
||||
import org.hibernate.dialect.PostgreSQL91Dialect;
|
||||
import org.hibernate.dialect.SQLServer2005Dialect;
|
||||
|
||||
import org.hibernate.testing.DialectCheck;
|
||||
import org.hibernate.testing.DialectChecks;
|
||||
import org.hibernate.testing.RequiresDialect;
|
||||
import org.hibernate.testing.RequiresDialectFeature;
|
||||
import org.hibernate.testing.RequiresDialects;
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
|
||||
import org.junit.Test;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
||||
/**
|
||||
* @author Vlad Mihalcea
|
||||
*/
|
||||
@RequiresDialectFeature( jiraKey = "HHH-10754", value = DialectChecks.SupportPartitionBy.class)
|
||||
public class FormulaWithPartitionByTest extends BaseCoreFunctionalTestCase {
|
||||
|
||||
@Test
|
||||
@TestForIssue(jiraKey = "HHH-10754")
|
||||
public void testFormulaAnnotationWithPartitionBy() {
|
||||
|
||||
Session session = openSession();
|
||||
Transaction transaction = session.beginTransaction();
|
||||
|
||||
DisplayItem displayItem20_1 = new DisplayItem();
|
||||
displayItem20_1.setId( 1 );
|
||||
displayItem20_1.setDiscountCode( "20" );
|
||||
displayItem20_1.setDiscountValue( 12.34d );
|
||||
|
||||
DisplayItem displayItem20_2 = new DisplayItem();
|
||||
displayItem20_2.setId( 2 );
|
||||
displayItem20_2.setDiscountCode( "20" );
|
||||
displayItem20_2.setDiscountValue( 15.89 );
|
||||
|
||||
DisplayItem displayItem100 = new DisplayItem();
|
||||
displayItem100.setId( 3 );
|
||||
displayItem100.setDiscountCode( "100" );
|
||||
displayItem100.setDiscountValue( 12.5 );
|
||||
|
||||
session.persist( displayItem20_1 );
|
||||
session.persist( displayItem20_2 );
|
||||
session.persist( displayItem100 );
|
||||
|
||||
transaction.commit();
|
||||
session.close();
|
||||
|
||||
session = openSession();
|
||||
transaction = session.beginTransaction();
|
||||
|
||||
List<DisplayItem> displayItems = session.createQuery( "select di from DisplayItem di order by di.id", DisplayItem.class).getResultList();
|
||||
|
||||
assertNotNull( displayItems );
|
||||
assertEquals( displayItems.size(), 3 );
|
||||
|
||||
assertEquals( 1, displayItems.get( 0 ).getItemsByCode().intValue() );
|
||||
assertEquals( 2, displayItems.get( 1 ).getItemsByCode().intValue() );
|
||||
assertEquals( 1, displayItems.get( 2 ).getItemsByCode().intValue() );
|
||||
|
||||
transaction.commit();
|
||||
session.close();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?>[] getAnnotatedClasses() {
|
||||
return new Class<?>[] {DisplayItem.class};
|
||||
}
|
||||
|
||||
@Entity(name = "DisplayItem")
|
||||
public static class DisplayItem implements Serializable {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
@Column(name = "DISCOUNT_CODE")
|
||||
private String discountCode;
|
||||
|
||||
@Column(name = "DISCOUNT_VALUE")
|
||||
private Double discountValue;
|
||||
|
||||
@Formula("ROW_NUMBER() OVER( PARTITION BY DISCOUNT_CODE ORDER BY SIGN(DISCOUNT_VALUE) DESC )")
|
||||
private Integer itemsByCode;
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Integer id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getDiscountCode() {
|
||||
return discountCode;
|
||||
}
|
||||
|
||||
public void setDiscountCode(String discountCode) {
|
||||
this.discountCode = discountCode;
|
||||
}
|
||||
|
||||
public Integer getItemsByCode() {
|
||||
return itemsByCode;
|
||||
}
|
||||
|
||||
public void setItemsByCode(Integer itemsByCode) {
|
||||
this.itemsByCode = itemsByCode;
|
||||
}
|
||||
|
||||
public Double getDiscountValue() {
|
||||
return discountValue;
|
||||
}
|
||||
|
||||
public void setDiscountValue(Double discountValue) {
|
||||
this.discountValue = discountValue;
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue