diff --git a/jOOQ-codegen/src/main/java/org/jooq/codegen/XMLGenerator.java b/jOOQ-codegen/src/main/java/org/jooq/codegen/XMLGenerator.java
index c4718a21ec..25d5a14c9f 100644
--- a/jOOQ-codegen/src/main/java/org/jooq/codegen/XMLGenerator.java
+++ b/jOOQ-codegen/src/main/java/org/jooq/codegen/XMLGenerator.java
@@ -37,6 +37,8 @@
*/
package org.jooq.codegen;
+import static org.jooq.impl.QOM.GenerationOption.STORED;
+import static org.jooq.impl.QOM.GenerationOption.VIRTUAL;
import static org.jooq.tools.StringUtils.isBlank;
import static org.jooq.util.xml.jaxb.TableConstraintType.CHECK;
import static org.jooq.util.xml.jaxb.TableConstraintType.FOREIGN_KEY;
@@ -197,6 +199,12 @@ public class XMLGenerator extends AbstractGenerator {
column.setOrdinalPosition(co.getPosition());
column.setReadonly(co.isReadonly());
+ if (type.isComputed()) {
+ column.setIsGenerated(type.isComputed());
+ column.setGenerationExpression(type.getGeneratedAlwaysAs());
+ column.setGenerationOption(type.getGenerationOption() == VIRTUAL ? "VIRTUAL" : type.getGenerationOption() == STORED ? "STORED" : null);
+ }
+
is.getColumns().add(column);
}
}
diff --git a/jOOQ-examples/jOOQ-jpa-example-entities/pom.xml b/jOOQ-examples/jOOQ-jpa-example-entities/pom.xml
index 08d9f8bc62..d43e071e13 100644
--- a/jOOQ-examples/jOOQ-jpa-example-entities/pom.xml
+++ b/jOOQ-examples/jOOQ-jpa-example-entities/pom.xml
@@ -62,18 +62,18 @@
${org.hibernate.version}
- javax.xml.bind
- jaxb-api
- 2.3.1
+ jakarta.xml.bind
+ jakarta.xml.bind-api
+ ${jaxb.version}
- javax.xml.bind
- jaxb-api
- 2.3.1
+ jakarta.xml.bind
+ jakarta.xml.bind-api
+ ${jaxb.version}
diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/mysql/MySQLTableDefinition.java b/jOOQ-meta/src/main/java/org/jooq/meta/mysql/MySQLTableDefinition.java
index bf4562eef4..42e4e339bf 100644
--- a/jOOQ-meta/src/main/java/org/jooq/meta/mysql/MySQLTableDefinition.java
+++ b/jOOQ-meta/src/main/java/org/jooq/meta/mysql/MySQLTableDefinition.java
@@ -52,6 +52,7 @@ import java.util.regex.Pattern;
import org.jooq.Record;
import org.jooq.TableOptions.TableType;
+import org.jooq.impl.QOM.GenerationOption;
import org.jooq.meta.AbstractTableDefinition;
import org.jooq.meta.ColumnDefinition;
import org.jooq.meta.DataTypeDefinition;
@@ -113,6 +114,12 @@ public class MySQLTableDefinition extends AbstractTableDefinition {
// [#6492] MariaDB supports a standard IS_GENERATED, but MySQL doesn't (yet)
boolean generated = record.get(COLUMNS.EXTRA) != null && record.get(COLUMNS.EXTRA).toUpperCase().contains("GENERATED");
+ GenerationOption generationOption =
+ "VIRTUAL GENERATED".equalsIgnoreCase(record.get(COLUMNS.EXTRA))
+ ? GenerationOption.VIRTUAL
+ : "STORED GENERATED".equalsIgnoreCase(record.get(COLUMNS.EXTRA))
+ ? GenerationOption.STORED
+ : null;
columnTypeFix:
if (unsigned || displayWidths) {
@@ -148,7 +155,9 @@ public class MySQLTableDefinition extends AbstractTableDefinition {
record.get(COLUMNS.IS_NULLABLE, boolean.class),
generated ? null : record.get(COLUMNS.COLUMN_DEFAULT),
name(getSchema().getName(), getName() + "_" + record.get(COLUMNS.COLUMN_NAME))
- ).generatedAlwaysAs(generated ? record.get(COLUMNS.GENERATION_EXPRESSION) : null);
+ )
+ .generatedAlwaysAs(generated ? record.get(COLUMNS.GENERATION_EXPRESSION) : null)
+ .generationOption(generationOption);
result.add(new DefaultColumnDefinition(
getDatabase().getTable(getSchema(), getName()),
diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresDatabase.java b/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresDatabase.java
index 919a3f1836..bf56bcc0e0 100644
--- a/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresDatabase.java
+++ b/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresDatabase.java
@@ -1112,6 +1112,20 @@ public class PostgresDatabase extends AbstractDatabase implements ResultQueryDat
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresTableDefinition.java b/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresTableDefinition.java
index 6b8fe380f2..fede7ea972 100644
--- a/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresTableDefinition.java
+++ b/jOOQ-meta/src/main/java/org/jooq/meta/postgres/PostgresTableDefinition.java
@@ -60,6 +60,7 @@ import org.jooq.Condition;
import org.jooq.Field;
import org.jooq.Record;
import org.jooq.TableOptions.TableType;
+import org.jooq.impl.QOM.GenerationOption;
import org.jooq.meta.AbstractTableDefinition;
import org.jooq.meta.ColumnDefinition;
import org.jooq.meta.DataTypeDefinition;
@@ -92,6 +93,10 @@ public class PostgresTableDefinition extends AbstractTableDefinition {
Field udtSchema = COLUMNS.UDT_SCHEMA;
Field precision = nvl(COLUMNS.DATETIME_PRECISION, COLUMNS.NUMERIC_PRECISION);
Field serialColumnDefault = inline("nextval('%_seq'::regclass)");
+ Field generationExpression = COLUMNS.GENERATION_EXPRESSION;
+ Field attgenerated = PG_ATTRIBUTE.ATTGENERATED;
+
+
@@ -123,7 +128,8 @@ public class PostgresTableDefinition extends AbstractTableDefinition {
COLUMNS.NUMERIC_SCALE,
(when(isIdentity, inline("YES"))).as(COLUMNS.IS_IDENTITY),
COLUMNS.IS_NULLABLE,
- COLUMNS.GENERATION_EXPRESSION,
+ generationExpression.as(COLUMNS.GENERATION_EXPRESSION),
+ attgenerated.as(PG_ATTRIBUTE.ATTGENERATED),
(when(isIdentity, inline(null, String.class)).else_(COLUMNS.COLUMN_DEFAULT)).as(COLUMNS.COLUMN_DEFAULT),
coalesce(COLUMNS.DOMAIN_SCHEMA, udtSchema).as(COLUMNS.UDT_SCHEMA),
coalesce(COLUMNS.DOMAIN_NAME, COLUMNS.UDT_NAME).as(COLUMNS.UDT_NAME),
@@ -166,7 +172,15 @@ public class PostgresTableDefinition extends AbstractTableDefinition {
record.get(COLUMNS.UDT_SCHEMA),
record.get(COLUMNS.UDT_NAME)
)
- ).generatedAlwaysAs(record.get(COLUMNS.GENERATION_EXPRESSION));
+ )
+ .generatedAlwaysAs(record.get(COLUMNS.GENERATION_EXPRESSION))
+ .generationOption(
+ "s".equals(record.get(PG_ATTRIBUTE.ATTGENERATED))
+ ? GenerationOption.STORED
+ : "v".equals(record.get(PG_ATTRIBUTE.ATTGENERATED))
+ ? GenerationOption.VIRTUAL
+ : null
+ );
ColumnDefinition column = new DefaultColumnDefinition(
getDatabase().getTable(getSchema(), getName()),
diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/sqlite/SQLiteTableDefinition.java b/jOOQ-meta/src/main/java/org/jooq/meta/sqlite/SQLiteTableDefinition.java
index 233107f875..db36c2ff20 100644
--- a/jOOQ-meta/src/main/java/org/jooq/meta/sqlite/SQLiteTableDefinition.java
+++ b/jOOQ-meta/src/main/java/org/jooq/meta/sqlite/SQLiteTableDefinition.java
@@ -42,6 +42,8 @@ import static org.jooq.impl.DSL.field;
import static org.jooq.impl.DSL.inline;
import static org.jooq.impl.DSL.name;
import static org.jooq.impl.DSL.selectOne;
+import static org.jooq.impl.QOM.GenerationOption.STORED;
+import static org.jooq.impl.QOM.GenerationOption.VIRTUAL;
import static org.jooq.meta.sqlite.sqlite_master.SQLiteMaster.SQLITE_MASTER;
import static org.jooq.tools.StringUtils.isBlank;
@@ -49,7 +51,6 @@ import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
-import org.jooq.Check;
import org.jooq.Configuration;
import org.jooq.Field;
import org.jooq.Query;
@@ -61,7 +62,6 @@ import org.jooq.impl.DSL;
import org.jooq.impl.ParserException;
import org.jooq.meta.AbstractTableDefinition;
import org.jooq.meta.ColumnDefinition;
-import org.jooq.meta.DefaultCheckConstraintDefinition;
import org.jooq.meta.DefaultColumnDefinition;
import org.jooq.meta.DefaultDataTypeDefinition;
import org.jooq.meta.SchemaDefinition;
@@ -123,8 +123,9 @@ public class SQLiteTableDefinition extends AbstractTableDefinition {
.select(fName, fType, fNotnull, fDefaultValue, fPk, fHidden)
.from("pragma_table_xinfo({0})", inline(getName()))
// 0 = ordinary column
- // 2 = generated column
- .where("hidden in (0, 2)")
+ // 2 = generated column (virtual)
+ // 3 = generated column (stored)
+ .where("hidden in (0, 2, 3)")
) {
String name = record.get(fName);
@@ -138,7 +139,7 @@ public class SQLiteTableDefinition extends AbstractTableDefinition {
int pk = record.get(fPk);
int hidden = record.get(fHidden);
boolean identity = false;
- boolean generated = hidden == 2;
+ boolean generated = hidden == 2 || hidden == 3;
String generator = null;
// [#8278] [#11172] SQLite doesn't store the data type for all views or virtual tables
@@ -198,7 +199,9 @@ public class SQLiteTableDefinition extends AbstractTableDefinition {
scale,
!record.get(fNotnull),
record.get(fDefaultValue)
- ).generatedAlwaysAs(generator);
+ )
+ .generatedAlwaysAs(generator)
+ .generationOption(hidden == 2 ? VIRTUAL : hidden == 3 ? STORED : null);
result.add(new DefaultColumnDefinition(
getDatabase().getTable(getSchema(), getName()),
diff --git a/jOOQ-meta/src/main/java/org/jooq/meta/xml/XMLTableDefinition.java b/jOOQ-meta/src/main/java/org/jooq/meta/xml/XMLTableDefinition.java
index 400c03380c..3afd6c6aec 100644
--- a/jOOQ-meta/src/main/java/org/jooq/meta/xml/XMLTableDefinition.java
+++ b/jOOQ-meta/src/main/java/org/jooq/meta/xml/XMLTableDefinition.java
@@ -38,6 +38,8 @@
package org.jooq.meta.xml;
import static java.lang.Boolean.TRUE;
+import static org.jooq.impl.QOM.GenerationOption.STORED;
+import static org.jooq.impl.QOM.GenerationOption.VIRTUAL;
import static org.jooq.meta.xml.XMLDatabase.unbox;
import static org.jooq.tools.StringUtils.defaultIfNull;
@@ -100,7 +102,15 @@ public class XMLTableDefinition extends AbstractTableDefinition {
unbox(column.getNumericScale()),
column.isIsNullable(),
column.getColumnDefault()
- );
+ )
+ .generatedAlwaysAs(TRUE.equals(column.isIsGenerated()) ? column.getGenerationExpression() : null)
+ .generationOption(TRUE.equals(column.isIsGenerated())
+ ? "STORED".equalsIgnoreCase(column.getGenerationOption())
+ ? STORED
+ : "VIRTUAL".equalsIgnoreCase(column.getGenerationOption())
+ ? VIRTUAL
+ : null
+ : null);
result.add(new DefaultColumnDefinition(
this,
diff --git a/jOOQ/src/main/java/org/jooq/impl/InformationSchemaExport.java b/jOOQ/src/main/java/org/jooq/impl/InformationSchemaExport.java
index bf27f5dd20..51645e0024 100644
--- a/jOOQ/src/main/java/org/jooq/impl/InformationSchemaExport.java
+++ b/jOOQ/src/main/java/org/jooq/impl/InformationSchemaExport.java
@@ -37,6 +37,8 @@
*/
package org.jooq.impl;
+import static org.jooq.impl.QOM.GenerationOption.STORED;
+import static org.jooq.impl.QOM.GenerationOption.VIRTUAL;
import static org.jooq.tools.StringUtils.isBlank;
import static org.jooq.util.xml.jaxb.TableConstraintType.CHECK;
import static org.jooq.util.xml.jaxb.TableConstraintType.FOREIGN_KEY;
@@ -51,6 +53,7 @@ import java.util.Set;
import org.jooq.Catalog;
import org.jooq.Check;
import org.jooq.Configuration;
+import org.jooq.DataType;
import org.jooq.Domain;
import org.jooq.Field;
import org.jooq.ForeignKey;
@@ -64,6 +67,7 @@ import org.jooq.SortField;
import org.jooq.SortOrder;
import org.jooq.Table;
import org.jooq.UniqueKey;
+import org.jooq.impl.QOM.GenerationOption;
import org.jooq.util.xml.jaxb.CheckConstraint;
import org.jooq.util.xml.jaxb.Column;
import org.jooq.util.xml.jaxb.IndexColumnUsage;
@@ -328,6 +332,7 @@ final class InformationSchemaExport {
Field>[] fields = t.fields();
for (int i = 0; i < fields.length; i++) {
Field> f = fields[i];
+ DataType> type = f.getDataType();
Column ic = new Column();
if (!isBlank(catalogName))
@@ -339,21 +344,27 @@ final class InformationSchemaExport {
ic.setTableName(t.getName());
ic.setColumnName(f.getName());
ic.setComment(f.getComment());
- ic.setDataType(f.getDataType().getTypeName(configuration));
+ ic.setDataType(type.getTypeName(configuration));
- if (f.getDataType().lengthDefined())
- ic.setCharacterMaximumLength(f.getDataType().length());
+ if (type.lengthDefined())
+ ic.setCharacterMaximumLength(type.length());
- if (f.getDataType().precisionDefined())
- ic.setNumericPrecision(f.getDataType().precision());
+ if (type.precisionDefined())
+ ic.setNumericPrecision(type.precision());
- if (f.getDataType().scaleDefined())
- ic.setNumericScale(f.getDataType().scale());
+ if (type.scaleDefined())
+ ic.setNumericScale(type.scale());
- ic.setColumnDefault(DSL.using(configuration).render(f.getDataType().defaultValue()));
- ic.setIsNullable(f.getDataType().nullable());
+ ic.setColumnDefault(DSL.using(configuration).render(type.defaultValue()));
+ ic.setIsNullable(type.nullable());
ic.setOrdinalPosition(i + 1);
- ic.setReadonly(f.getDataType().readonly());
+ ic.setReadonly(type.readonly());
+
+ if (type.computed()) {
+ ic.setIsGenerated(type.computed());
+ ic.setGenerationExpression(DSL.using(configuration).render(type.generatedAlwaysAs()));
+ ic.setGenerationOption(type.generationOption() == VIRTUAL ? "VIRTUAL" : type.generationOption() == STORED ? "STORED" : null);
+ }
result.getColumns().add(ic);
}
diff --git a/jOOQ/src/main/java/org/jooq/impl/InformationSchemaMetaImpl.java b/jOOQ/src/main/java/org/jooq/impl/InformationSchemaMetaImpl.java
index 4a342cfe8a..cf32982ea9 100644
--- a/jOOQ/src/main/java/org/jooq/impl/InformationSchemaMetaImpl.java
+++ b/jOOQ/src/main/java/org/jooq/impl/InformationSchemaMetaImpl.java
@@ -43,19 +43,27 @@ import static java.util.Collections.emptyList;
import static java.util.Comparator.comparing;
import static java.util.Comparator.comparingInt;
import static org.jooq.impl.DSL.name;
+import static org.jooq.impl.QOM.GenerationOption.STORED;
+import static org.jooq.impl.QOM.GenerationOption.VIRTUAL;
import static org.jooq.impl.Tools.EMPTY_CHECK;
import static org.jooq.impl.Tools.EMPTY_SORTFIELD;
import static org.jooq.tools.StringUtils.defaultIfNull;
import static org.jooq.util.xml.jaxb.TableConstraintType.PRIMARY_KEY;
import java.math.BigInteger;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
import org.jooq.Catalog;
import org.jooq.Check;
import org.jooq.Configuration;
import org.jooq.DataType;
import org.jooq.Domain;
+import org.jooq.Field;
import org.jooq.ForeignKey;
import org.jooq.Index;
import org.jooq.Name;
@@ -69,6 +77,7 @@ import org.jooq.TableOptions;
import org.jooq.TableOptions.TableType;
import org.jooq.UniqueKey;
import org.jooq.exception.SQLDialectNotSupportedException;
+import org.jooq.impl.QOM.GenerationOption;
import org.jooq.tools.StringUtils;
import org.jooq.util.xml.jaxb.CheckConstraint;
import org.jooq.util.xml.jaxb.Column;
@@ -201,7 +210,7 @@ final class InformationSchemaMetaImpl extends AbstractMeta {
InformationSchemaDomain> id = new InformationSchemaDomain