Skip to main content

Automatic and Custom Rollbacks

There are two types of rollback functionality:

  • Automatic rollbacks: Generated automatically based on the change type
  • Custom rollbacks: Explicitly specified by you in your changelog
caution

SQL changelogs, do not support auto rollback, regardless of the Change Type. You must write custom rollback statements for all formatted SQL changelogs, can also write your own rollbacks if you want to override the default rollback statement for a Change Type that supports auto rollback.

rollback-error-sql

Automatic rollback statements

For many Change Types, such as createTable, addColumn, and renameColumn, Liquibase automatically generates the SQL statements necessary to complete the rollback, so you can simply run a command like rollback on your desired changeset(s) and be done.

When you run the update command on a createTable changeset, Liquibase executes the SQL statement CREATE TABLE myTable. When you run the rollback command to revert that changeset, Liquibase recognizes that the inverse of the original change is DROP TABLE myTable and executes that statement. In this case, you aren't required to add anything special to your changelog.

Liquibase command 'rollback' was executed successfully.
Liquibase: Rollback has been successful.

However, if you try to run rollback on dropTable, Liquibase cannot automatically generate the rollback SQL:

Unexpected error running Liquibase: 

To roll back your dropTable statement, you have to specify custom logic in your changelog so that Liquibase knows how to correctly restore your database.

Custom rollback statements

Liquibase cannot automatically generate rollback SQL for Change Types like dropTable and insert. To roll back database updates that include these changesets, you must write custom rollback statements in your desired changeset(s) and then run the rollback command.

In these cases, you must specify custom rollback syntax in your changelog for every changeset that you might want to roll back. This way, when you run the rollback command, Liquibase knows what to do.

For more information and example:

--changeset stephen-atwell:1
create table testTable ( id int primary key, name varchar(255) );
--rollback drop table testTable;

--changeset stephen-atwell:2
insert into testTable values ('1','The First', 'Country')
insert into testTable values ('2','The Second', 'Country2')
--rollback delete from testTable where id='1'
--rollback delete from testTable where id='2'

info

When rolling back stored logic, Liquibase does not restore the previously stored version. Instead, Liquibase rolls back to the exact file/code specified in the custom rollback.

Multiple rollbacks

You can also specify multiple Change Types within a single rollback statement or across multiple rollback statements:

- changeSet:
id: multiRollbackTest
author: stephen-atwell
changes:
- createTable:
tableName: multiRollback1
columns:
- column:
name: id
- createTable:
tableName: multiRollback2
columns:
- column:
name: id
- createTable:
tableName: multiRollback3
columns:
- column:
name: id
rollback:
- dropTable:
tableName: multiRollback1
- dropTable:
tableName: multiRollback2
rollback:
- dropTable:
tableName: multiRollback3

Empty rollback statements

If you do not want to revert a change in a rollback mode, use either the keyword empty or the keyword not required inside the rollback tag. In XML, YAML, and JSON changelogs, you can also use an empty string inside the rollback tag.

--changeset stephen-atwell:1
create table testTable ( id int primary key, name varchar(255) );
--rollback empty