diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AbstractMigrateMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AbstractMigrateMojo.java index 8c8ac3f984..c1fd88058a 100644 --- a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AbstractMigrateMojo.java +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AbstractMigrateMojo.java @@ -100,4 +100,13 @@ public abstract class AbstractMigrateMojo extends AbstractMigrationsMojo { return f; } + + static final String fileName(String id, String fileName, String suffix) { + String result = fileName != null ? fileName : id + "-" + suffix; + + if (!result.endsWith(".sql")) + result = result + ".sql"; + + return result; + } } diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/SnapshotMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddSnapshotMojo.java similarity index 66% rename from jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/SnapshotMojo.java rename to jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddSnapshotMojo.java index de7707772b..0d2adf5d60 100644 --- a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/SnapshotMojo.java +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddSnapshotMojo.java @@ -44,6 +44,8 @@ import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; import java.io.File; import java.io.FileWriter; import java.io.PrintWriter; +import java.nio.file.Files; +import java.nio.file.StandardOpenOption; import java.util.EnumSet; import org.jooq.DDLExportConfiguration; @@ -56,19 +58,26 @@ import org.jooq.Queries; import org.jooq.exception.DataMigrationVerificationException; import org.apache.maven.plugins.annotations.Mojo; +import org.apache.maven.plugins.annotations.Parameter; /** - * Create a snapshot of the current version. + * Create a snapshot of the current version and add it to the migration. * * @author Lukas Eder */ @Mojo( - name = "snapshot", + name = "addSnapshot", defaultPhase = GENERATE_SOURCES, requiresDependencyResolution = TEST, threadSafe = true ) -public class SnapshotMojo extends AbstractMigrateMojo { +public class AddSnapshotMojo extends AbstractMigrateMojo { + + /** + * The file name to add untracked objects to, defaulting to [version]-added.sql. + */ + @Parameter(property = "jooq.migrate.addSnapshot.fileName") + String fileName; @Override final void execute1(Migration migration) throws Exception { @@ -82,26 +91,21 @@ public class SnapshotMojo extends AbstractMigrateMojo { } HistoryVersion current = history.current(); - File file = new File(file(directory), current.version().id() + "/snapshots/" + current.version().id() + "-snapshot.sql"); + File file = new File(file(directory), current.version().id() + "/snapshots/" + fileName(current.version().id(), fileName, "snapshot")); file.getParentFile().mkdirs(); - try (FileWriter f = new FileWriter(file); - PrintWriter w = new PrintWriter(f) - ) { - DDLExportConfiguration config = new DDLExportConfiguration(); + DDLExportConfiguration config = new DDLExportConfiguration(); - // Don't create schema in snapshots if it is managed by the migration. - if (TRUE.equals(migration.settings().isMigrationSchemataCreateSchemaIfNotExists())) - config = config.flags(EnumSet.complementOf(EnumSet.of(DDLFlag.SCHEMA))); + // Don't create schema in snapshots if it is managed by the migration. + if (TRUE.equals(migration.settings().isMigrationSchemataCreateSchemaIfNotExists())) + config = config.flags(EnumSet.complementOf(EnumSet.of(DDLFlag.SCHEMA))); - Meta meta = current.version().meta(); - String export = meta.ddl(config).toString(); + Meta meta = current.version().meta(); + String export = meta.ddl(config).toString(); - if (getLog().isInfoEnabled()) - getLog().info("Writing snapshot to: " + file + "\n" + export); + if (getLog().isInfoEnabled()) + getLog().info("Writing snapshot to: " + file + "\n" + export); - w.println(export); - w.flush(); - } + Files.writeString(file.toPath(), export, StandardOpenOption.CREATE, StandardOpenOption.TRUNCATE_EXISTING); } } diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddUntrackedMojo.java similarity index 66% rename from jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddMojo.java rename to jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddUntrackedMojo.java index 2372811af3..756b9e3e56 100644 --- a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddMojo.java +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/AddUntrackedMojo.java @@ -44,6 +44,8 @@ import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; import java.io.File; import java.io.FileWriter; import java.io.PrintWriter; +import java.nio.file.Files; +import java.nio.file.StandardOpenOption; import java.util.EnumSet; import org.jooq.Commit; @@ -56,6 +58,7 @@ import org.jooq.Migration; import org.jooq.Queries; import org.apache.maven.plugins.annotations.Mojo; +import org.apache.maven.plugins.annotations.Parameter; /** * Add objects from the configured database schemas to the migration. @@ -63,12 +66,18 @@ import org.apache.maven.plugins.annotations.Mojo; * @author Lukas Eder */ @Mojo( - name = "add", + name = "addUntracked", defaultPhase = GENERATE_SOURCES, requiresDependencyResolution = TEST, threadSafe = true ) -public class AddMojo extends AbstractMigrateMojo { +public class AddUntrackedMojo extends AbstractMigrateMojo { + + /** + * The file name to add untracked objects to, defaulting to [version]-added.sql. + */ + @Parameter(property = "jooq.migrate.addUntracked.fileName") + String fileName; @Override final void execute1(Migration migration) throws Exception { @@ -77,26 +86,25 @@ public class AddMojo extends AbstractMigrateMojo { if (untracked.queries().length > 0) { History history = migration.dsl().migrations().history(); String id = history.available() ? history.current().version().id() : migration.from().id(); - - File file = new File(file(directory), id + "/increments/" + id + "-added.sql"); + File file = new File(file(directory), id + "/increments/" + fileName(id, fileName, "added")); file.getParentFile().mkdirs(); - try (FileWriter f = new FileWriter(file); - PrintWriter w = new PrintWriter(f) - ) { - if (getLog().isInfoEnabled()) - getLog().info("Writing untracked objects to: " + file + "\n" + untracked); + StringBuilder sb = new StringBuilder(); - w.println("-- Untracked objects of version: " + id); + if (getLog().isInfoEnabled()) + getLog().info("Writing untracked objects to: " + file + "\n" + untracked); - if (Commit.ROOT.equals(id)) { - w.println("-- Objects that were present before the root version will not be created during migration on any databases."); - w.println("-- They are added to this file only as a baseline."); - } + sb.append("-- Untracked objects of version: " + id + "\n"); - w.println(untracked); - w.flush(); + if (Commit.ROOT.equals(id)) { + sb.append("-- Objects that were present before the root version will not be created during migration on any databases.\n"); + sb.append("-- They are added to this file only as a baseline.\n"); } + + sb.append(untracked); + sb.append("\n"); + Files.writeString(file.toPath(), sb.toString(), StandardOpenOption.CREATE, StandardOpenOption.APPEND); } } + } diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/HistoryMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogHistoryMojo.java similarity index 56% rename from jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/HistoryMojo.java rename to jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogHistoryMojo.java index fd6341e656..46dfeb4f7d 100644 --- a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/HistoryMojo.java +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogHistoryMojo.java @@ -39,16 +39,9 @@ package org.jooq.migrations.maven; import static org.apache.maven.plugins.annotations.LifecyclePhase.GENERATE_SOURCES; import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; -import static org.jooq.tools.StringUtils.isEmpty; -import java.time.Instant; - -import org.jooq.HistoryVersion; import org.jooq.Migration; -import org.jooq.Version; -import org.jooq.tools.StringUtils; -import org.apache.maven.plugin.logging.Log; import org.apache.maven.plugins.annotations.Mojo; /** @@ -57,39 +50,15 @@ import org.apache.maven.plugins.annotations.Mojo; * @author Lukas Eder */ @Mojo( - name = "history", + name = "logHistory", defaultPhase = GENERATE_SOURCES, requiresDependencyResolution = TEST, threadSafe = true ) -public class HistoryMojo extends AbstractMigrateMojo { +public class LogHistoryMojo extends AbstractMigrateMojo { @Override final void execute1(Migration migration) throws Exception { - if (getLog().isInfoEnabled()) - for (HistoryVersion version : migration.dsl().migrations().history()) - log(getLog(), version); - } - - static final void log(Log log, HistoryVersion version) { - log.info(" " + string(version.migratedAt()) + " - Version: " + string(version.version())); - - if (version.version().parents().size() > 1) { - log.info(" Merged parents: "); - - for (Version p : version.version().parents()) - log.info(" - " + string(p)); - } - } - - private static final String string(Instant instant) { - if (instant == null) - return "0000-00-00T00:00:00.000Z"; - else - return StringUtils.rightPad(instant.toString(), 24); - } - - private static final String string(Version version) { - return version.id() + (!isEmpty(version.message()) ? " (" + version.message() + ")" : ""); + migration.logHistory(); } } diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMigrationMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMigrationMojo.java new file mode 100644 index 0000000000..6bf14225df --- /dev/null +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMigrationMojo.java @@ -0,0 +1,64 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Other licenses: + * ----------------------------------------------------------------------------- + * Commercial licenses for this work are available. These replace the above + * Apache-2.0 license and offer limited warranties, support, maintenance, and + * commercial database integrations. + * + * For more information, please visit: https://www.jooq.org/legal/licensing + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + */ +package org.jooq.migrations.maven; + +import static org.apache.maven.plugins.annotations.LifecyclePhase.GENERATE_SOURCES; +import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; + +import org.jooq.Migration; + +import org.apache.maven.plugins.annotations.Mojo; + +/** + * Log the outstanding migration queries. + * + * @author Lukas Eder + */ +@Mojo( + name = "logMigration", + defaultPhase = GENERATE_SOURCES, + requiresDependencyResolution = TEST, + threadSafe = true +) +public class LogMigrationMojo extends AbstractMigrateMojo { + + @Override + final void execute1(Migration migration) throws Exception { + migration.logMigration(); + } +} diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMojo.java index 6b9972dd73..c608895adf 100644 --- a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMojo.java +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogMojo.java @@ -37,25 +37,15 @@ */ package org.jooq.migrations.maven; -import static java.util.stream.Collectors.toList; import static org.apache.maven.plugins.annotations.LifecyclePhase.GENERATE_SOURCES; import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; -import java.util.List; -import java.util.stream.Collectors; -import java.util.stream.StreamSupport; - -import org.jooq.History; -import org.jooq.HistoryVersion; import org.jooq.Migration; -import org.jooq.Query; -import org.jooq.tools.StringUtils; -import org.apache.maven.plugin.logging.Log; import org.apache.maven.plugins.annotations.Mojo; /** - * Log the queries of the outstanding migration. + * Log various aspects of the current state of the database migration. * * @author Lukas Eder */ @@ -69,40 +59,8 @@ public class LogMojo extends AbstractMigrateMojo { @Override final void execute1(Migration migration) throws Exception { - if (getLog().isInfoEnabled()) { - History history = migration.dsl().migrations().history(); - List versions = StreamSupport - .stream(history.spliterator(), false) - .collect(toList()); - - if (versions.isEmpty()) { - getLog().info("No migration history available yet"); - } - else { - getLog().info("Migration history"); - - for (HistoryVersion version : versions.subList( - Math.max(0, versions.size() - 5), - versions.size() - )) { - HistoryMojo.log(getLog(), version); - } - } - - Query[] queries = migration.queries().queries(); - - getLog().info("Outstanding queries from " + migration.from() + " to " + migration.to() + ": " - + (queries.length == 0 ? "none" : "") - ); - - log(getLog(), queries); - } - } - - static final void log(Log log, Query[] queries) { - int pad = ("" + queries.length).length(); - - for (int i = 0; i < queries.length; i++) - log.info(" Query " + StringUtils.leftPad("" + (i + 1), pad) + ": " + queries[i]); + migration.logHistory(); + migration.logMigration(); + migration.logUntracked(); } } diff --git a/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogUntrackedMojo.java b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogUntrackedMojo.java new file mode 100644 index 0000000000..0dcc44ad54 --- /dev/null +++ b/jOOQ-migrations-maven/src/main/java/org/jooq/migrations/maven/LogUntrackedMojo.java @@ -0,0 +1,64 @@ +/* + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + * Other licenses: + * ----------------------------------------------------------------------------- + * Commercial licenses for this work are available. These replace the above + * Apache-2.0 license and offer limited warranties, support, maintenance, and + * commercial database integrations. + * + * For more information, please visit: https://www.jooq.org/legal/licensing + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + */ +package org.jooq.migrations.maven; + +import static org.apache.maven.plugins.annotations.LifecyclePhase.GENERATE_SOURCES; +import static org.apache.maven.plugins.annotations.ResolutionScope.TEST; + +import org.jooq.Migration; + +import org.apache.maven.plugins.annotations.Mojo; + +/** + * Log the untracked database changes in the migrated schemas. + * + * @author Lukas Eder + */ +@Mojo( + name = "logUntracked", + defaultPhase = GENERATE_SOURCES, + requiresDependencyResolution = TEST, + threadSafe = true +) +public class LogUntrackedMojo extends AbstractMigrateMojo { + + @Override + final void execute1(Migration migration) throws Exception { + migration.logUntracked(); + } +} diff --git a/jOOQ/src/main/java/org/jooq/FilePattern.java b/jOOQ/src/main/java/org/jooq/FilePattern.java index 503df706e3..d06cd92e31 100644 --- a/jOOQ/src/main/java/org/jooq/FilePattern.java +++ b/jOOQ/src/main/java/org/jooq/FilePattern.java @@ -330,12 +330,15 @@ public final class FilePattern { ) throws java.io.IOException { if (file.isFile()) { if (regex == null || regex.matcher(file.getCanonicalPath().replace("\\", "/")).matches()) { - log.info("Reading from: " + file + " [*]"); + if (log.isDebugEnabled()) + log.debug("Reading from: " + file + " [*]"); + load0(file, loader); } } else if (file.isDirectory()) { - log.info("Reading from: " + file); + if (log.isDebugEnabled()) + log.debug("Reading from: " + file); File[] files = file.listFiles(); diff --git a/jOOQ/src/main/java/org/jooq/Migration.java b/jOOQ/src/main/java/org/jooq/Migration.java index 71c6c91d43..dc2e1be25d 100644 --- a/jOOQ/src/main/java/org/jooq/Migration.java +++ b/jOOQ/src/main/java/org/jooq/Migration.java @@ -90,6 +90,22 @@ public interface Migration extends Scope { @NotNull Queries untracked(); + /** + * Log the most recent versions from the migration history to the configured + * logger. + */ + void logHistory() throws DataMigrationVerificationException; + + /** + * Log the outstanding migration to the configured logger. + */ + void logMigration() throws DataMigrationVerificationException; + + /** + * Log the untracked database changes of the migration schemas. + */ + void logUntracked() throws DataMigrationVerificationException; + /** * Verify the correctness of a migration. * diff --git a/jOOQ/src/main/java/org/jooq/impl/MigrationImpl.java b/jOOQ/src/main/java/org/jooq/impl/MigrationImpl.java index b8a72adf7c..54068c94f1 100644 --- a/jOOQ/src/main/java/org/jooq/impl/MigrationImpl.java +++ b/jOOQ/src/main/java/org/jooq/impl/MigrationImpl.java @@ -41,7 +41,6 @@ import static java.lang.Boolean.FALSE; import static java.lang.Boolean.TRUE; import static org.jooq.impl.DSL.createSchemaIfNotExists; import static org.jooq.impl.DSL.dropSchemaIfExists; -import static org.jooq.impl.DSL.dropTableIfExists; import static org.jooq.impl.DSL.name; import static org.jooq.impl.DSL.table; import static org.jooq.impl.History.HISTORY; @@ -53,13 +52,16 @@ import static org.jooq.impl.HistoryStatus.REVERTING; import static org.jooq.impl.HistoryStatus.STARTING; import static org.jooq.impl.HistoryStatus.SUCCESS; import static org.jooq.impl.SchemaImpl.DEFAULT_SCHEMA; +import static org.jooq.impl.Tools.collect; import static org.jooq.impl.Tools.map; import static org.jooq.tools.StringUtils.isEmpty; import java.io.PrintWriter; import java.io.StringWriter; import java.sql.Timestamp; +import java.time.Instant; import java.util.HashSet; +import java.util.List; import java.util.Set; import org.jooq.Commit; @@ -68,6 +70,7 @@ import org.jooq.Configuration; import org.jooq.Constants; import org.jooq.ContextTransactionalRunnable; import org.jooq.Files; +import org.jooq.HistoryVersion; import org.jooq.Meta; import org.jooq.Migration; import org.jooq.MigrationContext; @@ -518,6 +521,66 @@ final class MigrationImpl extends AbstractScope implements Migration { } } + @Override + public final void logHistory() { + List versions = collect(() -> history.iterator()); + + if (versions.isEmpty()) { + log.info("No migration history available yet"); + } + else { + log.info("Migration history"); + + for (HistoryVersion version : versions.subList( + Math.max(0, versions.size() - 5), + versions.size() + )) { + log(version); + } + } + } + + static final void log(HistoryVersion version) { + log.info(" " + string(version.migratedAt()) + " - Version: " + string(version.version())); + + if (version.version().parents().size() > 1) { + log.info(" Merged parents: "); + + for (Version p : version.version().parents()) + log.info(" - " + string(p)); + } + } + + private static final String string(Instant instant) { + if (instant == null) + return "0000-00-00T00:00:00.000Z"; + else + return StringUtils.rightPad(instant.toString(), 24); + } + + private static final String string(Version version) { + return version.id() + (!isEmpty(version.message()) ? " (" + version.message() + ")" : ""); + } + + @Override + public final void logMigration() { + Query[] q = queries().queries(); + log.info("Outstanding queries from " + from().id() + " to " + to().id() + ": " + (q.length == 0 ? "none" : "")); + log(q); + } + + @Override + public final void logUntracked() { + Query[] q = untracked().queries(); + log.info("Untracked changes at " + from().id() + ": " + (q.length == 0 ? "none" : "")); + log(q); + } + + static final void log(Query[] queries) { + for (int i = 0; i < queries.length; i++) + log.info(queries[i]); + } + // ------------------------------------------------------------------------- // The Object API // ------------------------------------------------------------------------- diff --git a/pom.xml b/pom.xml index a477cd63b6..cfc89b631b 100644 --- a/pom.xml +++ b/pom.xml @@ -901,7 +901,6 @@ -