package liquibase.change.core;

import liquibase.change.AbstractSQLChange;
import liquibase.change.ChangeMetaData;

/**
 * Allows execution of arbitrary SQL.  This change can be used when existing changes are either don't exist,
 * are not flexible enough, or buggy. 
 */
public class RawSQLChange extends AbstractSQLChange {

    private String comments;
    public RawSQLChange() {
        super("sql", "Custom SQL", ChangeMetaData.PRIORITY_DEFAULT);
    }

    public RawSQLChange(String sql) {
        this();
        setSql(sql);
    }

    public String getComments() {
        return comments;
    }

    public void setComments(String comments) {
        this.comments = comments;
    }

    public String getConfirmationMessage() {
        return "Custom SQL executed";
    }
}

@@ -27,16 +27,71 @@
 ore;%0D%0A%0D%0A
+import java.util.ArrayList;%0D%0Aimport java.util.List;%0D%0A%0D%0A
 import l
@@ -166,16 +166,275 @@
 taData;%0D
+%0Aimport liquibase.database.Database;%0D%0Aimport liquibase.database.core.MSSQLDatabase;%0D%0Aimport liquibase.exception.DatabaseException;%0D%0Aimport liquibase.statement.SqlStatement;%0D%0Aimport liquibase.statement.core.RawSqlStatement;%0D%0Aimport liquibase.util.StringUtils;%0D
 %0A%0D%0A/**%0D%0A
@@ -1123,12 +1123,945 @@
 %0D%0A    %7D%0D
+%0A%0D%0A%09public SqlStatement%5B%5D generateStatements(Database database) %7B%0D%0A%09%09List%3CSqlStatement%3E returnStatements = new ArrayList%3CSqlStatement%3E();%0D%0A%0D%0A%09%09if (StringUtils.trimToNull(getSql()) == null) %7B%0D%0A%09%09%09return new SqlStatement%5B0%5D;%0D%0A%09%09%7D%0D%0A%0D%0A%09%09String processedSQL = getSql().replaceAll(%22%5Cr%5Cn%22, %22%5Cn%22).replaceAll(%22%5Cr%22, %22%5Cn%22);%0D%0A%09%09for (String statement : StringUtils.processMutliLineSQL(processedSQL, isStrippingComments(),%0D%0A%09%09%09%09isSplittingStatements(), getEndDelimiter())) %7B%0D%0A%09%09%09if (database instanceof MSSQLDatabase) %7B%0D%0A%09%09%09%09statement = statement.replaceAll(%22%5Cn%22, %22%5Cr%5Cn%22);%0D%0A%09%09%09%7D%0D%0A%09%09%09%0D%0A%09%09%09String escapedStatement;%0D%0A%09%09%09try %7B%0D%0A%09%09%09%09escapedStatement = database.getConnection().nativeSQL(statement);%0D%0A%09%09%09%7D catch (DatabaseException e) %7B%0D%0A%09%09%09%09escapedStatement = statement;%0D%0A%09%09%09%7D%0D%0A%0D%0A%09%09%09returnStatements.add(new RawSqlStatement(escapedStatement, getEndDelimiter()));%0D%0A%09%09%7D%0D%0A%0D%0A%09%09return returnStatements.toArray(new SqlStatement%5BreturnStatements.size()%5D);%0D%0A%09%7D%0D
 %0A%7D%0D%0A

Convert raw query to native representation