Liquibase 配置如下:
liquibase:
enabled: true
change-log: classpath:db/db-changelog.xml
change-log.xml
<includeAll path="changelogs" relativeToChangelogFile="true" />
使用Main方法啓動項目,腳本文件的路徑:
classpath:db/changelogs/*
將項目使用spring boot打成執行jar,腳本文件的路徑變成了
BOOT-INF/classes/db/changelogs/*
因爲路徑不同的問題,導致腳本會執行多次出錯
解決方法:
通過研究Liquibase源碼,知道文件路徑的解析是通過 XMLChangeLogSAXParser
通過自定義的實現的方式將 BOOT-INF/classes/ 移除,使兩種啓動方式的路徑一致
1. 編寫自己的一個 XMLChangeLogSAXParser
public class ChangeLogParser extends XMLChangeLogSAXParser
2. 使Liquibase能掃描到我們的實現
在 META-INF/MANIFEST.MF 中增加
Liquibase-Package: com.xx (ChangeLogParser所在的包)
完整的 ChangeLogParser 代碼
public static class ChangeLogParser extends XMLChangeLogSAXParser
{
private final static String BOOT_CLASSES = "BOOT-INF/classes/";
@Override
public int getPriority() {
return 2;
}
@Override
public DatabaseChangeLog parse(String physicalChangeLogLocation, ChangeLogParameters changeLogParameters, ResourceAccessor resourceAccessor) throws ChangeLogParseException {
DatabaseChangeLog log = super.parse(physicalChangeLogLocation, changeLogParameters, resourceAccessor);
Iterator<ChangeSet> iterator = log.getChangeSets().iterator();
while( iterator.hasNext() )
{
ChangeSet set = iterator.next();
String filePath = set.getFilePath();
if( filePath.startsWith(BOOT_CLASSES) )
{
set.setFilePath(filePath.substring(BOOT_CLASSES.length()));
}
}
return log;
}
}