diff --git a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/DBMigrationEngine.java b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/DBMigrationEngine.java index 5f8540cef20050d2f60e2048e0ecd32ff3f0bc97..64bb61c1fbd3cda9079528988fc7f60334df7d2b 100644 --- a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/DBMigrationEngine.java +++ b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/DBMigrationEngine.java @@ -74,6 +74,8 @@ public final class DBMigrationEngine private final IMigrationStepExecutor migrationStepExecutor; + private final IMigrationStepExecutor migrationStepExecutorAdmin; + /** * Creates an instance for the specified DAO factory and SQL script provider. * @@ -87,6 +89,7 @@ public final class DBMigrationEngine logDAO = daoFactory.getDatabaseVersionLogDAO(); scriptExecutor = daoFactory.getSqlScriptExecutor(); migrationStepExecutor = daoFactory.getMigrationStepExecutor(); + migrationStepExecutorAdmin = daoFactory.getMigrationStepExecutorAdmin(); this.scriptProvider = scriptProvider; this.shouldCreateFromScratch = shouldCreateFromScratch; } @@ -256,11 +259,15 @@ public final class DBMigrationEngine throw new EnvironmentFailureException(message); } final long time = System.currentTimeMillis(); + migrationStepExecutorAdmin.init(migrationScript); migrationStepExecutor.init(migrationScript); + migrationStepExecutorAdmin.performPreMigration(); migrationStepExecutor.performPreMigration(); scriptExecutor.execute(migrationScript, true, logDAO); migrationStepExecutor.performPostMigration(); + migrationStepExecutorAdmin.performPostMigration(); migrationStepExecutor.finish(); + migrationStepExecutorAdmin.finish(); if (operationLog.isInfoEnabled()) { operationLog.info("Successfully migrated from version " + version + " to " diff --git a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/IDAOFactory.java b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/IDAOFactory.java index 200168f2424a7f34df1ed9ca8d86c432c74a91b7..3cefac8c8057d341c4e72f2f8c56c66d353cbd25 100644 --- a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/IDAOFactory.java +++ b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/IDAOFactory.java @@ -50,4 +50,10 @@ public interface IDAOFactory * Returns the java migration step executor. */ public IMigrationStepExecutor getMigrationStepExecutor(); + + /** + * Returns the java migration step executor to be run as the database admin user. + */ + public IMigrationStepExecutor getMigrationStepExecutorAdmin(); + } diff --git a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/h2/H2DAOFactory.java b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/h2/H2DAOFactory.java index 28a77690fabc262f1505e236ad558e945583f525..546b2282b886a55f04ea4f762fb014e16fdf58ac 100644 --- a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/h2/H2DAOFactory.java +++ b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/h2/H2DAOFactory.java @@ -49,6 +49,8 @@ public class H2DAOFactory implements IDAOFactory private final IMigrationStepExecutor migrationStepExecutor; + private final IMigrationStepExecutor migrationStepExecutorAdmin; + /** * Creates an instance based on the specified configuration context. */ @@ -56,7 +58,8 @@ public class H2DAOFactory implements IDAOFactory { final DataSource dataSource = context.getDataSource(); sqlScriptExecutor = new SqlScriptExecutor(dataSource, context.isScriptSingleStepMode()); - migrationStepExecutor = new MigrationStepExecutor(dataSource); + migrationStepExecutor = new MigrationStepExecutor(dataSource, false); + migrationStepExecutorAdmin = new MigrationStepExecutor(context.getAdminDataSource(), true); databaseVersionLogDAO = new DatabaseVersionLogDAO(dataSource, context.getLobHandler()); try { @@ -95,4 +98,9 @@ public class H2DAOFactory implements IDAOFactory return migrationStepExecutor; } + public IMigrationStepExecutor getMigrationStepExecutorAdmin() + { + return migrationStepExecutorAdmin; + } + } diff --git a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutor.java b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutor.java index e58a76896b9d2790e399817c056a87857e5f977d..eac57a47cf1bc10f50c6d3de90c981fd85c9eb89 100644 --- a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutor.java +++ b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutor.java @@ -49,16 +49,22 @@ public class MigrationStepExecutor extends SimpleJdbcDaoSupport implements IMigr private static final String JAVA_MIGRATION_STEP_PREFIX = "--JAVA"; + private static final String JAVA_ADMIN_MIGRATION_STEP_PREFIX = "--JAVA_ADMIN"; + + private final boolean isAdmin; + private IMigrationStep migrationStep; private boolean inited; - public MigrationStepExecutor(final DataSource dataSource) + public MigrationStepExecutor(final DataSource dataSource, boolean isAdmin) { setDataSource(dataSource); + this.isAdmin = isAdmin; } - private final static IMigrationStep tryExtractMigrationStep(final Script sqlScript) + private final static IMigrationStep tryExtractMigrationStep(final Script sqlScript, + final boolean isAdmin) { assert sqlScript != null : "SQL script not provided"; @@ -71,17 +77,20 @@ public class MigrationStepExecutor extends SimpleJdbcDaoSupport implements IMigr ParserUtilities.tryGetFirstAcceptedLine(content, NonEmptyLineFilter.INSTANCE); if (firstNonEmptyLineOrNull != null) { - return tryExtractMigrationStepFromLine(firstNonEmptyLineOrNull.getText()); + return tryExtractMigrationStepFromLine(firstNonEmptyLineOrNull.getText(), isAdmin); } return null; } - private final static IMigrationStep tryExtractMigrationStepFromLine(final String lineToProcess) + private final static IMigrationStep tryExtractMigrationStepFromLine(final String lineToProcess, + final boolean isAdmin) { final String line = StringUtils.deleteWhitespace(lineToProcess); - if (line != null && line.startsWith(JAVA_MIGRATION_STEP_PREFIX)) + final String prefix = + isAdmin ? JAVA_ADMIN_MIGRATION_STEP_PREFIX : JAVA_MIGRATION_STEP_PREFIX; + if (line != null && line.startsWith(prefix)) { - final String className = StringUtils.removeStart(line, JAVA_MIGRATION_STEP_PREFIX); + final String className = StringUtils.removeStart(line, prefix); try { return (IMigrationStep) ClassUtils.createInstance(Class.forName(className)); @@ -101,7 +110,7 @@ public class MigrationStepExecutor extends SimpleJdbcDaoSupport implements IMigr public final void init(final Script migrationScript) { - migrationStep = tryExtractMigrationStep(migrationScript); + migrationStep = tryExtractMigrationStep(migrationScript, isAdmin); if (migrationStep != null) { operationLog.info(String.format( diff --git a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/postgresql/PostgreSQLDAOFactory.java b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/postgresql/PostgreSQLDAOFactory.java index 595df6dd41c52950a3a3409db79a8b0e69805276..337a31b369f473e42d264123a9336a398de3d870 100644 --- a/dbmigration/source/java/ch/systemsx/cisd/dbmigration/postgresql/PostgreSQLDAOFactory.java +++ b/dbmigration/source/java/ch/systemsx/cisd/dbmigration/postgresql/PostgreSQLDAOFactory.java @@ -50,6 +50,8 @@ public class PostgreSQLDAOFactory implements IDAOFactory private final IMigrationStepExecutor migrationStepExecutor; + private final IMigrationStepExecutor migrationStepExecutorAdmin; + /** * Creates an instance based on the specified configuration context. */ @@ -57,7 +59,8 @@ public class PostgreSQLDAOFactory implements IDAOFactory { final DataSource dataSource = context.getDataSource(); sqlScriptExecutor = new SqlScriptExecutor(dataSource, context.isScriptSingleStepMode()); - migrationStepExecutor = new MigrationStepExecutor(dataSource); + migrationStepExecutor = new MigrationStepExecutor(dataSource, false); + migrationStepExecutorAdmin = new MigrationStepExecutor(context.getAdminDataSource(), true); databaseVersionLogDAO = new DatabaseVersionLogDAO(dataSource, context.getLobHandler()); try { @@ -99,4 +102,9 @@ public class PostgreSQLDAOFactory implements IDAOFactory return migrationStepExecutor; } + public IMigrationStepExecutor getMigrationStepExecutorAdmin() + { + return migrationStepExecutorAdmin; + } + } diff --git a/dbmigration/sourceTest/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutorTest.java b/dbmigration/sourceTest/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutorTest.java index e295bf0ae3467556df805a59f58964924eb356f8..5b8c01711b0cc72fe5944f96a65990314646bccd 100644 --- a/dbmigration/sourceTest/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutorTest.java +++ b/dbmigration/sourceTest/java/ch/systemsx/cisd/dbmigration/java/MigrationStepExecutorTest.java @@ -65,7 +65,8 @@ public final class MigrationStepExecutorTest @Test public final void testHappyCase() { - final MigrationStepExecutor migrationStepExecutor = new MigrationStepExecutor(dataSource); + final MigrationStepExecutor migrationStepExecutor = + new MigrationStepExecutor(dataSource, false); Script script = new Script("001To002.sql", "-- JAVA ch.systemsx.cisd.dbmigration.java.MigrationStepFrom001To002"); @@ -84,10 +85,34 @@ public final class MigrationStepExecutorTest + "migration script '001To002.sql'.", logRecorder.getLogContent()); } + @Test + public final void testHappyCaseAdmin() + { + final MigrationStepExecutor migrationStepExecutor = + new MigrationStepExecutor(dataSource, true); + Script script = + new Script("001To002.sql", + "-- JAVA_ADMIN ch.systemsx.cisd.dbmigration.java.MigrationStepFrom001To002"); + migrationStepExecutor.init(script); + migrationStepExecutor.performPreMigration(); + migrationStepExecutor.performPostMigration(); + migrationStepExecutor.finish(); + assertEquals("Migration step class 'MigrationStepFrom001To002' found for " + + "migration script '001To002.sql'.", logRecorder.getLogContent()); + logRecorder.resetLogContent(); + script = + new Script("001To002.sql", "\n\n \n" + + "--JAVA_ADMIN ch.systemsx.cisd.dbmigration.java.MigrationStepFrom001To002"); + migrationStepExecutor.init(script); + assertEquals("Migration step class 'MigrationStepFrom001To002' found for " + + "migration script '001To002.sql'.", logRecorder.getLogContent()); + } + @Test public final void testFinish() { - final MigrationStepExecutor migrationStepExecutor = new MigrationStepExecutor(dataSource); + final MigrationStepExecutor migrationStepExecutor = + new MigrationStepExecutor(dataSource, false); final Script script = new Script("001To002.sql", "-- JAVA ch.systemsx.cisd.dbmigration.java.MigrationStepFrom001To002"); @@ -109,7 +134,8 @@ public final class MigrationStepExecutorTest @Test public final void testUnhappyCase() { - final MigrationStepExecutor migrationStepExecutor = new MigrationStepExecutor(dataSource); + final MigrationStepExecutor migrationStepExecutor = + new MigrationStepExecutor(dataSource, false); Script script = new Script("002To003.sql", "\n-- This is a comment\n" + "-- JAVA ch.systemsx.cisd.dbmigration.java.MigrationStepFrom002To003"); @@ -144,7 +170,8 @@ public final class MigrationStepExecutorTest @Test public final void testClassNotFound() { - final MigrationStepExecutor migrationStepExecutor = new MigrationStepExecutor(dataSource); + final MigrationStepExecutor migrationStepExecutor = + new MigrationStepExecutor(dataSource, false); final Script script = new Script("003To004.sql", "-- JAVA ch.systemsx.cisd.dbmigration.java.MigrationStepFrom003To003");