HHH-9936 - Same Sequence is created and dropped multiple times

This commit is contained in:
Steve Ebersole 2015-08-04 11:49:15 -05:00
parent 6974744092
commit 41836726e1
4 changed files with 71 additions and 50 deletions

View File

@ -10,20 +10,20 @@ import java.io.Serializable;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Collections;
import java.util.Properties;
import org.hibernate.HibernateException;
import org.hibernate.MappingException;
import org.hibernate.boot.model.naming.ObjectNameNormalizer;
import org.hibernate.boot.model.relational.Database;
import org.hibernate.boot.model.relational.NamedAuxiliaryDatabaseObject;
import org.hibernate.boot.model.relational.Namespace;
import org.hibernate.boot.model.relational.QualifiedName;
import org.hibernate.boot.model.relational.QualifiedNameParser;
import org.hibernate.boot.model.relational.Sequence;
import org.hibernate.dialect.Dialect;
import org.hibernate.engine.jdbc.env.spi.JdbcEnvironment;
import org.hibernate.engine.spi.SessionImplementor;
import org.hibernate.internal.log.DeprecationLogger;
import org.hibernate.internal.util.config.ConfigurationHelper;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.type.Type;
@ -57,12 +57,14 @@ public class SequenceGenerator
/**
* The parameters parameter, appended to the create sequence DDL.
* For example (Oracle): <tt>INCREMENT BY 1 START WITH 1 MAXVALUE 100 NOCACHE</tt>.
*
* @deprecated No longer supported. To specify initial-value or increment use the
* org.hibernate.id.enhanced.SequenceStyleGenerator generator instead.
*/
public static final String PARAMETERS = "parameters";
private QualifiedName qualifiedSequenceName;
private QualifiedName logicalQualifiedSequenceName;
private String sequenceName;
private String parameters;
private Type identifierType;
private String sql;
@ -81,20 +83,24 @@ public class SequenceGenerator
@Override
@SuppressWarnings("StatementWithEmptyBody")
public void configure(Type type, Properties params, ServiceRegistry serviceRegistry) throws MappingException {
identifierType = type;
parameters = params.getProperty( PARAMETERS );
DeprecationLogger.DEPRECATION_LOGGER.deprecatedSequenceGenerator( getClass().getName() );
identifierType = type;
final JdbcEnvironment jdbcEnvironment = serviceRegistry.getService( JdbcEnvironment.class );
final Dialect dialect = jdbcEnvironment.getDialect();
final ObjectNameNormalizer normalizer = ( ObjectNameNormalizer ) params.get( IDENTIFIER_NORMALIZER );
qualifiedSequenceName = QualifiedNameParser.INSTANCE.parse(
logicalQualifiedSequenceName = QualifiedNameParser.INSTANCE.parse(
ConfigurationHelper.getString( SEQUENCE, params, "hibernate_sequence" ),
normalizer.normalizeIdentifierQuoting( params.getProperty( CATALOG ) ),
normalizer.normalizeIdentifierQuoting( params.getProperty( SCHEMA ) )
);
sequenceName = jdbcEnvironment.getQualifiedObjectNameFormatter().format( qualifiedSequenceName, dialect );
sql = dialect.getSequenceNextValString( sequenceName );
if ( params.containsKey( PARAMETERS ) ) {
LOG.warn(
"Use of 'parameters' config setting is no longer supported; " +
"to specify initial-value or increment use the " +
"org.hibernate.id.enhanced.SequenceStyleGenerator generator instead."
);
}
}
@Override
@ -140,11 +146,7 @@ public class SequenceGenerator
@Override
@SuppressWarnings( {"deprecation"})
public String[] sqlCreateStrings(Dialect dialect) throws HibernateException {
String[] ddl = dialect.getCreateSequenceStrings( sequenceName );
if ( parameters != null ) {
ddl[ddl.length - 1] += ' ' + parameters;
}
return ddl;
return dialect.getCreateSequenceStrings( sequenceName, 1, 1 );
}
@Override
@ -164,22 +166,29 @@ public class SequenceGenerator
@Override
public void registerExportables(Database database) {
// we cannot register a proper Sequence object here because of the free-form
//'parameters' as opposed to specific initialValue/increment values
final Namespace namespace = database.locateNamespace(
qualifiedSequenceName.getCatalogName(),
qualifiedSequenceName.getSchemaName()
logicalQualifiedSequenceName.getCatalogName(),
logicalQualifiedSequenceName.getSchemaName()
);
Sequence sequence = namespace.locateSequence( logicalQualifiedSequenceName.getObjectName() );
if ( sequence != null ) {
sequence.validate( 1, 1 );
}
else {
sequence = namespace.createSequence(
logicalQualifiedSequenceName.getObjectName(),
1,
1
);
}
database.addAuxiliaryDatabaseObject(
new NamedAuxiliaryDatabaseObject(
qualifiedSequenceName.getObjectName().render(),
namespace,
sqlCreateStrings( database.getDialect() ),
sqlDropStrings( database.getDialect() ),
Collections.<String>emptySet()
)
final JdbcEnvironment jdbcEnvironment = database.getJdbcEnvironment();
final Dialect dialect = jdbcEnvironment.getDialect();
this.sequenceName = jdbcEnvironment.getQualifiedObjectNameFormatter().format(
sequence.getName(),
dialect
);
this.sql = jdbcEnvironment.getDialect().getSequenceNextValString( sequenceName );
}
}

View File

@ -159,4 +159,13 @@ public interface DeprecationLogger {
void connectionProviderClassDeprecated(
String providerClassName,
String actualProviderClassName);
@LogMessage(level = WARN)
@Message(
id = 90000014,
value = "Found use of deprecated [%s] sequence-based id generator; " +
"use org.hibernate.id.enhanced.SequenceStyleGenerator instead. " +
"See Hibernate Domain Model Mapping Guide for details."
)
void deprecatedSequenceGenerator(String generatorImpl);
}

View File

@ -16,6 +16,7 @@ import java.util.Properties;
import org.hibernate.Session;
import org.hibernate.boot.Metadata;
import org.hibernate.boot.MetadataSources;
import org.hibernate.boot.model.naming.Identifier;
import org.hibernate.boot.model.naming.ObjectNameNormalizer;
import org.hibernate.boot.model.relational.SimpleAuxiliaryDatabaseObject;
import org.hibernate.boot.registry.StandardServiceRegistry;
@ -26,6 +27,7 @@ import org.hibernate.engine.jdbc.env.spi.JdbcEnvironment;
import org.hibernate.engine.jdbc.spi.JdbcServices;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.engine.spi.SessionImplementor;
import org.hibernate.id.enhanced.SequenceStyleGenerator;
import org.hibernate.internal.SessionImpl;
import org.hibernate.jdbc.Work;
import org.hibernate.type.StandardBasicTypes;
@ -55,7 +57,7 @@ public class SequenceHiLoGeneratorNoIncrementTest extends BaseUnitTestCase {
private StandardServiceRegistry serviceRegistry;
private SessionFactoryImplementor sessionFactory;
private SequenceHiLoGenerator generator;
private SequenceStyleGenerator generator;
private SessionImplementor session;
@Before
@ -70,12 +72,13 @@ public class SequenceHiLoGeneratorNoIncrementTest extends BaseUnitTestCase {
.applySetting( AvailableSettings.HBM2DDL_AUTO, "create-drop" )
.build();
generator = new SequenceHiLoGenerator();
generator = new SequenceStyleGenerator();
// Build the properties used to configure the id generator
Properties properties = new Properties();
properties.setProperty( SequenceGenerator.SEQUENCE, TEST_SEQUENCE );
properties.setProperty( SequenceHiLoGenerator.MAX_LO, "0" ); // JPA allocationSize of 1
properties.setProperty( SequenceStyleGenerator.SEQUENCE_PARAM, TEST_SEQUENCE );
properties.setProperty( SequenceStyleGenerator.OPT_PARAM, "legacy-hilo" );
properties.setProperty( SequenceStyleGenerator.INCREMENT_PARAM, "0" ); // JPA allocationSize of 1
properties.put(
PersistentIdentifierGenerator.IDENTIFIER_NORMALIZER,
new ObjectNameNormalizer() {
@ -88,15 +91,7 @@ public class SequenceHiLoGeneratorNoIncrementTest extends BaseUnitTestCase {
generator.configure( StandardBasicTypes.LONG, properties, serviceRegistry );
final Metadata metadata = new MetadataSources( serviceRegistry ).buildMetadata();
metadata.getDatabase().addAuxiliaryDatabaseObject(
new SimpleAuxiliaryDatabaseObject(
Collections.<String>emptySet(),
null,
null,
generator.sqlCreateStrings( TestingDatabaseInfo.DIALECT ),
generator.sqlDropStrings( TestingDatabaseInfo.DIALECT )
)
);
generator.registerExportables( metadata.getDatabase() );
sessionFactory = (SessionFactoryImplementor) metadata.buildSessionFactory();
}

View File

@ -57,12 +57,16 @@ public class LegacySequenceExportTest extends BaseUnitTestCase {
.buildMetadata();
metadata.validate();
int auxCount = 0;
for ( AuxiliaryDatabaseObject auxiliaryDatabaseObject : metadata.getDatabase().getAuxiliaryDatabaseObjects() ) {
auxCount++;
assertEquals( 0, metadata.getDatabase().getAuxiliaryDatabaseObjects().size() );
int count = 0;
for ( Namespace namespace : metadata.getDatabase().getNamespaces() ) {
for ( Sequence sequence : namespace.getSequences() ) {
count++;
}
}
assertEquals( 1, auxCount );
assertEquals( 1, count );
}
@Test
@ -74,12 +78,16 @@ public class LegacySequenceExportTest extends BaseUnitTestCase {
.buildMetadata();
metadata.validate();
int auxCount = 0;
for ( AuxiliaryDatabaseObject auxiliaryDatabaseObject : metadata.getDatabase().getAuxiliaryDatabaseObjects() ) {
auxCount++;
assertEquals( 0, metadata.getDatabase().getAuxiliaryDatabaseObjects().size() );
int count = 0;
for ( Namespace namespace : metadata.getDatabase().getNamespaces() ) {
for ( Sequence sequence : namespace.getSequences() ) {
count++;
}
}
assertEquals( 1, auxCount );
assertEquals( 1, count );
}
@Entity( name = "Entity1" )