Liquibase:将 autoIncrement 列添加到已存在数据的表中

Posted

技术标签:

【中文标题】Liquibase:将 autoIncrement 列添加到已存在数据的表中【英文标题】:Liquibase: added autoIncrement column into a table with data already present 【发布时间】:2021-10-05 21:31:00 【问题描述】:

大家好,我对 Liquibase 有一些疑问

我创建了一个带有经典变更集的表 (PostgreSQL)

<changeSet id="create_table">
    <createTable tableName="table" schemaName="schema">
        <column name="name" type="varchar">
            <constraints nullable="false"/>
        </column>
        <column name="surname" type="varchar">
            <constraints nullable="false"/>
        </column>
    </createTable>
</changeSet>

我已经在此表中添加了一些数据。 我想添加一个新列 'id' 并将其作为主键作为自动增量列。 我该怎么做?

因为如果我尝试添加这样的变更集:

<changeSet id="added_pk">
    <addColumn tableName="table"
               schemaName="schema">
        <column name="id" type="bigint">
            <constraints unique="true" nullable="false" uniqueConstraintName="PK_TABLE_ID"/>
        </column>
    </addColumn>
    <addAutoIncrement columnDataType="bigint"
                      columnName="id"
                      tableName="table"
                      schemaName="schema"
                      incrementBy="1" startWith="1"/>
</changeSet>

运行脚本时出现错误:“关系“表”的“id”列包含空值”。 这取决于已经存在的值。我该如何处理这种情况? (我宁愿避免在添加新列之前截断所有数据)

非常感谢! 问候

【问题讨论】:

【参考方案1】:

重命名数据库中的当前表。删除 liquibase 更改日志。重新运行包含新 id 字段的 liquibase 文件(您可以组合两个 changeSet,这样您还可以决定 id 字段的位置)。创建新表后,您可以将旧表中的数据传输到新表中。这样旧表中的数据将自动接收 id。删除最后的旧表。

【讨论】:

以上是关于Liquibase:将 autoIncrement 列添加到已存在数据的表中的主要内容,如果未能解决你的问题,请参考以下文章

处理将 MySQL 布尔类型从 tinyint 更改为 bit 的 liquibase 升级

将 autoincrement id 字段加一

无法使用Liquibase标记数据库以备将来回滚

liquibase 从表中加载数据

将 Liquibase 引入现有项目和 MySQL

使用 liquibase 将数据从一个数据库复制到另一个数据库