Skip to content
Anjunar/ DOCS

Existing databases

Two ways into the history: adopting a database that already matches, and accepting a change you migrated by hand.

Adopt

A database without history

A database that hbm2ddl created has no history and is refused by default. With adoptExistingSchema the executor records it as revision 1 without executing DDL, but only if every table and sequence of the target exists and the database matches exactly.

properties
hibernate.ddl_manager.adopt_existing_schema=true
scala
ExecutionOptions(adoptExistingSchema = true)
Constraint names

The one common difference

Hibernate names enum CHECK constraints the PostgreSQL way, the framework after a hash of the column ID. The refusal lists both names; rename the constraint and start again.

sql
ALTER TABLE "public"."letter" RENAME CONSTRAINT "letter_status_check" TO "<name from the refusal>";

The executor also compares each check's definition, so a renamed constraint passes only if it enforces exactly the modelled values. An @OrderColumn's position >= 0 differs from the modelled range and must be replaced.

Manual migration

Changes the executor cannot plan

Type and primary key changes, among others, need a data migration and are refused. The refusal names the target's fingerprint. Migrate the database by hand to exactly the target, then start once with that fingerprint.

scala
ExecutionOptions(acceptManualMigration = Some("9d4c1e7a52b8f03c6e1d9a47b2c85f10e3a6d7c94b1f2e08c5a3d6b9e7f40c21"))
What the executor checks
The database matches the target, under the lock.
Everything the target dropped or renamed is gone under its old name.
Then the target is recorded as the next revision, status ManuallyMigrated, without DDL.
An option naming another target is refused, so it cannot accept a later change by accident.