Liquibase checksum validation fails when a previously executed changeset has been modified since it was first applied to the database. The stored checksum no longer matches the calculated checksum of the current changeset, triggering a validation error. Resolve this by accepting the new checksum, using validCheckSum tags, or clearing outdated checksums.
Liquibase tracks all applied changesets by storing their MD5 checksums in the DATABASECHANGELOG table. When Liquibase runs, it recalculates the checksum of each changeset and compares it to the stored value. If a changeset has been modified after being applied to the database, the checksums will not match, and Liquibase raises a validation error to prevent accidental re-execution of altered changes. This error acts as a safety mechanism because modifying applied changesets can corrupt database state or break assumptions made during the original migration. The error forces developers to explicitly acknowledge and handle the checksum discrepancy before proceeding.
Check the Liquibase error message to identify which changeset has the checksum mismatch. The error output will show:
Checksum validation failed: changeset-id
Expected: 1:abc123def456
Actual: 1:xyz789uvw012Note both the changeset ID and the two different checksum values.
Check your version control system to see if the changeset was intentionally modified:
git log -p path/to/changelog.xml | grep -A 10 -B 10 "changeset-id"If the modification is intentional and safe (like fixing a bug), proceed with accepting the new checksum. If it was accidental, revert the change.
Add a <validCheckSum> tag to accept the old checksum as valid. This tells Liquibase that both the old and new checksums are acceptable:
<changeSet id="my-changeset" author="dev">
<validCheckSum>1:abc123def456</validCheckSum>
<!-- your SQL here -->
</changeSet>Alternatively, use the special value "1:any" to accept any checksum (use with caution):
<validCheckSum>1:any</validCheckSum>This is useful when you've already applied the changeset to production and need to accommodate the checksum difference on other environments.
If the changeset should be re-executed with the new content, add the runOnChange="true" attribute:
<changeSet id="my-changeset" author="dev" runOnChange="true">
<!-- your modified SQL here -->
</changeSet>This tells Liquibase to recalculate the checksum on every deployment and re-run the changeset if content changed. Use this when the modification is intentional and should be applied to all environments.
If the issue occurred after upgrading Liquibase versions, clear the old checksums and let Liquibase recalculate them:
# Using the old Liquibase version first (recommended)
liquibase clear-checksums
# Then upgrade and run normally
liquibase updateThis is the safest approach when Liquibase algorithm improvements change checksum calculation. Always use the OLD version to clear before upgrading.
If other options aren't viable, you can manually update the stored checksum in the database:
UPDATE databasechangelog
SET md5sum = '1:xyz789uvw012'
WHERE id = 'my-changeset' AND author = 'dev';Use the NEW checksum value from the error message. Only do this if you're confident the modification is safe and consistent across all environments.
Best Practices for Avoiding Checksum Errors: (1) Never modify an applied changeset once it's been deployed. Instead, create a new changeset with the fix. (2) If you must modify an unapplied changeset (only in development), use the validCheckSum tag before committing. (3) When upgrading Liquibase, always run clear-checksums with the old version first. (4) Use consistent file encoding (UTF-8) and line endings (LF) across your team. (5) Prefer using relative file paths in includes to avoid path-related checksum issues. Version-Specific Issues: Liquibase 4.21.x and 4.23.x have known issues where checksum calculation changed for certain changeset types (dbms-specific changes, sequence creation). If upgrading within these versions, clear-checksums is essential. PostgreSQL-Specific: Ensure your database user has appropriate permissions to query the databasechangelog table when Liquibase validates checksums. Connection pooling tools may also interfere with transaction handling during validation.
ERROR: syntax error at end of input
Syntax error at end of input in PostgreSQL
Bind message supplies N parameters but prepared statement requires M
Bind message supplies N parameters but prepared statement requires M in PostgreSQL
Multidimensional arrays must have sub-arrays with matching dimensions
Multidimensional arrays must have sub-arrays with matching dimensions
ERROR: value too long for type character varying
Value too long for type character varying
insufficient columns in unique constraint for partition key
How to fix "insufficient columns in unique constraint for partition key" in PostgreSQL