diff --git a/jOOQ/src/main/java/org/jooq/DSLContext.java b/jOOQ/src/main/java/org/jooq/DSLContext.java index 9366fd0b9b..b43b9bc686 100644 --- a/jOOQ/src/main/java/org/jooq/DSLContext.java +++ b/jOOQ/src/main/java/org/jooq/DSLContext.java @@ -9647,6 +9647,60 @@ public interface DSLContext extends Scope { @Support({ DUCKDB, H2, POSTGRES, YUGABYTEDB }) AlterViewStep alterViewIfExists(Table view); + /** + * The ALTER MATERIALIZED VIEW statement. + * + * @see DSL#alterMaterializedView(String) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedView(@Stringly.Name String view); + + /** + * The ALTER MATERIALIZED VIEW statement. + * + * @see DSL#alterMaterializedView(Name) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedView(Name view); + + /** + * The ALTER MATERIALIZED VIEW statement. + * + * @see DSL#alterMaterializedView(Table) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedView(Table view); + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + * + * @see DSL#alterMaterializedViewIfExists(String) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedViewIfExists(@Stringly.Name String view); + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + * + * @see DSL#alterMaterializedViewIfExists(Name) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedViewIfExists(Name view); + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + * + * @see DSL#alterMaterializedViewIfExists(Table) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + AlterViewStep alterMaterializedViewIfExists(Table view); + /** * The ALTER VIEW statement. * diff --git a/jOOQ/src/main/java/org/jooq/impl/AlterViewImpl.java b/jOOQ/src/main/java/org/jooq/impl/AlterViewImpl.java index 287f4429d2..d96ad8c874 100644 --- a/jOOQ/src/main/java/org/jooq/impl/AlterViewImpl.java +++ b/jOOQ/src/main/java/org/jooq/impl/AlterViewImpl.java @@ -76,6 +76,7 @@ implements final Table view; final QueryPartListView> fields; + final boolean materialized; final boolean ifExists; Comment comment; Table renameTo; @@ -85,12 +86,14 @@ implements Configuration configuration, Table view, Collection> fields, + boolean materialized, boolean ifExists ) { this( configuration, view, fields, + materialized, ifExists, null, null, @@ -101,12 +104,14 @@ implements AlterViewImpl( Configuration configuration, Table view, + boolean materialized, boolean ifExists ) { this( configuration, view, null, + materialized, ifExists ); } @@ -115,6 +120,7 @@ implements Configuration configuration, Table view, Collection> fields, + boolean materialized, boolean ifExists, Comment comment, Table renameTo, @@ -124,6 +130,7 @@ implements this.view = view; this.fields = new QueryPartList<>(fields); + this.materialized = materialized; this.ifExists = ifExists; this.comment = comment; this.renameTo = renameTo; @@ -226,11 +233,20 @@ implements case POSTGRES: case SQLITE: case YUGABYTEDB: - ctx.visit(begin(dropView(view), createView(view, fields.toArray(Tools.EMPTY_FIELD)).as(as))); + if (materialized) + ctx.visit(begin(dropMaterializedView(view), createMaterializedView(view, fields.toArray(Tools.EMPTY_FIELD)).as(as))); + else + ctx.visit(begin(dropView(view), createView(view, fields.toArray(Tools.EMPTY_FIELD)).as(as))); + break; default: - ctx.visit(K_ALTER).sql(' ').visit(K_VIEW).sql(' ').visit(view); + ctx.visit(K_ALTER).sql(' '); + + if (materialized) + ctx.visit(K_MATERIALIZED).sql(' '); + + ctx.visit(K_VIEW).sql(' ').visit(view); if (!fields.isEmpty()) ctx.sql(" (").visit(QueryPartCollectionView.wrap(fields).qualify(false)).sql(')'); @@ -319,13 +335,19 @@ implements private final void accept1(Context ctx) { ctx.start(Clause.ALTER_VIEW_VIEW) - .visit(K_ALTER).sql(' ') - .visit(SUPPORT_ALTER_TABLE_RENAME.contains(ctx.dialect()) ? K_TABLE : K_VIEW); + .visit(K_ALTER).sql(' '); + + if (SUPPORT_ALTER_TABLE_RENAME.contains(ctx.dialect())) + ctx.visit(K_TABLE).sql(' '); + else if (materialized) + ctx.visit(K_MATERIALIZED).sql(' ').visit(K_VIEW).sql(' '); + else + ctx.visit(K_VIEW).sql(' '); if (ifExists && supportsIfExists(ctx)) ctx.sql(' ').visit(K_IF_EXISTS); - ctx.sql(' ').visit(view) + ctx.sql(' ').visit(view).sql(' ') .end(Clause.ALTER_VIEW_VIEW); if (renameTo != null) @@ -356,6 +378,11 @@ implements return QOM.unmodifiable(fields); } + @Override + public final boolean $materialized() { + return materialized; + } + @Override public final boolean $ifExists() { return ifExists; @@ -378,36 +405,41 @@ implements @Override public final QOM.AlterView $view(Table newValue) { - return $constructor().apply(newValue, $fields(), $ifExists(), $comment(), $renameTo(), $as()); + return $constructor().apply(newValue, $fields(), $materialized(), $ifExists(), $comment(), $renameTo(), $as()); } @Override public final QOM.AlterView $fields(Collection> newValue) { - return $constructor().apply($view(), newValue, $ifExists(), $comment(), $renameTo(), $as()); + return $constructor().apply($view(), newValue, $materialized(), $ifExists(), $comment(), $renameTo(), $as()); + } + + @Override + public final QOM.AlterView $materialized(boolean newValue) { + return $constructor().apply($view(), $fields(), newValue, $ifExists(), $comment(), $renameTo(), $as()); } @Override public final QOM.AlterView $ifExists(boolean newValue) { - return $constructor().apply($view(), $fields(), newValue, $comment(), $renameTo(), $as()); + return $constructor().apply($view(), $fields(), $materialized(), newValue, $comment(), $renameTo(), $as()); } @Override public final QOM.AlterView $comment(Comment newValue) { - return $constructor().apply($view(), $fields(), $ifExists(), newValue, $renameTo(), $as()); + return $constructor().apply($view(), $fields(), $materialized(), $ifExists(), newValue, $renameTo(), $as()); } @Override public final QOM.AlterView $renameTo(Table newValue) { - return $constructor().apply($view(), $fields(), $ifExists(), $comment(), newValue, $as()); + return $constructor().apply($view(), $fields(), $materialized(), $ifExists(), $comment(), newValue, $as()); } @Override public final QOM.AlterView $as(Select newValue) { - return $constructor().apply($view(), $fields(), $ifExists(), $comment(), $renameTo(), newValue); + return $constructor().apply($view(), $fields(), $materialized(), $ifExists(), $comment(), $renameTo(), newValue); } - public final Function6, ? super Collection>, ? super Boolean, ? super Comment, ? super Table, ? super Select, ? extends QOM.AlterView> $constructor() { - return (a1, a2, a3, a4, a5, a6) -> new AlterViewImpl(configuration(), a1, (Collection>) a2, a3, a4, a5, a6); + public final Function7, ? super Collection>, ? super Boolean, ? super Boolean, ? super Comment, ? super Table, ? super Select, ? extends QOM.AlterView> $constructor() { + return (a1, a2, a3, a4, a5, a6, a7) -> new AlterViewImpl(configuration(), a1, (Collection>) a2, a3, a4, a5, a6, a7); } @@ -437,6 +469,7 @@ implements + } diff --git a/jOOQ/src/main/java/org/jooq/impl/DSL.java b/jOOQ/src/main/java/org/jooq/impl/DSL.java index daec92aad7..15f229f791 100644 --- a/jOOQ/src/main/java/org/jooq/impl/DSL.java +++ b/jOOQ/src/main/java/org/jooq/impl/DSL.java @@ -7740,6 +7740,96 @@ public class DSL { return dsl().alterViewIfExists(view); } + /** + * The ALTER MATERIALIZED VIEW statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedView(String) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedView(@Stringly.Name String view) { + return dsl().alterMaterializedView(view); + } + + /** + * The ALTER MATERIALIZED VIEW statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedView(Name) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedView(Name view) { + return dsl().alterMaterializedView(view); + } + + /** + * The ALTER MATERIALIZED VIEW statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedView(Table) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedView(Table view) { + return dsl().alterMaterializedView(view); + } + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedViewIfExists(String) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedViewIfExists(@Stringly.Name String view) { + return dsl().alterMaterializedViewIfExists(view); + } + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedViewIfExists(Name) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedViewIfExists(Name view) { + return dsl().alterMaterializedViewIfExists(view); + } + + /** + * The ALTER MATERIALIZED VIEW IF EXISTS statement. + *

+ * Unlike statement construction methods in the {@link DSLContext} API, this + * creates an unattached, and thus not directly renderable or executable + * statement. It can be used as a subquery or nested in procedural logic. + * + * @see DSLContext#alterMaterializedViewIfExists(Table) + */ + @NotNull @CheckReturnValue + @Support({ POSTGRES, YUGABYTEDB }) + public static org.jooq.AlterViewStep alterMaterializedViewIfExists(Table view) { + return dsl().alterMaterializedViewIfExists(view); + } + /** * The ALTER VIEW statement. *

diff --git a/jOOQ/src/main/java/org/jooq/impl/DefaultDSLContext.java b/jOOQ/src/main/java/org/jooq/impl/DefaultDSLContext.java index a71ff3b0bc..e7099142c9 100644 --- a/jOOQ/src/main/java/org/jooq/impl/DefaultDSLContext.java +++ b/jOOQ/src/main/java/org/jooq/impl/DefaultDSLContext.java @@ -3033,42 +3033,72 @@ public class DefaultDSLContext extends AbstractScope implements DSLContext, Seri @Override public org.jooq.AlterViewStep alterView(@Stringly.Name String view) { - return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, false); + return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, false, false); } @Override public org.jooq.AlterViewStep alterView(Name view) { - return new AlterViewImpl(configuration(), DSL.table(view), null, false); + return new AlterViewImpl(configuration(), DSL.table(view), null, false, false); } @Override public org.jooq.AlterViewStep alterView(Table view) { - return new AlterViewImpl(configuration(), view, null, false); + return new AlterViewImpl(configuration(), view, null, false, false); } @Override public org.jooq.AlterViewStep alterViewIfExists(@Stringly.Name String view) { - return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, true); + return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, false, true); } @Override public org.jooq.AlterViewStep alterViewIfExists(Name view) { - return new AlterViewImpl(configuration(), DSL.table(view), null, true); + return new AlterViewImpl(configuration(), DSL.table(view), null, false, true); } @Override public org.jooq.AlterViewStep alterViewIfExists(Table view) { - return new AlterViewImpl(configuration(), view, null, true); + return new AlterViewImpl(configuration(), view, null, false, true); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedView(@Stringly.Name String view) { + return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, true, false); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedView(Name view) { + return new AlterViewImpl(configuration(), DSL.table(view), null, true, false); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedView(Table view) { + return new AlterViewImpl(configuration(), view, null, true, false); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedViewIfExists(@Stringly.Name String view) { + return new AlterViewImpl(configuration(), DSL.table(DSL.name(view)), null, true, true); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedViewIfExists(Name view) { + return new AlterViewImpl(configuration(), DSL.table(view), null, true, true); + } + + @Override + public org.jooq.AlterViewStep alterMaterializedViewIfExists(Table view) { + return new AlterViewImpl(configuration(), view, null, true, true); } @Override public org.jooq.AlterViewStep alterView(Table view, Field... fields) { - return new AlterViewImpl(configuration(), view, Arrays.asList(fields), false); + return new AlterViewImpl(configuration(), view, Arrays.asList(fields), false, false); } @Override public org.jooq.AlterViewStep alterView(Table view, Collection> fields) { - return new AlterViewImpl(configuration(), view, new QueryPartList<>(fields), false); + return new AlterViewImpl(configuration(), view, new QueryPartList<>(fields), false, false); } @Override diff --git a/jOOQ/src/main/java/org/jooq/impl/Interpreter.java b/jOOQ/src/main/java/org/jooq/impl/Interpreter.java index ff91e3b231..c60861eebb 100644 --- a/jOOQ/src/main/java/org/jooq/impl/Interpreter.java +++ b/jOOQ/src/main/java/org/jooq/impl/Interpreter.java @@ -838,8 +838,10 @@ final class Interpreter { return; } - else if (!existing.options.type().isView()) + else if (existing.options.type() != VIEW && !query.$materialized()) throw objectNotView(table); + else if (existing.options.type() != MATERIALIZED_VIEW && query.$materialized()) + throw objectNotMaterializedView(table); if (query.$renameTo() != null && checkNotExists(schema, query.$renameTo())) existing.name((UnqualifiedName) query.$renameTo().getUnqualifiedName()); diff --git a/jOOQ/src/main/java/org/jooq/impl/ParserImpl.java b/jOOQ/src/main/java/org/jooq/impl/ParserImpl.java index 3b24bb5020..f7159a4f4c 100644 --- a/jOOQ/src/main/java/org/jooq/impl/ParserImpl.java +++ b/jOOQ/src/main/java/org/jooq/impl/ParserImpl.java @@ -3017,6 +3017,11 @@ final class DefaultParseContext extends AbstractScope implements ParseContext { break; + case 'M': + if (parseKeywordIf("MATERIALIZED VIEW")) + return parseAlterView(true); + + break; case 'P': if (parseKeywordIf("PACKAGE")) throw notImplemented("ALTER PACKAGE", "https://github.com/jOOQ/jOOQ/issues/9190"); @@ -3063,7 +3068,7 @@ final class DefaultParseContext extends AbstractScope implements ParseContext { case 'V': if (parseKeywordIf("VIEW")) - return parseAlterView(); + return parseAlterView(false); break; } @@ -4259,7 +4264,7 @@ final class DefaultParseContext extends AbstractScope implements ParseContext { return IGNORE.get(); } - private final DDLQuery parseAlterView() { + private final DDLQuery parseAlterView(boolean materialized) { boolean ifExists = parseKeywordIf("IF EXISTS"); Table oldName = parseTableName(); Field[] fields = EMPTY_FIELD; @@ -4287,14 +4292,22 @@ final class DefaultParseContext extends AbstractScope implements ParseContext { parseKeyword("AS", "TO"); Table newName = parseTableName(); - return ifExists - ? dsl.alterViewIfExists(oldName).renameTo(newName) - : dsl.alterView(oldName).renameTo(newName); + return ( + ifExists + ? materialized + ? dsl.alterMaterializedViewIfExists(oldName) + : dsl.alterViewIfExists(oldName) + : materialized + ? dsl.alterMaterializedView(oldName) + : dsl.alterView(oldName) + ).renameTo(newName); } else if (parseKeywordIf("OWNER TO") && parseUser() != null) return IGNORE.get(); else if (parseKeywordIf("SET")) - return dsl.alterView(oldName).comment(parseOptionsDescription()); + return (materialized + ? dsl.alterMaterializedView(oldName) + : dsl.alterView(oldName)).comment(parseOptionsDescription()); else throw expected("AS", "OWNER TO", "RENAME", "SET"); } diff --git a/jOOQ/src/main/java/org/jooq/impl/QOM.java b/jOOQ/src/main/java/org/jooq/impl/QOM.java index 1281bbf0fb..a234463044 100644 --- a/jOOQ/src/main/java/org/jooq/impl/QOM.java +++ b/jOOQ/src/main/java/org/jooq/impl/QOM.java @@ -1956,6 +1956,7 @@ public final class QOM { { @NotNull Table $view(); @NotNull UnmodifiableList> $fields(); + boolean $materialized(); boolean $ifExists(); @Nullable Comment $comment(); @Nullable Table $renameTo(); @@ -1965,6 +1966,8 @@ public final class QOM { @CheckReturnValue @NotNull AlterView $fields(Collection> fields); @CheckReturnValue + @NotNull AlterView $materialized(boolean materialized); + @CheckReturnValue @NotNull AlterView $ifExists(boolean ifExists); @CheckReturnValue @NotNull AlterView $comment(Comment comment);