Move VersionType logic to VersionJavaTypeDescriptor

This commit is contained in:
Christian Beikov 2021-10-05 15:39:56 +02:00
parent 81e66fa970
commit 653f62ac60
57 changed files with 625 additions and 530 deletions

View File

@ -6,14 +6,10 @@
*/ */
package org.hibernate.userguide.collections.type; package org.hibernate.userguide.collections.type;
import java.sql.Timestamp;
import java.util.Comparator;
import java.util.Date; import java.util.Date;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.AbstractSingleColumnStandardBasicType; import org.hibernate.type.AbstractSingleColumnStandardBasicType;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JdbcTimestampTypeDescriptor; import org.hibernate.type.descriptor.java.JdbcTimestampTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor; import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor;
@ -22,9 +18,7 @@ import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor;
*/ */
//tag::collections-map-custom-key-type-mapping-example[] //tag::collections-map-custom-key-type-mapping-example[]
public class TimestampEpochType public class TimestampEpochType extends AbstractSingleColumnStandardBasicType<Date> {
extends AbstractSingleColumnStandardBasicType<Date>
implements VersionType<Date> {
public static final TimestampEpochType INSTANCE = new TimestampEpochType(); public static final TimestampEpochType INSTANCE = new TimestampEpochType();
@ -41,26 +35,7 @@ public class TimestampEpochType
} }
@Override @Override
public Date next( public Date fromStringValue(CharSequence xml) throws HibernateException {
Date current,
SharedSessionContractImplementor session) {
return seed( session );
}
@Override
public Date seed(
SharedSessionContractImplementor session) {
return new Timestamp( System.currentTimeMillis() );
}
@Override
public Comparator<Date> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
@Override
public Date fromStringValue(
CharSequence xml) throws HibernateException {
return fromString( xml ); return fromString( xml );
} }
} }

View File

@ -6,7 +6,7 @@
*/ */
package org.hibernate; package org.hibernate;
import org.hibernate.type.VersionType; import org.hibernate.type.BasicType;
/** /**
* Represents a replication strategy. * Represents a replication strategy.
@ -20,7 +20,7 @@ public enum ReplicationMode {
*/ */
EXCEPTION { EXCEPTION {
@Override @Override
public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, VersionType versionType) { public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, BasicType<Object> versionType) {
throw new AssertionFailure( "should not be called" ); throw new AssertionFailure( "should not be called" );
} }
}, },
@ -29,7 +29,7 @@ public enum ReplicationMode {
*/ */
IGNORE { IGNORE {
@Override @Override
public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, VersionType versionType) { public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, BasicType<Object> versionType) {
return false; return false;
} }
}, },
@ -38,7 +38,7 @@ public enum ReplicationMode {
*/ */
OVERWRITE { OVERWRITE {
@Override @Override
public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, VersionType versionType) { public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, BasicType<Object> versionType) {
return true; return true;
} }
}, },
@ -48,9 +48,9 @@ public enum ReplicationMode {
LATEST_VERSION { LATEST_VERSION {
@Override @Override
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, VersionType versionType) { public boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, BasicType<Object> versionType) {
// always overwrite non-versioned data (because we don't know which is newer) // always overwrite non-versioned data (because we don't know which is newer)
return versionType == null || versionType.getComparator().compare( currentVersion, newVersion ) <= 0; return versionType == null || versionType.getJavaTypeDescriptor().getComparator().compare( currentVersion, newVersion ) <= 0;
} }
}; };
@ -64,6 +64,6 @@ public enum ReplicationMode {
* *
* @return {@code true} indicates the data should be overwritten; {@code false} indicates it should not. * @return {@code true} indicates the data should be overwritten; {@code false} indicates it should not.
*/ */
public abstract boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, VersionType versionType); public abstract boolean shouldOverwriteCurrentVersion(Object entity, Object currentVersion, Object newVersion, BasicType<Object> versionType);
} }

View File

@ -29,7 +29,7 @@ public enum SourceType {
} }
/** /**
* Get the corresponding Hibernate {@link org.hibernate.type.VersionType} name. * Get the corresponding Hibernate {@link org.hibernate.type.BasicType} name.
* *
* @return The corresponding type name. * @return The corresponding type name.
*/ */

View File

@ -12,7 +12,7 @@ import org.hibernate.cache.cfg.spi.CollectionDataCachingConfig;
import org.hibernate.cache.spi.access.AccessType; import org.hibernate.cache.spi.access.AccessType;
import org.hibernate.mapping.Collection; import org.hibernate.mapping.Collection;
import org.hibernate.metamodel.model.domain.NavigableRole; import org.hibernate.metamodel.model.domain.NavigableRole;
import org.hibernate.type.VersionType; import org.hibernate.type.BasicType;
/** /**
* @author Steve Ebersole * @author Steve Ebersole
@ -46,7 +46,7 @@ public class CollectionDataCachingConfigImpl
if ( !isVersioned() ) { if ( !isVersioned() ) {
return null; return null;
} }
return ( (VersionType) collectionDescriptor.getOwner().getVersion().getType() ).getComparator(); return ( (BasicType<?>) collectionDescriptor.getOwner().getVersion().getType() ).getJavaTypeDescriptor().getComparator();
} }
@Override @Override

View File

@ -24,7 +24,7 @@ import org.hibernate.mapping.Collection;
import org.hibernate.mapping.PersistentClass; import org.hibernate.mapping.PersistentClass;
import org.hibernate.mapping.RootClass; import org.hibernate.mapping.RootClass;
import org.hibernate.metamodel.model.domain.NavigableRole; import org.hibernate.metamodel.model.domain.NavigableRole;
import org.hibernate.type.VersionType; import org.hibernate.type.BasicType;
/** /**
* DomainDataRegionConfig implementation * DomainDataRegionConfig implementation
@ -99,7 +99,7 @@ public class DomainDataRegionConfigImpl implements DomainDataRegionConfig {
x -> new EntityDataCachingConfigImpl( x -> new EntityDataCachingConfigImpl(
rootEntityName, rootEntityName,
bootEntityDescriptor.isVersioned() bootEntityDescriptor.isVersioned()
? (Supplier<Comparator>) () -> ( (VersionType) bootEntityDescriptor.getVersion().getType() ).getComparator() ? (Supplier<Comparator>) () -> ( (BasicType<?>) bootEntityDescriptor.getVersion().getType() ).getJavaTypeDescriptor().getComparator()
: null, : null,
bootEntityDescriptor.isMutable(), bootEntityDescriptor.isMutable(),
accessType accessType

View File

@ -21,8 +21,8 @@ import org.hibernate.persister.entity.Lockable;
import org.hibernate.pretty.MessageHelper; import org.hibernate.pretty.MessageHelper;
import org.hibernate.sql.Update; import org.hibernate.sql.Update;
import org.hibernate.stat.spi.StatisticsImplementor; import org.hibernate.stat.spi.StatisticsImplementor;
import org.hibernate.type.BasicType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType;
import org.jboss.logging.Logger; import org.jboss.logging.Logger;
@ -84,7 +84,7 @@ public class UpdateLockingStrategy implements LockingStrategy {
final JdbcCoordinator jdbcCoordinator = session.getJdbcCoordinator(); final JdbcCoordinator jdbcCoordinator = session.getJdbcCoordinator();
final PreparedStatement st = jdbcCoordinator.getStatementPreparer().prepareStatement( sql ); final PreparedStatement st = jdbcCoordinator.getStatementPreparer().prepareStatement( sql );
try { try {
final VersionType lockableVersionType = lockable.getVersionType(); final BasicType<?> lockableVersionType = lockable.getVersionType();
lockableVersionType.nullSafeSet( st, version, 1, session ); lockableVersionType.nullSafeSet( st, version, 1, session );
int offset = 2; int offset = 2;

View File

@ -17,7 +17,7 @@ import org.hibernate.property.access.spi.Getter;
import org.hibernate.type.IdentifierType; import org.hibernate.type.IdentifierType;
import org.hibernate.type.PrimitiveType; import org.hibernate.type.PrimitiveType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType; import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
/** /**
* Helper for dealing with unsaved value handling * Helper for dealing with unsaved value handling
@ -114,18 +114,19 @@ public class UnsavedValueFactory {
* *
* @return The appropriate VersionValue * @return The appropriate VersionValue
*/ */
public static VersionValue getUnsavedVersionValue( public static <X> VersionValue getUnsavedVersionValue(
String versionUnsavedValue, String versionUnsavedValue,
Getter versionGetter, Getter versionGetter,
VersionType versionType, VersionJavaTypeDescriptor<X> versionType,
Constructor constructor) { Constructor constructor) {
if ( versionUnsavedValue == null ) { if ( versionUnsavedValue == null ) {
if ( constructor!=null ) { if ( constructor!=null ) {
final Object defaultValue = versionGetter.get( instantiate( constructor ) ); @SuppressWarnings("unchecked")
final X defaultValue = (X) versionGetter.get( instantiate( constructor ) );
// if the version of a newly instantiated object is not the same // if the version of a newly instantiated object is not the same
// as the version seed value, use that as the unsaved-value // as the version seed value, use that as the unsaved-value
return versionType.isEqual( versionType.seed( null ), defaultValue ) return versionType.areEqual( versionType.seed( null ), defaultValue )
? VersionValue.UNDEFINED ? VersionValue.UNDEFINED
: new VersionValue( defaultValue ); : new VersionValue( defaultValue );
} }

View File

@ -9,7 +9,7 @@ package org.hibernate.engine.internal;
import org.hibernate.engine.spi.SharedSessionContractImplementor; import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.CoreMessageLogger; import org.hibernate.internal.CoreMessageLogger;
import org.hibernate.persister.entity.EntityPersister; import org.hibernate.persister.entity.EntityPersister;
import org.hibernate.type.VersionType; import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
import org.jboss.logging.Logger; import org.jboss.logging.Logger;
@ -31,21 +31,21 @@ public final class Versioning {
} }
/** /**
* Create an initial optimistic locking value according the {@link VersionType} * Create an initial optimistic locking value according the {@link VersionJavaTypeDescriptor}
* contract for the version property. * contract for the version property.
* *
* @param versionType The version type. * @param versionType The version type.
* @param session The originating session * @param session The originating session
* @return The initial optimistic locking value * @return The initial optimistic locking value
*/ */
private static Object seed(VersionType versionType, SharedSessionContractImplementor session) { private static Object seed(VersionJavaTypeDescriptor<Object> versionType, SharedSessionContractImplementor session) {
final Object seed = versionType.seed( session ); final Object seed = versionType.seed( session );
LOG.tracef( "Seeding: %s", seed ); LOG.tracef( "Seeding: %s", seed );
return seed; return seed;
} }
/** /**
* Create an initial optimistic locking value according the {@link VersionType} * Create an initial optimistic locking value according the {@link VersionJavaTypeDescriptor}
* contract for the version property <b>if required</b> and inject it into * contract for the version property <b>if required</b> and inject it into
* the snapshot state. * the snapshot state.
* *
@ -59,7 +59,7 @@ public final class Versioning {
public static boolean seedVersion( public static boolean seedVersion(
Object[] fields, Object[] fields,
int versionProperty, int versionProperty,
VersionType versionType, VersionJavaTypeDescriptor<Object> versionType,
SharedSessionContractImplementor session) { SharedSessionContractImplementor session) {
final Object initialVersion = fields[versionProperty]; final Object initialVersion = fields[versionProperty];
if ( if (
@ -80,21 +80,20 @@ public final class Versioning {
/** /**
* Generate the next increment in the optimistic locking value according * Generate the next increment in the optimistic locking value according
* the {@link VersionType} contract for the version property. * the {@link VersionJavaTypeDescriptor} contract for the version property.
* *
* @param version The current version * @param version The current version
* @param versionType The version type * @param versionType The version type
* @param session The originating session * @param session The originating session
* @return The incremented optimistic locking value. * @return The incremented optimistic locking value.
*/ */
@SuppressWarnings("unchecked") public static Object increment(Object version, VersionJavaTypeDescriptor<Object> versionType, SharedSessionContractImplementor session) {
public static Object increment(Object version, VersionType versionType, SharedSessionContractImplementor session) {
final Object next = versionType.next( version, session ); final Object next = versionType.next( version, session );
if ( LOG.isTraceEnabled() ) { if ( LOG.isTraceEnabled() ) {
LOG.tracef( LOG.tracef(
"Incrementing: %s to %s", "Incrementing: %s to %s",
versionType.toLoggableString( version, session.getFactory() ), versionType.toString( version ),
versionType.toLoggableString( next, session.getFactory() ) versionType.toString( next )
); );
} }
return next; return next;

View File

@ -55,6 +55,7 @@ import org.hibernate.query.spi.QueryEngine;
import org.hibernate.service.spi.ServiceRegistryImplementor; import org.hibernate.service.spi.ServiceRegistryImplementor;
import org.hibernate.stat.spi.StatisticsImplementor; import org.hibernate.stat.spi.StatisticsImplementor;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
/** /**
@ -444,4 +445,9 @@ public class SessionFactoryDelegatingImpl implements SessionFactoryImplementor,
public AllowableParameterType<?> resolveParameterBindType(Class<?> clazz) { public AllowableParameterType<?> resolveParameterBindType(Class<?> clazz) {
return delegate.resolveParameterBindType( clazz ); return delegate.resolveParameterBindType( clazz );
} }
@Override
public WrapperOptions getWrapperOptions() {
return delegate.getWrapperOptions();
}
} }

View File

@ -410,7 +410,7 @@ public abstract class AbstractSaveEventListener
substitute = Versioning.seedVersion( substitute = Versioning.seedVersion(
values, values,
persister.getVersionProperty(), persister.getVersionProperty(),
persister.getVersionType(), persister.getVersionJavaTypeDescriptor(),
source source
) || substitute; ) || substitute;
} }

View File

@ -394,7 +394,7 @@ public class DefaultFlushEntityEventListener implements FlushEntityEventListener
); );
final Object nextVersion = isVersionIncrementRequired ? final Object nextVersion = isVersionIncrementRequired ?
Versioning.increment( entry.getVersion(), persister.getVersionType(), event.getSession() ) : Versioning.increment( entry.getVersion(), persister.getVersionJavaTypeDescriptor(), event.getSession() ) :
entry.getVersion(); //use the current version entry.getVersion(); //use the current version
Versioning.setVersion( values, nextVersion, persister ); Versioning.setVersion( values, nextVersion, persister );

View File

@ -25,6 +25,7 @@ import org.hibernate.internal.CoreLogging;
import org.hibernate.internal.CoreMessageLogger; import org.hibernate.internal.CoreMessageLogger;
import org.hibernate.persister.entity.EntityPersister; import org.hibernate.persister.entity.EntityPersister;
import org.hibernate.pretty.MessageHelper; import org.hibernate.pretty.MessageHelper;
import org.hibernate.type.BasicType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
/** /**
@ -96,11 +97,12 @@ public class DefaultReplicateEventListener extends AbstractSaveEventListener imp
/// HHH-2378 /// HHH-2378
final Object realOldVersion = persister.isVersioned() ? oldVersion : null; final Object realOldVersion = persister.isVersioned() ? oldVersion : null;
@SuppressWarnings("unchecked")
boolean canReplicate = replicationMode.shouldOverwriteCurrentVersion( boolean canReplicate = replicationMode.shouldOverwriteCurrentVersion(
entity, entity,
realOldVersion, realOldVersion,
persister.getVersion( entity ), persister.getVersion( entity ),
persister.getVersionType() (BasicType<Object>) persister.getVersionType()
); );
// if can replicate, will result in a SQL UPDATE // if can replicate, will result in a SQL UPDATE

View File

@ -85,7 +85,7 @@ public class StatelessSessionImpl extends AbstractSharedSessionContract implemen
boolean substitute = Versioning.seedVersion( boolean substitute = Versioning.seedVersion(
state, state,
persister.getVersionProperty(), persister.getVersionProperty(),
persister.getVersionType(), persister.getVersionJavaTypeDescriptor(),
this this
); );
if ( substitute ) { if ( substitute ) {
@ -138,7 +138,7 @@ public class StatelessSessionImpl extends AbstractSharedSessionContract implemen
Object oldVersion; Object oldVersion;
if ( persister.isVersioned() ) { if ( persister.isVersioned() ) {
oldVersion = persister.getVersion( entity ); oldVersion = persister.getVersion( entity );
Object newVersion = Versioning.increment( oldVersion, persister.getVersionType(), this ); Object newVersion = Versioning.increment( oldVersion, persister.getVersionJavaTypeDescriptor(), this );
Versioning.setVersion( state, newVersion, persister ); Versioning.setVersion( state, newVersion, persister );
persister.setPropertyValues( entity, state ); persister.setPropertyValues( entity, state );
} }

View File

@ -258,7 +258,6 @@ import org.hibernate.type.CompositeType;
import org.hibernate.type.EntityType; import org.hibernate.type.EntityType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.TypeHelper; import org.hibernate.type.TypeHelper;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor; import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.hibernate.type.descriptor.java.MutabilityPlan; import org.hibernate.type.descriptor.java.MutabilityPlan;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
@ -2070,6 +2069,7 @@ public abstract class AbstractEntityPersister
boolean includeProperty(int propertyNumber); boolean includeProperty(int propertyNumber);
} }
@Override
public Object forceVersionIncrement(Object id, Object currentVersion, SharedSessionContractImplementor session) { public Object forceVersionIncrement(Object id, Object currentVersion, SharedSessionContractImplementor session) {
if ( !isVersioned() ) { if ( !isVersioned() ) {
throw new AssertionFailure( "cannot force version increment on non-versioned entity" ); throw new AssertionFailure( "cannot force version increment on non-versioned entity" );
@ -2081,7 +2081,7 @@ public abstract class AbstractEntityPersister
throw new HibernateException( "LockMode.FORCE is currently not supported for generated version properties" ); throw new HibernateException( "LockMode.FORCE is currently not supported for generated version properties" );
} }
Object nextVersion = ((VersionType) getVersionType()).next( currentVersion, session ); Object nextVersion = getVersionJavaTypeDescriptor().next( currentVersion, session );
if ( LOG.isTraceEnabled() ) { if ( LOG.isTraceEnabled() ) {
LOG.trace( LOG.trace(
"Forcing version increment [" + MessageHelper.infoString( this, id, getFactory() ) + "; " "Forcing version increment [" + MessageHelper.infoString( this, id, getFactory() ) + "; "
@ -4494,7 +4494,7 @@ public abstract class AbstractEntityPersister
} }
public Comparator<?> getVersionComparator() { public Comparator<?> getVersionComparator() {
return isVersioned() ? getVersionType().getComparator() : null; return isVersioned() ? getVersionType().getJavaTypeDescriptor().getComparator() : null;
} }
// temporary ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // temporary ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
@ -4522,10 +4522,10 @@ public abstract class AbstractEntityPersister
return !entityMetamodel.getIdentifierProperty().isVirtual(); return !entityMetamodel.getIdentifierProperty().isVirtual();
} }
public VersionType<?> getVersionType() { public BasicType<?> getVersionType() {
return entityMetamodel.getVersionProperty() == null return entityMetamodel.getVersionProperty() == null
? null ? null
: (VersionType<?>) entityMetamodel.getVersionProperty().getType(); : (BasicType<?>) entityMetamodel.getVersionProperty().getType();
} }
public int getVersionProperty() { public int getVersionProperty() {

View File

@ -48,8 +48,9 @@ import org.hibernate.sql.ast.tree.from.RootTableGroupProducer;
import org.hibernate.sql.ast.tree.from.TableGroup; import org.hibernate.sql.ast.tree.from.TableGroup;
import org.hibernate.tuple.entity.EntityMetamodel; import org.hibernate.tuple.entity.EntityMetamodel;
import org.hibernate.tuple.entity.EntityTuplizer; import org.hibernate.tuple.entity.EntityTuplizer;
import org.hibernate.type.BasicType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType; import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
/** /**
* Contract describing mapping information and persistence logic for a particular strategy of entity mapping. A given * Contract describing mapping information and persistence logic for a particular strategy of entity mapping. A given
@ -364,7 +365,15 @@ public interface EntityPersister
* *
* @return The type of the version property; or null, if not versioned. * @return The type of the version property; or null, if not versioned.
*/ */
VersionType<?> getVersionType(); BasicType<?> getVersionType();
default VersionJavaTypeDescriptor<Object> getVersionJavaTypeDescriptor() {
final BasicType<?> versionType = getVersionType();
//noinspection unchecked
return versionType == null
? null
: (VersionJavaTypeDescriptor<Object>) versionType.getJavaTypeDescriptor();
}
/** /**
* If {@link #isVersioned()}, then what is the index of the property * If {@link #isVersioned()}, then what is the index of the property

View File

@ -314,7 +314,6 @@ import org.hibernate.sql.results.internal.SqlSelectionImpl;
import org.hibernate.sql.results.internal.StandardEntityGraphTraversalStateImpl; import org.hibernate.sql.results.internal.StandardEntityGraphTraversalStateImpl;
import org.hibernate.type.BasicType; import org.hibernate.type.BasicType;
import org.hibernate.type.JavaObjectType; import org.hibernate.type.JavaObjectType;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor; import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
@ -711,7 +710,7 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
throw new SemanticException( "increment option specified for update of non-versioned entity" ); throw new SemanticException( "increment option specified for update of non-versioned entity" );
} }
final VersionType<?> versionType = persister.getVersionType(); final BasicType<?> versionType = persister.getVersionType();
if ( versionType instanceof UserVersionType ) { if ( versionType instanceof UserVersionType ) {
throw new SemanticException( "user-defined version types not supported for increment option" ); throw new SemanticException( "user-defined version types not supported for increment option" );
} }
@ -728,30 +727,20 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
final ColumnReference versionColumn = targetColumnReferences.get( 0 ); final ColumnReference versionColumn = targetColumnReferences.get( 0 );
final Expression value; final Expression value;
if ( isTimestampBasedVersion( versionType ) ) { if ( versionMapping.getJdbcMapping().getJdbcTypeDescriptor().isTemporal() ) {
value = new VersionTypeSeedParameterSpecification( versionType ); value = new VersionTypeSeedParameterSpecification( versionType, persister.getVersionJavaTypeDescriptor() );
} }
else { else {
final BasicValuedMapping basicValuedMapping = (BasicValuedMapping) versionType;
value = new BinaryArithmeticExpression( value = new BinaryArithmeticExpression(
versionColumn, versionColumn,
ADD, ADD,
new QueryLiteral<>( 1, basicValuedMapping ), new QueryLiteral<>( 1, versionType ),
basicValuedMapping versionType
); );
} }
assignmentConsumer.accept( new Assignment( versionColumn, value ) ); assignmentConsumer.accept( new Assignment( versionColumn, value ) );
} }
private boolean isTimestampBasedVersion(VersionType<?> versionType) {
if ( versionType instanceof BasicType<?> ) {
return ( (BasicType<?>) versionType ).getJdbcTypeDescriptor().isTemporal();
}
final Class<?> javaType = versionType.getReturnedClass();
return java.util.Date.class.isAssignableFrom( javaType )
|| Calendar.class.isAssignableFrom( javaType );
}
@Override @Override
public List<Assignment> visitSetClause(SqmSetClause setClause) { public List<Assignment> visitSetClause(SqmSetClause setClause) {
final List<Assignment> assignments = new ArrayList<>( setClause.getAssignments().size() ); final List<Assignment> assignments = new ArrayList<>( setClause.getAssignments().size() );
@ -1024,8 +1013,10 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
); );
if ( needsVersionInsert ) { if ( needsVersionInsert ) {
final VersionType versionType = entityDescriptor.getVersionType(); final Expression expression = new VersionTypeSeedParameterSpecification(
final Expression expression = new VersionTypeSeedParameterSpecification( versionType ); entityDescriptor.getVersionMapping().getJdbcMapping(),
entityDescriptor.getVersionJavaTypeDescriptor()
);
insertStatement.getSourceSelectStatement().forEachQuerySpec( insertStatement.getSourceSelectStatement().forEachQuerySpec(
querySpec -> { querySpec -> {
querySpec.getSelectClause().addSqlSelection( querySpec.getSelectClause().addSqlSelection(

View File

@ -12,7 +12,7 @@ import java.sql.SQLException;
import org.hibernate.metamodel.mapping.JdbcMapping; import org.hibernate.metamodel.mapping.JdbcMapping;
import org.hibernate.sql.exec.spi.ExecutionContext; import org.hibernate.sql.exec.spi.ExecutionContext;
import org.hibernate.sql.exec.spi.JdbcParameterBindings; import org.hibernate.sql.exec.spi.JdbcParameterBindings;
import org.hibernate.type.VersionType; import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
/** /**
* Parameter bind specification used for optimistic lock version seeding (from insert statements). * Parameter bind specification used for optimistic lock version seeding (from insert statements).
@ -20,15 +20,15 @@ import org.hibernate.type.VersionType;
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class VersionTypeSeedParameterSpecification extends JdbcParameterImpl { public class VersionTypeSeedParameterSpecification extends JdbcParameterImpl {
private final VersionType type; private final VersionJavaTypeDescriptor<?> type;
/** /**
* Constructs a version seed parameter bind specification. * Constructs a version seed parameter bind specification.
* *
* @param type The version type. * @param type The version type.
*/ */
public VersionTypeSeedParameterSpecification(VersionType type) { public VersionTypeSeedParameterSpecification(JdbcMapping jdbcMapping, VersionJavaTypeDescriptor<?> type) {
super( (JdbcMapping) type ); super( jdbcMapping );
this.type = type; this.type = type;
} }
@ -38,6 +38,12 @@ public class VersionTypeSeedParameterSpecification extends JdbcParameterImpl {
int startPosition, int startPosition,
JdbcParameterBindings jdbcParamBindings, JdbcParameterBindings jdbcParamBindings,
ExecutionContext executionContext) throws SQLException { ExecutionContext executionContext) throws SQLException {
type.nullSafeSet( statement, type.seed( executionContext.getSession() ), startPosition, executionContext.getSession() ); //noinspection unchecked
getJdbcMapping().getJdbcValueBinder().bind(
statement,
type.seed( executionContext.getSession() ),
startPosition,
executionContext.getSession()
);
} }
} }

View File

@ -51,8 +51,8 @@ import org.hibernate.sql.results.internal.NullValueAssembler;
import org.hibernate.sql.results.jdbc.spi.JdbcValuesSourceProcessingState; import org.hibernate.sql.results.jdbc.spi.JdbcValuesSourceProcessingState;
import org.hibernate.sql.results.jdbc.spi.RowProcessingState; import org.hibernate.sql.results.jdbc.spi.RowProcessingState;
import org.hibernate.stat.spi.StatisticsImplementor; import org.hibernate.stat.spi.StatisticsImplementor;
import org.hibernate.type.BasicType;
import org.hibernate.type.TypeHelper; import org.hibernate.type.TypeHelper;
import org.hibernate.type.VersionType;
import static org.hibernate.internal.log.LoggingHelper.toLoggableString; import static org.hibernate.internal.log.LoggingHelper.toLoggableString;
@ -517,7 +517,7 @@ public abstract class AbstractEntityInitializer extends AbstractFetchParentAcces
if ( version != null ) { if ( version != null ) {
// null version means the object is in the process of being loaded somewhere else in the ResultSet // null version means the object is in the process of being loaded somewhere else in the ResultSet
final VersionType<?> versionType = concreteDescriptor.getVersionType(); final BasicType<?> versionType = concreteDescriptor.getVersionType();
final Object currentVersion = versionAssembler.assemble( rowProcessingState ); final Object currentVersion = versionAssembler.assemble( rowProcessingState );
if ( !versionType.isEqual( version, currentVersion ) ) { if ( !versionType.isEqual( version, currentVersion ) ) {
final StatisticsImplementor statistics = rowProcessingState.getSession().getFactory().getStatistics(); final StatisticsImplementor statistics = rowProcessingState.getSession().getFactory().getStatistics();

View File

@ -33,9 +33,10 @@ import org.hibernate.tuple.entity.EntityBasedBasicAttribute;
import org.hibernate.tuple.entity.EntityBasedCompositionAttribute; import org.hibernate.tuple.entity.EntityBasedCompositionAttribute;
import org.hibernate.tuple.entity.VersionProperty; import org.hibernate.tuple.entity.VersionProperty;
import org.hibernate.type.AssociationType; import org.hibernate.type.AssociationType;
import org.hibernate.type.BasicType;
import org.hibernate.type.CompositeType; import org.hibernate.type.CompositeType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType; import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
/** /**
* Responsible for generation of runtime metamodel {@link Property} representations. * Responsible for generation of runtime metamodel {@link Property} representations.
@ -107,10 +108,11 @@ public final class PropertyFactory {
boolean lazyAvailable) { boolean lazyAvailable) {
String mappedUnsavedValue = ( (KeyValue) property.getValue() ).getNullValue(); String mappedUnsavedValue = ( (KeyValue) property.getValue() ).getNullValue();
//noinspection unchecked
VersionValue unsavedValue = UnsavedValueFactory.getUnsavedVersionValue( VersionValue unsavedValue = UnsavedValueFactory.getUnsavedVersionValue(
mappedUnsavedValue, mappedUnsavedValue,
getGetter( property ), getGetter( property ),
(VersionType) property.getType(), ( VersionJavaTypeDescriptor<Object>) ((BasicType<?>) property.getType()).getJavaTypeDescriptor(),
getConstructor( property.getPersistentClass() ) getConstructor( property.getPersistentClass() )
); );

View File

@ -7,29 +7,19 @@
package org.hibernate.type; package org.hibernate.type;
import java.sql.Types; import java.sql.Types;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.hibernate.type.descriptor.java.PrimitiveByteArrayTypeDescriptor; import org.hibernate.type.descriptor.java.PrimitiveByteArrayTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
import org.hibernate.type.descriptor.jdbc.VarbinaryTypeDescriptor; import org.hibernate.type.descriptor.jdbc.VarbinaryTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.spi.JdbcTypeDescriptorRegistry;
import org.hibernate.type.spi.TypeConfiguration;
/** /**
* A type that maps between a {@link Types#VARBINARY VARBINARY} and {@code byte[]} * A type that maps between a {@link Types#VARBINARY VARBINARY} and {@code byte[]}
* *
* Implementation of the {@link VersionType} interface should be considered deprecated.
* For binary entity versions/timestamps, {@link RowVersionType} should be used instead.
*
* @author Gavin King * @author Gavin King
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class BinaryType public class BinaryType
extends AbstractSingleColumnStandardBasicType<byte[]> extends AbstractSingleColumnStandardBasicType<byte[]>
implements VersionType<byte[]>, AdjustableBasicType<byte[]> { implements AdjustableBasicType<byte[]> {
public static final BinaryType INSTANCE = new BinaryType(); public static final BinaryType INSTANCE = new BinaryType();
@ -46,47 +36,4 @@ public class BinaryType
return new String[] { getName(), "byte[]", byte[].class.getName() }; return new String[] { getName(), "byte[]", byte[].class.getName() };
} }
/**
* Generate an initial version.
*
* @param session The session from which this request originates.
* @return an instance of the type
* @deprecated use {@link RowVersionType} for binary entity versions/timestamps
*/
@Override
@Deprecated
public byte[] seed(SharedSessionContractImplementor session) {
// Note : simply returns null for seed() and next() as the only known
// application of binary types for versioning is for use with the
// TIMESTAMP datatype supported by Sybase and SQL Server, which
// are completely db-generated values...
return null;
}
/**
* Increment the version.
*
* @param session The session from which this request originates.
* @param current the current version
* @return an instance of the type
* @deprecated use {@link RowVersionType} for binary entity versions/timestamps
*/
@Override
@Deprecated
public byte[] next(byte[] current, SharedSessionContractImplementor session) {
return current;
}
/**
* Get a comparator for version values.
*
* @return The comparator to use to compare different version values.
* @deprecated use {@link RowVersionType} for binary entity versions/timestamps
*/
@Override
@Deprecated
public Comparator<byte[]> getComparator() {
return PrimitiveByteArrayTypeDescriptor.INSTANCE.getComparator();
}
} }

View File

@ -7,9 +7,7 @@
package org.hibernate.type; package org.hibernate.type;
import java.io.Serializable; import java.io.Serializable;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.ByteTypeDescriptor; import org.hibernate.type.descriptor.java.ByteTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.TinyIntTypeDescriptor; import org.hibernate.type.descriptor.jdbc.TinyIntTypeDescriptor;
@ -21,7 +19,7 @@ import org.hibernate.type.descriptor.jdbc.TinyIntTypeDescriptor;
*/ */
public class ByteType public class ByteType
extends AbstractSingleColumnStandardBasicType<Byte> extends AbstractSingleColumnStandardBasicType<Byte>
implements PrimitiveType<Byte>, DiscriminatorType<Byte>, VersionType<Byte> { implements PrimitiveType<Byte>, DiscriminatorType<Byte> {
public static final ByteType INSTANCE = new ByteType(); public static final ByteType INSTANCE = new ByteType();
@ -60,19 +58,4 @@ public class ByteType
public Byte fromStringValue(CharSequence xml) { public Byte fromStringValue(CharSequence xml) {
return fromString( xml ); return fromString( xml );
} }
@Override
public Byte next(Byte current, SharedSessionContractImplementor session) {
return (byte) ( current + 1 );
}
@Override
public Byte seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Comparator<Byte> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
} }

View File

@ -7,18 +7,16 @@
package org.hibernate.type; package org.hibernate.type;
import java.util.Calendar; import java.util.Calendar;
import java.util.Comparator;
import java.util.GregorianCalendar; import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.type.descriptor.java.CalendarTypeDescriptor; import org.hibernate.type.descriptor.java.CalendarTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link Calendar} * A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link Calendar}
* *
@ -27,7 +25,7 @@ import org.hibernate.type.spi.TypeConfiguration;
*/ */
public class CalendarType public class CalendarType
extends AbstractSingleColumnStandardBasicType<Calendar> extends AbstractSingleColumnStandardBasicType<Calendar>
implements VersionType<Calendar>, AllowableTemporalParameterType<Calendar> { implements AllowableTemporalParameterType<Calendar> {
public static final CalendarType INSTANCE = new CalendarType(); public static final CalendarType INSTANCE = new CalendarType();
@ -45,21 +43,6 @@ public class CalendarType
return new String[] { getName(), Calendar.class.getName(), GregorianCalendar.class.getName() }; return new String[] { getName(), Calendar.class.getName(), GregorianCalendar.class.getName() };
} }
@Override
public Calendar next(Calendar current, SharedSessionContractImplementor session) {
return seed( session );
}
@Override
public Calendar seed(SharedSessionContractImplementor session) {
return Calendar.getInstance();
}
@Override
public Comparator<Calendar> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
@Override @Override
public AllowableTemporalParameterType resolveTemporalPrecision( public AllowableTemporalParameterType resolveTemporalPrecision(
TemporalType temporalPrecision, TemporalType temporalPrecision,

View File

@ -12,7 +12,6 @@ import java.sql.PreparedStatement;
import java.sql.ResultSet; import java.sql.ResultSet;
import java.sql.SQLException; import java.sql.SQLException;
import java.util.Arrays; import java.util.Arrays;
import java.util.Comparator;
import java.util.Map; import java.util.Map;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
@ -30,6 +29,7 @@ import org.hibernate.type.descriptor.java.JavaTypedExpressable;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.internal.UserTypeJavaTypeWrapper; import org.hibernate.type.internal.UserTypeJavaTypeWrapper;
import org.hibernate.type.internal.UserTypeSqlTypeAdapter; import org.hibernate.type.internal.UserTypeSqlTypeAdapter;
import org.hibernate.type.internal.UserTypeVersionJavaTypeWrapper;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import org.hibernate.usertype.EnhancedUserType; import org.hibernate.usertype.EnhancedUserType;
import org.hibernate.usertype.Sized; import org.hibernate.usertype.Sized;
@ -52,7 +52,7 @@ import org.hibernate.usertype.UserVersionType;
*/ */
public class CustomType public class CustomType
extends AbstractType extends AbstractType
implements BasicType, IdentifierType, DiscriminatorType, VersionType, StringRepresentableType, ProcedureParameterNamedBinder, ProcedureParameterExtractionAware { implements BasicType, IdentifierType, DiscriminatorType, StringRepresentableType, ProcedureParameterNamedBinder, ProcedureParameterExtractionAware {
private final UserType<Object> userType; private final UserType<Object> userType;
private final String[] registrationKeys; private final String[] registrationKeys;
@ -84,6 +84,9 @@ public class CustomType
//noinspection rawtypes //noinspection rawtypes
this.mappedJavaTypeDescriptor = (BasicJavaDescriptor) ( (JavaTypedExpressable) userType ).getExpressableJavaTypeDescriptor(); this.mappedJavaTypeDescriptor = (BasicJavaDescriptor) ( (JavaTypedExpressable) userType ).getExpressableJavaTypeDescriptor();
} }
else if ( userType instanceof UserVersionType ) {
this.mappedJavaTypeDescriptor = new UserTypeVersionJavaTypeWrapper<>( (UserVersionType) userType );
}
else { else {
this.mappedJavaTypeDescriptor = new UserTypeJavaTypeWrapper<>( userType ); this.mappedJavaTypeDescriptor = new UserTypeJavaTypeWrapper<>( userType );
} }
@ -255,21 +258,6 @@ public class CustomType
return fromStringValue( sequence ); return fromStringValue( sequence );
} }
@Override
public Comparator getComparator() {
return (Comparator) getUserType();
}
@Override
public Object next(Object current, SharedSessionContractImplementor session) {
return ( (UserVersionType) getUserType() ).next( current, session );
}
@Override
public Object seed(SharedSessionContractImplementor session) {
return ( (UserVersionType) getUserType() ).seed( session );
}
@Override @Override
public String toLoggableString(Object value, SessionFactoryImplementor factory) { public String toLoggableString(Object value, SessionFactoryImplementor factory) {
if ( value == null ) { if ( value == null ) {

View File

@ -6,16 +6,15 @@
*/ */
package org.hibernate.type; package org.hibernate.type;
import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.Date; import java.util.Date;
import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.CoreMessageLogger; import org.hibernate.internal.CoreMessageLogger;
import org.hibernate.type.descriptor.java.DbTimestampJavaTypeDescriptor;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.hibernate.type.descriptor.java.JdbcTimestampTypeDescriptor;
import org.hibernate.type.descriptor.java.TemporalJavaTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
import org.jboss.logging.Logger; import org.jboss.logging.Logger;
@ -38,6 +37,14 @@ public class DbTimestampType extends TimestampType {
DbTimestampType.class.getName() DbTimestampType.class.getName()
); );
public DbTimestampType() {
this( TimestampTypeDescriptor.INSTANCE, JdbcTimestampTypeDescriptor.INSTANCE );
}
public DbTimestampType(JdbcTypeDescriptor jdbcTypeDescriptor, JavaTypeDescriptor<Date> javaTypeDescriptor) {
super( jdbcTypeDescriptor, new DbTimestampJavaTypeDescriptor<>( (TemporalJavaTypeDescriptor<Date>) javaTypeDescriptor ) );
}
@Override @Override
public String getName() { public String getName() {
return "dbtimestamp"; return "dbtimestamp";
@ -48,97 +55,4 @@ public class DbTimestampType extends TimestampType {
return new String[] {getName()}; return new String[] {getName()};
} }
@Override
public Date seed(SharedSessionContractImplementor session) {
if ( session == null ) {
LOG.trace( "Incoming session was null; using current jvm time" );
return super.seed( null );
}
else if ( !session.getJdbcServices().getJdbcEnvironment().getDialect().supportsCurrentTimestampSelection() ) {
LOG.debug( "Falling back to vm-based timestamp, as dialect does not support current timestamp selection" );
return super.seed( session );
}
else {
return getCurrentTimestamp( session );
}
}
private Date getCurrentTimestamp(SharedSessionContractImplementor session) {
Dialect dialect = session.getJdbcServices().getJdbcEnvironment().getDialect();
String timestampSelectString = dialect.getCurrentTimestampSelectString();
if ( dialect.isCurrentTimestampSelectStringCallable() ) {
return useCallableStatement( timestampSelectString, session );
}
return usePreparedStatement( timestampSelectString, session );
}
private Timestamp usePreparedStatement(String timestampSelectString, SharedSessionContractImplementor session) {
PreparedStatement ps = null;
try {
ps = session
.getJdbcCoordinator()
.getStatementPreparer()
.prepareStatement( timestampSelectString, false );
ResultSet rs = session.getJdbcCoordinator().getResultSetReturn().extract( ps );
rs.next();
Timestamp ts = rs.getTimestamp( 1 );
if ( LOG.isTraceEnabled() ) {
LOG.tracev(
"Current timestamp retrieved from db : {0} (nanos={1}, time={2})",
ts,
ts.getNanos(),
ts.getTime()
);
}
return ts;
}
catch (SQLException e) {
throw session.getJdbcServices().getSqlExceptionHelper().convert(
e,
"could not select current db timestamp",
timestampSelectString
);
}
finally {
if ( ps != null ) {
session.getJdbcCoordinator().getLogicalConnection().getResourceRegistry().release( ps );
session.getJdbcCoordinator().afterStatementExecution();
}
}
}
private Timestamp useCallableStatement(String callString, SharedSessionContractImplementor session) {
CallableStatement cs = null;
try {
cs = (CallableStatement) session
.getJdbcCoordinator()
.getStatementPreparer()
.prepareStatement( callString, true );
cs.registerOutParameter( 1, java.sql.Types.TIMESTAMP );
session.getJdbcCoordinator().getResultSetReturn().execute( cs );
Timestamp ts = cs.getTimestamp( 1 );
if ( LOG.isTraceEnabled() ) {
LOG.tracev(
"Current timestamp retrieved from db : {0} (nanos={1}, time={2})",
ts,
ts.getNanos(),
ts.getTime()
);
}
return ts;
}
catch (SQLException e) {
throw session.getJdbcServices().getSqlExceptionHelper().convert(
e,
"could not call current db timestamp function",
callString
);
}
finally {
if ( cs != null ) {
session.getJdbcCoordinator().getLogicalConnection().getResourceRegistry().release( cs );
session.getJdbcCoordinator().afterStatementExecution();
}
}
}
} }

View File

@ -8,18 +8,16 @@ package org.hibernate.type;
import java.time.Instant; import java.time.Instant;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
import java.util.Comparator;
import java.util.Locale; import java.util.Locale;
import jakarta.persistence.TemporalType;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.compare.ComparableComparator;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.type.descriptor.java.InstantJavaDescriptor; import org.hibernate.type.descriptor.java.InstantJavaDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link java.time.LocalDateTime}. * A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link java.time.LocalDateTime}.
* *
@ -27,7 +25,7 @@ import org.hibernate.type.spi.TypeConfiguration;
*/ */
public class InstantType public class InstantType
extends AbstractSingleColumnStandardBasicType<Instant> extends AbstractSingleColumnStandardBasicType<Instant>
implements VersionType<Instant>, AllowableTemporalParameterType<Instant> { implements AllowableTemporalParameterType<Instant> {
/** /**
* Singleton access * Singleton access
*/ */
@ -39,22 +37,6 @@ public class InstantType
super( TimestampTypeDescriptor.INSTANCE, InstantJavaDescriptor.INSTANCE ); super( TimestampTypeDescriptor.INSTANCE, InstantJavaDescriptor.INSTANCE );
} }
@Override
public Instant seed(SharedSessionContractImplementor session) {
return Instant.now();
}
@Override
public Instant next(Instant current, SharedSessionContractImplementor session) {
return Instant.now();
}
@Override
@SuppressWarnings("unchecked")
public Comparator<Instant> getComparator() {
return ComparableComparator.INSTANCE;
}
@Override @Override
public String getName() { public String getName() {
return "instant"; return "instant";

View File

@ -7,9 +7,7 @@
package org.hibernate.type; package org.hibernate.type;
import java.io.Serializable; import java.io.Serializable;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.IntegerTypeDescriptor; import org.hibernate.type.descriptor.java.IntegerTypeDescriptor;
/** /**
@ -19,7 +17,7 @@ import org.hibernate.type.descriptor.java.IntegerTypeDescriptor;
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class IntegerType extends AbstractSingleColumnStandardBasicType<Integer> public class IntegerType extends AbstractSingleColumnStandardBasicType<Integer>
implements PrimitiveType<Integer>, DiscriminatorType<Integer>, VersionType<Integer> { implements PrimitiveType<Integer>, DiscriminatorType<Integer> {
public static final IntegerType INSTANCE = new IntegerType(); public static final IntegerType INSTANCE = new IntegerType();
@ -53,19 +51,4 @@ public class IntegerType extends AbstractSingleColumnStandardBasicType<Integer>
public Integer stringToObject(CharSequence sequence) { public Integer stringToObject(CharSequence sequence) {
return fromString( sequence ); return fromString( sequence );
} }
@Override
public Integer seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Integer next(Integer current, SharedSessionContractImplementor session) {
return current + 1;
}
@Override
public Comparator<Integer> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
} }

View File

@ -7,17 +7,15 @@
package org.hibernate.type; package org.hibernate.type;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.util.Comparator;
import jakarta.persistence.TemporalType;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.compare.ComparableComparator;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.type.descriptor.java.LocalDateTimeJavaDescriptor; import org.hibernate.type.descriptor.java.LocalDateTimeJavaDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link LocalDateTime}. * A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link LocalDateTime}.
* *
@ -25,7 +23,7 @@ import org.hibernate.type.spi.TypeConfiguration;
*/ */
public class LocalDateTimeType public class LocalDateTimeType
extends AbstractSingleColumnStandardBasicType<LocalDateTime> extends AbstractSingleColumnStandardBasicType<LocalDateTime>
implements VersionType<LocalDateTime>, AllowableTemporalParameterType<LocalDateTime> { implements AllowableTemporalParameterType<LocalDateTime> {
/** /**
* Singleton access * Singleton access
*/ */
@ -45,22 +43,6 @@ public class LocalDateTimeType
return true; return true;
} }
@Override
public LocalDateTime seed(SharedSessionContractImplementor session) {
return LocalDateTime.now();
}
@Override
public LocalDateTime next(LocalDateTime current, SharedSessionContractImplementor session) {
return LocalDateTime.now();
}
@Override
@SuppressWarnings("unchecked")
public Comparator<LocalDateTime> getComparator() {
return ComparableComparator.INSTANCE;
}
@Override @Override
public AllowableTemporalParameterType resolveTemporalPrecision( public AllowableTemporalParameterType resolveTemporalPrecision(
TemporalType temporalPrecision, TemporalType temporalPrecision,

View File

@ -7,9 +7,7 @@
package org.hibernate.type; package org.hibernate.type;
import java.io.Serializable; import java.io.Serializable;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.LongTypeDescriptor; import org.hibernate.type.descriptor.java.LongTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor; import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor;
@ -21,7 +19,7 @@ import org.hibernate.type.descriptor.jdbc.BigIntTypeDescriptor;
*/ */
public class LongType public class LongType
extends AbstractSingleColumnStandardBasicType<Long> extends AbstractSingleColumnStandardBasicType<Long>
implements PrimitiveType<Long>, DiscriminatorType<Long>, VersionType<Long> { implements PrimitiveType<Long>, DiscriminatorType<Long> {
public static final LongType INSTANCE = new LongType(); public static final LongType INSTANCE = new LongType();
@ -56,19 +54,4 @@ public class LongType
return Long.valueOf( sequence.toString() ); return Long.valueOf( sequence.toString() );
} }
@Override
public Long next(Long current, SharedSessionContractImplementor session) {
return current + 1L;
}
@Override
public Long seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Comparator<Long> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
} }

View File

@ -7,24 +7,22 @@
package org.hibernate.type; package org.hibernate.type;
import java.time.OffsetDateTime; import java.time.OffsetDateTime;
import java.util.Comparator;
import jakarta.persistence.TemporalType;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.query.CastType; import org.hibernate.query.CastType;
import org.hibernate.type.descriptor.java.OffsetDateTimeJavaDescriptor; import org.hibernate.type.descriptor.java.OffsetDateTimeJavaDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampWithTimeZoneDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampWithTimeZoneDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class OffsetDateTimeType public class OffsetDateTimeType
extends AbstractSingleColumnStandardBasicType<OffsetDateTime> extends AbstractSingleColumnStandardBasicType<OffsetDateTime>
implements VersionType<OffsetDateTime>, AllowableTemporalParameterType<OffsetDateTime> { implements AllowableTemporalParameterType<OffsetDateTime> {
/** /**
* Singleton access * Singleton access
@ -35,21 +33,6 @@ public class OffsetDateTimeType
super( TimestampWithTimeZoneDescriptor.INSTANCE, OffsetDateTimeJavaDescriptor.INSTANCE ); super( TimestampWithTimeZoneDescriptor.INSTANCE, OffsetDateTimeJavaDescriptor.INSTANCE );
} }
@Override
public OffsetDateTime seed(SharedSessionContractImplementor session) {
return OffsetDateTime.now();
}
@Override
public OffsetDateTime next(OffsetDateTime current, SharedSessionContractImplementor session) {
return OffsetDateTime.now();
}
@Override
public Comparator<OffsetDateTime> getComparator() {
return OffsetDateTime.timeLineOrder();
}
@Override @Override
public String getName() { public String getName() {
return OffsetDateTime.class.getSimpleName(); return OffsetDateTime.class.getSimpleName();

View File

@ -6,9 +6,6 @@
*/ */
package org.hibernate.type; package org.hibernate.type;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.RowVersionTypeDescriptor; import org.hibernate.type.descriptor.java.RowVersionTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.VarbinaryTypeDescriptor; import org.hibernate.type.descriptor.jdbc.VarbinaryTypeDescriptor;
@ -21,8 +18,7 @@ import org.hibernate.type.descriptor.jdbc.VarbinaryTypeDescriptor;
* @author Gail Badner * @author Gail Badner
*/ */
public class RowVersionType public class RowVersionType
extends AbstractSingleColumnStandardBasicType<byte[]> extends AbstractSingleColumnStandardBasicType<byte[]> {
implements VersionType<byte[]> {
public static final RowVersionType INSTANCE = new RowVersionType(); public static final RowVersionType INSTANCE = new RowVersionType();
@ -39,22 +35,4 @@ public class RowVersionType
return new String[] { getName() }; return new String[] { getName() };
} }
@Override
public byte[] seed(SharedSessionContractImplementor session) {
// Note : simply returns null for seed() and next() as the only known
// application of binary types for versioning is for use with the
// TIMESTAMP datatype supported by Sybase and SQL Server, which
// are completely db-generated values...
return null;
}
@Override
public byte[] next(byte[] current, SharedSessionContractImplementor session) {
return current;
}
@Override
public Comparator<byte[]> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
} }

View File

@ -7,9 +7,7 @@
package org.hibernate.type; package org.hibernate.type;
import java.io.Serializable; import java.io.Serializable;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.ShortTypeDescriptor; import org.hibernate.type.descriptor.java.ShortTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.SmallIntTypeDescriptor; import org.hibernate.type.descriptor.jdbc.SmallIntTypeDescriptor;
@ -21,7 +19,7 @@ import org.hibernate.type.descriptor.jdbc.SmallIntTypeDescriptor;
*/ */
public class ShortType public class ShortType
extends AbstractSingleColumnStandardBasicType<Short> extends AbstractSingleColumnStandardBasicType<Short>
implements PrimitiveType<Short>, DiscriminatorType<Short>, VersionType<Short> { implements PrimitiveType<Short>, DiscriminatorType<Short> {
public static final ShortType INSTANCE = new ShortType(); public static final ShortType INSTANCE = new ShortType();
@ -56,19 +54,4 @@ public class ShortType
return Short.valueOf( sequence.toString() ); return Short.valueOf( sequence.toString() );
} }
@Override
public Short seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Short next(Short current, SharedSessionContractImplementor session) {
return (short) ( current + 1 );
}
@Override
public Comparator<Short> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
} }

View File

@ -7,18 +7,19 @@
package org.hibernate.type; package org.hibernate.type;
import java.sql.Timestamp; import java.sql.Timestamp;
import java.util.Comparator;
import java.util.Date; import java.util.Date;
import jakarta.persistence.TemporalType;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.hibernate.type.descriptor.java.JdbcTimestampTypeDescriptor; import org.hibernate.type.descriptor.java.JdbcTimestampTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link Timestamp} * A type that maps between {@link java.sql.Types#TIMESTAMP TIMESTAMP} and {@link Timestamp}
* *
@ -27,7 +28,7 @@ import org.hibernate.type.spi.TypeConfiguration;
*/ */
public class TimestampType public class TimestampType
extends AbstractSingleColumnStandardBasicType<Date> extends AbstractSingleColumnStandardBasicType<Date>
implements VersionType<Date>, AllowableTemporalParameterType<Date> { implements AllowableTemporalParameterType<Date> {
public static final TimestampType INSTANCE = new TimestampType(); public static final TimestampType INSTANCE = new TimestampType();
@ -35,6 +36,10 @@ public class TimestampType
super( TimestampTypeDescriptor.INSTANCE, JdbcTimestampTypeDescriptor.INSTANCE ); super( TimestampTypeDescriptor.INSTANCE, JdbcTimestampTypeDescriptor.INSTANCE );
} }
protected TimestampType(JdbcTypeDescriptor jdbcTypeDescriptor, JavaTypeDescriptor<Date> javaTypeDescriptor) {
super( jdbcTypeDescriptor, javaTypeDescriptor );
}
@Override @Override
public String getName() { public String getName() {
return "timestamp"; return "timestamp";
@ -45,21 +50,6 @@ public class TimestampType
return new String[] { getName(), Timestamp.class.getName(), Date.class.getName() }; return new String[] { getName(), Timestamp.class.getName(), Date.class.getName() };
} }
@Override
public Date next(Date current, SharedSessionContractImplementor session) {
return seed( session );
}
@Override
public Date seed(SharedSessionContractImplementor session) {
return new Timestamp( System.currentTimeMillis() );
}
@Override
public Comparator<Date> getComparator() {
return getJavaTypeDescriptor().getComparator();
}
@Override @Override
public Date fromStringValue(CharSequence xml) throws HibernateException { public Date fromStringValue(CharSequence xml) throws HibernateException {
return fromString( xml ); return fromString( xml );

View File

@ -7,24 +7,22 @@
package org.hibernate.type; package org.hibernate.type;
import java.time.ZonedDateTime; import java.time.ZonedDateTime;
import java.util.Comparator;
import jakarta.persistence.TemporalType;
import org.hibernate.QueryException; import org.hibernate.QueryException;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.ZonedDateTimeComparator;
import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType; import org.hibernate.metamodel.model.domain.AllowableTemporalParameterType;
import org.hibernate.query.CastType; import org.hibernate.query.CastType;
import org.hibernate.type.descriptor.java.ZonedDateTimeJavaDescriptor; import org.hibernate.type.descriptor.java.ZonedDateTimeJavaTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.TimestampWithTimeZoneDescriptor; import org.hibernate.type.descriptor.jdbc.TimestampWithTimeZoneDescriptor;
import org.hibernate.type.spi.TypeConfiguration; import org.hibernate.type.spi.TypeConfiguration;
import jakarta.persistence.TemporalType;
/** /**
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class ZonedDateTimeType public class ZonedDateTimeType
extends AbstractSingleColumnStandardBasicType<ZonedDateTime> extends AbstractSingleColumnStandardBasicType<ZonedDateTime>
implements VersionType<ZonedDateTime>, AllowableTemporalParameterType<ZonedDateTime> { implements AllowableTemporalParameterType<ZonedDateTime> {
/** /**
* Singleton access * Singleton access
@ -32,23 +30,7 @@ public class ZonedDateTimeType
public static final ZonedDateTimeType INSTANCE = new ZonedDateTimeType(); public static final ZonedDateTimeType INSTANCE = new ZonedDateTimeType();
public ZonedDateTimeType() { public ZonedDateTimeType() {
super( TimestampWithTimeZoneDescriptor.INSTANCE, ZonedDateTimeJavaDescriptor.INSTANCE ); super( TimestampWithTimeZoneDescriptor.INSTANCE, ZonedDateTimeJavaTypeDescriptor.INSTANCE );
}
@Override
public ZonedDateTime seed(SharedSessionContractImplementor session) {
return ZonedDateTime.now();
}
@Override
public ZonedDateTime next(ZonedDateTime current, SharedSessionContractImplementor session) {
return ZonedDateTime.now();
}
@Override
@SuppressWarnings("unchecked")
public Comparator<ZonedDateTime> getComparator() {
return ZonedDateTimeComparator.INSTANCE;
} }
@Override @Override

View File

@ -10,6 +10,7 @@ import java.math.BigInteger;
import java.util.Locale; import java.util.Locale;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.java.spi.Primitive; import org.hibernate.type.descriptor.java.spi.Primitive;
@ -19,7 +20,9 @@ import org.hibernate.type.descriptor.java.spi.Primitive;
* @author Steve Ebersole * @author Steve Ebersole
* @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com) * @author Lukasz Antoniak (lukasz dot antoniak at gmail dot com)
*/ */
public class ByteTypeDescriptor extends AbstractClassTypeDescriptor<Byte> implements Primitive<Byte> { public class ByteTypeDescriptor extends AbstractClassTypeDescriptor<Byte> implements Primitive<Byte>, VersionJavaTypeDescriptor<Byte>{
private static final Byte ZERO = (byte) 0;
public static final ByteTypeDescriptor INSTANCE = new ByteTypeDescriptor(); public static final ByteTypeDescriptor INSTANCE = new ByteTypeDescriptor();
public ByteTypeDescriptor() { public ByteTypeDescriptor() {
@ -170,4 +173,13 @@ public class ByteTypeDescriptor extends AbstractClassTypeDescriptor<Byte> implem
) )
); );
} }
@Override
public Byte next(Byte current, SharedSessionContractImplementor session) {
return (byte) ( current + 1 );
}
@Override
public Byte seed(SharedSessionContractImplementor session) {
return ZERO;
}
} }

View File

@ -13,6 +13,7 @@ import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType; import jakarta.persistence.TemporalType;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.compare.CalendarComparator; import org.hibernate.internal.util.compare.CalendarComparator;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
@ -25,7 +26,7 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class CalendarTypeDescriptor extends AbstractTemporalTypeDescriptor<Calendar> { public class CalendarTypeDescriptor extends AbstractTemporalTypeDescriptor<Calendar> implements VersionJavaTypeDescriptor<Calendar> {
public static final CalendarTypeDescriptor INSTANCE = new CalendarTypeDescriptor(); public static final CalendarTypeDescriptor INSTANCE = new CalendarTypeDescriptor();
public static class CalendarMutabilityPlan extends MutableMutabilityPlan<Calendar> { public static class CalendarMutabilityPlan extends MutableMutabilityPlan<Calendar> {
@ -158,4 +159,14 @@ public class CalendarTypeDescriptor extends AbstractTemporalTypeDescriptor<Calen
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public Calendar next(Calendar current, SharedSessionContractImplementor session) {
return seed( session );
}
@Override
public Calendar seed(SharedSessionContractImplementor session) {
return Calendar.getInstance();
}
} }

View File

@ -0,0 +1,248 @@
/*
* 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.type.descriptor.java;
import java.lang.reflect.Type;
import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Timestamp;
import java.util.Comparator;
import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.CoreMessageLogger;
import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
import org.hibernate.type.spi.TypeConfiguration;
import org.jboss.logging.Logger;
import jakarta.persistence.TemporalType;
/**
* Wrapper Java type descriptor for that uses the database timestamp as seed value for versions.
*
* @author Christian Beikov
*/
public class DbTimestampJavaTypeDescriptor<T> implements VersionJavaTypeDescriptor<T>, TemporalJavaTypeDescriptor<T> {
private static final CoreMessageLogger LOG = Logger.getMessageLogger(
CoreMessageLogger.class,
DbTimestampJavaTypeDescriptor.class.getName()
);
private final TemporalJavaTypeDescriptor<T> delegate;
public DbTimestampJavaTypeDescriptor(TemporalJavaTypeDescriptor<T> delegate) {
this.delegate = delegate;
}
@Override
public T next(T current, SharedSessionContractImplementor session) {
return seed( session );
}
@Override
@SuppressWarnings("unchecked")
public T seed(SharedSessionContractImplementor session) {
if ( session == null ) {
LOG.trace( "Incoming session was null; using current jvm time" );
return ((VersionJavaTypeDescriptor<T>) delegate).seed( null );
}
else if ( !session.getJdbcServices().getJdbcEnvironment().getDialect().supportsCurrentTimestampSelection() ) {
LOG.debug( "Falling back to vm-based timestamp, as dialect does not support current timestamp selection" );
return ((VersionJavaTypeDescriptor<T>) delegate).seed( session );
}
else {
return getCurrentTimestamp( session );
}
}
private T getCurrentTimestamp(SharedSessionContractImplementor session) {
Dialect dialect = session.getJdbcServices().getJdbcEnvironment().getDialect();
String timestampSelectString = dialect.getCurrentTimestampSelectString();
if ( dialect.isCurrentTimestampSelectStringCallable() ) {
return useCallableStatement( timestampSelectString, session );
}
return usePreparedStatement( timestampSelectString, session );
}
private T usePreparedStatement(String timestampSelectString, SharedSessionContractImplementor session) {
PreparedStatement ps = null;
try {
ps = session
.getJdbcCoordinator()
.getStatementPreparer()
.prepareStatement( timestampSelectString, false );
ResultSet rs = session.getJdbcCoordinator().getResultSetReturn().extract( ps );
rs.next();
Timestamp ts = rs.getTimestamp( 1 );
if ( LOG.isTraceEnabled() ) {
LOG.tracev(
"Current timestamp retrieved from db : {0} (nanos={1}, time={2})",
ts,
ts.getNanos(),
ts.getTime()
);
}
return delegate.wrap( ts, session );
}
catch (SQLException e) {
throw session.getJdbcServices().getSqlExceptionHelper().convert(
e,
"could not select current db timestamp",
timestampSelectString
);
}
finally {
if ( ps != null ) {
session.getJdbcCoordinator().getLogicalConnection().getResourceRegistry().release( ps );
session.getJdbcCoordinator().afterStatementExecution();
}
}
}
private T useCallableStatement(String callString, SharedSessionContractImplementor session) {
CallableStatement cs = null;
try {
cs = (CallableStatement) session
.getJdbcCoordinator()
.getStatementPreparer()
.prepareStatement( callString, true );
cs.registerOutParameter( 1, java.sql.Types.TIMESTAMP );
session.getJdbcCoordinator().getResultSetReturn().execute( cs );
Timestamp ts = cs.getTimestamp( 1 );
if ( LOG.isTraceEnabled() ) {
LOG.tracev(
"Current timestamp retrieved from db : {0} (nanos={1}, time={2})",
ts,
ts.getNanos(),
ts.getTime()
);
}
return delegate.wrap( ts, session );
}
catch (SQLException e) {
throw session.getJdbcServices().getSqlExceptionHelper().convert(
e,
"could not call current db timestamp function",
callString
);
}
finally {
if ( cs != null ) {
session.getJdbcCoordinator().getLogicalConnection().getResourceRegistry().release( cs );
session.getJdbcCoordinator().afterStatementExecution();
}
}
}
@Override
public JdbcTypeDescriptor getRecommendedJdbcType(JdbcTypeDescriptorIndicators indicators) {
return delegate.getRecommendedJdbcType( indicators );
}
@Override
public T fromString(CharSequence string) {
return delegate.fromString( string );
}
@Override
public Type getJavaType() {
return delegate.getJavaType();
}
@Override
public MutabilityPlan<T> getMutabilityPlan() {
return delegate.getMutabilityPlan();
}
@Override
public long getDefaultSqlLength(Dialect dialect) {
return delegate.getDefaultSqlLength( dialect );
}
@Override
public long getLongSqlLength() {
return delegate.getLongSqlLength();
}
@Override
public int getDefaultSqlPrecision(Dialect dialect) {
return delegate.getDefaultSqlPrecision( dialect );
}
@Override
public int getDefaultSqlScale() {
return delegate.getDefaultSqlScale();
}
@Override
public Comparator<T> getComparator() {
return delegate.getComparator();
}
@Override
public int extractHashCode(T value) {
return delegate.extractHashCode( value );
}
@Override
public boolean areEqual(T one, T another) {
return delegate.areEqual( one, another );
}
@Override
public String extractLoggableRepresentation(T value) {
return delegate.extractLoggableRepresentation( value );
}
@Override
public String toString(T value) {
return delegate.toString( value );
}
@Override
public <X> X unwrap(T value, Class<X> type, WrapperOptions options) {
return delegate.unwrap( value, type, options );
}
@Override
public <X> T wrap(X value, WrapperOptions options) {
return delegate.wrap( value, options );
}
@Override
public <X> T coerce(X value, CoercionContext coercionContext) {
return delegate.coerce( value, coercionContext );
}
@Override
public Class<T> getJavaTypeClass() {
return delegate.getJavaTypeClass();
}
@Override
public String getCheckCondition(String columnName, JdbcTypeDescriptor sqlType, Dialect dialect) {
return delegate.getCheckCondition( columnName, sqlType, dialect );
}
@Override
public TemporalType getPrecision() {
return delegate.getPrecision();
}
@Override
public <X> TemporalJavaTypeDescriptor<X> resolveTypeForPrecision(
TemporalType precision,
TypeConfiguration typeConfiguration) {
return delegate.resolveTypeForPrecision( precision, typeConfiguration );
}
}

View File

@ -19,6 +19,7 @@ import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType; import jakarta.persistence.TemporalType;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
@ -30,7 +31,8 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class InstantJavaDescriptor extends AbstractTemporalTypeDescriptor<Instant> { public class InstantJavaDescriptor extends AbstractTemporalTypeDescriptor<Instant>
implements VersionJavaTypeDescriptor<Instant> {
/** /**
* Singleton access * Singleton access
*/ */
@ -185,4 +187,15 @@ public class InstantJavaDescriptor extends AbstractTemporalTypeDescriptor<Instan
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public Instant seed(SharedSessionContractImplementor session) {
return Instant.now();
}
@Override
public Instant next(Instant current, SharedSessionContractImplementor session) {
return Instant.now();
}
} }

View File

@ -11,6 +11,7 @@ import java.math.BigInteger;
import java.util.Locale; import java.util.Locale;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.java.spi.Primitive; import org.hibernate.type.descriptor.java.spi.Primitive;
@ -19,7 +20,10 @@ import org.hibernate.type.descriptor.java.spi.Primitive;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class IntegerTypeDescriptor extends AbstractClassTypeDescriptor<Integer> implements Primitive<Integer> { public class IntegerTypeDescriptor extends AbstractClassTypeDescriptor<Integer>
implements Primitive<Integer>, VersionJavaTypeDescriptor<Integer> {
public static final Integer ZERO = 0;
public static final IntegerTypeDescriptor INSTANCE = new IntegerTypeDescriptor(); public static final IntegerTypeDescriptor INSTANCE = new IntegerTypeDescriptor();
public IntegerTypeDescriptor() { public IntegerTypeDescriptor() {
@ -175,4 +179,15 @@ public class IntegerTypeDescriptor extends AbstractClassTypeDescriptor<Integer>
) )
); );
} }
@Override
public Integer seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Integer next(Integer current, SharedSessionContractImplementor session) {
return current + 1;
}
} }

View File

@ -21,6 +21,7 @@ import jakarta.persistence.TemporalType;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
@ -32,7 +33,7 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class JdbcTimestampTypeDescriptor extends AbstractTemporalTypeDescriptor<Date> { public class JdbcTimestampTypeDescriptor extends AbstractTemporalTypeDescriptor<Date> implements VersionJavaTypeDescriptor<Date> {
public static final JdbcTimestampTypeDescriptor INSTANCE = new JdbcTimestampTypeDescriptor(); public static final JdbcTimestampTypeDescriptor INSTANCE = new JdbcTimestampTypeDescriptor();
@SuppressWarnings("WeakerAccess") @SuppressWarnings("WeakerAccess")
@ -208,4 +209,15 @@ public class JdbcTimestampTypeDescriptor extends AbstractTemporalTypeDescriptor<
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public Date next(Date current, SharedSessionContractImplementor session) {
return seed( session );
}
@Override
public Date seed(SharedSessionContractImplementor session) {
return new Timestamp( System.currentTimeMillis() );
}
} }

View File

@ -18,6 +18,7 @@ import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType; import jakarta.persistence.TemporalType;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptorIndicators;
@ -29,7 +30,8 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class LocalDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<LocalDateTime> { public class LocalDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<LocalDateTime>
implements VersionJavaTypeDescriptor<LocalDateTime> {
/** /**
* Singleton access * Singleton access
*/ */
@ -160,4 +162,14 @@ public class LocalDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public LocalDateTime seed(SharedSessionContractImplementor session) {
return LocalDateTime.now();
}
@Override
public LocalDateTime next(LocalDateTime current, SharedSessionContractImplementor session) {
return LocalDateTime.now();
}
} }

View File

@ -11,6 +11,7 @@ import java.math.BigInteger;
import java.util.Locale; import java.util.Locale;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.java.spi.Primitive; import org.hibernate.type.descriptor.java.spi.Primitive;
@ -19,7 +20,10 @@ import org.hibernate.type.descriptor.java.spi.Primitive;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class LongTypeDescriptor extends AbstractClassTypeDescriptor<Long> implements Primitive<Long> { public class LongTypeDescriptor extends AbstractClassTypeDescriptor<Long>
implements Primitive<Long>, VersionJavaTypeDescriptor<Long> {
private static final Long ZERO = (long) 0;
public static final LongTypeDescriptor INSTANCE = new LongTypeDescriptor(); public static final LongTypeDescriptor INSTANCE = new LongTypeDescriptor();
public LongTypeDescriptor() { public LongTypeDescriptor() {
@ -175,4 +179,14 @@ public class LongTypeDescriptor extends AbstractClassTypeDescriptor<Long> implem
public int getDefaultSqlScale() { public int getDefaultSqlScale() {
return 0; return 0;
} }
@Override
public Long next(Long current, SharedSessionContractImplementor session) {
return current + 1L;
}
@Override
public Long seed(SharedSessionContractImplementor session) {
return ZERO;
}
} }

View File

@ -13,12 +13,14 @@ import java.time.ZoneId;
import java.time.ZonedDateTime; import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
import java.util.Calendar; import java.util.Calendar;
import java.util.Comparator;
import java.util.Date; import java.util.Date;
import java.util.GregorianCalendar; import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType; import jakarta.persistence.TemporalType;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.DateTypeDescriptor; import org.hibernate.type.descriptor.jdbc.DateTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
@ -32,7 +34,8 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class OffsetDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<OffsetDateTime> { public class OffsetDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<OffsetDateTime>
implements VersionJavaTypeDescriptor<OffsetDateTime> {
/** /**
* Singleton access * Singleton access
*/ */
@ -200,4 +203,19 @@ public class OffsetDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public OffsetDateTime seed(SharedSessionContractImplementor session) {
return OffsetDateTime.now();
}
@Override
public OffsetDateTime next(OffsetDateTime current, SharedSessionContractImplementor session) {
return OffsetDateTime.now();
}
@Override
public Comparator<OffsetDateTime> getComparator() {
return OffsetDateTime.timeLineOrder();
}
} }

View File

@ -16,6 +16,7 @@ import java.util.Comparator;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
import org.hibernate.engine.jdbc.BinaryStream; import org.hibernate.engine.jdbc.BinaryStream;
import org.hibernate.engine.jdbc.internal.BinaryStreamImpl; import org.hibernate.engine.jdbc.internal.BinaryStreamImpl;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.sql.ast.spi.SqlAppender; import org.hibernate.sql.ast.spi.SqlAppender;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
@ -24,7 +25,8 @@ import org.hibernate.type.descriptor.WrapperOptions;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class PrimitiveByteArrayTypeDescriptor extends AbstractClassTypeDescriptor<byte[]> { public class PrimitiveByteArrayTypeDescriptor extends AbstractClassTypeDescriptor<byte[]>
implements VersionJavaTypeDescriptor<byte[]> {
public static final PrimitiveByteArrayTypeDescriptor INSTANCE = new PrimitiveByteArrayTypeDescriptor(); public static final PrimitiveByteArrayTypeDescriptor INSTANCE = new PrimitiveByteArrayTypeDescriptor();
@SuppressWarnings({ "unchecked" }) @SuppressWarnings({ "unchecked" })
@ -132,4 +134,18 @@ public class PrimitiveByteArrayTypeDescriptor extends AbstractClassTypeDescripto
throw unknownWrap( value.getClass() ); throw unknownWrap( value.getClass() );
} }
@Override
public byte[] seed(SharedSessionContractImplementor session) {
// Note : simply returns null for seed() and next() as the only known
// application of binary types for versioning is for use with the
// TIMESTAMP datatype supported by Sybase and SQL Server, which
// are completely db-generated values...
return null;
}
@Override
public byte[] next(byte[] current, SharedSessionContractImplementor session) {
return current;
}
} }

View File

@ -16,6 +16,7 @@ import java.util.Comparator;
import org.hibernate.HibernateException; import org.hibernate.HibernateException;
import org.hibernate.engine.jdbc.BinaryStream; import org.hibernate.engine.jdbc.BinaryStream;
import org.hibernate.engine.jdbc.internal.BinaryStreamImpl; import org.hibernate.engine.jdbc.internal.BinaryStreamImpl;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.compare.RowVersionComparator; import org.hibernate.internal.util.compare.RowVersionComparator;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
@ -25,7 +26,8 @@ import org.hibernate.type.descriptor.WrapperOptions;
* @author Steve Ebersole * @author Steve Ebersole
* @author Gail Badner * @author Gail Badner
*/ */
public class RowVersionTypeDescriptor extends AbstractClassTypeDescriptor<byte[]> { public class RowVersionTypeDescriptor extends AbstractClassTypeDescriptor<byte[]>
implements VersionJavaTypeDescriptor<byte[]> {
public static final RowVersionTypeDescriptor INSTANCE = new RowVersionTypeDescriptor(); public static final RowVersionTypeDescriptor INSTANCE = new RowVersionTypeDescriptor();
@SuppressWarnings({ "unchecked" }) @SuppressWarnings({ "unchecked" })
@ -128,4 +130,18 @@ public class RowVersionTypeDescriptor extends AbstractClassTypeDescriptor<byte[]
throw unknownWrap( value.getClass() ); throw unknownWrap( value.getClass() );
} }
@Override
public byte[] seed(SharedSessionContractImplementor session) {
// Note : simply returns null for seed() and next() as the only known
// application of binary types for versioning is for use with the
// TIMESTAMP datatype supported by Sybase and SQL Server, which
// are completely db-generated values...
return null;
}
@Override
public byte[] next(byte[] current, SharedSessionContractImplementor session) {
return current;
}
} }

View File

@ -10,6 +10,7 @@ import java.math.BigInteger;
import java.util.Locale; import java.util.Locale;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.java.spi.Primitive; import org.hibernate.type.descriptor.java.spi.Primitive;
@ -18,7 +19,10 @@ import org.hibernate.type.descriptor.java.spi.Primitive;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class ShortTypeDescriptor extends AbstractClassTypeDescriptor<Short> implements Primitive<Short> { public class ShortTypeDescriptor extends AbstractClassTypeDescriptor<Short>
implements Primitive<Short>, VersionJavaTypeDescriptor<Short> {
private static final Short ZERO = (short) 0;
public static final ShortTypeDescriptor INSTANCE = new ShortTypeDescriptor(); public static final ShortTypeDescriptor INSTANCE = new ShortTypeDescriptor();
public ShortTypeDescriptor() { public ShortTypeDescriptor() {
@ -167,4 +171,13 @@ public class ShortTypeDescriptor extends AbstractClassTypeDescriptor<Short> impl
) )
); );
} }
@Override
public Short seed(SharedSessionContractImplementor session) {
return ZERO;
}
@Override
public Short next(Short current, SharedSessionContractImplementor session) {
return (short) ( current + 1 );
}
} }

View File

@ -4,19 +4,16 @@
* License: GNU Lesser General Public License (LGPL), version 2.1 or later. * 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>. * See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/ */
package org.hibernate.type; package org.hibernate.type.descriptor.java;
import java.util.Comparator;
import org.hibernate.engine.spi.SharedSessionContractImplementor; import org.hibernate.engine.spi.SharedSessionContractImplementor;
/** /**
* Additional contract for types which may be used to version (and optimistic lock) data. * Additional contract for types which may be used to version (and optimistic lock) data.
* *
* @author Gavin King * @author Christian Beikov
* @author Steve Ebersole
*/ */
public interface VersionType<T> extends Type { public interface VersionJavaTypeDescriptor<T> extends JavaTypeDescriptor<T> {
/** /**
* Generate an initial version. * Generate an initial version.
* *
@ -34,10 +31,4 @@ public interface VersionType<T> extends Type {
*/ */
T next(T current, SharedSessionContractImplementor session); T next(T current, SharedSessionContractImplementor session);
/**
* Get a comparator for version values.
*
* @return The comparator to use to compare different version values.
*/
Comparator<T> getComparator();
} }

View File

@ -13,12 +13,15 @@ import java.time.ZoneId;
import java.time.ZonedDateTime; import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
import java.util.Calendar; import java.util.Calendar;
import java.util.Comparator;
import java.util.Date; import java.util.Date;
import java.util.GregorianCalendar; import java.util.GregorianCalendar;
import jakarta.persistence.TemporalType; import jakarta.persistence.TemporalType;
import org.hibernate.dialect.Dialect; import org.hibernate.dialect.Dialect;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.internal.util.ZonedDateTimeComparator;
import org.hibernate.type.descriptor.WrapperOptions; import org.hibernate.type.descriptor.WrapperOptions;
import org.hibernate.type.descriptor.jdbc.DateTypeDescriptor; import org.hibernate.type.descriptor.jdbc.DateTypeDescriptor;
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor; import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
@ -32,14 +35,14 @@ import org.hibernate.type.spi.TypeConfiguration;
* *
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class ZonedDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<ZonedDateTime> { public class ZonedDateTimeJavaTypeDescriptor extends AbstractTemporalTypeDescriptor<ZonedDateTime> implements VersionJavaTypeDescriptor<ZonedDateTime> {
/** /**
* Singleton access * Singleton access
*/ */
public static final ZonedDateTimeJavaDescriptor INSTANCE = new ZonedDateTimeJavaDescriptor(); public static final ZonedDateTimeJavaTypeDescriptor INSTANCE = new ZonedDateTimeJavaTypeDescriptor();
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public ZonedDateTimeJavaDescriptor() { public ZonedDateTimeJavaTypeDescriptor() {
super( ZonedDateTime.class, ImmutableMutabilityPlan.INSTANCE ); super( ZonedDateTime.class, ImmutableMutabilityPlan.INSTANCE );
} }
@ -199,4 +202,19 @@ public class ZonedDateTimeJavaDescriptor extends AbstractTemporalTypeDescriptor<
public int getDefaultSqlPrecision(Dialect dialect) { public int getDefaultSqlPrecision(Dialect dialect) {
return dialect.getDefaultTimestampPrecision(); return dialect.getDefaultTimestampPrecision();
} }
@Override
public ZonedDateTime seed(SharedSessionContractImplementor session) {
return ZonedDateTime.now();
}
@Override
public ZonedDateTime next(ZonedDateTime current, SharedSessionContractImplementor session) {
return ZonedDateTime.now();
}
@Override
public Comparator<ZonedDateTime> getComparator() {
return ZonedDateTimeComparator.INSTANCE;
}
} }

View File

@ -69,7 +69,7 @@ import org.hibernate.type.descriptor.java.TimeZoneTypeDescriptor;
import org.hibernate.type.descriptor.java.UUIDTypeDescriptor; import org.hibernate.type.descriptor.java.UUIDTypeDescriptor;
import org.hibernate.type.descriptor.java.UrlTypeDescriptor; import org.hibernate.type.descriptor.java.UrlTypeDescriptor;
import org.hibernate.type.descriptor.java.ZoneOffsetJavaDescriptor; import org.hibernate.type.descriptor.java.ZoneOffsetJavaDescriptor;
import org.hibernate.type.descriptor.java.ZonedDateTimeJavaDescriptor; import org.hibernate.type.descriptor.java.ZonedDateTimeJavaTypeDescriptor;
/** /**
* *
@ -115,7 +115,7 @@ public class JavaTypeDescriptorBaseline {
target.addBaselineDescriptor( LocalTimeJavaDescriptor.INSTANCE ); target.addBaselineDescriptor( LocalTimeJavaDescriptor.INSTANCE );
target.addBaselineDescriptor( OffsetDateTimeJavaDescriptor.INSTANCE ); target.addBaselineDescriptor( OffsetDateTimeJavaDescriptor.INSTANCE );
target.addBaselineDescriptor( OffsetTimeJavaDescriptor.INSTANCE ); target.addBaselineDescriptor( OffsetTimeJavaDescriptor.INSTANCE );
target.addBaselineDescriptor( ZonedDateTimeJavaDescriptor.INSTANCE ); target.addBaselineDescriptor( ZonedDateTimeJavaTypeDescriptor.INSTANCE );
target.addBaselineDescriptor( CalendarTypeDescriptor.INSTANCE ); target.addBaselineDescriptor( CalendarTypeDescriptor.INSTANCE );
target.addBaselineDescriptor( DateTypeDescriptor.INSTANCE ); target.addBaselineDescriptor( DateTypeDescriptor.INSTANCE );

View File

@ -28,7 +28,7 @@ import org.hibernate.usertype.UserType;
* @author Steve Ebersole * @author Steve Ebersole
*/ */
public class UserTypeJavaTypeWrapper<J> implements BasicJavaDescriptor<J> { public class UserTypeJavaTypeWrapper<J> implements BasicJavaDescriptor<J> {
private final UserType<J> userType; protected final UserType<J> userType;
private final MutabilityPlan<J> mutabilityPlan; private final MutabilityPlan<J> mutabilityPlan;
private final Comparator<J> comparator; private final Comparator<J> comparator;

View File

@ -0,0 +1,32 @@
/*
* 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.type.internal;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.type.descriptor.java.VersionJavaTypeDescriptor;
import org.hibernate.usertype.UserVersionType;
/**
*
* @author Christian Beikov
*/
public class UserTypeVersionJavaTypeWrapper<J> extends UserTypeJavaTypeWrapper<J> implements VersionJavaTypeDescriptor<J> {
public UserTypeVersionJavaTypeWrapper(UserVersionType<J> userType) {
super( userType );
}
@Override
public J seed(SharedSessionContractImplementor session) {
return ( (UserVersionType<J>) userType ).seed( session );
}
@Override
public J next(J current, SharedSessionContractImplementor session) {
return ( (UserVersionType<J>) userType ).next( current, session );
}
}

View File

@ -15,7 +15,7 @@ import org.hibernate.engine.spi.SharedSessionContractImplementor;
* *
* @author Gavin King * @author Gavin King
*/ */
public interface UserVersionType extends UserType, Comparator { public interface UserVersionType<T> extends UserType<T>, Comparator<T> {
/** /**
* Generate an initial version. * Generate an initial version.
* *
@ -24,7 +24,7 @@ public interface UserVersionType extends UserType, Comparator {
* the "unsaved value" of entities. * the "unsaved value" of entities.
* @return an instance of the type * @return an instance of the type
*/ */
Object seed(SharedSessionContractImplementor session); T seed(SharedSessionContractImplementor session);
/** /**
* Increment the version. * Increment the version.
@ -33,5 +33,5 @@ public interface UserVersionType extends UserType, Comparator {
* @param current the current version * @param current the current version
* @return an instance of the type * @return an instance of the type
*/ */
Object next(Object current, SharedSessionContractImplementor session); T next(T current, SharedSessionContractImplementor session);
} }

View File

@ -64,9 +64,9 @@ import org.hibernate.sql.ast.tree.from.TableGroup;
import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl; import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl;
import org.hibernate.tuple.entity.EntityMetamodel; import org.hibernate.tuple.entity.EntityMetamodel;
import org.hibernate.tuple.entity.EntityTuplizer; import org.hibernate.tuple.entity.EntityTuplizer;
import org.hibernate.type.BasicType;
import org.hibernate.type.CollectionType; import org.hibernate.type.CollectionType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor; import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
/** /**
@ -237,7 +237,7 @@ public class GoofyPersisterClassProvider implements PersisterClassResolver {
} }
@Override @Override
public VersionType getVersionType() { public BasicType<?> getVersionType() {
return null; return null;
} }

View File

@ -62,8 +62,8 @@ import org.hibernate.persister.walking.spi.EntityIdentifierDefinition;
import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl; import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl;
import org.hibernate.tuple.entity.EntityMetamodel; import org.hibernate.tuple.entity.EntityMetamodel;
import org.hibernate.tuple.entity.EntityTuplizer; import org.hibernate.tuple.entity.EntityTuplizer;
import org.hibernate.type.BasicType;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor; import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Assertions;
@ -262,7 +262,7 @@ public class PersisterClassProviderTest {
} }
@Override @Override
public VersionType getVersionType() { public BasicType<?> getVersionType() {
return null; return null;
} }

View File

@ -63,9 +63,9 @@ import org.hibernate.sql.ast.tree.from.TableGroup;
import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl; import org.hibernate.tuple.entity.BytecodeEnhancementMetadataNonPojoImpl;
import org.hibernate.tuple.entity.EntityMetamodel; import org.hibernate.tuple.entity.EntityMetamodel;
import org.hibernate.tuple.entity.EntityTuplizer; import org.hibernate.tuple.entity.EntityTuplizer;
import org.hibernate.type.BasicType;
import org.hibernate.type.StandardBasicTypes; import org.hibernate.type.StandardBasicTypes;
import org.hibernate.type.Type; import org.hibernate.type.Type;
import org.hibernate.type.VersionType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor; import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
public class CustomPersister implements EntityPersister { public class CustomPersister implements EntityPersister {
@ -295,7 +295,7 @@ public class CustomPersister implements EntityPersister {
/** /**
* @see EntityPersister#getVersionType() * @see EntityPersister#getVersionType()
*/ */
public VersionType getVersionType() { public BasicType<?> getVersionType() {
return null; return null;
} }

View File

@ -9,7 +9,7 @@ package org.hibernate.orm.test.mapping.type.java;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.time.ZoneId; import java.time.ZoneId;
import java.time.ZonedDateTime; import java.time.ZonedDateTime;
import org.hibernate.type.descriptor.java.ZonedDateTimeJavaDescriptor; import org.hibernate.type.descriptor.java.ZonedDateTimeJavaTypeDescriptor;
/** /**
* @author Jordan Gigov * @author Jordan Gigov
@ -20,7 +20,7 @@ public class ZonedDateTimeDescriptorTest extends AbstractDescriptorTest<ZonedDat
final ZonedDateTime different = ZonedDateTime.of( LocalDateTime.of( 2016, 10, 8, 15, 13 ), ZoneId.of( "EET" ) ); final ZonedDateTime different = ZonedDateTime.of( LocalDateTime.of( 2016, 10, 8, 15, 13 ), ZoneId.of( "EET" ) );
public ZonedDateTimeDescriptorTest() { public ZonedDateTimeDescriptorTest() {
super(ZonedDateTimeJavaDescriptor.INSTANCE); super( ZonedDateTimeJavaTypeDescriptor.INSTANCE);
} }
@Override @Override

View File

@ -21,8 +21,9 @@ import org.hibernate.dialect.SybaseASE15Dialect;
import org.hibernate.testing.RequiresDialect; import org.hibernate.testing.RequiresDialect;
import org.hibernate.testing.TestForIssue; import org.hibernate.testing.TestForIssue;
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase; import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
import org.hibernate.type.BasicType;
import org.hibernate.type.RowVersionType; import org.hibernate.type.RowVersionType;
import org.hibernate.type.VersionType;
import static org.junit.Assert.assertSame; import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue; import static org.junit.Assert.assertTrue;
@ -36,7 +37,7 @@ public class SybaseTimestampComparisonAnnotationsTest extends BaseCoreFunctional
@Test @Test
@TestForIssue( jiraKey = "HHH-10413" ) @TestForIssue( jiraKey = "HHH-10413" )
public void testComparableTimestamps() { public void testComparableTimestamps() {
final VersionType versionType = final BasicType<?> versionType =
sessionFactory().getEntityPersister( Thing.class.getName() ).getVersionType(); sessionFactory().getEntityPersister( Thing.class.getName() ).getVersionType();
assertSame( RowVersionType.INSTANCE, versionType ); assertSame( RowVersionType.INSTANCE, versionType );

View File

@ -16,9 +16,10 @@ import org.hibernate.dialect.SybaseASE15Dialect;
import org.hibernate.testing.RequiresDialect; import org.hibernate.testing.RequiresDialect;
import org.hibernate.testing.TestForIssue; import org.hibernate.testing.TestForIssue;
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase; import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
import org.hibernate.type.BasicType;
import org.hibernate.type.BinaryType; import org.hibernate.type.BinaryType;
import org.hibernate.type.RowVersionType; import org.hibernate.type.RowVersionType;
import org.hibernate.type.VersionType;
import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertSame; import static org.junit.Assert.assertSame;
@ -225,7 +226,7 @@ public class SybaseTimestampVersioningTest extends BaseCoreFunctionalTestCase {
@Test @Test
@TestForIssue( jiraKey = "HHH-10413" ) @TestForIssue( jiraKey = "HHH-10413" )
public void testComparableTimestamps() { public void testComparableTimestamps() {
final VersionType versionType = final BasicType<?> versionType =
sessionFactory().getEntityPersister( User.class.getName() ).getVersionType(); sessionFactory().getEntityPersister( User.class.getName() ).getVersionType();
assertSame( RowVersionType.INSTANCE, versionType ); assertSame( RowVersionType.INSTANCE, versionType );