diff --git a/hibernate-core/src/main/java/org/hibernate/NaturalIdLoadAccess.java b/hibernate-core/src/main/java/org/hibernate/NaturalIdLoadAccess.java index d44cf93cb5..d53d5aa1ba 100644 --- a/hibernate-core/src/main/java/org/hibernate/NaturalIdLoadAccess.java +++ b/hibernate-core/src/main/java/org/hibernate/NaturalIdLoadAccess.java @@ -154,7 +154,7 @@ public interface NaturalIdLoadAccess { * @deprecated use {@link #using(Map)} with {@link Map#of}, which is * slightly more typesafe */ - @Deprecated(since = "6.3") + @Deprecated(since = "6.3", forRemoval = true) NaturalIdLoadAccess using(Object... mappings); /** diff --git a/hibernate-core/src/main/java/org/hibernate/NaturalIdMultiLoadAccess.java b/hibernate-core/src/main/java/org/hibernate/NaturalIdMultiLoadAccess.java index 519fea7094..7c2367f5b3 100644 --- a/hibernate-core/src/main/java/org/hibernate/NaturalIdMultiLoadAccess.java +++ b/hibernate-core/src/main/java/org/hibernate/NaturalIdMultiLoadAccess.java @@ -4,13 +4,13 @@ */ package org.hibernate; +import java.util.HashMap; import java.util.List; import java.util.Map; import org.hibernate.graph.GraphSemantic; import org.hibernate.graph.RootGraph; - -import static org.hibernate.internal.util.collections.CollectionHelper.asMap; +import org.hibernate.internal.util.collections.CollectionHelper; /** * Loads multiple instances of a given entity type at once, by @@ -184,8 +184,17 @@ public interface NaturalIdMultiLoadAccess { * * @deprecated use {@link Map#of} instead */ - @Deprecated(since = "6.3") + @Deprecated(since = "6.3", forRemoval = true) static Map compoundValue(Object... elements) { - return asMap( elements ); + assert elements != null; + assert elements.length % 2 == 0; + + final HashMap map = new HashMap<>(); + CollectionHelper.collectMapEntries( map::put, elements ); + for ( int i = 0; i < elements.length; i += 2 ) { + map.put( (String) elements[ i ], (Object) elements[ i+1 ] ); + } + + return map; } } diff --git a/hibernate-core/src/main/java/org/hibernate/boot/model/internal/GeneratorBinder.java b/hibernate-core/src/main/java/org/hibernate/boot/model/internal/GeneratorBinder.java index 7aa761945e..b16c62d846 100644 --- a/hibernate-core/src/main/java/org/hibernate/boot/model/internal/GeneratorBinder.java +++ b/hibernate-core/src/main/java/org/hibernate/boot/model/internal/GeneratorBinder.java @@ -43,7 +43,6 @@ import org.hibernate.id.uuid.UuidValueGenerator; import org.hibernate.internal.CoreLogging; import org.hibernate.internal.CoreMessageLogger; import org.hibernate.internal.util.StringHelper; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.mapping.GeneratorCreator; import org.hibernate.mapping.KeyValue; import org.hibernate.mapping.PersistentClass; @@ -74,6 +73,7 @@ import static org.hibernate.boot.model.internal.GeneratorStrategies.generatorCla import static org.hibernate.id.IdentifierGenerator.GENERATOR_NAME; import static org.hibernate.internal.util.NullnessUtil.castNonNull; import static org.hibernate.internal.util.StringHelper.qualify; +import static org.hibernate.internal.util.collections.CollectionHelper.combineUntyped; import static org.hibernate.resource.beans.internal.Helper.allowExtensionsInCdi; /** @@ -883,7 +883,7 @@ public class GeneratorBinder { Locale.ROOT, "Identifier attribute '%s' has too many generator annotations: %s", getPath( propertyHolder, inferredData ), - CollectionHelper.combineUntyped( idGeneratorAnnotations, generatorAnnotations ) + combineUntyped( idGeneratorAnnotations, generatorAnnotations ) ) ); } if ( !idGeneratorAnnotations.isEmpty() ) { diff --git a/hibernate-core/src/main/java/org/hibernate/internal/util/collections/CollectionHelper.java b/hibernate-core/src/main/java/org/hibernate/internal/util/collections/CollectionHelper.java index 91211ce1c2..9a9dae1aa3 100644 --- a/hibernate-core/src/main/java/org/hibernate/internal/util/collections/CollectionHelper.java +++ b/hibernate-core/src/main/java/org/hibernate/internal/util/collections/CollectionHelper.java @@ -5,7 +5,6 @@ package org.hibernate.internal.util.collections; import java.util.ArrayList; -import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.HashMap; @@ -20,6 +19,14 @@ import java.util.concurrent.ConcurrentHashMap; import java.util.function.BiConsumer; import java.util.function.Function; +import static java.util.Arrays.asList; +import static java.util.Collections.emptyList; +import static java.util.Collections.emptyMap; +import static java.util.Collections.emptySet; +import static java.util.Collections.singleton; +import static java.util.Collections.singletonList; +import static java.util.Collections.singletonMap; + /** * Various helper util methods for handling collections. * @@ -130,7 +137,7 @@ public final class CollectionHelper { * * @return The proper size. */ - public static int determineProperSizing(Map original) { + public static int determineProperSizing(Map original) { return determineProperSizing( original.size() ); } @@ -147,17 +154,12 @@ public final class CollectionHelper { if ( original == null ) { return null; } - - final HashMap copy = new HashMap<>( determineProperSizing( original ) ); - - original.forEach( - (key, value) -> copy.put( - keyTransformer.apply( key ), - valueTransformer.apply( value ) - ) - ); - - return copy; + else { + final HashMap copy = new HashMap<>( determineProperSizing( original ) ); + original.forEach( (key, value) -> copy.put( keyTransformer.apply( key ), + valueTransformer.apply( value ) ) ); + return copy; + } } public static Map makeMap( @@ -171,19 +173,15 @@ public final class CollectionHelper { Function keyProducer, Function valueProducer) { if ( isEmpty( collection ) ) { - return Collections.emptyMap(); + return emptyMap(); } - - final Map map = new HashMap<>( determineProperSizing( collection.size() )); - - for ( E element : collection ) { - map.put( - keyProducer.apply( element ), - valueProducer.apply( element ) - ); + else { + final Map map = new HashMap<>( determineProperSizing( collection.size() ) ); + for ( E element : collection ) { + map.put( keyProducer.apply( element ), valueProducer.apply( element ) ); + } + return map; } - - return map; } /** @@ -194,7 +192,7 @@ public final class CollectionHelper { * * @return The proper size. */ - public static int determineProperSizing(Set original) { + public static int determineProperSizing(Set original) { return determineProperSizing( original.size() ); } @@ -207,8 +205,7 @@ public final class CollectionHelper { * @return The proper size. */ public static int determineProperSizing(int numberOfElements) { - int actual = ( (int) ( numberOfElements / LOAD_FACTOR ) ) + 1; - return Math.max( actual, MINIMUM_INITIAL_CAPACITY ); + return Math.max( ( (int) ( numberOfElements / LOAD_FACTOR ) ) + 1, MINIMUM_INITIAL_CAPACITY ); } /** @@ -255,26 +252,26 @@ public final class CollectionHelper { if ( source == null ) { return null; } - - final int size = source.size(); - final Set copy = CollectionHelper.setOfSize( size + 1 ); - copy.addAll( source ); - return copy; + else { + final Set copy = setOfSize( source.size() + 1 ); + copy.addAll( source ); + return copy; + } } public static boolean isEmpty(Collection collection) { return collection == null || collection.isEmpty(); } - public static boolean isEmpty(Map map) { + public static boolean isEmpty(Map map) { return map == null || map.isEmpty(); } - public static boolean isNotEmpty(Collection collection) { + public static boolean isNotEmpty(Collection collection) { return !isEmpty( collection ); } - public static boolean isNotEmpty(Map map) { + public static boolean isNotEmpty(Map map) { return !isEmpty( map ); } @@ -305,23 +302,20 @@ public final class CollectionHelper { } public static Set setOf(Collection values) { - if ( isEmpty( values ) ) { - return Collections.emptySet(); - } - return new HashSet<>( values ); + return isEmpty( values ) ? emptySet() : new HashSet<>( values ); } public static Properties asProperties(Map map) { - if ( map instanceof Properties ) { - return ( (Properties) map ); + if ( map instanceof Properties properties ) { + return properties; } - - final Properties properties = new Properties(); - if ( isNotEmpty( map ) ) { - properties.putAll( map ); + else { + final Properties properties = new Properties(); + if ( isNotEmpty( map ) ) { + properties.putAll( map ); + } + return properties; } - - return properties; } /** @@ -335,9 +329,9 @@ public final class CollectionHelper { public static Set toSmallSet(Set set) { switch ( set.size() ) { case 0: - return Collections.EMPTY_SET; + return emptySet(); case 1: - return Collections.singleton( set.iterator().next() ); + return singleton( set.iterator().next() ); default: //TODO assert tests pass even if this is set to return an unmodifiable Set return set; @@ -354,10 +348,10 @@ public final class CollectionHelper { public static Map toSmallMap(final Map map) { switch ( map.size() ) { case 0: - return Collections.EMPTY_MAP; + return emptyMap(); case 1: Map.Entry entry = map.entrySet().iterator().next(); - return Collections.singletonMap( entry.getKey(), entry.getValue() ); + return singletonMap( entry.getKey(), entry.getValue() ); default: //TODO assert tests pass even if this is set to return an unmodifiable Map return map; @@ -374,15 +368,16 @@ public final class CollectionHelper { public static List toSmallList(ArrayList arrayList) { switch ( arrayList.size() ) { case 0: - return Collections.EMPTY_LIST; + return emptyList(); case 1: - return Collections.singletonList( arrayList.get( 0 ) ); + return singletonList( arrayList.get( 0 ) ); default: arrayList.trimToSize(); return arrayList; } } + @Deprecated(forRemoval = true) @SuppressWarnings( "unchecked" ) public static void collectMapEntries(BiConsumer mapEntryConsumer, Object[] mappings) { // even numbered @@ -393,96 +388,6 @@ public final class CollectionHelper { } } - @SuppressWarnings( "unchecked" ) - public static Map asMap(Object[] elements) { - assert elements != null; - assert elements.length % 2 == 0; - - final HashMap map = new HashMap<>(); - collectMapEntries( map::put, elements ); - for ( int i = 0; i < elements.length; i += 2 ) { - map.put( (K) elements[ i ], (S) elements[ i+1 ] ); - } - - return map; - } - - public static Map toMap(String... pairs) { - assert pairs.length % 2 == 0; - if ( pairs.length == 2 ) { - return Collections.singletonMap( pairs[0], pairs[1] ); - } - - final Map result = new HashMap<>(); - applyToMap( result, pairs ); - return result; - } - - private static void applyToMap(Map map, String... pairs) { - assert pairs.length % 2 == 0; - for ( int i = 0; i < pairs.length; i+=2 ) { - map.put( pairs[i], pairs[i+1] ); - } - } - - public static Map toMap(Object... pairs) { - assert pairs.length % 2 == 0; - if ( pairs.length == 2 ) { - return Collections.singletonMap( (String) pairs[0], pairs[1] ); - } - - final Map result = new HashMap<>(); - applyToMap( result, pairs ); - return result; - } - - public static Map toSettingsMap(Object... pairs) { - assert pairs.length % 2 == 0; - if ( pairs.length == 2 ) { - return Collections.singletonMap( (String) pairs[0], pairs[1] ); - } - - final Map result = new HashMap<>(); - applyToMap( result, pairs ); - return result; - } - - @SuppressWarnings({ "unchecked", "rawtypes" }) - private static void applyToMap(Map map, Object... pairs) { - assert pairs.length % 2 == 0; - for ( int i = 0; i < pairs.length; i+=2 ) { - ( (Map) map ).put( pairs[i], pairs[i+1] ); - } - } - - public static String[] asPairs(Map map) { - final String[] pairs = new String[ map.size() * 2 ]; - int i = 0; - for ( Map.Entry entry : map.entrySet() ) { - pairs[i++] = entry.getKey(); - pairs[i++] = entry.getValue(); - } - return pairs; - } - - public static Properties toProperties(Object... pairs) { - final Properties properties = new Properties(); - if ( pairs.length > 0 ) { - assert pairs.length % 2 == 0; - for ( int i = 0; i < pairs.length; i+=2 ) { - properties.put( pairs[i], pairs[i+1] ); - } - } - return properties; - } - - public static void applyToProperties(Properties properties, Object... pairs) { - assert pairs.length % 2 == 0; - for ( int i = 0; i < pairs.length; i+=2 ) { - properties.put( pairs[i], pairs[i+1] ); - } - } - public static List combine(List list1, List list2) { final ArrayList combined = arrayList( list1.size() + list2.size() ); combined.addAll( list1 ); @@ -498,10 +403,11 @@ public final class CollectionHelper { return combined; } + @SafeVarargs public static List combine(List... lists) { final ArrayList combined = new ArrayList<>(); - for ( int i = 0; i < lists.length; i++ ) { - combined.addAll( lists[i] ); + for ( List list : lists ) { + combined.addAll( list ); } return combined; } @@ -518,10 +424,11 @@ public final class CollectionHelper { return values == null ? 0 : values.size(); } + @SafeVarargs public static Set toSet(X... values) { final HashSet result = new HashSet<>(); if ( isNotEmpty( values ) ) { - result.addAll( Arrays.asList( values ) ); + result.addAll( asList( values ) ); } return result; } @@ -532,16 +439,19 @@ public final class CollectionHelper { if ( totalCount == 0 ) { return new ArrayList<>(); } - final ArrayList joined = new ArrayList<>( totalCount ); - if ( first != null ) { - joined.addAll( first ); + else { + final ArrayList joined = new ArrayList<>( totalCount ); + if ( first != null ) { + joined.addAll( first ); + } + if ( second != null ) { + joined.addAll( second ); + } + return joined; } - if ( second != null ) { - joined.addAll( second ); - } - return joined; } + @SafeVarargs public static List mutableJoin(Collection first, Collection... others) { // it can be empty, but not null assert first != null; diff --git a/hibernate-core/src/main/java/org/hibernate/loader/internal/NaturalIdLoadAccessImpl.java b/hibernate-core/src/main/java/org/hibernate/loader/internal/NaturalIdLoadAccessImpl.java index 41572c42c1..d1ca3a04a1 100644 --- a/hibernate-core/src/main/java/org/hibernate/loader/internal/NaturalIdLoadAccessImpl.java +++ b/hibernate-core/src/main/java/org/hibernate/loader/internal/NaturalIdLoadAccessImpl.java @@ -49,7 +49,7 @@ public class NaturalIdLoadAccessImpl extends BaseNaturalIdLoadAccessImpl i return this; } - @Override @Deprecated + @Override @Deprecated(forRemoval = true) public NaturalIdLoadAccess using(Object... mappings) { CollectionHelper.collectMapEntries( naturalIdParameters::put, mappings ); return this; diff --git a/hibernate-core/src/main/java/org/hibernate/query/sql/internal/NativeQueryImpl.java b/hibernate-core/src/main/java/org/hibernate/query/sql/internal/NativeQueryImpl.java index 5e142919ac..6301a2c49e 100644 --- a/hibernate-core/src/main/java/org/hibernate/query/sql/internal/NativeQueryImpl.java +++ b/hibernate-core/src/main/java/org/hibernate/query/sql/internal/NativeQueryImpl.java @@ -8,7 +8,6 @@ import java.io.Serializable; import java.time.Instant; import java.util.Calendar; import java.util.Collection; -import java.util.Collections; import java.util.Date; import java.util.HashSet; import java.util.List; @@ -20,11 +19,11 @@ import java.util.function.Supplier; import org.hibernate.CacheMode; import org.hibernate.FlushMode; +import org.hibernate.metamodel.spi.MappingMetamodelImplementor; import org.hibernate.query.QueryFlushMode; import org.hibernate.HibernateException; import org.hibernate.LockMode; import org.hibernate.LockOptions; -import org.hibernate.MappingException; import org.hibernate.ScrollMode; import org.hibernate.dialect.Dialect; import org.hibernate.engine.query.spi.NativeQueryInterpreter; @@ -35,11 +34,8 @@ import org.hibernate.graph.RootGraph; import org.hibernate.graph.spi.RootGraphImplementor; import org.hibernate.internal.AbstractSharedSessionContract; import org.hibernate.internal.util.MathHelper; -import org.hibernate.internal.util.StringHelper; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.jpa.spi.NativeQueryTupleTransformer; import org.hibernate.metamodel.model.domain.BasicDomainType; -import org.hibernate.persister.entity.EntityPersister; import org.hibernate.query.BindableType; import org.hibernate.query.KeyedPage; import org.hibernate.query.KeyedResultList; @@ -55,6 +51,7 @@ import org.hibernate.query.internal.DelegatingDomainQueryExecutionContext; import org.hibernate.query.internal.ParameterMetadataImpl; import org.hibernate.query.internal.QueryOptionsImpl; import org.hibernate.query.internal.ResultSetMappingResolutionContext; +import org.hibernate.query.named.NamedObjectRepository; import org.hibernate.query.named.NamedResultSetMappingMemento; import org.hibernate.query.results.Builders; import org.hibernate.query.results.ResultBuilder; @@ -72,7 +69,6 @@ import org.hibernate.query.spi.DomainQueryExecutionContext; import org.hibernate.query.spi.MutableQueryOptions; import org.hibernate.query.spi.NonSelectQueryPlan; import org.hibernate.query.spi.ParameterMetadataImplementor; -import org.hibernate.query.spi.QueryEngine; import org.hibernate.query.spi.QueryInterpretationCache; import org.hibernate.query.spi.QueryOptions; import org.hibernate.query.spi.QueryParameterBinding; @@ -90,7 +86,6 @@ import org.hibernate.query.sql.spi.ParameterOccurrence; import org.hibernate.query.sql.spi.SelectInterpretationsKey; import org.hibernate.sql.exec.internal.CallbackImpl; import org.hibernate.sql.exec.spi.Callback; -import org.hibernate.sql.results.jdbc.spi.JdbcValuesMappingProducer; import org.hibernate.sql.results.spi.SingleResultConsumer; import org.hibernate.transform.ResultTransformer; import org.hibernate.type.BasicType; @@ -109,9 +104,18 @@ import jakarta.persistence.TemporalType; import jakarta.persistence.Tuple; import jakarta.persistence.TypedQuery; import jakarta.persistence.metamodel.SingularAttribute; +import org.hibernate.type.BasicTypeRegistry; +import org.hibernate.type.spi.TypeConfiguration; +import static java.lang.Character.isWhitespace; +import static java.util.Collections.addAll; +import static org.hibernate.internal.util.StringHelper.unqualify; +import static org.hibernate.internal.util.collections.CollectionHelper.isEmpty; +import static org.hibernate.internal.util.collections.CollectionHelper.isNotEmpty; +import static org.hibernate.internal.util.collections.CollectionHelper.makeCopy; import static org.hibernate.jpa.HibernateHints.HINT_NATIVE_LOCK_MODE; import static org.hibernate.query.results.Builders.resultClassBuilder; +import static org.hibernate.query.results.ResultSetMapping.resolveResultSetMapping; /** * @author Steve Ebersole @@ -142,22 +146,12 @@ public class NativeQueryImpl SharedSessionContractImplementor session) { this( memento, - () -> { - if ( memento.getResultMappingName() != null ) { - return buildResultSetMapping( memento.getResultMappingName(), false, session ); - } - else if ( memento.getResultType() != null ) { - return buildResultSetMapping( memento.getResultType().getName(), false, session ); - } - - return buildResultSetMapping( memento.getSqlString(), false, session ); - }, + () -> buildResultSetMapping( getResultSetMappingName( memento ), false, session ), (resultSetMapping, querySpaceConsumer, context ) -> { if ( memento.getResultMappingName() != null ) { - final NamedResultSetMappingMemento resultSetMappingMemento = session.getFactory() - .getQueryEngine() - .getNamedObjectRepository() - .getResultSetMappingMemento( memento.getResultMappingName() ); + final NamedResultSetMappingMemento resultSetMappingMemento = + getNamedObjectRepository( session ) + .getResultSetMappingMemento( memento.getResultMappingName() ); if ( resultSetMappingMemento != null ) { resultSetMappingMemento.resolve( resultSetMapping, querySpaceConsumer, context ); return true; @@ -165,21 +159,33 @@ public class NativeQueryImpl } if ( memento.getResultType() != null ) { - resultSetMapping.addResultBuilder( - resultClassBuilder( - memento.getResultType(), - context - ) - ); + resultSetMapping.addResultBuilder( resultClassBuilder( memento.getResultType(), context ) ); return true; } - - return false; + else { + return false; + } }, session ); } + private static NamedObjectRepository getNamedObjectRepository(SharedSessionContractImplementor session) { + return session.getFactory().getQueryEngine().getNamedObjectRepository(); + } + + private static String getResultSetMappingName(NamedNativeQueryMemento memento) { + if ( memento.getResultMappingName() != null ) { + return memento.getResultMappingName(); + } + else if ( memento.getResultType() != null ) { + return memento.getResultType().getName(); + } + else { + return memento.getSqlString(); + } + } + /** * Constructs a NativeQueryImpl given a sql query defined in the mappings. */ @@ -195,10 +201,9 @@ public class NativeQueryImpl }, (resultSetMapping, querySpaceConsumer, context) -> { if ( memento.getResultMappingName() != null ) { - final NamedResultSetMappingMemento resultSetMappingMemento = session.getFactory() - .getQueryEngine() - .getNamedObjectRepository() - .getResultSetMappingMemento( memento.getResultMappingName() ); + final NamedResultSetMappingMemento resultSetMappingMemento = + getNamedObjectRepository( session ) + .getResultSetMappingMemento( memento.getResultMappingName() ); if ( resultSetMappingMemento != null ) { resultSetMappingMemento.resolve( resultSetMapping, querySpaceConsumer, context ); return true; @@ -206,14 +211,12 @@ public class NativeQueryImpl } if ( memento.getResultType() != null ) { - resultSetMapping.addResultBuilder( resultClassBuilder( - memento.getResultType(), - context - ) ); + resultSetMapping.addResultBuilder( resultClassBuilder( memento.getResultType(), context ) ); return true; } - - return false; + else { + return false; + } }, session ); @@ -223,19 +226,16 @@ public class NativeQueryImpl } else if ( resultJavaType != null && !resultJavaType.isArray() ) { switch ( resultSetMapping.getNumberOfResultBuilders() ) { - case 0: { + case 0: throw new IllegalArgumentException( "Named query exists, but did not specify a resultClass" ); - } - case 1: { + case 1: final Class actualResultJavaType = resultSetMapping.getResultBuilders().get( 0 ).getJavaType(); if ( actualResultJavaType != null && !resultJavaType.isAssignableFrom( actualResultJavaType ) ) { throw buildIncompatibleException( resultJavaType, actualResultJavaType ); } break; - } - default: { + default: throw new IllegalArgumentException( "Cannot create TypedQuery for query with more than one return" ); - } } } } @@ -251,10 +251,9 @@ public class NativeQueryImpl memento, () -> buildResultSetMapping( resultSetMappingName, false, session ), (resultSetMapping, querySpaceConsumer, context) -> { - final NamedResultSetMappingMemento mappingMemento = session.getFactory() - .getQueryEngine() - .getNamedObjectRepository() - .getResultSetMappingMemento( resultSetMappingName ); + final NamedResultSetMappingMemento mappingMemento = + getNamedObjectRepository( session ) + .getResultSetMappingMemento( resultSetMappingName ); assert mappingMemento != null; mappingMemento.resolve( resultSetMapping, querySpaceConsumer, context ); return true; @@ -273,10 +272,8 @@ public class NativeQueryImpl this.originalSqlString = memento.getOriginalSqlString(); - final ParameterInterpretation parameterInterpretation = resolveParameterInterpretation( - originalSqlString, - session - ); + final ParameterInterpretation parameterInterpretation = + resolveParameterInterpretation( originalSqlString, session ); this.sqlString = parameterInterpretation.getAdjustedSqlString(); this.parameterMetadata = parameterInterpretation.toParameterMetadata( session ); @@ -286,14 +283,8 @@ public class NativeQueryImpl this.resultSetMapping = resultSetMappingCreator.get(); - //noinspection UnnecessaryLocalVariable - final boolean appliedAnyResults = resultSetMappingHandler.resolveResultSetMapping( - resultSetMapping, - querySpaces::add, - this - ); - - this.resultMappingSuppliedToCtor = appliedAnyResults; + this.resultMappingSuppliedToCtor = + resultSetMappingHandler.resolveResultSetMapping( resultSetMapping, querySpaces::add, this ); applyOptions( memento ); } @@ -304,9 +295,8 @@ public class NativeQueryImpl AbstractSharedSessionContract session) { super( session ); - final ParameterInterpretation parameterInterpretation = resolveParameterInterpretation( sqlString, session ); - this.originalSqlString = sqlString; + final ParameterInterpretation parameterInterpretation = resolveParameterInterpretation( sqlString, session ); this.sqlString = parameterInterpretation.getAdjustedSqlString(); this.parameterMetadata = parameterInterpretation.toParameterMetadata( session ); this.parameterOccurrences = parameterInterpretation.getOrderedParameterOccurrences(); @@ -314,11 +304,7 @@ public class NativeQueryImpl this.querySpaces = new HashSet<>(); this.resultSetMapping = buildResultSetMapping( resultSetMappingMemento.getName(), false, session ); - resultSetMappingMemento.resolve( - resultSetMapping, - this::addSynchronizedQuerySpace, - this - ); + resultSetMappingMemento.resolve( resultSetMapping, this::addSynchronizedQuerySpace, this ); this.resultMappingSuppliedToCtor = true; } @@ -328,14 +314,14 @@ public class NativeQueryImpl this.querySpaces = new HashSet<>(); - final ParameterInterpretation parameterInterpretation = resolveParameterInterpretation( sqlString, session ); this.originalSqlString = sqlString; + final ParameterInterpretation parameterInterpretation = resolveParameterInterpretation( sqlString, session ); this.sqlString = parameterInterpretation.getAdjustedSqlString(); this.parameterMetadata = parameterInterpretation.toParameterMetadata( session ); this.parameterOccurrences = parameterInterpretation.getOrderedParameterOccurrences(); this.parameterBindings = parameterMetadata.createBindings( session.getFactory() ); - this.resultSetMapping = ResultSetMapping.resolveResultSetMapping( sqlString, true, session.getFactory() ); + this.resultSetMapping = resolveResultSetMapping( sqlString, true, session.getFactory() ); this.resultMappingSuppliedToCtor = false; } @@ -351,7 +337,7 @@ public class NativeQueryImpl String registeredName, boolean isDynamic, SharedSessionContractImplementor session) { - return ResultSetMapping.resolveResultSetMapping( registeredName, isDynamic, session.getFactory() ); + return resolveResultSetMapping( registeredName, isDynamic, session.getFactory() ); } public List getParameterOccurrences() { @@ -359,24 +345,19 @@ public class NativeQueryImpl } private ParameterInterpretation resolveParameterInterpretation( - String sqlString, - SharedSessionContractImplementor session) { - final SessionFactoryImplementor sessionFactory = session.getFactory(); - final QueryEngine queryEngine = sessionFactory.getQueryEngine(); - final QueryInterpretationCache interpretationCache = queryEngine.getInterpretationCache(); + String sqlString, SharedSessionContractImplementor session) { + return session.getFactory().getQueryEngine().getInterpretationCache() + .resolveNativeQueryParameters( sqlString, + s -> parameterInterpretation( sqlString, session ) ); + } - return interpretationCache.resolveNativeQueryParameters( - sqlString, - s -> { - final ParameterRecognizerImpl parameterRecognizer = new ParameterRecognizerImpl(); - - session.getFactory().getServiceRegistry() - .requireService( NativeQueryInterpreter.class ) - .recognizeParameters( sqlString, parameterRecognizer ); - - return new ParameterInterpretationImpl( parameterRecognizer ); - } - ); + private static ParameterInterpretationImpl parameterInterpretation( + String sqlString, SharedSessionContractImplementor session) { + final ParameterRecognizerImpl parameterRecognizer = new ParameterRecognizerImpl(); + session.getFactory().getServiceRegistry() + .requireService( NativeQueryInterpreter.class ) + .recognizeParameters( sqlString, parameterRecognizer ); + return new ParameterInterpretationImpl( parameterRecognizer ); } protected void applyOptions(NamedNativeQueryMemento memento) { @@ -389,7 +370,7 @@ public class NativeQueryImpl setFirstResult( memento.getFirstResult() ); } - final Set copy = CollectionHelper.makeCopy( memento.getQuerySpaces() ); + final Set copy = makeCopy( memento.getQuerySpaces() ); if ( copy != null ) { this.querySpaces = copy; } @@ -557,16 +538,14 @@ public class NativeQueryImpl public Boolean isSelectQuery() { if ( resultMappingSuppliedToCtor || resultSetMapping.getNumberOfResultBuilders() > 0 - || isReadOnly() ) { + || isReadOnly() + // as a last resort, see if the SQL starts with "select" + || startsWithSelect() ) { return true; } - - if ( startsWithSelect() ) { - // as a last resort, see if the SQL starts with "select" - return true; + else { + return null; } - - return null; } private boolean startsWithSelect() { @@ -605,21 +584,16 @@ public class NativeQueryImpl private boolean shouldFlush() { if ( getSession().isTransactionInProgress() ) { - FlushMode effectiveFlushMode = getQueryOptions().getFlushMode(); - if ( effectiveFlushMode == null ) { - effectiveFlushMode = getSession().getHibernateFlushMode(); - } - - if ( effectiveFlushMode == FlushMode.ALWAYS ) { - return true; - } - - if ( effectiveFlushMode == FlushMode.AUTO ) { - return getSession().getFactory().getSessionFactoryOptions().isJpaBootstrap(); - } + final FlushMode flushMode = getQueryOptions().getFlushMode(); + return switch ( flushMode == null ? getSession().getHibernateFlushMode() : flushMode ) { + case AUTO -> getSession().getFactory().getSessionFactoryOptions().isJpaBootstrap(); + case ALWAYS -> true; + default -> false; + }; + } + else { + return false; } - - return false; } @Override @@ -644,19 +618,16 @@ public class NativeQueryImpl } protected SelectQueryPlan resolveSelectQueryPlan() { - if ( isCacheableQuery() ) { - final QueryInterpretationCache.Key cacheKey = generateSelectInterpretationsKey( resultSetMapping ); - return getSession().getFactory().getQueryEngine().getInterpretationCache() - .resolveSelectQueryPlan( cacheKey, () -> createQueryPlan( resultSetMapping ) ); - } - else { - return createQueryPlan( resultSetMapping ); - } + return isCacheableQuery() + ? getInterpretationCache() + .resolveSelectQueryPlan( selectInterpretationsKey(), this::createQueryPlan ) + : createQueryPlan(); } - private NativeSelectQueryPlan createQueryPlan(ResultSetMapping resultSetMapping) { - final String sqlString = expandParameterLists(); + private NativeSelectQueryPlan createQueryPlan() { final NativeSelectQueryDefinition queryDefinition = new NativeSelectQueryDefinition<>() { + final String sqlString = expandParameterLists(); + @Override public String getSqlString() { return sqlString; @@ -682,18 +653,17 @@ public class NativeQueryImpl return querySpaces; } }; - - return getSessionFactory().getQueryEngine().getNativeQueryInterpreter() - .createQueryPlan( queryDefinition, getSessionFactory() ); + return getNativeQueryInterpreter().createQueryPlan( queryDefinition, getSessionFactory() ); } /* * Used by Hibernate Reactive */ protected NativeSelectQueryPlan createCountQueryPlan() { - final BasicType longType = getSessionFactory().getTypeConfiguration().getBasicTypeForJavaType(Long.class); - final String sqlString = expandParameterLists(); final NativeSelectQueryDefinition queryDefinition = new NativeSelectQueryDefinition<>() { + final BasicType longType = getTypeConfiguration().getBasicTypeForJavaType(Long.class); + final String sqlString = expandParameterLists(); + @Override public String getSqlString() { return "select count(*) from (" + sqlString + ") a_"; @@ -721,9 +691,15 @@ public class NativeQueryImpl return querySpaces; } }; + return getNativeQueryInterpreter().createQueryPlan( queryDefinition, getSessionFactory() ); + } - return getSessionFactory().getQueryEngine().getNativeQueryInterpreter() - .createQueryPlan( queryDefinition, getSessionFactory() ); + private TypeConfiguration getTypeConfiguration() { + return getSessionFactory().getTypeConfiguration(); + } + + private NativeQueryInterpreter getNativeQueryInterpreter() { + return getSessionFactory().getQueryEngine().getNativeQueryInterpreter(); } protected String expandParameterLists() { @@ -749,8 +725,8 @@ public class NativeQueryImpl } final Collection bindValues = binding.getBindValues(); - int bindValueCount = bindValues.size(); - int bindValueMaxCount = determineBindValueMaxCount( paddingEnabled, inExprLimit, bindValueCount ); + final int bindValueCount = bindValues.size(); + final int bindValueMaxCount = determineBindValueMaxCount( paddingEnabled, inExprLimit, bindValueCount ); if ( inExprLimit > 0 && bindValueCount > inExprLimit ) { log.tooManyInExpressions( @@ -773,7 +749,7 @@ public class NativeQueryImpl boolean isEnclosedInParens = true; for ( int i = sourcePosition - 1; i >= 0; i-- ) { final char ch = sqlString.charAt( i ); - if ( !Character.isWhitespace( ch ) ) { + if ( !isWhitespace( ch ) ) { isEnclosedInParens = ch == '('; break; } @@ -781,7 +757,7 @@ public class NativeQueryImpl if ( isEnclosedInParens ) { for ( int i = sourcePosition + 1; i < sqlString.length(); i++ ) { final char ch = sqlString.charAt( i ); - if ( !Character.isWhitespace( ch ) ) { + if ( !isWhitespace( ch ) ) { isEnclosedInParens = ch == ')'; break; } @@ -802,16 +778,11 @@ public class NativeQueryImpl final String expansionListAsString; // HHH-8901 if ( bindValueMaxCount == 0 ) { - if ( isEnclosedInParens ) { - expansionListAsString = "null"; - } - else { - expansionListAsString = "(null)"; - } + expansionListAsString = isEnclosedInParens ? "null" : "(null)"; } else { // Shift 1 bit instead of multiplication by 2 - char[] chars; + final char[] chars; if ( isEnclosedInParens ) { chars = new char[( bindValueMaxCount << 1 ) - 1]; chars[0] = '?'; @@ -863,7 +834,7 @@ public class NativeQueryImpl return bindValueMaxCount; } - private SelectInterpretationsKey generateSelectInterpretationsKey(JdbcValuesMappingProducer resultSetMapping) { + private SelectInterpretationsKey selectInterpretationsKey() { return new SelectInterpretationsKey( getQueryString(), resultSetMapping, @@ -894,26 +865,33 @@ public class NativeQueryImpl return resolveNonSelectQueryPlan().executeUpdate( this ); } + private BasicTypeRegistry getBasicTypeRegistry() { + return getTypeConfiguration().getBasicTypeRegistry(); + } + + private QueryInterpretationCache getInterpretationCache() { + return getSession().getFactory().getQueryEngine().getInterpretationCache(); + } + private NonSelectQueryPlan resolveNonSelectQueryPlan() { NonSelectQueryPlan queryPlan = null; final QueryInterpretationCache.Key cacheKey = generateNonSelectInterpretationsKey(); if ( cacheKey != null ) { - queryPlan = getSession().getFactory().getQueryEngine().getInterpretationCache().getNonSelectQueryPlan( cacheKey ); + queryPlan = getInterpretationCache().getNonSelectQueryPlan( cacheKey ); } if ( queryPlan == null ) { final String sqlString = expandParameterLists(); queryPlan = new NativeNonSelectQueryPlanImpl( sqlString, querySpaces, parameterOccurrences ); if ( cacheKey != null ) { - getSession().getFactory().getQueryEngine().getInterpretationCache().cacheNonSelectQueryPlan( cacheKey, queryPlan ); + getInterpretationCache().cacheNonSelectQueryPlan( cacheKey, queryPlan ); } } return queryPlan; } - protected NonSelectInterpretationsKey generateNonSelectInterpretationsKey() { // todo (6.0) - should this account for query spaces in determining "cacheable"? return isCacheableQuery() @@ -933,12 +911,7 @@ public class NativeQueryImpl } public NativeQueryImplementor addScalar(int position, Class type) { - return registerBuilder( - Builders.scalar( - position, - getSessionFactory().getTypeConfiguration().getBasicTypeRegistry().getRegisteredType( type ) - ) - ); + return registerBuilder( Builders.scalar( position, getBasicTypeRegistry().getRegisteredType( type ) ) ); } protected NativeQueryImplementor registerBuilder(ResultBuilder builder) { @@ -948,13 +921,8 @@ public class NativeQueryImpl @Override public NativeQuery addScalar(String columnAlias, @SuppressWarnings("rawtypes") BasicTypeReference type) { - return registerBuilder( - Builders.scalar( - columnAlias, - getSessionFactory().getTypeConfiguration().getBasicTypeRegistry() - .resolve( (BasicTypeReference) type ) - ) - ); + return registerBuilder( Builders.scalar( columnAlias, + getBasicTypeRegistry().resolve( (BasicTypeReference) type ) ) ); } @Override @@ -1003,10 +971,8 @@ public class NativeQueryImpl @Override public InstantiationResultNode addInstantiation(Class targetJavaType) { - final DynamicResultBuilderInstantiation builder = Builders.instantiation( - targetJavaType, - getSessionFactory() - ); + final DynamicResultBuilderInstantiation builder = + Builders.instantiation( targetJavaType, getSessionFactory() ); registerBuilder( builder ); return builder; } @@ -1038,11 +1004,8 @@ public class NativeQueryImpl @Override public DynamicResultBuilderEntityStandard addRoot(String tableAlias, String entityName) { - final DynamicResultBuilderEntityStandard resultBuilder = Builders.entity( - tableAlias, - entityName, - getSessionFactory() - ); + final DynamicResultBuilderEntityStandard resultBuilder = + Builders.entity( tableAlias, entityName, getSessionFactory() ); resultSetMapping.addResultBuilder( resultBuilder ); return resultBuilder; } @@ -1054,7 +1017,7 @@ public class NativeQueryImpl @Override public NativeQueryImplementor addEntity(String entityName) { - return addEntity( StringHelper.unqualify( entityName ), entityName ); + return addEntity( unqualify( entityName ), entityName ); } @Override @@ -1076,7 +1039,7 @@ public class NativeQueryImpl @Override public NativeQueryImplementor addEntity(Class entityType, LockMode lockMode) { - return addEntity( StringHelper.unqualify( entityType.getName() ), entityType.getName(), lockMode); + return addEntity( unqualify( entityType.getName() ), entityType.getName(), lockMode); } @Override @@ -1103,7 +1066,7 @@ public class NativeQueryImpl } private FetchReturn createFetchJoin(String tableAlias, String path) { - int loc = path.indexOf( '.' ); + final int loc = path.indexOf( '.' ); if ( loc < 0 ) { throw new PathException( "Not a property path '" + path + "'" ); } @@ -1141,7 +1104,7 @@ public class NativeQueryImpl if ( querySpaces == null ) { querySpaces = new HashSet<>(); } - Collections.addAll( querySpaces, spaces ); + addAll( querySpaces, spaces ); } } @@ -1150,25 +1113,23 @@ public class NativeQueryImpl if ( querySpaces == null ) { querySpaces = new HashSet<>(); } - Collections.addAll( querySpaces, (String[]) spaces ); + addAll( querySpaces, (String[]) spaces ); } } + private MappingMetamodelImplementor getMappingMetamodel() { + return getSession().getFactory().getRuntimeMetamodels().getMappingMetamodel(); + } + @Override - public NativeQueryImplementor addSynchronizedEntityName(String entityName) throws MappingException { - final EntityPersister entityDescriptor = getSession().getFactory().getRuntimeMetamodels() - .getMappingMetamodel() - .getEntityDescriptor( entityName ); - addQuerySpaces( entityDescriptor.getQuerySpaces() ); + public NativeQueryImplementor addSynchronizedEntityName(String entityName) { + addQuerySpaces( getMappingMetamodel().getEntityDescriptor( entityName ).getQuerySpaces() ); return this; } @Override - public NativeQueryImplementor addSynchronizedEntityClass(@SuppressWarnings("rawtypes") Class entityClass) throws MappingException { - final EntityPersister entityDescriptor = getSession().getFactory().getRuntimeMetamodels() - .getMappingMetamodel() - .getEntityDescriptor( entityClass ); - addQuerySpaces( entityDescriptor.getQuerySpaces() ); + public NativeQueryImplementor addSynchronizedEntityClass(@SuppressWarnings("rawtypes") Class entityClass) { + addQuerySpaces( getMappingMetamodel().getEntityDescriptor( entityClass ).getQuerySpaces() ); return this; } @@ -1303,19 +1264,19 @@ public class NativeQueryImpl } protected void applySynchronizeSpace(Object value) { - if ( value instanceof String ) { - addSynchronizedQuerySpace( (String) value ); + if ( value instanceof String string ) { + addSynchronizedQuerySpace( string ); } - else if ( value instanceof Class ) { - addSynchronizedEntityClass( (Class) value ); + else if ( value instanceof Class clazz ) { + addSynchronizedEntityClass( clazz ); } - else if ( value instanceof Object[] ) { - for ( Object element : (Object[]) value ) { + else if ( value instanceof Object[] array ) { + for ( Object element : array ) { applySynchronizeSpace( element ); } } - else if ( value instanceof Iterable ) { - for ( Object element : (Iterable) value ) { + else if ( value instanceof Iterable iterable ) { + for ( Object element : iterable ) { applySynchronizeSpace( element ); } } @@ -1474,9 +1435,6 @@ public class NativeQueryImpl return this; } - - - @Override public NativeQueryImplementor setParameterList(int position, @SuppressWarnings("rawtypes") Collection values) { super.setParameterList( position, values ); @@ -1620,12 +1578,9 @@ public class NativeQueryImpl @Override public ParameterMetadataImplementor toParameterMetadata(SharedSessionContractImplementor session1) { - if ( CollectionHelper.isEmpty( positionalParameters ) && CollectionHelper.isEmpty( namedParameters ) ) { - return ParameterMetadataImpl.EMPTY; - } - else { - return new ParameterMetadataImpl( positionalParameters, namedParameters ); - } + return isEmpty( positionalParameters ) && isEmpty( namedParameters ) + ? ParameterMetadataImpl.EMPTY + : new ParameterMetadataImpl( positionalParameters, namedParameters ); } @Override @@ -1635,17 +1590,17 @@ public class NativeQueryImpl @Override public String toString() { - final StringBuilder buffer = new StringBuilder( "ParameterInterpretationImpl (" ) - .append( sqlString ) - .append( ") : {" ); + final StringBuilder buffer = + new StringBuilder( "ParameterInterpretationImpl (" ) + .append( sqlString ) + .append( ") : {" ); final String lineSeparator = System.lineSeparator(); - if ( CollectionHelper.isNotEmpty( parameterList ) ) { + if ( isNotEmpty( parameterList ) ) { for ( int i = 0, size = parameterList.size(); i < size; i++ ) { buffer.append( lineSeparator ).append( " ," ); } buffer.setLength( buffer.length() - 1 ); } - return buffer.append( lineSeparator ).append( "}" ).toString(); } } diff --git a/hibernate-core/src/main/java/org/hibernate/query/sqm/internal/AbstractSqmSelectionQuery.java b/hibernate-core/src/main/java/org/hibernate/query/sqm/internal/AbstractSqmSelectionQuery.java index dedace087a..b768a99325 100644 --- a/hibernate-core/src/main/java/org/hibernate/query/sqm/internal/AbstractSqmSelectionQuery.java +++ b/hibernate-core/src/main/java/org/hibernate/query/sqm/internal/AbstractSqmSelectionQuery.java @@ -113,8 +113,8 @@ abstract class AbstractSqmSelectionQuery extends AbstractSelectionQuery { private SqmSelectStatement getSqmSelectStatement() { final SqmStatement sqmStatement = getSqmStatement(); - if ( sqmStatement instanceof SqmSelectStatement ) { - return (SqmSelectStatement) sqmStatement; + if ( sqmStatement instanceof SqmSelectStatement selectStatement ) { + return selectStatement; } else { throw new IllegalSelectQueryException( "Not a select query" ); @@ -157,8 +157,9 @@ abstract class AbstractSqmSelectionQuery extends AbstractSelectionQuery { if ( keyedPage == null ) { throw new IllegalArgumentException( "KeyedPage was null" ); } - final List> results = new SqmSelectionQueryImpl>( this, keyedPage ) - .getResultList(); + final List> results = + new SqmSelectionQueryImpl>( this, keyedPage ) + .getResultList(); final Page page = keyedPage.getPage(); return new KeyedResultList<>( collectResults( results, page.getSize(), keyedPage.getKeyInterpretation() ), diff --git a/hibernate-core/src/test/java/org/hibernate/orm/test/jpa/ejb3configuration/ConfigurationObjectSettingTest.java b/hibernate-core/src/test/java/org/hibernate/orm/test/jpa/ejb3configuration/ConfigurationObjectSettingTest.java index 4a75495349..b04b2b5688 100644 --- a/hibernate-core/src/test/java/org/hibernate/orm/test/jpa/ejb3configuration/ConfigurationObjectSettingTest.java +++ b/hibernate-core/src/test/java/org/hibernate/orm/test/jpa/ejb3configuration/ConfigurationObjectSettingTest.java @@ -19,7 +19,6 @@ import org.hibernate.dialect.Dialect; import org.hibernate.dialect.H2Dialect; import org.hibernate.engine.jdbc.dialect.internal.DialectResolverInitiator; import org.hibernate.engine.jdbc.dialect.spi.DialectResolver; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl; import org.hibernate.jpa.boot.spi.Bootstrap; import org.hibernate.orm.test.dialect.resolver.TestingDialectResolutionInfo; @@ -34,6 +33,8 @@ import org.junit.jupiter.api.Test; import jakarta.persistence.SharedCacheMode; import jakarta.persistence.ValidationMode; +import static java.util.Collections.emptyMap; +import static java.util.Collections.singletonMap; import static org.assertj.core.api.Assertions.assertThat; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertNull; @@ -294,6 +295,22 @@ public class ConfigurationObjectSettingTest { // verifySchemaGenSettingsPrecedence(); } + public static Map toMap(String... pairs) { + assert pairs.length % 2 == 0; + switch ( pairs.length ) { + case 0: + return emptyMap(); + case 2: + return singletonMap( pairs[0], pairs[1] ); + default: + final Map result = new HashMap<>(); + for ( int i = 0; i < pairs.length; i+=2 ) { + result.put( pairs[i], pairs[i+1] ); + } + return result; + } + } + private void verifySchemaGenSettings( String dbActionSettingName, String scriptActionSettingName, @@ -304,7 +321,7 @@ public class ConfigurationObjectSettingTest { final boolean createSchemas = true; final String dbName = "H2"; - final Map settings = CollectionHelper.toMap( + final Map settings = toMap( dbActionSettingName, dbAction.getExternalJpaName(), scriptActionSettingName, scriptAction.getExternalJpaName(), createSchemasSettingName, Boolean.toString( createSchemas ), diff --git a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutabilityMapAsBasicTests.java b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutabilityMapAsBasicTests.java index f02e6578a6..2e7a63b081 100644 --- a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutabilityMapAsBasicTests.java +++ b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutabilityMapAsBasicTests.java @@ -7,7 +7,6 @@ package org.hibernate.orm.test.mapping.mutability.attribute; import java.util.Map; import org.hibernate.annotations.Mutability; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.mapping.BasicValue; import org.hibernate.mapping.Property; import org.hibernate.metamodel.mapping.AttributeMapping; @@ -154,7 +153,7 @@ public class ImmutabilityMapAsBasicTests { scope.inTransaction( (session) -> { session.persist( new TestEntity( 1, - CollectionHelper.toMap( + Map.of( "abc", "123", "def", "456" ) diff --git a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutableMapAsBasicTests.java b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutableMapAsBasicTests.java index 3194f1db6b..137cc99c00 100644 --- a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutableMapAsBasicTests.java +++ b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/ImmutableMapAsBasicTests.java @@ -7,7 +7,6 @@ package org.hibernate.orm.test.mapping.mutability.attribute; import java.util.Map; import org.hibernate.annotations.Immutable; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.mapping.BasicValue; import org.hibernate.mapping.PersistentClass; import org.hibernate.mapping.Property; @@ -171,7 +170,7 @@ public class ImmutableMapAsBasicTests { scope.inTransaction( (session) -> { session.persist( new TestEntity( 1, - CollectionHelper.toMap( + Map.of( "abc", "123", "def", "456" ) diff --git a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/MutableMapAsBasicTests.java b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/MutableMapAsBasicTests.java index 7d2c02a554..07ef91f285 100644 --- a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/MutableMapAsBasicTests.java +++ b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/attribute/MutableMapAsBasicTests.java @@ -6,7 +6,6 @@ package org.hibernate.orm.test.mapping.mutability.attribute; import java.util.Map; -import org.hibernate.internal.util.collections.CollectionHelper; import org.hibernate.orm.test.mapping.mutability.converted.MapConverter; import org.hibernate.testing.jdbc.SQLStatementInspector; @@ -86,7 +85,7 @@ public class MutableMapAsBasicTests { scope.inTransaction( (session) -> { session.persist( new TestEntity( 1, - CollectionHelper.toMap( + Map.of( "abc", "123", "def", "456" ) diff --git a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/converted/MapConverter.java b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/converted/MapConverter.java index 708d03865c..61dee3ff84 100644 --- a/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/converted/MapConverter.java +++ b/hibernate-core/src/test/java/org/hibernate/orm/test/mapping/mutability/converted/MapConverter.java @@ -4,12 +4,15 @@ */ package org.hibernate.orm.test.mapping.mutability.converted; +import java.util.HashMap; import java.util.Map; import org.hibernate.internal.util.collections.CollectionHelper; import jakarta.persistence.AttributeConverter; +import static java.util.Collections.emptyMap; +import static java.util.Collections.singletonMap; import static org.hibernate.internal.util.StringHelper.isEmpty; import static org.hibernate.internal.util.StringHelper.join; import static org.hibernate.internal.util.StringHelper.split; @@ -20,11 +23,37 @@ import static org.hibernate.internal.util.StringHelper.split; public class MapConverter implements AttributeConverter, String> { @Override public String convertToDatabaseColumn(Map map) { - return CollectionHelper.isEmpty( map ) ? null : join( ", ", CollectionHelper.asPairs( map ) ); + return CollectionHelper.isEmpty( map ) ? null : join( ", ", asPairs( map ) ); } @Override public Map convertToEntityAttribute(String pairs) { - return isEmpty( pairs ) ? null : CollectionHelper.toMap( split( ", ", pairs ) ); + return isEmpty( pairs ) ? null : toMap( split( ", ", pairs ) ); + } + + public static Map toMap(String... pairs) { + assert pairs.length % 2 == 0; + switch ( pairs.length ) { + case 0: + return emptyMap(); + case 2: + return singletonMap( pairs[0], pairs[1] ); + default: + final Map result = new HashMap<>(); + for ( int i = 0; i < pairs.length; i+=2 ) { + result.put( pairs[i], pairs[i+1] ); + } + return result; + } + } + + public static String[] asPairs(Map map) { + final String[] pairs = new String[ map.size() * 2 ]; + int i = 0; + for ( Map.Entry entry : map.entrySet() ) { + pairs[i++] = entry.getKey(); + pairs[i++] = entry.getValue(); + } + return pairs; } }