From dd6b16512e126c55157ea4b66c0e81044c9caaa6 Mon Sep 17 00:00:00 2001 From: Lukas Eder Date: Thu, 21 Mar 2024 09:03:07 +0100 Subject: [PATCH] [jOOQ/jOOQ#15732] Add code generation support for arrays --- .../java/org/jooq/codegen/GenerationUtil.java | 2 ++ .../java/org/jooq/meta/AbstractDatabase.java | 1 + .../org/jooq/meta/duckdb/DuckDBDatabase.java | 8 ++++++- .../system/main/tables/DuckdbConstraints.java | 23 +++++-------------- .../system/main/tables/DuckdbTypes.java | 11 ++------- .../java/org/jooq/impl/DefaultDataType.java | 22 ++++++++++-------- 6 files changed, 30 insertions(+), 37 deletions(-) diff --git a/jOOQ-codegen/src/main/java/org/jooq/codegen/GenerationUtil.java b/jOOQ-codegen/src/main/java/org/jooq/codegen/GenerationUtil.java index 54ac85fbbb..11deba76a4 100644 --- a/jOOQ-codegen/src/main/java/org/jooq/codegen/GenerationUtil.java +++ b/jOOQ-codegen/src/main/java/org/jooq/codegen/GenerationUtil.java @@ -541,6 +541,8 @@ class GenerationUtil { + case DUCKDB: + return new BaseType(t.replaceFirst("(?i:array)|\\[\\]", ""), u); case POSTGRES: diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/AbstractDatabase.java b/jOOQ-meta/src/main/java/org/jooq/meta/AbstractDatabase.java index 565ff8f4cb..af0a4f1d28 100644 --- a/jOOQ-meta/src/main/java/org/jooq/meta/AbstractDatabase.java +++ b/jOOQ-meta/src/main/java/org/jooq/meta/AbstractDatabase.java @@ -3472,6 +3472,7 @@ public abstract class AbstractDatabase implements Database { + case DUCKDB: case H2: case POSTGRES: case YUGABYTEDB: diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/DuckDBDatabase.java b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/DuckDBDatabase.java index 077fa45600..d918b456a3 100644 --- a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/DuckDBDatabase.java +++ b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/DuckDBDatabase.java @@ -96,6 +96,8 @@ import org.jooq.meta.TableDefinition; import org.jooq.meta.UDTDefinition; import org.jooq.meta.XMLSchemaCollectionDefinition; +import org.jetbrains.annotations.NotNull; + /** * The DuckDB database * @@ -116,7 +118,11 @@ public class DuckDBDatabase extends AbstractDatabase implements ResultQueryDatab @Override protected DSLContext create0() { - return DSL.using(getConnection(), SQLDialect.DUCKDB); + DSLContext ctx = DSL.using(getConnection(), SQLDialect.DUCKDB); + + // Cannot fully qualify column references of table valued functions + ctx.settings().setRenderSchema(false); + return ctx; } @Override diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbConstraints.java b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbConstraints.java index 14858abcdc..252eecb58d 100644 --- a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbConstraints.java +++ b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbConstraints.java @@ -13,7 +13,6 @@ import org.jooq.Table; import org.jooq.TableField; import org.jooq.TableOptions; import org.jooq.impl.DSL; -import org.jooq.impl.DefaultDataType; import org.jooq.impl.SQLDataType; import org.jooq.impl.TableImpl; import org.jooq.meta.duckdb.system.main.Main; @@ -91,26 +90,16 @@ public class DuckdbConstraints extends TableImpl { public final TableField EXPRESSION = createField(DSL.name("expression"), SQLDataType.VARCHAR, this, ""); /** - * @deprecated Unknown data type. If this is a qualified, user-defined type, - * it may have been excluded from code generation. If this is a built-in - * type, you can define an explicit {@link org.jooq.Binding} to specify how - * this type should be handled. Deprecation can be turned off using - * {@literal } in your code generator - * configuration. + * The column + * system.main.duckdb_constraints.constraint_column_indexes. */ - @Deprecated - public final TableField CONSTRAINT_COLUMN_INDEXES = createField(DSL.name("constraint_column_indexes"), DefaultDataType.getDefaultDataType("BIGINT[]"), this, ""); + public final TableField CONSTRAINT_COLUMN_INDEXES = createField(DSL.name("constraint_column_indexes"), SQLDataType.BIGINT.array(), this, ""); /** - * @deprecated Unknown data type. If this is a qualified, user-defined type, - * it may have been excluded from code generation. If this is a built-in - * type, you can define an explicit {@link org.jooq.Binding} to specify how - * this type should be handled. Deprecation can be turned off using - * {@literal } in your code generator - * configuration. + * The column + * system.main.duckdb_constraints.constraint_column_names. */ - @Deprecated - public final TableField CONSTRAINT_COLUMN_NAMES = createField(DSL.name("constraint_column_names"), DefaultDataType.getDefaultDataType("VARCHAR[]"), this, ""); + public final TableField CONSTRAINT_COLUMN_NAMES = createField(DSL.name("constraint_column_names"), SQLDataType.VARCHAR.array(), this, ""); private DuckdbConstraints(Name alias, Table aliased) { this(alias, aliased, (Field[]) null, null); diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbTypes.java b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbTypes.java index 097ab99401..f90f7fb5ff 100644 --- a/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbTypes.java +++ b/jOOQ-meta/src/main/java/org/jooq/meta/duckdb/system/main/tables/DuckdbTypes.java @@ -16,7 +16,6 @@ import org.jooq.TableField; import org.jooq.TableOptions; import org.jooq.UniqueKey; import org.jooq.impl.DSL; -import org.jooq.impl.DefaultDataType; import org.jooq.impl.SQLDataType; import org.jooq.impl.TableImpl; import org.jooq.meta.duckdb.system.main.Keys; @@ -100,15 +99,9 @@ public class DuckdbTypes extends TableImpl { public final TableField INTERNAL = createField(DSL.name("internal"), SQLDataType.BOOLEAN, this, ""); /** - * @deprecated Unknown data type. If this is a qualified, user-defined type, - * it may have been excluded from code generation. If this is a built-in - * type, you can define an explicit {@link org.jooq.Binding} to specify how - * this type should be handled. Deprecation can be turned off using - * {@literal } in your code generator - * configuration. + * The column system.main.duckdb_types.labels. */ - @Deprecated - public final TableField LABELS = createField(DSL.name("labels"), DefaultDataType.getDefaultDataType("VARCHAR[]"), this, ""); + public final TableField LABELS = createField(DSL.name("labels"), SQLDataType.VARCHAR.array(), this, ""); private DuckdbTypes(Name alias, Table aliased) { this(alias, aliased, (Field[]) null, null); diff --git a/jOOQ/src/main/java/org/jooq/impl/DefaultDataType.java b/jOOQ/src/main/java/org/jooq/impl/DefaultDataType.java index 6ece66efc0..33d3071965 100644 --- a/jOOQ/src/main/java/org/jooq/impl/DefaultDataType.java +++ b/jOOQ/src/main/java/org/jooq/impl/DefaultDataType.java @@ -41,6 +41,7 @@ import static java.util.Collections.unmodifiableCollection; // ... import static org.jooq.SQLDialect.CLICKHOUSE; // ... +import static org.jooq.SQLDialect.DUCKDB; import static org.jooq.SQLDialect.FIREBIRD; import static org.jooq.SQLDialect.H2; import static org.jooq.SQLDialect.HSQLDB; @@ -140,28 +141,29 @@ import org.jetbrains.annotations.ApiStatus.Internal; @Internal public class DefaultDataType extends AbstractDataTypeX { - private static final Set ENCODED_TIMESTAMP_PRECISION = SQLDialect.supportedBy(HSQLDB, MARIADB); - private static final Set NO_SUPPORT_TIMESTAMP_PRECISION = SQLDialect.supportedBy(FIREBIRD, MYSQL, SQLITE); - private static final Set SUPPORT_POSTGRES_ARRAY_NOTATION = SQLDialect.supportedBy(POSTGRES, YUGABYTEDB); - private static final Set SUPPORT_HSQLDB_ARRAY_NOTATION = SQLDialect.supportedBy(H2, HSQLDB, POSTGRES, YUGABYTEDB); - private static final Set SUPPORT_TRINO_ARRAY_NOTATION = SQLDialect.supportedBy(CLICKHOUSE, TRINO); + private static final Set ENCODED_TIMESTAMP_PRECISION = SQLDialect.supportedBy(HSQLDB, MARIADB); + private static final Set NO_SUPPORT_TIMESTAMP_PRECISION = SQLDialect.supportedBy(FIREBIRD, MYSQL, SQLITE); + private static final Set SUPPORT_POSTGRES_PREFIX_ARRAY_NOTATION = SQLDialect.supportedBy(POSTGRES, YUGABYTEDB); + private static final Set SUPPORT_POSTGRES_SUFFIX_ARRAY_NOTATION = SQLDialect.supportedBy(DUCKDB, POSTGRES, YUGABYTEDB); + private static final Set SUPPORT_HSQLDB_ARRAY_NOTATION = SQLDialect.supportedBy(H2, HSQLDB, POSTGRES, YUGABYTEDB); + private static final Set SUPPORT_TRINO_ARRAY_NOTATION = SQLDialect.supportedBy(CLICKHOUSE, TRINO); /** * A pattern for data type name normalisation. */ - private static final Pattern P_NORMALISE = Pattern.compile("\"|\\.|\\s|\\(\\w+(\\s*,\\s*\\w+)*\\)|(NOT\\s*NULL)?"); + private static final Pattern P_NORMALISE = Pattern.compile("\"|\\.|\\s|\\(\\w+(\\s*,\\s*\\w+)*\\)|(NOT\\s*NULL)?"); /** * A pattern to be used to replace all precision, scale, and length * information. */ - private static final Pattern P_TYPE_NAME = Pattern.compile("\\([^)]*\\)"); + private static final Pattern P_TYPE_NAME = Pattern.compile("\\([^)]*\\)"); /** * A pattern to be used to extract all precision, scale, and length * information. */ - private static final Pattern P_PRECISION_SCALE = Pattern.compile("\\(\\s*(\\d+)(?:\\s*,\\s*(\\d+))?\\s*\\)"); + private static final Pattern P_PRECISION_SCALE = Pattern.compile("\\(\\s*(\\d+)(?:\\s*,\\s*(\\d+))?\\s*\\)"); // ------------------------------------------------------------------------- // Data type caches @@ -712,12 +714,12 @@ public class DefaultDataType extends AbstractDataTypeX { result = TYPES_BY_NAME[SQLDialect.DEFAULT.ordinal()].get("INTEGER"); // [#4065] PostgreSQL reports array types as _typename, e.g. _varchar - else if (arrayCheck && SUPPORT_POSTGRES_ARRAY_NOTATION.contains(dialect) && typeName.charAt(0) == '_') + else if (arrayCheck && SUPPORT_POSTGRES_PREFIX_ARRAY_NOTATION.contains(dialect) && typeName.charAt(0) == '_') result = getDataType(dialect, typeName.substring(1)).getArrayDataType(); // [#8545] CockroachDB is a little different from PostgreSQL. We're reading crdb_sql_type rather // than data_type / udt_name from information_schema.columns - else if (arrayCheck && SUPPORT_POSTGRES_ARRAY_NOTATION.contains(dialect) && typeName.endsWith("[]")) + else if (arrayCheck && SUPPORT_POSTGRES_SUFFIX_ARRAY_NOTATION.contains(dialect) && typeName.endsWith("[]")) result = getDataType(dialect, typeName.substring(0, typeName.length() - 2)).getArrayDataType(); // [#6466] HSQLDB reports array types as XYZARRAY. H2 should, too