diff --git a/hibernate-core/src/main/java/org/hibernate/dialect/unique/DefaultUniqueDelegate.java b/hibernate-core/src/main/java/org/hibernate/dialect/unique/DefaultUniqueDelegate.java index a9c8ac33fc..5d9a34881e 100644 --- a/hibernate-core/src/main/java/org/hibernate/dialect/unique/DefaultUniqueDelegate.java +++ b/hibernate-core/src/main/java/org/hibernate/dialect/unique/DefaultUniqueDelegate.java @@ -23,9 +23,9 @@ package org.hibernate.dialect.unique; import java.util.Iterator; import org.hibernate.dialect.Dialect; -import org.hibernate.mapping.Column; -import org.hibernate.mapping.Table; -import org.hibernate.mapping.UniqueKey; +import org.hibernate.metamodel.relational.Column; +import org.hibernate.metamodel.relational.Table; +import org.hibernate.metamodel.relational.UniqueKey; /** * The default UniqueDelegate implementation for most dialects. Uses @@ -41,6 +41,29 @@ public class DefaultUniqueDelegate implements UniqueDelegate { this.dialect = dialect; } + @Override + public String applyUniqueToColumn( org.hibernate.mapping.Table table, + org.hibernate.mapping.Column column ) { +// if ( column.isUnique() +// && ( column.isNullable() +// || dialect.supportsNotNullUnique() ) ) { +// if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { +// // If the constraint is supported, do not add to the column syntax. +// UniqueKey uk = getOrCreateUniqueKey( column.getQuotedName( dialect ) + '_' ); +// uk.addColumn( column ); +// } +// else if ( dialect.supportsUnique() ) { +// // Otherwise, add to the column syntax if supported. +// sb.append( " unique" ); +// } +// } + + org.hibernate.mapping.UniqueKey uk = table.getOrCreateUniqueKey( + column.getQuotedName( dialect ) + '_' ); + uk.addColumn( column ); + return ""; + } + @Override public String applyUniqueToColumn( Table table, Column column ) { // if ( column.isUnique() @@ -57,12 +80,25 @@ public class DefaultUniqueDelegate implements UniqueDelegate { // } // } - UniqueKey uk = table.getOrCreateUniqueKey( - column.getQuotedName( dialect ) + '_' ); + UniqueKey uk = table.getOrCreateUniqueKey( column.getColumnName() + .encloseInQuotesIfQuoted( dialect ) + '_' ); uk.addColumn( column ); return ""; } + @Override + public String applyUniquesToTable( org.hibernate.mapping.Table table ) { + // TODO: Am I correct that this shouldn't be done unless the constraint + // isn't created in an alter table? +// Iterator uniqueKeyIterator = table.getUniqueKeyIterator(); +// while ( uniqueKeyIterator.hasNext() ) { +// UniqueKey uniqueKey = (UniqueKey) uniqueKeyIterator.next(); +// +// sb.append( ", " ).append( createUniqueConstraint( uniqueKey) ); +// } + return ""; + } + @Override public String applyUniquesToTable( Table table ) { // TODO: Am I correct that this shouldn't be done unless the constraint @@ -77,7 +113,7 @@ public class DefaultUniqueDelegate implements UniqueDelegate { } @Override - public String applyUniquesOnAlter( UniqueKey uniqueKey, + public String applyUniquesOnAlter( org.hibernate.mapping.UniqueKey uniqueKey, String defaultCatalog, String defaultSchema ) { // if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { // return super.sqlCreateString( dialect, p, defaultCatalog, defaultSchema ); @@ -97,7 +133,25 @@ public class DefaultUniqueDelegate implements UniqueDelegate { } @Override - public String dropUniquesOnAlter( UniqueKey uniqueKey, + public String applyUniquesOnAlter( UniqueKey uniqueKey ) { +// if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { +// return super.sqlCreateString( dialect, p, defaultCatalog, defaultSchema ); +// } +// else { +// return Index.buildSqlCreateIndexString( dialect, getName(), getTable(), getColumnIterator(), true, +// defaultCatalog, defaultSchema ); +// } + + return new StringBuilder( "alter table " ) + .append( uniqueKey.getTable().getQualifiedName( dialect ) ) + .append( " add constraint " ) + .append( uniqueKey.getName() ) + .append( uniqueConstraintSql( uniqueKey ) ) + .toString(); + } + + @Override + public String dropUniquesOnAlter( org.hibernate.mapping.UniqueKey uniqueKey, String defaultCatalog, String defaultSchema ) { // if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { // return super.sqlDropString( dialect, defaultCatalog, defaultSchema ); @@ -115,7 +169,23 @@ public class DefaultUniqueDelegate implements UniqueDelegate { } @Override - public String uniqueConstraintSql( UniqueKey uniqueKey ) { + public String dropUniquesOnAlter( UniqueKey uniqueKey ) { +// if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { +// return super.sqlDropString( dialect, defaultCatalog, defaultSchema ); +// } +// else { +// return Index.buildSqlDropIndexString( dialect, getTable(), getName(), defaultCatalog, defaultSchema ); +// } + + return new StringBuilder( "alter table " ) + .append( uniqueKey.getTable().getQualifiedName( dialect ) ) + .append( " drop constraint " ) + .append( dialect.quote( uniqueKey.getName() ) ) + .toString(); + } + + @Override + public String uniqueConstraintSql( org.hibernate.mapping.UniqueKey uniqueKey ) { // TODO: This may not be necessary, but not all callers currently // check it on their own. Go through their logic. // if ( !isGenerated( dialect ) ) return null; @@ -124,7 +194,29 @@ public class DefaultUniqueDelegate implements UniqueDelegate { sb.append( " unique (" ); Iterator columnIterator = uniqueKey.getColumnIterator(); while ( columnIterator.hasNext() ) { - Column column = (Column) columnIterator.next(); + org.hibernate.mapping.Column column + = (org.hibernate.mapping.Column) columnIterator.next(); + sb.append( column.getQuotedName( dialect ) ); + if ( columnIterator.hasNext() ) { + sb.append( ", " ); + } + } + + return sb.append( ')' ).toString(); + } + + @Override + public String uniqueConstraintSql( UniqueKey uniqueKey ) { + // TODO: This may not be necessary, but not all callers currently + // check it on their own. Go through their logic. +// if ( !isGenerated( dialect ) ) return null; + + StringBuilder sb = new StringBuilder(); + sb.append( " unique (" ); + Iterator columnIterator = uniqueKey.getColumns().iterator(); + while ( columnIterator.hasNext() ) { + org.hibernate.mapping.Column column + = (org.hibernate.mapping.Column) columnIterator.next(); sb.append( column.getQuotedName( dialect ) ); if ( columnIterator.hasNext() ) { sb.append( ", " ); diff --git a/hibernate-core/src/main/java/org/hibernate/dialect/unique/UniqueDelegate.java b/hibernate-core/src/main/java/org/hibernate/dialect/unique/UniqueDelegate.java index cbe2e19667..042f0c8c3c 100644 --- a/hibernate-core/src/main/java/org/hibernate/dialect/unique/UniqueDelegate.java +++ b/hibernate-core/src/main/java/org/hibernate/dialect/unique/UniqueDelegate.java @@ -20,9 +20,9 @@ */ package org.hibernate.dialect.unique; -import org.hibernate.mapping.Column; -import org.hibernate.mapping.Table; -import org.hibernate.mapping.UniqueKey; +import org.hibernate.metamodel.relational.Column; +import org.hibernate.metamodel.relational.Table; +import org.hibernate.metamodel.relational.UniqueKey; /** * Dialect-level delegate in charge of applying "uniqueness" to a column. @@ -40,6 +40,18 @@ import org.hibernate.mapping.UniqueKey; */ public interface UniqueDelegate { + /** + * If the delegate supports unique constraints, this method should simply + * create the UniqueKey on the Table. Otherwise, the constraint isn't + * supported and "unique" should be added to the column definition. + * + * @param table + * @param column + * @return String + */ + public String applyUniqueToColumn( org.hibernate.mapping.Table table, + org.hibernate.mapping.Column column ); + /** * If the delegate supports unique constraints, this method should simply * create the UniqueKey on the Table. Otherwise, the constraint isn't @@ -51,6 +63,16 @@ public interface UniqueDelegate { */ public String applyUniqueToColumn( Table table, Column column ); + /** + * If creating unique constraints in separate alter statements are not + * supported, this method should return the syntax necessary to create + * the constraint on the original create table statement. + * + * @param table + * @return String + */ + public String applyUniquesToTable( org.hibernate.mapping.Table table ); + /** * If creating unique constraints in separate alter statements are not * supported, this method should return the syntax necessary to create @@ -70,9 +92,18 @@ public interface UniqueDelegate { * @param defaultSchema * @return String */ - public String applyUniquesOnAlter( UniqueKey uniqueKey, + public String applyUniquesOnAlter( org.hibernate.mapping.UniqueKey uniqueKey, String defaultCatalog, String defaultSchema ); + /** + * If creating unique constraints in separate alter statements is + * supported, generate the necessary "alter" syntax for the given key. + * + * @param uniqueKey + * @return String + */ + public String applyUniquesOnAlter( UniqueKey uniqueKey ); + /** * If dropping unique constraints in separate alter statements is * supported, generate the necessary "alter" syntax for the given key. @@ -82,9 +113,27 @@ public interface UniqueDelegate { * @param defaultSchema * @return String */ - public String dropUniquesOnAlter( UniqueKey uniqueKey, + public String dropUniquesOnAlter( org.hibernate.mapping.UniqueKey uniqueKey, String defaultCatalog, String defaultSchema ); + /** + * If dropping unique constraints in separate alter statements is + * supported, generate the necessary "alter" syntax for the given key. + * + * @param uniqueKey + * @return String + */ + public String dropUniquesOnAlter( UniqueKey uniqueKey ); + + /** + * Generates the syntax necessary to create the unique constraint (reused + * by all methods). Ex: "unique (column1, column2, ...)" + * + * @param uniqueKey + * @return String + */ + public String uniqueConstraintSql( org.hibernate.mapping.UniqueKey uniqueKey ); + /** * Generates the syntax necessary to create the unique constraint (reused * by all methods). Ex: "unique (column1, column2, ...)" diff --git a/hibernate-core/src/main/java/org/hibernate/mapping/UniqueKey.java b/hibernate-core/src/main/java/org/hibernate/mapping/UniqueKey.java index 4368c7e293..bf4bf07eda 100644 --- a/hibernate-core/src/main/java/org/hibernate/mapping/UniqueKey.java +++ b/hibernate-core/src/main/java/org/hibernate/mapping/UniqueKey.java @@ -38,7 +38,9 @@ public class UniqueKey extends Constraint { String constraintName, String defaultCatalog, String defaultSchema) { - return dialect.getUniqueDelegate().uniqueConstraintSql( this ); +// return dialect.getUniqueDelegate().uniqueConstraintSql( this ); + // Not used. + return ""; } @Override diff --git a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Database.java b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Database.java index f15f565790..3291b967ed 100644 --- a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Database.java +++ b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Database.java @@ -115,10 +115,8 @@ public class Database { for ( Schema schema : schemaMap.values() ) { for ( Table table : schema.getTables() ) { - if ( ! dialect.supportsUniqueConstraintInCreateAlterTable() ) { - for ( UniqueKey uniqueKey : table.getUniqueKeys() ) { - addSqlCreateStrings( dialect, exportIdentifiers, script, uniqueKey ); - } + for ( UniqueKey uniqueKey : table.getUniqueKeys() ) { + addSqlCreateStrings( dialect, exportIdentifiers, script, uniqueKey ); } for ( Index index : table.getIndexes() ) { diff --git a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Table.java b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Table.java index 72ce0df0f2..1c70ac1cef 100644 --- a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Table.java +++ b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/Table.java @@ -199,20 +199,8 @@ public class Table extends AbstractTableSpecification implements Exportable { } - // If the column is 1.) unique and nullable or 2.) unique, - // not null, and the dialect supports unique not null - if ( col.isUnique() - && ( col.isNullable() - || dialect.supportsNotNullUnique() ) ) { - if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { - // If the constraint is supported, do not add to the column syntax. - UniqueKey uk = getOrCreateUniqueKey( col.getColumnName().encloseInQuotesIfQuoted( dialect ) + '_' ); - uk.addColumn( col ); - } - else if ( dialect.supportsUnique() ) { - // Otherwise, add to the column syntax if supported. - buf.append( " unique" ); - } + if ( col.isUnique() ) { + buf.append( dialect.getUniqueDelegate().applyUniqueToColumn( this, col ) ); } if ( col.getCheckCondition() != null && dialect.supportsColumnCheck() ) { @@ -231,14 +219,7 @@ public class Table extends AbstractTableSpecification implements Exportable { .append( getPrimaryKey().sqlConstraintStringInCreateTable( dialect ) ); } - if ( dialect.supportsUniqueConstraintInCreateAlterTable() ) { - for ( UniqueKey uk : uniqueKeys.values() ) { - String constraint = uk.sqlConstraintStringInCreateTable( dialect ); - if ( constraint != null ) { - buf.append( ", " ).append( constraint ); - } - } - } + buf.append( dialect.getUniqueDelegate().applyUniquesToTable( this ) ); if ( dialect.supportsTableCheck() ) { for ( CheckConstraint checkConstraint : checkConstraints ) { diff --git a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/UniqueKey.java b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/UniqueKey.java index 1c5413e473..339ba1d20e 100644 --- a/hibernate-core/src/main/java/org/hibernate/metamodel/relational/UniqueKey.java +++ b/hibernate-core/src/main/java/org/hibernate/metamodel/relational/UniqueKey.java @@ -47,54 +47,22 @@ public class UniqueKey extends AbstractConstraint implements Constraint { } @Override - public boolean isCreationVetoed(Dialect dialect) { - if ( !dialect.supportsUniqueConstraintInCreateAlterTable() ) return true; - if ( dialect.supportsNotNullUnique() ) return false; - - for ( Column column : getColumns() ) { - // Dialect does not support "not null unique" and this column is not null. - if ( ! column.isNullable() ) return true; - } - return false; - } - - public String sqlConstraintStringInCreateTable(Dialect dialect) { - // TODO: This may not be necessary, but not all callers currently - // check it on their own. Go through their logic. - if ( isCreationVetoed( dialect ) ) return null; - - StringBuilder buf = new StringBuilder( "unique (" ); - boolean first = true; - for ( Column column : getColumns() ) { - if ( first ) { - first = false; - } - else { - buf.append( ", " ); - } - buf.append( column.getColumnName().encloseInQuotesIfQuoted( dialect ) ); - } - return buf.append( ')' ).toString(); + public String[] sqlCreateStrings(Dialect dialect) { + return new String[] { + dialect.getUniqueDelegate().applyUniquesOnAlter( this ) + }; } @Override - public String sqlConstraintStringInAlterTable(Dialect dialect) { - // TODO: This may not be necessary, but not all callers currently - // check it on their own. Go through their logic. - if ( isCreationVetoed( dialect ) ) return null; - - StringBuilder buf = new StringBuilder( - dialect.getAddUniqueConstraintString( getName() ) ).append( '(' ); - boolean first = true; - for ( Column column : getColumns() ) { - if ( first ) { - first = false; - } - else { - buf.append( ", " ); - } - buf.append( column.getColumnName().encloseInQuotesIfQuoted( dialect ) ); - } - return buf.append( ')' ).toString(); + public String[] sqlDropStrings(Dialect dialect) { + return new String[] { + dialect.getUniqueDelegate().dropUniquesOnAlter( this ) + }; + } + + @Override + protected String sqlConstraintStringInAlterTable(Dialect dialect) { + // not used + return ""; } }