问题
I have two tables declared as follows:
<changeSet author="istvan" id="country-table-changelog">
<createTable tableName="country">
<column name="id" type="uuid">
<constraints nullable="false" unique="true" />
</column>
<column name="name" type="varchar">
<constraints nullable="false" unique="true" />
</column>
</createTable>
</changeSet>
<changeSet author="istvan" id="region-table-changelog">
<createTable tableName="region">
<column name="id" type="uuid" >
<constraints nullable="false" unique="true" />
</column>
<column name="country_id" type="uuid">
<constraints nullable="false" />
</column>
<column name="name" type="varchar">
<constraints nullable="false" unique="true" />
</column>
</createTable>
</changeSet>
<changeSet author="istvan" id="region-country-foreign-key-constraint">
<addForeignKeyConstraint
baseTableName="region"
baseColumnNames="country_id"
referencedTableName="country"
referencedColumnNames="id"
constraintName="fk_region_country"
onDelete="CASCADE"
onUpdate="RESTRICT"/>
</changeSet>
I want to fill both tables from liquibase changelog file with some values like:
INSERT INTO country VALUES('aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa', 'HUNGARY');
INSERT INTO region VALUES('bbbbbbbb-bbbb-bbbb-bbbb-bbbbbbbbbbbb', 'aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa', 'Baranya');
In the example I used aaaa's and bbbb's just because of simplicity. I want to generate those UUID's by the DBMS.
What is the best way to do it? Do I have to use SQL in my changelog files or is it possible with XML? I prefer DBMS independent solution like XML or JSON.
My second question is that how can I declare a column with UUID that creates the UUID on insert. Something like:
<column name="id" type="uuid" value="??? GENERATE UUID ???">
<constraints nullable="false" unique="true" />
</column>
Thank you for your time!
回答1:
You can do this by using properties that are defined depending on the current DBMS.
<property name="uuid_type" value="uuid" dbms="postgresql"/>
<property name="uuid_type" value="uniqueidentifier" dbms="mssql"/>
<property name="uuid_type" value="RAW(16)" dbms="oracle"/>
<property name="uuid_function" value="uid.uuid_generate_v4()" dbms="postgresql"/>
<property name="uuid_function" value="NEWID()" dbms="mssql"/>
<property name="uuid_function" value="sys_guid()" dbms="oracle"/>
Then use those properties when defining the table:
<column name="id" type="${uuid_type}" defaultValueComputed="${uuid_function}">
<constraints nullable="false" unique="true" />
</column>
Note that you need to use defaultValueComputed
, not value
If the column is defined with a default value, just leave it out in your insert statements and the database will then generate the UUID when inserting.
回答2:
For MySQL, put your property just before changeSet tag:
<property name="u_id" value="uuid()" dbms="mysql"/>
then
<column name="ID" type="varchar(255)" valueComputed="${u_id}"/>
NOTE: here valueComputed
is used, not defaultValueComputed
.
回答3:
Some databases supports UUID columns: Generate UUID values by default for each row on column of UUID type in H2 Database Engine
I don't think that Liquibase has embedded UUID generator, have a look at defaultValueComputed/valueComputed property for column (http://www.liquibase.org/documentation/column.html) + DB function to generate UUID
回答4:
Like Rammgarot noted, since we are dealing with columns that need to have unique values, we should use valueComputed
instead of defaultValueComputed
.
来源:https://stackoverflow.com/questions/42361350/liquibase-insert-rows-with-uuid