diff --git a/pom.xml b/pom.xml
index 20e190a..5644e4c 100644
--- a/pom.xml
+++ b/pom.xml
@@ -363,6 +363,24 @@
+
+ mysql
+ mysql-connector-java
+ 8.0.28
+ provided
+
+
+ org.mariadb.jdbc
+ mariadb-java-client
+ 2.7.5
+ provided
+
+
+ com.microsoft.sqlserver
+ mssql-jdbc
+ 10.2.0.jre8
+ provided
+
org.appng
appng-testsupport
diff --git a/src/main/java/org/appng/application/manager/business/SqlExecutor.java b/src/main/java/org/appng/application/manager/business/SqlExecutor.java
index 5f7f392..0e59690 100644
--- a/src/main/java/org/appng/application/manager/business/SqlExecutor.java
+++ b/src/main/java/org/appng/application/manager/business/SqlExecutor.java
@@ -16,6 +16,7 @@
package org.appng.application.manager.business;
import java.sql.ResultSet;
+import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@@ -38,9 +39,7 @@
import org.flywaydb.core.api.configuration.Configuration;
import org.flywaydb.core.api.configuration.FluentConfiguration;
import org.flywaydb.core.internal.database.hsqldb.HSQLDBParser;
-import org.flywaydb.core.internal.database.mysql.MySQLParser;
import org.flywaydb.core.internal.database.postgresql.PostgreSQLParser;
-import org.flywaydb.core.internal.database.sqlserver.SQLServerParser;
import org.flywaydb.core.internal.parser.Parser;
import org.flywaydb.core.internal.parser.ParsingContext;
import org.flywaydb.core.internal.resource.StringResource;
@@ -54,13 +53,16 @@
import org.springframework.jdbc.support.rowset.SqlRowSet;
import org.springframework.jdbc.support.rowset.SqlRowSetMetaData;
import org.springframework.stereotype.Component;
+import org.springframework.util.ClassUtils;
import com.google.common.collect.Streams;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
+import lombok.extern.slf4j.Slf4j;
+@Slf4j
@Component
public class SqlExecutor extends ServiceAware implements DataProvider, ActionProvider {
@@ -161,24 +163,41 @@ public static class SqlStatement {
public List getQueries(String sql, DatabaseConnection conn) {
Configuration configuration = new FluentConfiguration().dataSource(conn.getJdbcUrl(), conn.getUserName(),
conn.getPasswordPlain());
- Parser parser = getParser(conn.getType(), configuration);
- SqlScript sqlScript = new ParserSqlScript(parser, new StringResource(sql), null, false);
- return Streams.stream(sqlScript.getSqlStatements())
- .map(org.flywaydb.core.internal.sqlscript.SqlStatement::getSql).collect(Collectors.toList());
+ try {
+ Parser parser = getParser(conn.getType(), configuration);
+ SqlScript sqlScript = new ParserSqlScript(parser, new StringResource(sql), null, false);
+ return Streams.stream(sqlScript.getSqlStatements())
+ .map(org.flywaydb.core.internal.sqlscript.SqlStatement::getSql).collect(Collectors.toList());
+ } catch (ReflectiveOperationException e) {
+ log.error("failed creating parser", e);
+ }
+ return new ArrayList<>();
}
- protected Parser getParser(DatabaseType type, Configuration configuration) {
- ParsingContext parsingContext = new ParsingContext();
+ protected Parser getParser(DatabaseType type, Configuration configuration) throws ReflectiveOperationException {
switch (type) {
case MYSQL:
- return new MySQLParser(configuration, parsingContext);
+ if (configuration.getUrl().contains(":mariadb:")) {
+ return createParser("mysql.mariadb.MariaDBDatabaseType", configuration);
+ } else {
+ return createParser("mysql.MySQLDatabaseType", configuration);
+ }
case MSSQL:
- return new SQLServerParser(configuration, parsingContext);
+ return createParser("sqlserver.SQLServerDatabaseType", configuration);
case POSTGRESQL:
- return new PostgreSQLParser(configuration, parsingContext);
+ return new PostgreSQLParser(configuration, new ParsingContext());
default:
- return new HSQLDBParser(configuration, parsingContext);
+ return new HSQLDBParser(configuration, new ParsingContext());
+ }
+ }
+
+ private Parser createParser(String className, Configuration configuration) throws ReflectiveOperationException {
+ String packagePrefix = "org.flywaydb.database.";
+ if (!ClassUtils.isPresent(packagePrefix + className, getClass().getClassLoader())) {
+ packagePrefix = "org.flywaydb.core.internal.database.";
}
+ return ((org.flywaydb.core.internal.database.DatabaseType) Class.forName(packagePrefix + className)
+ .newInstance()).createParser(configuration, null, new ParsingContext());
}
}
diff --git a/src/test/java/org/appng/application/manager/business/SqlExecutorTest.java b/src/test/java/org/appng/application/manager/business/SqlExecutorTest.java
index 4e63206..9e5687a 100644
--- a/src/test/java/org/appng/application/manager/business/SqlExecutorTest.java
+++ b/src/test/java/org/appng/application/manager/business/SqlExecutorTest.java
@@ -16,6 +16,10 @@
package org.appng.application.manager.business;
import org.appng.api.support.CallableAction;
+import org.appng.core.domain.DatabaseConnection.DatabaseType;
+import org.flywaydb.core.api.configuration.ClassicConfiguration;
+import org.flywaydb.core.internal.parser.Parser;
+import org.junit.Assert;
import org.junit.Test;
import org.springframework.test.context.ContextConfiguration;
@@ -34,4 +38,21 @@ public void testExecute() throws Exception {
validate(callableAction.getAction());
}
+ @Test
+ public void testParser() throws ReflectiveOperationException {
+ assertType("MySQLParser", "jdbc:mysql://localhost", DatabaseType.MYSQL);
+ assertType("MariaDBParser", "jdbc:mariadb://localhost", DatabaseType.MYSQL);
+ assertType("SQLServerParser", "jdbc:sqlserver://localhost", DatabaseType.MSSQL);
+ assertType("PostgreSQLParser", "jdbc:postgresql://localhost", DatabaseType.POSTGRESQL);
+ assertType("HSQLDBParser", "jdbc:hsqldb:hsql://localhost", DatabaseType.HSQL);
+ }
+
+ private void assertType(String className, String url, DatabaseType type) throws ReflectiveOperationException {
+ ClassicConfiguration cfg = new ClassicConfiguration();
+ cfg.setDataSource(url, null, null);
+ Parser parser = new SqlExecutor().getParser(type, cfg);
+ Assert.assertNotNull(parser);
+ Assert.assertEquals(className, parser.getClass().getSimpleName());
+ }
+
}