You are viewing a plain text version of this content. The canonical link for it is here.
Posted to ddlutils-dev@db.apache.org by to...@apache.org on 2006/05/07 14:23:31 UTC

svn commit: r404752 - in /db/ddlutils/trunk/src: java/org/apache/ddlutils/alteration/ java/org/apache/ddlutils/model/ java/org/apache/ddlutils/platform/ java/org/apache/ddlutils/platform/derby/ test/org/apache/ddlutils/alteration/ test/org/apache/ddlut...

Author: tomdz
Date: Sun May  7 05:23:28 2006
New Revision: 404752

URL: http://svn.apache.org/viewcvs?rev=404752&view=rev
Log:
Enhanced the way in which sql builders can redefine aspects of the database alteration
Added tests

Added:
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/IndexImpBase.java
Modified:
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddForeignKeyChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddIndexChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddPrimaryKeyChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddTableChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnAutoIncrementChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDataTypeChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDefaultValueChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnRequiredChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnSizeChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/PrimaryKeyChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveColumnChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveForeignKeyChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveIndexChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemovePrimaryKeyChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveTableChange.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/ForeignKey.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Index.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/NonUniqueIndex.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Reference.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/model/UniqueIndex.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java
    db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/derby/DerbyBuilder.java
    db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestAlterationAlgorithm.java
    db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestModelComparator.java
    db/ddlutils/trunk/src/test/org/apache/ddlutils/io/TestAlteration.java

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java Sun May  7 05:23:28 2006
@@ -16,7 +16,9 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.DdlUtilsException;
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -49,5 +51,23 @@
     public Column getNewColumn()
     {
         return _newColumn;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Column newColumn = null;
+
+        try
+        {
+            newColumn = (Column)_newColumn.clone();
+        }
+        catch (CloneNotSupportedException ex)
+        {
+            throw new DdlUtilsException(ex);
+        }
+        database.findTable(getChangedTable().getName()).addColumn(newColumn);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddForeignKeyChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddForeignKeyChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddForeignKeyChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddForeignKeyChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,8 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.DdlUtilsException;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.ForeignKey;
 import org.apache.ddlutils.model.Table;
 
@@ -52,4 +54,24 @@
     {
         return _newForeignKey;
     }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        ForeignKey newFK = null;
+
+        try
+        {
+            newFK = (ForeignKey)_newForeignKey.clone();
+            newFK.setForeignTable(database.findTable(_newForeignKey.getForeignTableName()));
+        }
+        catch (CloneNotSupportedException ex)
+        {
+            throw new DdlUtilsException(ex);
+        }
+        database.findTable(getChangedTable().getName()).addForeignKey(newFK);
+    }
+
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddIndexChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddIndexChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddIndexChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddIndexChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,8 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.DdlUtilsException;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Index;
 import org.apache.ddlutils.model.Table;
 
@@ -49,5 +51,23 @@
     public Index getNewIndex()
     {
         return _newIndex;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Index newIndex = null;
+
+        try
+        {
+            newIndex = (Index)_newIndex.clone();
+        }
+        catch (CloneNotSupportedException ex)
+        {
+            throw new DdlUtilsException(ex);
+        }
+        database.findTable(getChangedTable().getName()).addIndex(newIndex);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddPrimaryKeyChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddPrimaryKeyChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddPrimaryKeyChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddPrimaryKeyChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -49,5 +50,20 @@
     public Column[] getPrimaryKeyColumns()
     {
         return _primaryKeyColumns;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+
+        for (int idx = 0; idx < _primaryKeyColumns.length; idx++)
+        {
+            Column column = table.findColumn(_primaryKeyColumns[idx].getName());
+
+            column.setPrimaryKey(true);
+        }
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddTableChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddTableChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddTableChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddTableChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,8 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.DdlUtilsException;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -50,4 +52,20 @@
     {
         return _newTable;
     }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        try
+        {
+            database.addTable((Table)_newTable.clone());
+        }
+        catch (CloneNotSupportedException ex)
+        {
+            throw new DdlUtilsException(ex);
+        }
+    }
+
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnAutoIncrementChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnAutoIncrementChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnAutoIncrementChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnAutoIncrementChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -50,5 +51,16 @@
     public Column getColumn()
     {
         return _column;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        column.setAutoIncrement(!_column.isAutoIncrement());
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDataTypeChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDataTypeChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDataTypeChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDataTypeChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -63,5 +64,16 @@
     public int getNewTypeCode()
     {
         return _newTypeCode;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        column.setTypeCode(_newTypeCode);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDefaultValueChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDefaultValueChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDefaultValueChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnDefaultValueChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -63,5 +64,16 @@
     public String getNewDefaultValue()
     {
         return _newDefaultValue;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        column.setDefaultValue(_newDefaultValue);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnRequiredChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnRequiredChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnRequiredChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnRequiredChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -50,5 +51,16 @@
     public Column getColumn()
     {
         return _column;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        column.setRequired(!_column.isRequired());
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnSizeChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnSizeChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnSizeChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ColumnSizeChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -77,5 +78,16 @@
     public int getNewScale()
     {
         return _newScale;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        column.setSizeAndScale(_newSize, _newScale);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelChange.java Sun May  7 05:23:28 2006
@@ -1,5 +1,7 @@
 package org.apache.ddlutils.alteration;
 
+import org.apache.ddlutils.model.Database;
+
 /*
  * Copyright 2006 The Apache Software Foundation.
  * 
@@ -23,4 +25,10 @@
  */
 public interface ModelChange
 {
+    /**
+     * Applies this change to the given database.
+     * 
+     * @param database The database
+     */
+    public void apply(Database database);
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java Sun May  7 05:23:28 2006
@@ -19,8 +19,10 @@
 import java.util.ArrayList;
 import java.util.List;
 
+import org.apache.commons.lang.StringUtils;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
+import org.apache.ddlutils.PlatformInfo;
 import org.apache.ddlutils.model.Column;
 import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.ForeignKey;
@@ -40,16 +42,20 @@
     /** The log for this comparator. */
     private final Log _log = LogFactory.getLog(ModelComparator.class);
 
+    /** The platform information. */
+    private PlatformInfo _platformInfo;
     /** Whether comparison is case sensitive. */
     private boolean _caseSensitive;
 
     /**
      * Creates a new model comparator object.
      * 
+     * @param platformInfo  The platform info
      * @param caseSensitive Whether comparison is case sensitive
      */
-    public ModelComparator(boolean caseSensitive)
+    public ModelComparator(PlatformInfo platformInfo, boolean caseSensitive)
     {
+        _platformInfo  = platformInfo;
         _caseSensitive = caseSensitive;
     }
 
@@ -304,11 +310,11 @@
             changes.add(new ColumnDataTypeChange(sourceTable, sourceColumn, targetColumn.getTypeCode()));
         }
 
-        // the concrete platform decides whether the size matters for a given data type
-        // so when the size differs we create a change object and the platform can filter
-        // it later if the size is not relevant
-        if ((sourceColumn.getSizeAsInt() != targetColumn.getSizeAsInt()) ||
-            (sourceColumn.getScale()     != targetColumn.getScale()))
+        boolean sizeMatters = _platformInfo.hasSize(sourceColumn.getTypeCode());
+
+        if ((sizeMatters &&
+            (!StringUtils.equals(sourceColumn.getSize(), targetColumn.getSize())) ||
+             sourceColumn.getScale() != targetColumn.getScale()))
         {
             changes.add(new ColumnSizeChange(sourceTable, sourceColumn, targetColumn.getSizeAsInt(), targetColumn.getScale()));
         }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/PrimaryKeyChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/PrimaryKeyChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/PrimaryKeyChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/PrimaryKeyChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -63,5 +64,26 @@
     public Column[] getNewPrimaryKeyColumns()
     {
         return _newPrimaryKeyColumns;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+
+        for (int idx = 0; idx < _oldPrimaryKeyColumns.length; idx++)
+        {
+            Column column = table.findColumn(_oldPrimaryKeyColumns[idx].getName());
+
+            column.setPrimaryKey(false);
+        }
+        for (int idx = 0; idx < _newPrimaryKeyColumns.length; idx++)
+        {
+            Column column = table.findColumn(_newPrimaryKeyColumns[idx].getName());
+
+            column.setPrimaryKey(true);
+        }
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveColumnChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveColumnChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveColumnChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveColumnChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -49,5 +50,16 @@
     public Column getColumn()
     {
         return _column;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table  table  = database.findTable(getChangedTable().getName());
+        Column column = table.findColumn(_column.getName());
+
+        table.removeColumn(column);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveForeignKeyChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveForeignKeyChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveForeignKeyChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveForeignKeyChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,7 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.ForeignKey;
 import org.apache.ddlutils.model.Table;
 
@@ -51,5 +52,15 @@
     public ForeignKey getForeignKey()
     {
         return _foreignKey;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+
+        table.removeForeignKey(_foreignKey);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveIndexChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveIndexChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveIndexChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveIndexChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,7 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Index;
 import org.apache.ddlutils.model.Table;
 
@@ -49,5 +50,16 @@
     public Index getIndex()
     {
         return _index;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+        Index index = table.findIndex(_index.getName());
+
+        table.removeIndex(index);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemovePrimaryKeyChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemovePrimaryKeyChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemovePrimaryKeyChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemovePrimaryKeyChange.java Sun May  7 05:23:28 2006
@@ -17,6 +17,7 @@
  */
 
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -49,5 +50,20 @@
     public Column[] getPrimaryKeyColumns()
     {
         return _primaryKeyColumns;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+
+        for (int idx = 0; idx < _primaryKeyColumns.length; idx++)
+        {
+            Column column = table.findColumn(_primaryKeyColumns[idx].getName());
+
+            column.setPrimaryKey(false);
+        }
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveTableChange.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveTableChange.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveTableChange.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/RemoveTableChange.java Sun May  7 05:23:28 2006
@@ -16,6 +16,7 @@
  * limitations under the License.
  */
 
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Table;
 
 /**
@@ -33,5 +34,15 @@
     public RemoveTableChange(Table table)
     {
         super(table);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void apply(Database database)
+    {
+        Table table = database.findTable(getChangedTable().getName());
+
+        database.removeTable(table);
     }
 }

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/ForeignKey.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/ForeignKey.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/ForeignKey.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/ForeignKey.java Sun May  7 05:23:28 2006
@@ -216,7 +216,7 @@
     /**
      * {@inheritDoc}
      */
-    protected Object clone() throws CloneNotSupportedException
+    public Object clone() throws CloneNotSupportedException
     {
         ForeignKey result = (ForeignKey)super.clone();
 
@@ -226,7 +226,7 @@
 
         for (Iterator it = _references.iterator(); it.hasNext();)
         {
-            result._references.add(it.next());
+            result._references.add(((Reference)it.next()).clone());
         }
 
         return result;

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Index.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Index.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Index.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Index.java Sun May  7 05:23:28 2006
@@ -91,6 +91,14 @@
     public void removeColumn(int idx);
 
     /**
+     * Clones this index.
+     * 
+     * @return The clone
+     * @throws CloneNotSupportedException If the cloning did fail
+     */
+    public Object clone() throws CloneNotSupportedException;
+
+    /**
      * Compares this index to the given one while ignoring the case of identifiers.
      * 
      * @param otherIndex The other index

Added: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/IndexImpBase.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/IndexImpBase.java?rev=404752&view=auto
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/IndexImpBase.java (added)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/IndexImpBase.java Sun May  7 05:23:28 2006
@@ -0,0 +1,115 @@
+package org.apache.ddlutils.model;
+
+/*
+ * Copyright 2006 The Apache Software Foundation.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ * 
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+import java.util.ArrayList;
+
+/**
+ * Base class for indices.
+ * 
+ * @author Thomas Dudziak
+ * @version $Revision: $
+ */
+public abstract class IndexImpBase implements Index
+{
+    /** The name of the index. */
+    protected String    _name;
+    /** The columns making up the index. */
+    protected ArrayList _columns = new ArrayList();
+
+    /**
+     * {@inheritDoc}
+     */
+    public String getName()
+    {
+        return _name;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void setName(String name)
+    {
+        _name = name;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public int getColumnCount()
+    {
+        return _columns.size();
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public IndexColumn getColumn(int idx)
+    {
+        return (IndexColumn)_columns.get(idx);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public IndexColumn[] getColumns()
+    {
+        return (IndexColumn[])_columns.toArray(new IndexColumn[_columns.size()]);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void addColumn(IndexColumn column)
+    {
+        if (column != null)
+        {
+            for (int idx = 0; idx < _columns.size(); idx++)
+            {
+                IndexColumn curColumn = getColumn(idx);
+
+                if (curColumn.getOrdinalPosition() > column.getOrdinalPosition())
+                {
+                    _columns.add(idx, column);
+                    return;
+                }
+            }
+            _columns.add(column);
+        }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void removeColumn(IndexColumn column)
+    {
+        _columns.remove(column);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public void removeColumn(int idx)
+    {
+        _columns.remove(idx);
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    public abstract Object clone() throws CloneNotSupportedException;
+}

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/NonUniqueIndex.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/NonUniqueIndex.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/NonUniqueIndex.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/NonUniqueIndex.java Sun May  7 05:23:28 2006
@@ -27,16 +27,11 @@
  * @author Thomas Dudziak
  * @version $Revision: 289996 $
  */
-public class NonUniqueIndex implements Index
+public class NonUniqueIndex extends IndexImpBase
 {
     /** Unique ID for serialization purposes. */
     private static final long serialVersionUID = -3591499395114850301L;
 
-    /** The name of the index. */
-    protected String    _name;
-    /** The columns making up the index. */
-    protected ArrayList _columns = new ArrayList();
-
     /**
      * {@inheritDoc}
      */
@@ -48,86 +43,9 @@
     /**
      * {@inheritDoc}
      */
-    public String getName()
-    {
-        return _name;
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public void setName(String name)
-    {
-        _name = name;
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public int getColumnCount()
-    {
-        return _columns.size();
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public IndexColumn getColumn(int idx)
-    {
-        return (IndexColumn)_columns.get(idx);
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public IndexColumn[] getColumns()
-    {
-        return (IndexColumn[])_columns.toArray(new IndexColumn[_columns.size()]);
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public void addColumn(IndexColumn column)
-    {
-        if (column != null)
-        {
-            for (int idx = 0; idx < _columns.size(); idx++)
-            {
-                IndexColumn curColumn = getColumn(idx);
-
-                if (curColumn.getOrdinalPosition() > column.getOrdinalPosition())
-                {
-                    _columns.add(idx, column);
-                    return;
-                }
-            }
-            _columns.add(column);
-        }
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public void removeColumn(IndexColumn column)
-    {
-        _columns.remove(column);
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    public void removeColumn(int idx)
-    {
-        _columns.remove(idx);
-    }
-
-    /**
-     * {@inheritDoc}
-     */
-    protected Object clone() throws CloneNotSupportedException
+    public Object clone() throws CloneNotSupportedException
     {
-        NonUniqueIndex result = (NonUniqueIndex)super.clone();
+        NonUniqueIndex result = new NonUniqueIndex();
 
         result._name    = _name;
         result._columns = (ArrayList)_columns.clone();

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Reference.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Reference.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Reference.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Reference.java Sun May  7 05:23:28 2006
@@ -178,7 +178,7 @@
     /**
      * {@inheritDoc}
      */
-    protected Object clone() throws CloneNotSupportedException
+    public Object clone() throws CloneNotSupportedException
     {
         Reference result = (Reference)super.clone();
 

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/UniqueIndex.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/UniqueIndex.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/UniqueIndex.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/UniqueIndex.java Sun May  7 05:23:28 2006
@@ -18,6 +18,8 @@
 
 import java.util.ArrayList;
 
+import org.apache.commons.lang.builder.EqualsBuilder;
+
 /**
  * Provides compatibility with Torque-style xml with separate &lt;index&gt; and
  * &lt;unique&gt; tags, but adds no functionality.  All indexes are treated the
@@ -26,7 +28,7 @@
  * @author John Marshall/Connectria
  * @version $Revision$
  */
-public class UniqueIndex extends NonUniqueIndex
+public class UniqueIndex extends IndexImpBase
 {
     /** Unique ID for serialization purposes. */
     private static final long serialVersionUID = -4097003126550294993L;
@@ -42,9 +44,9 @@
     /**
      * {@inheritDoc}
      */
-    protected Object clone() throws CloneNotSupportedException
+    public Object clone() throws CloneNotSupportedException
     {
-        UniqueIndex result = (UniqueIndex)super.clone();
+        UniqueIndex result = new UniqueIndex();
 
         result._name    = _name;
         result._columns = (ArrayList)_columns.clone();
@@ -61,8 +63,9 @@
         {
             UniqueIndex other = (UniqueIndex)obj;
 
-            // Note that we ignore the name here
-            return _columns.equals(other._columns);
+            return new EqualsBuilder().append(_name,    other._name)
+                                      .append(_columns, other._columns)
+                                      .isEquals();
         }
         else
         {

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java Sun May  7 05:23:28 2006
@@ -347,13 +347,16 @@
      *
      * @param currentModel  The current database schema
      * @param desiredModel  The desired database schema
+     * @param params        The parameters used in the creation of new tables. Note that for existing
+     *                      tables, the parameters won't be applied
      */
-    public void alterDatabase2(Database currentModel, Database desiredModel) throws IOException
+    public void alterDatabase2(Database currentModel, Database desiredModel, CreationParameters params) throws IOException
     {
-        ModelComparator comparator = new ModelComparator(getPlatform().isDelimitedIdentifierModeOn());
+        ModelComparator comparator = new ModelComparator(getPlatformInfo(),
+                                                         getPlatform().isDelimitedIdentifierModeOn());
         List            changes    = comparator.compare(currentModel, desiredModel);
 
-        processChanges(currentModel, desiredModel, changes);
+        processChanges(currentModel, desiredModel, changes, params);
     }
 
     /**
@@ -420,13 +423,18 @@
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
      * @param changes      The changes
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      */
-    protected void processChanges(Database currentModel, Database desiredModel, List changes) throws IOException
+    protected void processChanges(Database           currentModel,
+                                  Database           desiredModel,
+                                  List               changes,
+                                  CreationParameters params) throws IOException
     {
         CallbackClosure callbackClosure = new CallbackClosure(this,
                                                               "processChange",
-                                                              new Class[] { Database.class, Database.class, null },
-                                                              new Object[] { currentModel, desiredModel, null });
+                                                              new Class[] { Database.class, Database.class, CreationParameters.class, null },
+                                                              new Object[] { currentModel, desiredModel, params, null });
 
         // 1st pass: removing external constraints and indices
         applyForSelectedChanges(changes,
@@ -453,6 +461,7 @@
 
         processTableStructureChanges(currentModel,
                                      desiredModel,
+                                     params,
                                      CollectionUtils.select(changes, predicate));
 
         // 4th pass: adding tables
@@ -472,11 +481,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
-    protected void processChange(Database    currentModel,
-                                 Database    desiredModel,
-                                 ModelChange change) throws IOException
+    protected void processChange(Database           currentModel,
+                                 Database           desiredModel,
+                                 CreationParameters params,
+                                 ModelChange        change) throws IOException
     {
         _log.warn("Change of type " + change.getClass() + " was not handled");
     }
@@ -486,10 +498,13 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
     protected void processChange(Database               currentModel,
                                  Database               desiredModel,
+                                 CreationParameters     params,
                                  RemoveForeignKeyChange change) throws IOException
     {
         writeExternalForeignKeyDropStmt(change.getChangedTable(), change.getForeignKey());
@@ -500,11 +515,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
-    protected void processChange(Database          currentModel,
-                                 Database          desiredModel,
-                                 RemoveIndexChange change) throws IOException
+    protected void processChange(Database           currentModel,
+                                 Database           desiredModel,
+                                 CreationParameters params,
+                                 RemoveIndexChange  change) throws IOException
     {
         writeExternalIndexDropStmt(change.getChangedTable(), change.getIndex());
     }
@@ -514,11 +532,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
-    protected void processChange(Database          currentModel,
-                                 Database          desiredModel,
-                                 RemoveTableChange change) throws IOException
+    protected void processChange(Database           currentModel,
+                                 Database           desiredModel,
+                                 CreationParameters params,
+                                 RemoveTableChange  change) throws IOException
     {
         dropTable(change.getChangedTable());
     }
@@ -528,11 +549,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
-    protected void processChange(Database       currentModel,
-                                 Database       desiredModel,
-                                 AddTableChange change) throws IOException
+    protected void processChange(Database           currentModel,
+                                 Database           desiredModel,
+                                 CreationParameters params,
+                                 AddTableChange     change) throws IOException
     {
         // TODO: where to get the parameters from ?
         writeTableCreationStmt(desiredModel, change.getNewTable(), null);
@@ -554,10 +578,13 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
     protected void processChange(Database            currentModel,
                                  Database            desiredModel,
+                                 CreationParameters  params,
                                  AddForeignKeyChange change) throws IOException
     {
         writeExternalForeignKeyCreateStmt(desiredModel,
@@ -570,11 +597,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param change       The change object
      */
-    protected void processChange(Database       currentModel,
-                                 Database       desiredModel,
-                                 AddIndexChange change) throws IOException
+    protected void processChange(Database           currentModel,
+                                 Database           desiredModel,
+                                 CreationParameters params,
+                                 AddIndexChange     change) throws IOException
     {
         writeExternalIndexCreateStmt(change.getChangedTable(), change.getNewIndex());
     }
@@ -584,11 +614,14 @@
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
+     * @param params       The parameters used in the creation of new tables. Note that for existing
+     *                     tables, the parameters won't be applied
      * @param changes      The change objects
      */
-    protected void processTableStructureChanges(Database   currentModel,
-                                                Database   desiredModel,
-                                                Collection changes) throws IOException
+    protected void processTableStructureChanges(Database           currentModel,
+                                                Database           desiredModel,
+                                                CreationParameters params,
+                                                Collection         changes) throws IOException
     {
         ListOrderedMap changesPerTable = new ListOrderedMap();
         ListOrderedMap unchangedFKs    = new ListOrderedMap();
@@ -631,13 +664,29 @@
                 writeExternalForeignKeyDropStmt(targetTable, (ForeignKey)fkIt.next());
             }
         }
+
+        // We're using a copy of the current model so that the table structure changes can
+        // modify it
+        Database copyOfCurrentModel = null;
+
+        try
+        {
+            copyOfCurrentModel = (Database)currentModel.clone();
+        }
+        catch (CloneNotSupportedException ex)
+        {
+            throw new DdlUtilsException(ex);
+        }
+        
         for (Iterator tableChangeIt = changesPerTable.entrySet().iterator(); tableChangeIt.hasNext();)
         {
-            Map.Entry entry = (Map.Entry)tableChangeIt.next();
+            Map.Entry entry       = (Map.Entry)tableChangeIt.next();
+            Table     targetTable = desiredModel.findTable((String)entry.getKey(), caseSensitive);
 
-            processTableStructureChanges(currentModel,
+            processTableStructureChanges(copyOfCurrentModel,
                                          desiredModel,
                                          (String)entry.getKey(),
+                                         params == null ? null : params.getParametersFor(targetTable),
                                          (List)entry.getValue());
         }
         // and finally we're re-creating the unchanged foreign keys
@@ -738,19 +787,66 @@
     }
     
     /**
-     * Processes the changes to the structure of a single table.
+     * Processes the changes to the structure of a single table. Database-specific
+     * implementations might redefine this method, but it is usually sufficient to
+     * redefine the {@link #processTableStructureChanges(Database, Database, Table, Table)}
+     * method instead.
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema
      * @param tableName    The name of the changed table
+     * @param parameters   The creation parameters for the desired table
      * @param changes      The change objects for this table
      */
     protected void processTableStructureChanges(Database currentModel,
                                                 Database desiredModel,
                                                 String   tableName,
+                                                Map      parameters,
+                                                List     changes) throws IOException
+    {
+        Table sourceTable = currentModel.findTable(tableName, getPlatform().isDelimitedIdentifierModeOn());
+        Table targetTable = desiredModel.findTable(tableName, getPlatform().isDelimitedIdentifierModeOn());
+
+        processTableStructureChanges(currentModel, desiredModel, sourceTable, targetTable, parameters, changes);
+
+        if (!changes.isEmpty())
+        {
+            Table tempTable       = getTemporaryTableFor(desiredModel, targetTable);
+            Table realTargetTable = getRealTargetTableFor(desiredModel, sourceTable, targetTable);
+
+            createTemporaryTable(desiredModel, tempTable, parameters);
+            writeCopyDataStatement(sourceTable, tempTable);
+            // Note that we don't drop the indices here because the DROP TABLE will take care of that
+            // Likewise, foreign keys have already been dropped as necessary
+            dropTable(sourceTable);
+            createTable(desiredModel, realTargetTable, parameters);
+            writeCopyDataStatement(tempTable, targetTable);
+            dropTable(tempTable);
+        }
+    }
+
+    /**
+     * Allows database-specific implementations to handle changes in a database
+     * specific manner. Any handled change should be applied to the given current
+     * model (which is a copy of the real original model) and be removed from the
+     * list of changes.<br/>
+     * In the default implementation, all {@link AddPrimaryKeyChange} changes are
+     * applied via an <code>ALTER TABLE ADD CONSTRAINT</code> statement.  
+     * 
+     * @param currentModel The current database schema
+     * @param desiredModel The desired database schema
+     * @param sourceTable  The original table
+     * @param targetTable  The desired table
+     * @param parameters   The creation parameters for the table
+     * @param changes      The change objects for the target table
+     */
+    protected void processTableStructureChanges(Database currentModel,
+                                                Database desiredModel,
+                                                Table    sourceTable,
+                                                Table    targetTable,
+                                                Map      parameters,
                                                 List     changes) throws IOException
     {
-        // we might be able to simplify if there is only one change
         if (changes.size() == 1)
         {
             TableChange change = (TableChange)changes.get(0);
@@ -758,29 +854,12 @@
             if (change instanceof AddPrimaryKeyChange)
             {
                 processChange(currentModel, desiredModel, (AddPrimaryKeyChange)change);
-                return;
+                change.apply(currentModel);
+                changes.clear();
             }
-            // TODO: Once named primary keys are supported, the removal can be handled
-            //       here as well (at least for named primary keys)
         }
-
-        // TODO: where to get the parameters from ?
-        Map   parameters      = null;
-        Table sourceTable     = currentModel.findTable(tableName, getPlatform().isDelimitedIdentifierModeOn());
-        Table targetTable     = desiredModel.findTable(tableName, getPlatform().isDelimitedIdentifierModeOn());
-        Table tempTable       = getTemporaryTableFor(desiredModel, targetTable);
-        Table realTargetTable = getRealTargetTableFor(desiredModel, sourceTable, targetTable);
-
-        createTemporaryTable(desiredModel, tempTable, parameters);
-        writeCopyDataStatement(sourceTable, tempTable);
-        // Note that we don't drop the indices here because the DROP TABLE will take care of that
-        // Likewise, foreign keys have already been dropped as necessary
-        dropTable(sourceTable);
-        createTable(desiredModel, realTargetTable, parameters);
-        writeCopyDataStatement(tempTable, targetTable);
-        dropTable(tempTable);
     }
-
+    
     /**
      * Creates a temporary table object that corresponds to the given table.
      * Database-specific implementations may redefine this method if e.g. the
@@ -943,11 +1022,9 @@
     {
         printIdentifier(getColumnName(sourceColumn));
     }
-    
+
     /**
-     * Processes the addition of a primary key to a table. Note that in the default
-     * implementation, this method is called only if this is the only change to the
-     * target table.
+     * Processes the addition of a primary key to a table.
      * 
      * @param currentModel The current database schema
      * @param desiredModel The desired database schema

Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/derby/DerbyBuilder.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/derby/DerbyBuilder.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/derby/DerbyBuilder.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/derby/DerbyBuilder.java Sun May  7 05:23:28 2006
@@ -18,9 +18,16 @@
 
 import java.io.IOException;
 import java.sql.Types;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
 
 import org.apache.ddlutils.Platform;
+import org.apache.ddlutils.alteration.AddColumnChange;
+import org.apache.ddlutils.alteration.ColumnSizeChange;
+import org.apache.ddlutils.alteration.TableChange;
 import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
 import org.apache.ddlutils.model.Index;
 import org.apache.ddlutils.model.Table;
 import org.apache.ddlutils.model.TypeMap;
@@ -108,5 +115,67 @@
             printIdentifier(getColumnName(sourceColumn));
             print(")");
         }
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    protected void processTableStructureChanges(Database currentModel, Database desiredModel, Table sourceTable, Table targetTable, Map parameters, List changes) throws IOException
+    {
+        // Derby provides a way to alter the size of a column but it is limited
+        // (no pk or fk columns, only for VARCHAR columns), so we don't use it
+        for (Iterator changeIt = changes.iterator(); changeIt.hasNext();)
+        {
+            TableChange change = (TableChange)changeIt.next();
+
+            if (change instanceof AddColumnChange)
+            {
+                processChange(currentModel, desiredModel, (AddColumnChange)change);
+                change.apply(currentModel);
+                changeIt.remove();
+            }
+        }
+        super.processTableStructureChanges(currentModel, desiredModel, sourceTable, targetTable, parameters, changes);
+    }
+
+    /**
+     * Processes the addition of a column to a table.
+     * 
+     * @param currentModel The current database schema
+     * @param desiredModel The desired database schema
+     * @param change       The change object
+     */
+    protected void processChange(Database        currentModel,
+                                 Database        desiredModel,
+                                 AddColumnChange change) throws IOException
+    {
+        print("ALTER TABLE ");
+        printlnIdentifier(getTableName(change.getChangedTable()));
+        printIndent();
+        print("ADD COLUMN ");
+        writeColumn(change.getChangedTable(), change.getNewColumn());
+        printEndOfStatement();
+    }
+
+    /**
+     * Processes the size change of a VARCHAR column.
+     * 
+     * @param currentModel The current database schema
+     * @param desiredModel The desired database schema
+     * @param change       The change object
+     */
+    protected void processVarCharSizeChange(Database         currentModel,
+                                            Database         desiredModel,
+                                            ColumnSizeChange change) throws IOException
+    {
+        print("ALTER TABLE ");
+        printlnIdentifier(getTableName(change.getChangedTable()));
+        printIndent();
+        print("ALTER ");
+        printIdentifier(getColumnName(change.getColumn()));
+        print(" SET DATA TYPE VARCHAR(");
+        print(change.getColumn().getSize());
+        print(")");
+        printEndOfStatement();
     }
 }

Modified: db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestAlterationAlgorithm.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestAlterationAlgorithm.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestAlterationAlgorithm.java (original)
+++ db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestAlterationAlgorithm.java Sun May  7 05:23:28 2006
@@ -69,7 +69,7 @@
         Database currentModel = parseDatabaseFromString(currentSchema);
         Database desiredModel = parseDatabaseFromString(desiredSchema);
 
-        _platform.getSqlBuilder().alterDatabase2(currentModel, desiredModel);
+        _platform.getSqlBuilder().alterDatabase2(currentModel, desiredModel, null);
 
         return _writer.toString();
     }
@@ -601,6 +601,52 @@
 
         assertEqualsIgnoringWhitespaces(
             "ALTER TABLE \"TableA\" ADD CONSTRAINT \"TableA_PK\" PRIMARY KEY (\"ColPK1\",\"ColPK2\");\n",
+            getAlterDatabaseSQL(model1Xml, model2Xml));
+    }
+
+    /**
+     * Tests the addition of a primary key and a column to an existing table.
+     */
+    public void testAddPrimaryKeyAndColumn() throws IOException
+    {
+        final String model1Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n" +
+            "<database name='test'>\n" +
+            "  <table name='TableA'>\n" +
+            "    <column name='ColPK1' type='INTEGER' required='true'/>\n" +
+            "    <column name='ColPK2' type='VARCHAR' size='64' required='true'/>\n" +
+            "  </table>\n" +
+            "</database>";
+        final String model2Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n" +
+            "<database name='test'>\n" +
+            "  <table name='TableA'>\n" +
+            "    <column name='ColPK1' type='INTEGER' primaryKey='true' required='true'/>\n" +
+            "    <column name='ColPK2' type='VARCHAR' size='64' primaryKey='true' required='true'/>\n" +
+            "    <column name='Col' type='DOUBLE'/>\n" +
+            "  </table>\n" +
+            "</database>";
+
+        assertEqualsIgnoringWhitespaces(
+            "ALTER TABLE \"TableA\" ADD CONSTRAINT \"TableA_PK\" PRIMARY KEY (\"ColPK1\",\"ColPK2\");\n"+
+            "CREATE TABLE \"TableA_\"\n"+
+            "(\n"+
+            "    \"ColPK1\" INTEGER NOT NULL,\n"+
+            "    \"ColPK2\" VARCHAR(64) NOT NULL,\n"+
+            "    \"Col\" DOUBLE,\n"+
+            "    PRIMARY KEY (\"ColPK1\",\"ColPK2\")\n"+
+            ");\n"+
+            "INSERT INTO \"TableA_\" (\"ColPK1\",\"ColPK2\") SELECT \"ColPK1\",\"ColPK2\" FROM \"TableA\";\n"+
+            "DROP TABLE \"TableA\";\n"+
+            "CREATE TABLE \"TableA\"\n"+
+            "(\n"+
+            "    \"ColPK1\" INTEGER NOT NULL,\n"+
+            "    \"ColPK2\" VARCHAR(64) NOT NULL,\n"+
+            "    \"Col\" DOUBLE,\n"+
+            "    PRIMARY KEY (\"ColPK1\",\"ColPK2\")\n"+
+            ");\n"+
+            "INSERT INTO \"TableA\" (\"ColPK1\",\"ColPK2\",\"Col\") SELECT \"ColPK1\",\"ColPK2\",\"Col\" FROM \"TableA_\";\n"+
+            "DROP TABLE \"TableA_\";\n",
             getAlterDatabaseSQL(model1Xml, model2Xml));
     }
 

Modified: db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestModelComparator.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestModelComparator.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestModelComparator.java (original)
+++ db/ddlutils/trunk/src/test/org/apache/ddlutils/alteration/TestModelComparator.java Sun May  7 05:23:28 2006
@@ -19,6 +19,7 @@
 import java.sql.Types;
 import java.util.List;
 
+import org.apache.ddlutils.PlatformInfo;
 import org.apache.ddlutils.TestBase;
 import org.apache.ddlutils.model.Database;
 
@@ -30,6 +31,22 @@
 public class TestModelComparator extends TestBase
 {
     /**
+     * Creates a new model comparator.
+     * 
+     * @return The model comparator
+     */
+    protected ModelComparator createModelComparator(boolean caseSensitive)
+    {
+        PlatformInfo platformInfo = new PlatformInfo();
+
+        platformInfo.setHasSize(Types.DECIMAL, true);
+        platformInfo.setHasSize(Types.NUMERIC, true);
+        platformInfo.setHasSize(Types.CHAR, true);
+        platformInfo.setHasSize(Types.VARCHAR, true);
+        return new ModelComparator(platformInfo, caseSensitive);
+    }
+
+    /**
      * Tests the addition of a table.
      */
     public void testAddTable()
@@ -54,7 +71,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -90,7 +107,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -123,7 +140,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -170,7 +187,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -211,7 +228,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(4,
                      changes.size());
@@ -268,7 +285,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -315,7 +332,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -371,7 +388,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -428,7 +445,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertTrue(changes.isEmpty());
     }
@@ -460,7 +477,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -498,7 +515,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -539,7 +556,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -587,7 +604,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -634,7 +651,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -681,7 +698,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(2,
                      changes.size());
@@ -717,7 +734,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -752,7 +769,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -789,7 +806,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -832,7 +849,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -875,7 +892,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -909,7 +926,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -944,7 +961,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -981,7 +998,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -1020,7 +1037,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -1039,8 +1056,8 @@
      * Tests removing the size of a column. This test shows how the comparator
      * reacts in the common case of comparing a model read from a live database
      * (which usually returns sizes for every column) and a model from XML.
-     * The model comparator will not filter out these changes, it is up to the
-     * platform to decide whether such a change is valid or can be ignored. 
+     * The model comparator will filter out these changes depending on the
+     * platform info with which the comparator was created. 
      */
     public void testRemoveColumnSize()
     {
@@ -1063,19 +1080,9 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
-
-        assertEquals(1,
-                     changes.size());
-
-        ColumnSizeChange change = (ColumnSizeChange)changes.get(0);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
-        assertEquals("Col",
-                     change.getColumn().getName());
-        assertEquals(0,
-                     change.getNewSize());
-        assertEquals(0,
-                     change.getNewScale());
+        assertTrue(changes.isEmpty());
     }
 
     /**
@@ -1102,7 +1109,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -1140,7 +1147,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertTrue(changes.isEmpty());
     }
@@ -1169,7 +1176,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(true).compare(model1, model2);
+        List     changes = createModelComparator(true).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -1206,7 +1213,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());
@@ -1241,7 +1248,7 @@
 
         Database model1  = parseDatabaseFromString(MODEL1);
         Database model2  = parseDatabaseFromString(MODEL2);
-        List     changes = new ModelComparator(false).compare(model1, model2);
+        List     changes = createModelComparator(false).compare(model1, model2);
 
         assertEquals(1,
                      changes.size());

Modified: db/ddlutils/trunk/src/test/org/apache/ddlutils/io/TestAlteration.java
URL: http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/test/org/apache/ddlutils/io/TestAlteration.java?rev=404752&r1=404751&r2=404752&view=diff
==============================================================================
--- db/ddlutils/trunk/src/test/org/apache/ddlutils/io/TestAlteration.java (original)
+++ db/ddlutils/trunk/src/test/org/apache/ddlutils/io/TestAlteration.java Sun May  7 05:23:28 2006
@@ -111,6 +111,78 @@
     }
 
     /**
+     * Tests the alteration of a column size.
+     */
+    public void testChangeSize()
+    {
+        final String model1Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='VARCHAR' size='20' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+        final String model2Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='VARCHAR' size='32' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+
+        createDatabase(model1Xml);
+
+        insertRow("roundtrip", new Object[] { new Integer(1), "test" });
+
+        alterDatabase(model2Xml);
+
+        assertEquals(getAdjustedModel(),
+                     readModelFromDatabase("roundtriptest"));
+
+        List beans = getRows("roundtrip");
+
+        assertEquals((Object)"test", beans.get(0), "avalue");
+    }
+
+    /**
+     * Tests the alteration of a column's datatype and size.
+     */
+    public void testChangeDatatypeAndSize()
+    {
+        final String model1Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='CHAR' size='4' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+        final String model2Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='VARCHAR' size='32' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+
+        createDatabase(model1Xml);
+
+        insertRow("roundtrip", new Object[] { new Integer(1), "test" });
+
+        alterDatabase(model2Xml);
+
+        assertEquals(getAdjustedModel(),
+                     readModelFromDatabase("roundtriptest"));
+
+        List beans = getRows("roundtrip");
+
+        assertEquals((Object)"test", beans.get(0), "avalue");
+    }
+
+    /**
      * Tests the alteration of a column null constraint.
      */
     public void testChangeNull()
@@ -497,6 +569,76 @@
         insertRow("roundtrip", new Object[] { new Integer(1) });
 
     	alterDatabase(model2Xml);
+
+        assertEquals(getAdjustedModel(),
+                     readModelFromDatabase("roundtriptest"));
+
+        List beans = getRows("roundtrip");
+
+        assertEquals(new Integer(0), beans.get(0), "avalue");
+    }
+
+    /**
+     * Tests the adding a primary key and a column.
+     */
+    public void testAddPKAndColumn()
+    {
+        final String model1Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+        final String model2Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='INTEGER' default='0'/>\n"+
+            "  </table>\n"+
+            "</database>";
+
+        createDatabase(model1Xml);
+
+        insertRow("roundtrip", new Object[] { new Integer(1) });
+
+        alterDatabase(model2Xml);
+
+        assertEquals(getAdjustedModel(),
+                     readModelFromDatabase("roundtriptest"));
+
+        List beans = getRows("roundtrip");
+
+        assertEquals(new Integer(0), beans.get(0), "avalue");
+    }
+
+    /**
+     * Tests the adding a primary key and a primary key column.
+     */
+    public void testAddPKAndPKColumn()
+    {
+        final String model1Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' required='true'/>\n"+
+            "  </table>\n"+
+            "</database>";
+        final String model2Xml = 
+            "<?xml version='1.0' encoding='ISO-8859-1'?>\n"+
+            "<database name='roundtriptest'>\n"+
+            "  <table name='roundtrip'>\n"+
+            "    <column name='pk' type='INTEGER' primaryKey='true' required='true'/>\n"+
+            "    <column name='avalue' type='INTEGER' primaryKey='true' required='true' default='0'/>\n"+
+            "  </table>\n"+
+            "</database>";
+
+        createDatabase(model1Xml);
+
+        insertRow("roundtrip", new Object[] { new Integer(1) });
+
+        alterDatabase(model2Xml);
 
         assertEquals(getAdjustedModel(),
                      readModelFromDatabase("roundtriptest"));