Skip to content

Commit

Permalink
0001753: Added support for expressions as default values to MySQL
Browse files Browse the repository at this point in the history
  • Loading branch information
evan-miller-jumpmind committed Sep 26, 2022
1 parent 88a1553 commit b74944d
Show file tree
Hide file tree
Showing 7 changed files with 90 additions and 0 deletions.
Expand Up @@ -30,5 +30,6 @@ public MariaDBSymmetricDialect(IParameterService parameterService,
IDatabasePlatform platform) {
super(parameterService, platform);
platform.getDatabaseInfo().setGeneratedColumnsSupported(!Version.isOlderThanVersion(getProductVersion(), "5.2"));
platform.getDatabaseInfo().setExpressionsAsDefaultValuesSupported(false);
}
}
Expand Up @@ -91,6 +91,7 @@ public MySqlSymmetricDialect(IParameterService parameterService, IDatabasePlatfo
: "utf8mb4");
this.triggerTemplate = new MySqlTriggerTemplate(this, isConvertZeroDateToNull, characterSet);
platform.getDatabaseInfo().setGeneratedColumnsSupported(!Version.isOlderThanVersion(version, "5.7.0"));
platform.getDatabaseInfo().setExpressionsAsDefaultValuesSupported(!Version.isOlderThanVersion(version, "8.0.13"));
}

@Override
Expand Down
Expand Up @@ -262,6 +262,8 @@ public static Table nextTable(XmlPullParser parser, String catalog, String schem
column.setUnique(FormatUtils.toBoolean(attributeValue));
} else if (attributeName.equalsIgnoreCase("generated")) {
column.setGenerated(FormatUtils.toBoolean(attributeValue));
} else if (attributeName.equalsIgnoreCase("expressionAsDefault")) {
column.setExpressionAsDefaultValue(FormatUtils.toBoolean(attributeValue));
}
}
if (table != null) {
Expand Down Expand Up @@ -550,6 +552,9 @@ public static void write(Table table, Writer output) {
if (column.isGenerated()) {
output.write(" generated=\"" + column.isGenerated() + "\"");
}
if (column.isExpressionAsDefaultValue()) {
output.write(" expressionAsDefault=\"" + column.isExpressionAsDefaultValue() + "\"");
}
if (column.getPlatformColumns() != null && column.getPlatformColumns().size() > 0) {
Collection<PlatformColumn> platformColumns = column.getPlatformColumns()
.values();
Expand Down
21 changes: 21 additions & 0 deletions symmetric-db/src/main/java/org/jumpmind/db/model/Column.java
Expand Up @@ -84,6 +84,8 @@ public class Column implements Cloneable, Serializable {
private boolean unique;
/** Whether the column is a generated/computed/virtual column. */
private boolean generated;
/** Whether the column has an expression for a default value. */
private boolean expressionAsDefaultValue;
/**
* The mapped JDBC type code
*/
Expand Down Expand Up @@ -287,6 +289,25 @@ public void setGenerated(boolean generated) {
this.generated = generated;
}

/**
* Determines whether this column has an expression for a default value.
*
* @return <code>true</code> if this column has an expression for a default value
*/
public boolean isExpressionAsDefaultValue() {
return expressionAsDefaultValue;
}

/**
* Specifies whether this column has an expression for a default value.
*
* @param expressionAsDefaultValue
* <code>true</code> if this column has an expression for a default value
*/
public void setExpressionAsDefaultValue(boolean expressionAsDefaultValue) {
this.expressionAsDefaultValue = expressionAsDefaultValue;
}

/**
* Returns the code (one of the constants in {@link java.sql.Types}) of the JDBC type of the column.
*
Expand Down
Expand Up @@ -91,6 +91,8 @@ public class DatabaseInfo {
private boolean nonPKIdentityColumnsSupported = true;
/** Whether generated/computed/virtual columns are supported. */
private boolean generatedColumnsSupported = false;
/** Whether expressions can be used as default values */
private boolean expressionsAsDefaultValuesSupported = false;
/**
* Whether the auto-increment definition is done via the DEFAULT part of the column definition.
*/
Expand Down Expand Up @@ -462,6 +464,25 @@ public void setGeneratedColumnsSupported(boolean generatedColumnsSupported) {
this.generatedColumnsSupported = generatedColumnsSupported;
}

/**
* Determines whether expressions can be used as default values.
*
* @return <code>true</code> if expressions can be used as default values
*/
public boolean isExpressionsAsDefaultValuesSupported() {
return expressionsAsDefaultValuesSupported;
}

/**
* Specifies whether expressions can be used as default values.
*
* @param expressionsAsDefaultValuesSupported
* <code>true</code> if expressions can be used as default values
*/
public void setExpressionsAsDefaultValuesSupported(boolean expressionsAsDefaultValuesSupported) {
this.expressionsAsDefaultValuesSupported = expressionsAsDefaultValuesSupported;
}

/**
* Determines whether the auto-increment specification uses the DEFAULT value of the column definition.
*
Expand Down
Expand Up @@ -62,6 +62,7 @@
import org.jumpmind.db.model.IndexColumn;
import org.jumpmind.db.model.PlatformColumn;
import org.jumpmind.db.model.Table;
import org.jumpmind.db.model.TypeMap;
import org.jumpmind.db.platform.AbstractDdlBuilder;
import org.jumpmind.db.platform.DatabaseNamesConstants;

Expand Down Expand Up @@ -181,6 +182,45 @@ protected void writeColumnDefaultValueStmt(Table table, Column column, StringBui
}
}

@Override
protected void writeColumnDefaultValue(Table table, Column column, StringBuilder ddl) {
int typeCode = column.getMappedTypeCode();
String defaultValue = getNativeDefaultValue(column);
String defaultValueStr = mapDefaultValue(defaultValue, typeCode);
PlatformColumn platformColumn = column.findPlatformColumn(databaseName);
if (TypeMap.isDateTimeType(typeCode) && defaultValueStr.toUpperCase().equals("CURRENT_TIMESTAMP") && hasSize(column)) {
String nativeType = getNativeType(column);
if (platformColumn != null) {
nativeType = platformColumn.getType();
}
if (nativeType.startsWith("DATETIME") || nativeType.startsWith("TIMESTAMP")) {
Integer size = column.getSizeAsInt();
if (platformColumn != null) {
size = platformColumn.getSize();
} else if (column.getSize() == null) {
size = databaseInfo.getDefaultSize(column.getMappedTypeCode());
}
if (size != null && size >= 0) {
int maxSize = databaseInfo.getMaxSize(nativeType);
if (maxSize > 0 && size > maxSize) {
size = maxSize;
}
ddl.append(defaultValueStr).append("(").append(size).append(")");
return;
}
}
} else if (databaseInfo.isExpressionsAsDefaultValuesSupported() && platformColumn != null
&& column.isExpressionAsDefaultValue()) {
if (defaultValue.startsWith("(") && defaultValue.endsWith(")")) {
ddl.append(defaultValueStr);
} else {
ddl.append("(").append(defaultValueStr).append(")");
}
return;
}
printDefaultValue(defaultValue, typeCode, ddl);
}

@Override
protected boolean shouldGeneratePrimaryKeys(Column[] primaryKeyColumns) {
// mySQL requires primary key indication for auto increment key columns
Expand Down
Expand Up @@ -159,6 +159,7 @@ protected Column readColumn(DatabaseMetaDataWrapper metaData, Map<String, Object
Row result = sqlTemplate.queryForRow(sql, l.toArray());
if ("DEFAULT_GENERATED".equals(result.getString("extra"))) {
column.setGenerated(false);
column.setExpressionAsDefaultValue(true);
} else if (column.getDefaultValue() == null || column.getDefaultValue().equals("NULL")) {
column.setDefaultValue(result.getString("generation_expression"));
}
Expand Down

0 comments on commit b74944d

Please sign in to comment.