[jOOQ/jOOQ#9736] Interpreter and DDL export support

This commit is contained in:
Lukas Eder 2024-11-14 14:35:04 +01:00
parent 992554b47d
commit 1859e47554
7 changed files with 70 additions and 23 deletions

View File

@ -108,6 +108,7 @@ import static org.jooq.meta.postgres.pg_catalog.Tables.PG_NAMESPACE;
import static org.jooq.meta.postgres.pg_catalog.Tables.PG_PROC;
import static org.jooq.meta.postgres.pg_catalog.Tables.PG_SEQUENCE;
import static org.jooq.meta.postgres.pg_catalog.Tables.PG_TYPE;
import static org.jooq.tools.jdbc.JDBCUtils.foreignKeyRule;
import static org.jooq.util.postgres.PostgresDSL.arrayAppend;
import java.math.BigDecimal;
@ -147,6 +148,7 @@ import org.jooq.conf.ParseUnknownFunctions;
import org.jooq.exception.DataAccessException;
import org.jooq.impl.DSL;
import org.jooq.impl.ParserException;
import org.jooq.impl.QOM.ForeignKeyRule;
import org.jooq.impl.SQLDataType;
import org.jooq.meta.AbstractDatabase;
import org.jooq.meta.AbstractIndexDefinition;
@ -186,6 +188,7 @@ import org.jooq.meta.postgres.pg_catalog.tables.PgIndex;
import org.jooq.meta.postgres.pg_catalog.tables.PgInherits;
import org.jooq.meta.postgres.pg_catalog.tables.PgType;
import org.jooq.tools.JooqLogger;
import org.jooq.tools.jdbc.JDBCUtils;
import org.jetbrains.annotations.NotNull;
@ -405,6 +408,8 @@ public class PostgresDatabase extends AbstractDatabase implements ResultQueryDat
String uniqueKey = record.get("pk_name", String.class);
String uniqueKeyTableName = record.get("pktable_name", String.class);
String uniqueKeyColumn = record.get("pkcolumn_name", String.class);
ForeignKeyRule deleteRule = foreignKeyRule(record.get("delete_rule", int.class));
ForeignKeyRule updateRule = foreignKeyRule(record.get("update_rule", int.class));
TableDefinition foreignKeyTable = getTable(foreignKeySchema, foreignKeyTableName);
TableDefinition uniqueKeyTable = getTable(uniqueKeySchema, uniqueKeyTableName);
@ -417,7 +422,9 @@ public class PostgresDatabase extends AbstractDatabase implements ResultQueryDat
uniqueKey,
uniqueKeyTable,
uniqueKeyTable.getColumn(uniqueKeyColumn),
true
true,
deleteRule,
updateRule
);
for (IndexDefinition index : getIndexes(uniqueKeyTable)) {

View File

@ -877,7 +877,9 @@ abstract class AbstractMeta extends AbstractScope implements Meta, Serializable
map(oldFk.getFieldsArray(), f -> (TableField) fkTable.field(f), TableField[]::new),
uk,
map(oldFk.getKeyFieldsArray(), f -> (TableField) ukTable.field(f), TableField[]::new),
oldFk.enforced()
oldFk.enforced(),
oldFk.getDeleteRule(),
oldFk.getUpdateRule()
);
}

View File

@ -79,6 +79,7 @@ import org.jooq.Comment;
import org.jooq.Configuration;
import org.jooq.Constraint;
import org.jooq.ConstraintEnforcementStep;
import org.jooq.ConstraintForeignKeyOnStep;
import org.jooq.CreateDomainAsStep;
import org.jooq.CreateDomainConstraintStep;
import org.jooq.CreateDomainDefaultStep;
@ -124,10 +125,14 @@ import org.jooq.TableOptions.TableType;
// ...
import org.jooq.UniqueKey;
import org.jooq.impl.QOM.CreateView;
import org.jooq.impl.QOM.ForeignKeyRule;
import org.jooq.DDLExportConfiguration.InlineForeignKeyConstraints;
import org.jooq.tools.JooqLogger;
import org.jooq.tools.StringUtils;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
/**
* @author Lukas Eder
*/
@ -486,7 +491,15 @@ final class DDL {
if (configuration.flags().contains(FOREIGN_KEY) && (table.getTableType() != VIEW || configuration.includeConstraintsOnViews()))
for (ForeignKey<?, ?> key : sortKeysIf(table.getReferences(), !configuration.respectConstraintOrder()))
result.add(enforced(constraint(key.getUnqualifiedName()).foreignKey(key.getFieldsArray()).references(key.getKey().getTable(), key.getKeyFieldsArray()), key.enforced()));
result.add(enforced(
rules(
constraint(key.getUnqualifiedName()).foreignKey(key.getFieldsArray())
.references(key.getKey().getTable(), key.getKeyFieldsArray()),
key.getDeleteRule(),
key.getUpdateRule()
),
key.enforced()
));
return result;
}
@ -783,6 +796,19 @@ final class DDL {
private ConstraintEnforcementStep rules(
ConstraintForeignKeyOnStep on,
ForeignKeyRule deleteRule,
ForeignKeyRule updateRule
) {
if (deleteRule != null)
on = on.onDelete(deleteRule);
if (updateRule != null)
on = on.onUpdate(updateRule);
return on;
}
private final Constraint enforced(ConstraintEnforcementStep check, boolean enforced) {
return enforced ? check : check.notEnforced();

View File

@ -507,7 +507,12 @@ final class InformationSchemaMetaImpl extends AbstractMeta {
continue tableConstraintLoop;
}
ForeignKey<Record, Record> key = Internal.createForeignKey(uniqueKey, table, xc.getConstraintName(), c.toArray(new TableField[0]));
ForeignKey<Record, Record> key = Internal.createForeignKey(
uniqueKey,
table,
xc.getConstraintName(),
c.toArray(new TableField[0])
);
table.foreignKeys.add(key);
break;
}

View File

@ -2441,8 +2441,8 @@ final class Interpreter {
uk,
map(referencedFields, f -> (TableField<Record, ?>) uk.getTable().field(f.name()), TableField[]::new),
enforced,
null,
null
onDelete,
onUpdate
));
}

View File

@ -93,6 +93,7 @@ import static org.jooq.impl.Tools.map;
import static org.jooq.tools.StringUtils.defaultIfEmpty;
import static org.jooq.tools.StringUtils.defaultString;
import static org.jooq.tools.StringUtils.isEmpty;
import static org.jooq.tools.jdbc.JDBCUtils.foreignKeyRule;
import java.io.Serializable;
import java.sql.DatabaseMetaData;
@ -151,6 +152,7 @@ import org.jooq.exception.SQLDialectNotSupportedException;
import org.jooq.impl.QOM.ForeignKeyRule;
import org.jooq.tools.JooqLogger;
import org.jooq.tools.StringUtils;
import org.jooq.tools.jdbc.JDBCUtils;
/**
* An implementation of the public {@link Meta} type.
@ -1009,23 +1011,6 @@ final class MetaImpl extends AbstractMeta {
String.class // IS_AUTOINCREMENT
};
private static final ForeignKeyRule foreignKeyRule(int code) {
switch (code) {
case DatabaseMetaData.importedKeyCascade:
return ForeignKeyRule.CASCADE;
case DatabaseMetaData.importedKeyNoAction:
return ForeignKeyRule.NO_ACTION;
case DatabaseMetaData.importedKeyRestrict:
return ForeignKeyRule.RESTRICT;
case DatabaseMetaData.importedKeySetDefault:
return ForeignKeyRule.SET_DEFAULT;
case DatabaseMetaData.importedKeySetNull:
return ForeignKeyRule.SET_NULL;
default:
return null;
}
}
private static final TableOptions tableOption(DSLContext ctx, MetaSchema schema, String tableName, TableType tableType) {
String sql = M_SOURCES(ctx.dialect());

View File

@ -55,6 +55,7 @@ import java.sql.Statement;
// ...
import org.jooq.SQLDialect;
import org.jooq.impl.QOM.ForeignKeyRule;
import org.jooq.tools.JooqLogger;
import org.jetbrains.annotations.NotNull;
@ -922,6 +923,27 @@ public class JDBCUtils {
return (value == null || (!value && statement.wasNull())) ? null : value;
}
/**
* Translate the {@link DatabaseMetaData#importedKeyCascade} and various
* other flag valuse to the jOOQ {@link ForeignKeyRule} representation.
*/
public static final ForeignKeyRule foreignKeyRule(int code) {
switch (code) {
case DatabaseMetaData.importedKeyCascade:
return ForeignKeyRule.CASCADE;
case DatabaseMetaData.importedKeyNoAction:
return ForeignKeyRule.NO_ACTION;
case DatabaseMetaData.importedKeyRestrict:
return ForeignKeyRule.RESTRICT;
case DatabaseMetaData.importedKeySetDefault:
return ForeignKeyRule.SET_DEFAULT;
case DatabaseMetaData.importedKeySetNull:
return ForeignKeyRule.SET_NULL;
default:
return null;
}
}
/**
* No instances.
*/