Room数据库迁移疑问:新增表及版本升级是否需编写迁移脚本?
Room迁移核心问题解答
嘿,我来帮你理清从SQLite转Room时遇到的这两个迁移关键点——毕竟上架后的应用动数据库可不能马虎:
问题1:新增表时,每次升级Room版本都需要编写迁移脚本吗?
答案是分场景而定,但面向存量用户的升级必须写:
- 如果你的更新只针对全新安装的用户:可以不用写迁移脚本,Room会自动根据Entity创建新表,但这种情况只适用于没有存量用户的新应用,显然你的应用已经上架,所以这个情况可以忽略。
- 如果是给已安装应用的用户推送升级:必须编写迁移脚本!Room对数据库版本的变更有严格校验,如果没有对应版本的迁移逻辑,它会直接抛出
IllegalStateException,导致应用崩溃。
举个新增表的迁移脚本示例(Kotlin):
// 定义从版本20到21的迁移逻辑 val MIGRATION_20_21 = object : Migration(20, 21) { override fun migrate(database: SupportSQLiteDatabase) { // 执行创建新表的SQL,注意和Entity结构完全匹配 database.execSQL(""" CREATE TABLE IF NOT EXISTS `FavoriteItems` ( `id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, `item_id` INTEGER NOT NULL, `added_time` INTEGER NOT NULL ) """.trimIndent()) } } // 在构建Room数据库时添加迁移 Room.databaseBuilder(context, AppDatabase::class.java, "your_app_db") .addMigrations(MIGRATION_20_21) .build()
小技巧:开启@Database注解里的exportSchema = true,Room会自动生成schema的JSON文件,你可以对照这个文件写SQL,避免语法或结构错误。
问题2:当前数据库版本是20,升级到21需要编写迁移脚本吗?
必须写! 只要数据库版本号从20提升到21,所有从旧版本(20)升级到新版本(21)的用户都需要对应的迁移逻辑。
这里要特别注意:绝对不要依赖fallbackToDestructiveMigration()来跳过迁移——这个方法会直接清空用户的现有数据库并重建,会导致用户数据丢失,对于已经上架的应用来说这是严重的体验事故。
另外,因为你是从原生SQLite转Room,还要额外确认:Room生成的schema和你原来SQLite的表结构完全一致(字段名、数据类型、约束、索引等),否则即使写了迁移脚本,也可能出现校验不通过的问题。
内容的提问来源于stack exchange,提问作者Mohammed Rampurawala
相关产品推荐
相关产品推荐

