在其他应用插入数据后,Android Room需要迁移

时间:2018-11-05 08:30:29

标签: android database-migration android-room

我正在开发一个Android应用程序,该应用程序带有在Android Room中运行的嵌入式SQLite数据库。我正在将应用程序从桌面Java迁移到Android,我需要将数据从与桌面应用程序一起使用的旧数据库导入Android数据库。当我尝试在Android应用程序中使用更改后的数据库时,我遇到了Room的问题。

我尝试使用Room创建的数据库文件,并使用为此编写的简短Java应用程序将数据从旧数据库移入该数据库。我只是清空相关表,从旧数据库中读取数据,然后将其插入新数据库中。

当我尝试将数据库文件移回我的Android设备并与Android应用程序一起使用时,出现了以下异常:

  

房间无法验证数据完整性。看起来您已更改架构,但忘记更新版本号。   您只需增加版本号即可解决此问题。

如果我在Room数据库代码中更改数据库的版本,则Room将需要一段代码来进行迁移,即使数据库的结构没有更改:

  

java.lang.IllegalStateException:需要从1迁移到2,但未找到。请通过RoomDatabase.Builder.addMigration(Migration ...)提供必要的迁移路径,或者允许通过RoomDatabase.Builder.fallbackToDestructiveMigration *方法之一进行破坏性迁移。

我尝试清除应用程序数据缓存并清除其所有数据,甚至卸载应用程序,然后使用修改后的数据库文件重新安装它。并没有解决问题。我还尝试了Room cannot verify the data integrity处的所有操作,包括在清单中设置android:allowBackup =“ false”,以及将fallbackToDestructiveMigration添加到数据库中。尝试fallbackToDestructiveMigration之后,我所有新数据库的数据都消失了。但是,然后我再次将更改后的数据库文件放回去,并且它可以正常工作。老实说,我不确定是什么步骤使它成功了。我认为这是在增加版本号,并使用fallbackToDestructiveMigration运行它,然后在fallbackToDestructiveMigration擦除了数据库中的数据后再次将新的数据库文件移回...

我的问题是,如果房间的结构没有任何变化,使其与我的应用的实体不兼容,那么Room如何知道数据库已被修改?即使我已经从设备中清除了应用程序的数据,又怎么知道呢?还有我下次没有采取的上述未提及的任何步骤吗?我问我可以包括什么都不做的迁移代码。但这似乎有点愚蠢,我希望版本号保持为1,因为该应用目前正在开发中。

1 个答案:

答案 0 :(得分:0)

添加一个空的迁移。

 private val MIGRATION_1_2 = object : Migration(1, 2) {
            override fun migrate(database: SupportSQLiteDatabase) {
                // empty migration.
            }
        }



  if (sInstance == null) {
            if (!checkDataBase())
                copyDataBase(context)

            synchronized(AppDatabase::class) {
                sInstance = Room.databaseBuilder(context.applicationContext, AppDatabase::class.java, DATABASE_NAME)

                        .addMigrations(MIGRATION_1_2)
                        .build()
            }
        }
        return sInstance!!

您可以从Florina Muntenescu查看此Migration Guide,以了解有关迁移的更多信息