127
CHAPTER 8: APIs
Transactions
Room allows for transactions in EXCLUSIVE mode. This means that if transaction A is in
progress, no other processes or threads are allowed to access a database in another
transaction B until transaction A is finished. More precisely, transaction B will have to wait
until A is finished.
To run a set of database operations inside a transaction in Kotlin, you can write the following:
val db = ...
db.runInTransaction { ->
// do DB work...
}
The transaction is marked ”successful” if the code inside the closure does not throw any
exception. Otherwise, the transaction will be rolled back.
Migrating Databases
To migrate databases from one version of your app to another version, you add migration
plans while accessing the database as follows:
val migs = arrayOf(
object : Migration(1,2) {
override fun migrate(db: SupportSQLiteDatabase) {
// code for the 1->2 migration...
// this is already running inside a transaction,
// don't add your own transaction code here!
}
}, object : Migration(2,3) {
override fun migrate(db: SupportSQLiteDatabase) {
// code for the 2->3 migration...
// this is already running inside a transaction,
// don't add your own transaction code here!
}
} // more migrations ...
)
private fun fetchDb() =
Room.databaseBuilder(
this, MyDatabase::class.java,
"MyDatabase.db")
.addMigrations(*migs)
.build()
It obviously makes no sense to use DAO classes here, because then you’d have to manage
several DAO variants, one for each version. That is why inside the migrate() methods you
need to access the database on a lower level, for example by executing SQL statements
without bindings to Kotlin objects. As an example, say you have an Employee table. You
upgrade from version 1 to 2 and need to add a column salary, and then you upgrade
Do'stlaringiz bilan baham: |