You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Room数据库手动迁移报错:category表索引缺失如何解决?

解决Room手动迁移中category表缺失index_category_parentId索引的问题

核心原因

Room自动生成表结构时,会根据CategoryEntity类中的@Index注解创建对应索引。手动迁移时必须手动通过SQL创建该索引,否则Room的结构校验会因"预期存在索引但实际缺失"而失败。

正确的手动迁移实现方式

你需要在Migration的migrate方法中,通过SQL语句创建索引,有两种可选写法:

方式1:创建表时同时定义索引

在创建category表的SQL中直接声明索引:

val MIGRATION_X_Y = object : Migration(旧版本号, 新版本号) {
    override fun migrate(database: SupportSQLiteDatabase) {
        database.execSQL("""
            CREATE TABLE `category` (
                `id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
                `name` TEXT NOT NULL,
                `parentId` INTEGER,
                INDEX `index_category_parentId` (`parentId`)
            )
        """.trimIndent())
    }
}

方式2:先建表,再单独创建索引

如果已经创建了表,可单独执行索引创建语句:

val MIGRATION_X_Y = object : Migration(旧版本号, 新版本号) {
    override fun migrate(database: SupportSQLiteDatabase) {
        // 先创建category表
        database.execSQL("""
            CREATE TABLE `category` (
                `id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
                `name` TEXT NOT NULL,
                `parentId` INTEGER
            )
        """.trimIndent())
        // 再创建非唯一索引
        database.execSQL("CREATE INDEX IF NOT EXISTS `index_category_parentId` ON `category`(`parentId`);")
    }
}

关键注意事项

  • 索引名称必须严格匹配:Room自动生成的索引命名规则是index_<表名>_<列名>,这里必须用index_category_parentId,不能自定义名称,否则校验仍会失败。
  • 非唯一索引无需额外关键字:默认创建的索引就是非唯一的,不需要添加UNIQUE关键字,和你实体类中@Index(unique = false)(默认值)的定义对应。

最后将这个Migration实例添加到Room.databaseBuilder的addMigrations方法中即可。

内容的提问来源于stack exchange,提问作者alexandre9865

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.02 10:20:38