plug cipher migration hook into room

Signed-off-by: Andy Scherzinger <info@andy-scherzinger.de>
This commit is contained in:
Andy Scherzinger 2022-07-26 20:30:01 +02:00
parent 9325e3f3f0
commit 125d6770b4
No known key found for this signature in database
GPG Key ID: 6CADC7E3523C308B
2 changed files with 32 additions and 6 deletions

View File

@ -92,7 +92,8 @@ public class DatabaseModule {
@Provides @Provides
@Singleton @Singleton
public TalkDatabase provideTalkDatabase(@NonNull final Context context) { public TalkDatabase provideTalkDatabase(@NonNull final Context context,
return TalkDatabase.getInstance(context); @NonNull final AppPreferences appPreferences) {
return TalkDatabase.getInstance(context, appPreferences);
} }
} }

View File

@ -21,6 +21,7 @@
package com.nextcloud.talk.data.source.local package com.nextcloud.talk.data.source.local
import android.content.Context import android.content.Context
import android.util.Log
import androidx.room.Database import androidx.room.Database
import androidx.room.Room import androidx.room.Room
import androidx.room.RoomDatabase import androidx.room.RoomDatabase
@ -36,7 +37,9 @@ import com.nextcloud.talk.data.storage.ArbitraryStoragesDao
import com.nextcloud.talk.data.storage.model.ArbitraryStorageEntity import com.nextcloud.talk.data.storage.model.ArbitraryStorageEntity
import com.nextcloud.talk.data.user.UsersDao import com.nextcloud.talk.data.user.UsersDao
import com.nextcloud.talk.data.user.model.UserEntity import com.nextcloud.talk.data.user.model.UserEntity
import com.nextcloud.talk.utils.preferences.AppPreferences
import net.sqlcipher.database.SQLiteDatabase import net.sqlcipher.database.SQLiteDatabase
import net.sqlcipher.database.SQLiteDatabaseHook
import net.sqlcipher.database.SupportFactory import net.sqlcipher.database.SupportFactory
import java.util.Locale import java.util.Locale
@ -58,20 +61,28 @@ abstract class TalkDatabase : RoomDatabase() {
abstract fun arbitraryStoragesDao(): ArbitraryStoragesDao abstract fun arbitraryStoragesDao(): ArbitraryStoragesDao
companion object { companion object {
const val TAG = "TalkDatabase"
@Volatile @Volatile
private var INSTANCE: TalkDatabase? = null private var INSTANCE: TalkDatabase? = null
@JvmStatic @JvmStatic
fun getInstance(context: Context): TalkDatabase = fun getInstance(context: Context, appPreferences: AppPreferences): TalkDatabase =
INSTANCE ?: synchronized(this) { INSTANCE ?: synchronized(this) {
INSTANCE ?: build(context).also { INSTANCE = it } INSTANCE ?: build(context, appPreferences).also { INSTANCE = it }
} }
private fun build(context: Context): TalkDatabase { private fun build(context: Context, appPreferences: AppPreferences): TalkDatabase {
val passCharArray = context.getString(R.string.nc_talk_database_encryption_key).toCharArray() val passCharArray = context.getString(R.string.nc_talk_database_encryption_key).toCharArray()
val passphrase: ByteArray = SQLiteDatabase.getBytes(passCharArray) val passphrase: ByteArray = SQLiteDatabase.getBytes(passCharArray)
val factory = SupportFactory(passphrase)
val factory = if (appPreferences.isDbRoomMigrated) {
Log.i(TAG, "No cipher migration needed")
SupportFactory(passphrase)
} else {
Log.i(TAG, "Add cipher migration hook")
SupportFactory(passphrase, getCipherMigrationHook())
}
val dbName = context val dbName = context
.resources .resources
@ -95,5 +106,19 @@ abstract class TalkDatabase : RoomDatabase() {
}) })
.build() .build()
} }
private fun getCipherMigrationHook(): SQLiteDatabaseHook {
return object : SQLiteDatabaseHook {
override fun preKey(database: SQLiteDatabase) {
// unused atm
}
override fun postKey(database: SQLiteDatabase) {
Log.i(TAG, "DB cipher_migrate START")
database.rawExecSQL("PRAGMA cipher_migrate;")
Log.i(TAG, "DB cipher_migrate END")
}
}
}
} }
} }