Search code examples
androidkotlinsqliteandroid-room

When using a Room database on an Android application, is it possible to pre-populate data


I am trying to learn how to use Room in an Android application to store local data. I have tried to follow the instructions from: https://developer.android.com/training/data-storage/room

I managed to get a simple application working, where the database was defined as:

@Database(entities = [Location::class], version = 1, exportSchema = true)
abstract class LocationDatabase : RoomDatabase() {
    abstract fun locationDAO(): LocationDAO
    companion object {
        @Volatile
        private var INSTANCE: LocationDatabase? = null
        fun getDatabase(context: Context): LocationDatabase {
            return INSTANCE ?: synchronized(this) {
                val instance = Room.databaseBuilder(
                    context.applicationContext,
                    LocationDatabase::class.java,
                    "location_database"
                )
                    .fallbackToDestructiveMigration()
                    .build()
                INSTANCE = instance
                instance
            }
        }
    }
}

By including the following in the App level build.gradle.kts file, I could extract the schema of the database when the project was built.

ksp {
            arg("room.schemaLocation", "$projectDir/schemas")
        }

I wanted to ask how I can use this schema to create a database file and prepopulate it and if can then be used as the content source when creating the application. What I'm trying to accomplish is to pre-populate the Room database with some data, which will be accessed while the application is running.

I attempted to locate some guidance on how to proceed on this, but failed to locate a resource that I could follow.


Solution

  • I wanted to ask how I can use this schema to create a database file and prepopulate it.

    The simplest way, rather than trying to interpret the saved schema, is to let Room do the interpretation by:

    1. Successfully compiling the project
    2. From the Android View of Android Studio locate the java (generated) folder/directory
    3. Within the java (generated) folder find the class that is the same name as the @Database annotated class (LocationDatabase in you case) BUT is suffixed with _Impl (In your case LocationDatabase_Impl).
    4. Find the createAllTables method, this will have a line of code that executes the SQL to create all the tables. This SQL is exactly what Room expects and can be copied to whatever tool you are using to build the pre-packaged database.
    5. Once populated and saved as a single file you can copy the file into the assets folder (which you may have to create)
      1. (if the is a -wal file then database has not been closed and you need to properly close the database e.g. with Navicat you have to close the application)
    6. You then include the createFromAsset method in the databaseBuilder call

    You may wish to refer to How to prepopulate database using Room? I don't see tutorials that explains in details using java which covers the steps in more detail.