1. Обзор
В нашей предыдущей статье мы показали Liquibase как инструмент для управления схемами и данными баз данных.
В этой статье мы подробнее рассмотрим функцию отката и то, как мы можем отменить операцию Liquibase.
Естественно, это критическая особенность любой системы производственного уровня.
2. Категории миграций Liquibase
Существует две категории операций Liquibase, в результате которых создается оператор отката по-разному:
- автоматический , где миграция может детерминировано генерировать шаги, необходимые для отката
- manual , где нам нужно выполнить команду отката, потому что инструкция миграции не может использоваться для детерминированной идентификации оператора
Например, откат оператора «создать таблицу»
будет заключаться в « удалении»
созданной таблицы . Это можно определить без сомнений, и поэтому оператор отката может быть сгенерирован автоматически.
С другой стороны, оператор отката для команды «удалить таблицу»
определить невозможно . Невозможно определить последнее состояние таблицы, поэтому оператор отката не может быть сгенерирован автоматически. Эти типы операторов миграции требуют ручных инструкций по откату.
3. Написание простого оператора отката
Давайте напишем простой набор изменений, который создаст таблицу при выполнении и добавит оператор отката в набор изменений:
<changeSet id="testRollback" author="foreach">
<createTable tableName="foreach_turorial">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
<column name="author" type="varchar(36)"/>
</createTable>
<rollback>
<dropTable tableName="foreach_test"/>
</rollback>
</changeSet>
Приведенный выше пример относится к первой категории, упомянутой выше. Он автоматически создаст оператор отката, если мы его не добавим. Но мы можем переопределить поведение по умолчанию, создав оператор отката.
Мы можем запустить миграцию с помощью команды:
mvn liquibase:update
После выполнения мы можем откатить действие, используя:
mvn liquibase:rollback
Это выполняет сегмент отката набора изменений и должен отменить задачу, выполненную на этапе обновления. Но если мы выполним только эту команду, сборка завершится ошибкой.
Причина в том, что мы не указываем лимит отката; база данных будет полностью уничтожена путем отката к начальному этапу. Поэтому необходимо определить одно из трех ограничений ниже, чтобы ограничить операцию отката, когда условие выполнено:
откатТег
rollbackCount
откатДата
3.1. Откат к тегу
Мы можем определить определенное состояние нашей базы данных как тег. Следовательно, мы можем вернуться к этому состоянию. Откат к имени тега «1.0» выглядит так:
mvn liquibase:rollback -Dliquibase.rollbackTag=1.0
Это выполняет операторы отката всех наборов изменений, выполненных после тега «1.0».
3.2. Откат по количеству
Здесь мы определяем, сколько наборов изменений нам нужно откатить. Если мы определим его равным единице, будет отменен последний выполненный набор изменений:
mvn liquibase:rollback -Dliquibase.rollbackCount=1
3.3. Откат к дате
Мы можем установить цель отката в виде даты, поэтому любой набор изменений, выполненный после этого дня, будет отменен:
mvn liquibase:rollback "-Dliquibase.rollbackDate=Jun 03, 2017"
Формат даты должен быть форматом данных ISO или соответствовать значению DateFormat.getDateInstance()
исполняющей платформы.
4. Параметры набора изменений для отката
Давайте рассмотрим возможные варианты использования оператора отката в наборах изменений.
4.1. Откат с несколькими инструкциями
Один тег отката может содержать более одной инструкции для выполнения:
<changeSet id="multiStatementRollback" author="foreach">
<createTable tableName="foreach_tutorial2">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
</createTable>
<createTable tableName="foreach_tutorial3">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
</createTable>
<rollback>
<dropTable tableName="foreach_tutorial2"/>
<dropTable tableName="foreach_tutorial3"/>
</rollback>
</changeSet>
Здесь мы опускаем две таблицы в один и тот же тег отката. Мы также можем разделить задачу на несколько операторов.
4.2. Несколько тегов отката
В наборе изменений у нас может быть более одного тега отката. Они выполняются в порядке появления в наборе изменений:
<changeSet id="multipleRollbackTags" author="foreach">
<createTable tableName="foreach_tutorial4">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
</createTable>
<createTable tableName="foreach_tutorial5">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
</createTable>
<rollback>
<dropTable tableName="foreach_tutorial4"/>
</rollback>
<rollback>
<dropTable tableName="foreach_tutorial5"/>
</rollback>
</changeSet>
4.3. Обратитесь к другому набору изменений для отката
Мы можем обратиться к другому набору изменений, возможно, к исходному набору изменений, если мы собираемся изменить некоторые детали базы данных. Это уменьшит дублирование кода и сможет правильно отменить сделанные изменения:
<changeSet id="referChangeSetForRollback" author="foreach">
<dropTable tableName="foreach_tutorial2"/>
<dropTable tableName="foreach_tutorial3"/>
<rollback changeSetId="multiStatementRollback" changeSetAuthor="foreach"/>
</changeSet>
4.4. Пустой тег отката
По умолчанию Liquibase пытается сгенерировать сценарий отката, если мы его не предоставили. Если нам нужно сломать эту функцию, мы можем иметь пустой тег отката, чтобы операция отката не отменялась:
<changeSet id="emptyRollback" author="foreach">
<createTable tableName="foreach_tutorial">
<column name="id" type="int"/>
<column name="heading" type="varchar(36)"/>
<column name="author" type="varchar(36)"/>
</createTable>
<rollback/>
</changeSet>
5. Параметры команды отката
Помимо отката базы данных до предыдущего состояния, Liquibase можно использовать по-разному. Это генерация SQL отката, создание будущего сценария отката и, наконец, мы можем протестировать миграцию и откат за один шаг.
5.1. Создать сценарий отката
Как и в случае с откатом, у нас есть три варианта генерации SQL для отката. Это:
- rollbackSQL
<tag>
— скрипт для отката базы данных до указанного тега - rollbackToDateSQL
<дата/время>
— SQL-скрипт для отката базы данных до состояния на указанную дату/время - rollbackCountSQL
<значение>
— SQL-скрипт для отката базы данных до состояния, указанного количеством шагов до
Давайте посмотрим один из примеров в действии:
mvn liquibase:rollbackCountSQL 2
5.2. Создать будущий сценарий отката
Эта команда генерирует необходимые SQL-команды отката, чтобы привести базу данных в текущее состояние из состояния, в котором наборы изменений, подходящие для выполнения в данный момент, были завершены. Это будет очень полезно, если необходимо предоставить сценарий отката для изменения, которое мы собираемся выполнить:
Это будет очень полезно, если необходимо предоставить сценарий отката для изменения, которое мы собираемся выполнить:
mvn liquibase:futureRollbackSQL
5.3. Запустить откат тестирования обновления
Эта команда выполняет обновление базы данных, а затем откатывает наборы изменений, чтобы привести базу данных в текущее состояние. Как будущий откат, так и откат тестирования обновления не изменяют текущую базу данных после завершения выполнения. Но откат тестирования обновления выполняет фактическую миграцию, а затем откатывает ее.
Это можно использовать для проверки выполнения изменений обновления без постоянного изменения базы данных:
mvn liquibase:updateTestingRollback
6. Заключение
В этом кратком руководстве мы рассмотрели некоторые функции командной строки и набора изменений функции отката Liquibase.
Как всегда, исходный код можно найти на GitHub .