У меня есть приложение, работающее в Scala, подключающееся к postgres БД, я впервые использую Liquibase для управления миграциями БД и изменениями схемы. Мне удалось подключиться и создать БД, но моя проблема в том, что когда я пытаюсь создать набор изменений для обновления БД, происходит сбой с ошибкой несуществующей схемы. Моя настройка ниже
CREATE SCHEMA IF NOT EXISTS "CONFIG";
------------------------------------------ Extension --------------------------------------
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
---------------------------------------- Tables ------------------------------------------
CREATE TABLE IF NOT EXISTS "CONFIG"."RESOURCE_TYPE" (
"ID" UUID DEFAULT uuid_generate_v4() NOT NULL,
"NAME" VARCHAR NOT NULL,
"PROPERTY_NAMES" VARCHAR NOT NULL,
"CATEGORY" VARCHAR NOT NULL,
"PRECEDENCE" INT,
CONSTRAINT PK_RESOURCE_TYPE PRIMARY KEY ("ID"),
CONSTRAINT U_RESOURCE_TYPE_NAME UNIQUE ("NAME")
);
COMMIT;
Выше моя базовая линия sql файл
Затем у меня есть откат sql файл
DROP TABLE IF EXISTS PIPELINE_CONF;
DROP SCHEMA CONFIG CASCADE;
COMMIT;
Мое главное приложение class
object TestApiApp extends App with TestService {
private val port: Int = settings.port
private val interface = settings.interface
implicit val system: ActorSystem = ActorSystem()
implicit val executor: ExecutionContextExecutor = system.dispatcher
implicit val materializer: ActorMaterializer = ActorMaterializer()
val logger: LoggingAdapter = Logging(system, getClass)
TestApiDomain.initDatabase()
implicit val session: AutoSession.type = RuntimeServiceApiDomain.connectToDB()
system.eventStream.subscribe(system.actorOf(Props(DeadLetterLogger(logger))), classOf[DeadLetter])
val bindFuture = Http().bindAndHandle(logRoute(routes), interface, port)
Console.println(s"Initializing service in http://$interface:$port")
}
Объект домена, который имеет соединения
object TestApiDomain {
val logger: Logger = LoggerFactory.getLogger("ApiModel")
val settings: SettingsImpl = Settings
val dbMaxConnections: Int = settings.dbMaxConnections
implicit val dbExecutionContext: ExecutionContext =
ExecutionContext.fromExecutor(Executors.newFixedThreadPool(dbMaxConnections))
def initDatabase(): Unit = {
val resourceAccessor = new FileSystemResourceAccessor
val database = DatabaseFactory.getInstance.openDatabase(Settings.dbJdbcUrl,
Settings.dbUser,
Settings.dbPassword,
null,
resourceAccessor)
val liquibase: Liquibase =
new Liquibase("liquibase/masterChangelog.xml", new ClassLoaderResourceAccessor(), database)
liquibase.clearCheckSums()
liquibase.update(new Contexts())
}
def connectToDB(): AutoSession.type = {
DBs.setupAll()
GlobalSettings.loggingSQLErrors = false
GlobalSettings.sqlFormatter = SQLFormatterSettings("utils.HibernateSQLFormatter")
AutoSession
}
}
Мой основной файл журнала изменений
<databaseChangeLog
xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:ext="http://www.liquibase.org/xml/ns/dbchangelog-ext"
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-3.1.xsd
http://www.liquibase.org/xml/ns/dbchangelog-ext http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-ext.xsd">
<changeSet id="" author="">
<preConditions onFail="MARK_RAN">
<dbms type="postgresql"/>
</preConditions>
<sqlFile path="hsqldb-config.sql"
relativeToChangelogFile="true"
splitStatements="false"
stripComments="false"/>
</changeSet>
<include file="changelogs/000-baseline/baseline.xml" relativeToChangelogFile="true"/>
</databaseChangeLog>
Базовый файл xml выглядит следующим образом
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<databaseChangeLog xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-2.0.xsd">
<changeSet id="beforeBaseline" author="foo">
<preConditions onFail="MARK_RAN">
<sqlCheck expectedResult="0">select count(*) from databasechangelog where id = 'beforeBaseline' and author = 'foo'</sqlCheck>
</preConditions>
<tagDatabase tag="version_0.0.0"/>
</changeSet>
<changeSet id="baseline" author="foo">
<preConditions onFail="MARK_RAN">
<sqlCheck expectedResult="0">select count(*) from databasechangelog where id = 'baseline' and author = 'foo'</sqlCheck>
</preConditions>
<sqlFile
path="baseline.sql"
relativeToChangelogFile="true"
splitStatements="false"
stripComments="false"/>
<rollback>
<sqlFile
path="rollback.sql"
relativeToChangelogFile="true"
splitStatements="false"
stripComments="false"/>
</rollback>
</changeSet>
<changeSet id="0.0.1" author="foo">
<modifyDataType tableName="RESOURCE_TYPE"
columnName="CATEGORY"
newDataType="varchar"
schemaName="CONFIG"
/>
</changeSet>
</databaseChangeLog>
Если вы видите файл выше, я пытаюсь изменить тип данных столбца на varchar вместо varchar, а не на null. Почему это не удается?
Я получаю ошибку ниже
*** RUN ABORTED *** (2 seconds, 408 milliseconds)
java.util.concurrent.ExecutionException: liquibase.exception.MigrationFailedException: Migration failed for change set liquibase/changelogs/000-baseline/baseline.xml::0.0.1::foo:
Reason: liquibase.exception.DatabaseException: ERROR: schema "config" does not exist [Failed SQL: (0) ALTER TABLE CONFIG.RESOURCE_TYPE ALTER COLUMN CATEGORY TYPE VARCHAR USING (CATEGORY::VARCHAR)]
at java.util.concurrent.FutureTask.report(FutureTask.java:122)
at java.util.concurrent.FutureTask.get(FutureTask.java:192)
Также проверил локальную базу данных, и я вижу, что схема существует
\dt "CONFIG".*
List of relations
Schema | Name | Type | Owner
--------+----------------------+-------+----------
CONFIG | RESOURCE_TYPE | table | ----
Я не знаю, сколько времени на отладку этого. Если вам нужна структура файлов, у меня она ниже