Author: tomdz
Date: Sun May 14 11:08:35 2006
New Revision: 406392
URL: http://svn.apache.org/viewcvs?rev=406392&view=rev
Log:
Enhanced alteration algorithm for SapDB/MaxDB
Added test for column ordering change
Modified:
db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/AddColumnChange.java
db/ddlutils/trunk/src/java/org/apache/ddlutils/alteration/ModelComparator.java
db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Table.java
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/SqlBuilder.java
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/mysql/MySqlBuilder.java
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/sapdb/SapDbBuilder.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=406392&r1=406391&r2=406392&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 14 11:08:35 2006
@@ -34,6 +34,8 @@
private Column _previousColumn;
/** The column before which the new column should be added. */
private Column _nextColumn;
+ /** Whether the column is added at the end. */
+ private boolean _atEnd;
/**
* Creates a new change object.
@@ -82,6 +84,28 @@
}
/**
+ * Determines whether the column is added at the end (when applied in the
order
+ * of creation of the changes).
+ *
+ * @return <code>true</code> if the column is added at the end
+ */
+ public boolean isAtEnd()
+ {
+ return _atEnd;
+ }
+
+ /**
+ * Specifies whether the column is added at the end (when applied in the
order
+ * of creation of the changes).
+ *
+ * @param atEnd <code>true</code> if the column is added at the end
+ */
+ public void setAtEnd(boolean atEnd)
+ {
+ _atEnd = atEnd;
+ }
+
+ /**
* [EMAIL PROTECTED]
*/
public void apply(Database database)
@@ -96,6 +120,18 @@
{
throw new DdlUtilsException(ex);
}
- database.findTable(getChangedTable().getName()).addColumn(newColumn);
+
+ Table table = database.findTable(getChangedTable().getName());
+
+ if ((_previousColumn != null) && (_nextColumn != null))
+ {
+ int idx = table.getColumnIndex(_previousColumn) + 1;
+
+ table.addColumn(idx, newColumn);
+ }
+ else
+ {
+ table.addColumn(newColumn);
+ }
}
}
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=406392&r1=406391&r2=406392&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 14 11:08:35 2006
@@ -17,6 +17,7 @@
*/
import java.util.ArrayList;
+import java.util.HashMap;
import java.util.List;
import org.apache.commons.lang.StringUtils;
@@ -201,6 +202,8 @@
}
}
+ HashMap addColumnChanges = new HashMap();
+
for (int columnIdx = 0; columnIdx < targetTable.getColumnCount();
columnIdx++)
{
Column targetColumn = targetTable.getColumn(columnIdx);
@@ -212,14 +215,34 @@
{
_log.info("Column " + targetColumn.getName() + " needs to
be created for table " + sourceTable.getName());
}
- changes.add(new AddColumnChange(sourceTable,
- targetColumn,
- columnIdx > 0 ?
targetTable.getColumn(columnIdx - 1) : null,
- columnIdx <
targetTable.getColumnCount() - 1 ? targetTable.getColumn(columnIdx + 1) :null));
+
+ AddColumnChange change = new AddColumnChange(sourceTable,
+ targetColumn,
+ columnIdx > 0 ?
targetTable.getColumn(columnIdx - 1) : null,
+ columnIdx <
targetTable.getColumnCount() - 1 ? targetTable.getColumn(columnIdx + 1) : null);
+
+ changes.add(change);
+ addColumnChanges.put(targetColumn, change);
}
else
{
changes.addAll(compareColumns(sourceTable, sourceColumn,
targetTable, targetColumn));
+ }
+ }
+ // if the last columns in the target table are added, then we note
this at the changes
+ for (int columnIdx = targetTable.getColumnCount() - 1; columnIdx >= 0;
columnIdx--)
+ {
+ Column targetColumn = targetTable.getColumn(columnIdx);
+ AddColumnChange change =
(AddColumnChange)addColumnChanges.get(targetColumn);
+
+ if (change == null)
+ {
+ // column was not added, so we can ignore any columns before
it that were added
+ break;
+ }
+ else
+ {
+ change.setAtEnd(true);
}
}
Modified: db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Table.java
URL:
http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Table.java?rev=406392&r1=406391&r2=406392&view=diff
==============================================================================
--- db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Table.java (original)
+++ db/ddlutils/trunk/src/java/org/apache/ddlutils/model/Table.java Sun May 14
11:08:35 2006
@@ -560,6 +560,26 @@
}
/**
+ * Determines the index of the given column.
+ *
+ * @param column The column
+ * @return The index or <code>-1</code> if it is no column of this table
+ */
+ public int getColumnIndex(Column column)
+ {
+ int idx = 0;
+
+ for (Iterator it = _columns.iterator(); it.hasNext(); idx++)
+ {
+ if (column == it.next())
+ {
+ return idx;
+ }
+ }
+ return -1;
+ }
+
+ /**
* Finds the index with the specified name, using case insensitive
matching.
* Note that this method is not called getIndex to avoid introspection
* problems.
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=406392&r1=406391&r2=406392&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 14 11:08:35 2006
@@ -2111,6 +2111,22 @@
}
/**
+ * Determines whether the given default spec is a non-empty spec that
shall be used in a DEFAULT
+ * expression. E.g. if the spec is an empty string and the type is a
numeric type, then it is
+ * no valid default value whereas if it is a string type, then it is valid.
+ *
+ * @param defaultSpec The default value spec
+ * @param typeCode The JDBC type code
+ * @return <code>true</code> if the default value spec is valid
+ */
+ protected boolean isValidDefaultValue(String defaultSpec, int typeCode)
+ {
+ return (defaultSpec != null) &&
+ ((defaultSpec.length() > 0) ||
+ (!TypeMap.isNumericType(typeCode) &&
!TypeMap.isDateTimeType(typeCode)));
+ }
+
+ /**
* Prints the default value stmt part for the column.
*
* @param table The table
@@ -2128,8 +2144,7 @@
throw new DynaSqlException("The platform does not support
default values for LONGVARCHAR or LONGVARBINARY columns");
}
// we write empty default value strings only if the type is not a
numeric or date/time type
- if ((column.getDefaultValue().length() > 0) ||
- (!TypeMap.isNumericType(column.getTypeCode()) &&
!TypeMap.isDateTimeType(column.getTypeCode())))
+ if (isValidDefaultValue(column.getDefaultValue(),
column.getTypeCode()))
{
print(" DEFAULT ");
writeColumnDefaultValue(table, column);
@@ -2150,23 +2165,32 @@
*/
protected void writeColumnDefaultValue(Table table, Column column) throws
IOException
{
- boolean shouldUseQuotes = !TypeMap.isNumericType(column.getTypeCode());
+ printDefaultValue(getNativeDefaultValue(column), column.getTypeCode());
+ }
- if (shouldUseQuotes)
- {
- // characters are only escaped when within a string literal
- print(getPlatformInfo().getValueQuoteToken());
- print(escapeStringValue(getNativeDefaultValue(column).toString()));
- print(getPlatformInfo().getValueQuoteToken());
- }
- else
+ /**
+ * Prints the default value of the column.
+ *
+ * @param defaultValue The default value
+ * @param typeCode The type code to write the default value for
+ */
+ protected void printDefaultValue(Object defaultValue, int typeCode) throws
IOException
+ {
+ if (defaultValue != null)
{
- Object nativeDefault = getNativeDefaultValue(column);
-
- if (nativeDefault != null)
- {
- print(nativeDefault.toString());
- }
+ boolean shouldUseQuotes = !TypeMap.isNumericType(typeCode);
+
+ if (shouldUseQuotes && (defaultValue != null))
+ {
+ // characters are only escaped when within a string literal
+ print(getPlatformInfo().getValueQuoteToken());
+ print(escapeStringValue(defaultValue.toString()));
+ print(getPlatformInfo().getValueQuoteToken());
+ }
+ else
+ {
+ print(defaultValue.toString());
+ }
}
}
Modified:
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/mysql/MySqlBuilder.java
URL:
http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/mysql/MySqlBuilder.java?rev=406392&r1=406391&r2=406392&view=diff
==============================================================================
---
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/mysql/MySqlBuilder.java
(original)
+++
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/mysql/MySqlBuilder.java
Sun May 14 11:08:35 2006
@@ -202,29 +202,33 @@
{
processChange(currentModel, desiredModel,
(RemoveColumnChange)change);
change.apply(currentModel);
+ changeIt.remove();
}
else if (change instanceof AddPrimaryKeyChange)
{
processChange(currentModel, desiredModel,
(AddPrimaryKeyChange)change);
change.apply(currentModel);
+ changeIt.remove();
}
else if (change instanceof PrimaryKeyChange)
{
processChange(currentModel, desiredModel,
(PrimaryKeyChange)change);
change.apply(currentModel);
+ changeIt.remove();
}
else if (change instanceof RemovePrimaryKeyChange)
{
processChange(currentModel, desiredModel,
(RemovePrimaryKeyChange)change);
change.apply(currentModel);
+ changeIt.remove();
}
else
{
// we gather all changed columns because we can use the ALTER
TABLE MODIFY COLUMN
// statement for them
changedColumns.add(((ColumnChange)change).getChangedColumn());
+ changeIt.remove();
}
- changeIt.remove();
}
for (Iterator columnIt = changedColumns.iterator();
columnIt.hasNext();)
{
Modified:
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/sapdb/SapDbBuilder.java
URL:
http://svn.apache.org/viewcvs/db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/sapdb/SapDbBuilder.java?rev=406392&r1=406391&r2=406392&view=diff
==============================================================================
---
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/sapdb/SapDbBuilder.java
(original)
+++
db/ddlutils/trunk/src/java/org/apache/ddlutils/platform/sapdb/SapDbBuilder.java
Sun May 14 11:08:35 2006
@@ -17,9 +17,21 @@
*/
import java.io.IOException;
+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.AddPrimaryKeyChange;
+import org.apache.ddlutils.alteration.ColumnDefaultValueChange;
+import org.apache.ddlutils.alteration.ColumnRequiredChange;
+import org.apache.ddlutils.alteration.PrimaryKeyChange;
+import org.apache.ddlutils.alteration.RemoveColumnChange;
+import org.apache.ddlutils.alteration.RemovePrimaryKeyChange;
+import org.apache.ddlutils.alteration.TableChange;
import org.apache.ddlutils.model.Column;
+import org.apache.ddlutils.model.Database;
import org.apache.ddlutils.model.Table;
import org.apache.ddlutils.platform.SqlBuilder;
@@ -60,5 +72,241 @@
protected void writeColumnAutoIncrementStmt(Table table, Column column)
throws IOException
{
print("DEFAULT SERIAL(1)");
+ }
+
+ /**
+ * [EMAIL PROTECTED]
+ */
+ protected void processTableStructureChanges(Database currentModel,
+ Database desiredModel,
+ Table sourceTable,
+ Table targetTable,
+ Map parameters,
+ List changes) throws
IOException
+ {
+ // First we drop primary keys as necessary
+ for (Iterator changeIt = changes.iterator(); changeIt.hasNext();)
+ {
+ TableChange change = (TableChange)changeIt.next();
+
+ if (change instanceof RemovePrimaryKeyChange)
+ {
+ processChange(currentModel, desiredModel,
(RemovePrimaryKeyChange)change);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ else if (change instanceof PrimaryKeyChange)
+ {
+ PrimaryKeyChange pkChange =
(PrimaryKeyChange)change;
+ RemovePrimaryKeyChange removePkChange = new
RemovePrimaryKeyChange(pkChange.getChangedTable(),
+
pkChange.getOldPrimaryKeyColumns());
+
+ processChange(currentModel, desiredModel, removePkChange);
+ removePkChange.apply(currentModel);
+ }
+ }
+ // Next we add/change/remove columns
+ // SapDB has a ALTER TABLE MODIFY COLUMN but it is limited regarding
the type conversions
+ // it can perform, so we don't use it here but rather rebuild the table
+ for (Iterator changeIt = changes.iterator(); changeIt.hasNext();)
+ {
+ TableChange change = (TableChange)changeIt.next();
+
+ if (change instanceof AddColumnChange)
+ {
+ AddColumnChange addColumnChange = (AddColumnChange)change;
+
+ // SapDB can only add not insert columns
+ if (addColumnChange.isAtEnd())
+ {
+ processChange(currentModel, desiredModel, addColumnChange);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ }
+ else if (change instanceof ColumnDefaultValueChange)
+ {
+ processChange(currentModel, desiredModel,
(ColumnDefaultValueChange)change);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ else if (change instanceof ColumnRequiredChange)
+ {
+ processChange(currentModel, desiredModel,
(ColumnRequiredChange)change);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ else if (change instanceof RemoveColumnChange)
+ {
+ processChange(currentModel, desiredModel,
(RemoveColumnChange)change);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ }
+ // Finally we add primary keys
+ for (Iterator changeIt = changes.iterator(); changeIt.hasNext();)
+ {
+ TableChange change = (TableChange)changeIt.next();
+
+ if (change instanceof AddPrimaryKeyChange)
+ {
+ processChange(currentModel, desiredModel,
(AddPrimaryKeyChange)change);
+ change.apply(currentModel);
+ changeIt.remove();
+ }
+ else if (change instanceof PrimaryKeyChange)
+ {
+ PrimaryKeyChange pkChange = (PrimaryKeyChange)change;
+ AddPrimaryKeyChange addPkChange = new
AddPrimaryKeyChange(pkChange.getChangedTable(),
+
pkChange.getNewPrimaryKeyColumns());
+
+ processChange(currentModel, desiredModel, addPkChange);
+ addPkChange.apply(currentModel);
+ changeIt.remove();
+ }
+ }
+ }
+
+ /**
+ * 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 ");
+ writeColumn(change.getChangedTable(), change.getNewColumn());
+ printEndOfStatement();
+ }
+
+ /**
+ * Processes the removal of a column from 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,
+ RemoveColumnChange change) throws IOException
+ {
+ print("ALTER TABLE ");
+ printlnIdentifier(getTableName(change.getChangedTable()));
+ printIndent();
+ print("DROP ");
+ printIdentifier(getColumnName(change.getColumn()));
+ print(" RELEASE SPACE");
+ printEndOfStatement();
+ }
+
+ /**
+ * Processes the removal of a primary key from 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,
+ RemovePrimaryKeyChange change) throws
IOException
+ {
+ print("ALTER TABLE ");
+ printlnIdentifier(getTableName(change.getChangedTable()));
+ printIndent();
+ print("DROP PRIMARY KEY");
+ printEndOfStatement();
+ }
+
+ /**
+ * Processes the change of the primary key of 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,
+ PrimaryKeyChange change) throws IOException
+ {
+ print("ALTER TABLE ");
+ printlnIdentifier(getTableName(change.getChangedTable()));
+ printIndent();
+ print("DROP PRIMARY KEY");
+ printEndOfStatement();
+ writeExternalPrimaryKeysCreateStmt(change.getChangedTable(),
change.getNewPrimaryKeyColumns());
+ }
+
+ /**
+ * Processes the change of the required constraint of a column.
+ *
+ * @param currentModel The current database schema
+ * @param desiredModel The desired database schema
+ * @param change The change object
+ */
+ protected void processChange(Database currentModel,
+ Database desiredModel,
+ ColumnRequiredChange change) throws
IOException
+ {
+ print("ALTER TABLE ");
+ printlnIdentifier(getTableName(change.getChangedTable()));
+ printIndent();
+ print("COLUMN ");
+ printIdentifier(getColumnName(change.getChangedColumn()));
+ if (change.getChangedColumn().isRequired())
+ {
+ print(" DEFAULT NULL");
+ }
+ else
+ {
+ print(" NOT NULL");
+ }
+ printEndOfStatement();
+ }
+
+ /**
+ * Processes the change of the default value of a column.
+ *
+ * @param currentModel The current database schema
+ * @param desiredModel The desired database schema
+ * @param change The change object
+ */
+ protected void processChange(Database currentModel,
+ Database desiredModel,
+ ColumnDefaultValueChange change) throws
IOException
+ {
+ print("ALTER TABLE ");
+ printlnIdentifier(getTableName(change.getChangedTable()));
+ printIndent();
+ print("COLUMN ");
+ printIdentifier(getColumnName(change.getChangedColumn()));
+
+ Table curTable =
currentModel.findTable(change.getChangedTable().getName(),
getPlatform().isDelimitedIdentifierModeOn());
+ Column curColumn =
curTable.findColumn(change.getChangedColumn().getName(),
getPlatform().isDelimitedIdentifierModeOn());
+ boolean hasDefault = curColumn.getParsedDefaultValue() != null;
+
+ if (isValidDefaultValue(change.getNewDefaultValue(),
curColumn.getTypeCode()))
+ {
+ if (hasDefault)
+ {
+ print(" ALTER DEFAULT ");
+ }
+ else
+ {
+ print(" ADD DEFAULT ");
+ }
+ printDefaultValue(change.getNewDefaultValue(),
curColumn.getTypeCode());
+ }
+ else if (hasDefault)
+ {
+ print(" DROP DEFAULT");
+ }
+ printEndOfStatement();
}
}
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=406392&r1=406391&r2=406392&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 14 11:08:35 2006
@@ -486,6 +486,53 @@
assertEquals((Object)null, beans.get(0), "avalue1");
assertEquals((Object)null, beans.get(0), "avalue2");
+ assertEquals(new Double(3.0), beans.get(0), "avalue3");
+ assertEquals((Object)null, beans.get(0), "avalue4");
+ }
+
+ /**
+ * Tests the addition of several columns at the end of the table. This test
+ * is known to fail on MaxDB where a DEFAULT specification is applied to
existing
+ * rows even if they are not defined as NOT NULL (column 'avalue3' in the
+ * target schema).
+ */
+ public void testAddColumnsAtTheEnd()
+ {
+ 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='avalue1' type='VARCHAR' size='32'/>\n"+
+ " <column name='avalue2' type='INTEGER'/>\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='avalue1' type='VARCHAR' size='32'/>\n"+
+ " <column name='avalue2' type='INTEGER'/>\n"+
+ " <column name='avalue3' type='DOUBLE' default='1.0'/>\n"+
+ " <column name='avalue4' type='CHAR' size='16'/>\n"+
+ " </table>\n"+
+ "</database>";
+
+ createDatabase(model1Xml);
+
+ insertRow("roundtrip", new Object[] { new Integer(1), "test", new
Integer(3) });
+
+ alterDatabase(model2Xml);
+
+ assertEquals(getAdjustedModel(),
+ readModelFromDatabase("roundtriptest"));
+
+ List beans = getRows("roundtrip");
+
+ assertEquals((Object)"test", beans.get(0), "avalue1");
+ assertEquals(new Integer(3), beans.get(0), "avalue2");
+ assertEquals((Object)null, beans.get(0), "avalue3");
assertEquals((Object)null, beans.get(0), "avalue4");
}
@@ -557,6 +604,51 @@
List beans = getRows("roundtrip");
assertEquals(new Integer(2), beans.get(0), "avalue");
+ }
+
+ /**
+ * Tests the change of the order of the columns of a table.
+ */
+ public void testChangeColumnOrder()
+ {
+ 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='avalue1' type='VARCHAR' size='32'/>\n"+
+ " <column name='avalue4' type='CHAR' size='16'/>\n"+
+ " <column name='avalue3' type='DOUBLE' default='1.0'/>\n"+
+ " <column name='avalue2' type='INTEGER'/>\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='avalue1' type='VARCHAR' size='32'/>\n"+
+ " <column name='avalue2' type='INTEGER'/>\n"+
+ " <column name='avalue3' type='DOUBLE' default='1.0'/>\n"+
+ " <column name='avalue4' type='CHAR' size='16'/>\n"+
+ " </table>\n"+
+ "</database>";
+
+ createDatabase(model1Xml);
+
+ insertRow("roundtrip", new Object[] { new Integer(1), "test", "value",
null, null });
+
+ alterDatabase(model2Xml);
+
+ assertEquals(getAdjustedModel(),
+ readModelFromDatabase("roundtriptest"));
+
+ List beans = getRows("roundtrip");
+
+ assertEquals((Object)"test", beans.get(0), "avalue1");
+ assertEquals((Object)null, beans.get(0), "avalue2");
+ assertEquals(new Double(1.0), beans.get(0), "avalue3");
+ assertEquals((Object)"value", beans.get(0), "avalue4");
}
/**