From 81b4e77a6620896a95c8ddfabbd95e80ff6a8098 Mon Sep 17 00:00:00 2001 From: johan12345 Date: Mon, 29 May 2023 19:50:01 +0200 Subject: [PATCH] exclude cached data from DB in backup --- app/src/main/AndroidManifest.xml | 2 + .../net/vonforst/evmap/storage/BackupAgent.kt | 54 +++++++++++++++++++ .../net/vonforst/evmap/storage/Database.kt | 28 ++++++++++ .../evmap/storage/FilterProfileDao.kt | 5 +- .../vonforst/evmap/storage/FilterValueDao.kt | 14 +++++ .../storage/RecentAutocompletePlaceDao.kt | 3 ++ app/src/main/res/xml/backup_rules.xml | 2 +- app/src/main/res/xml/backup_rules_api31.xml | 4 +- 8 files changed, 108 insertions(+), 4 deletions(-) create mode 100644 app/src/main/java/net/vonforst/evmap/storage/BackupAgent.kt diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index fad863ac..19a37193 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -26,6 +26,8 @@ android:allowBackup="true" android:fullBackupContent="@xml/backup_rules" android:dataExtractionRules="@xml/backup_rules_api31" + android:fullBackupOnly="true" + android:backupAgent=".storage.BackupAgent" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:roundIcon="@mipmap/ic_launcher_round" diff --git a/app/src/main/java/net/vonforst/evmap/storage/BackupAgent.kt b/app/src/main/java/net/vonforst/evmap/storage/BackupAgent.kt new file mode 100644 index 00000000..5d093263 --- /dev/null +++ b/app/src/main/java/net/vonforst/evmap/storage/BackupAgent.kt @@ -0,0 +1,54 @@ +package net.vonforst.evmap.storage + +import android.app.backup.BackupAgent +import android.app.backup.BackupDataInput +import android.app.backup.BackupDataOutput +import android.app.backup.FullBackupDataOutput +import android.os.ParcelFileDescriptor +import kotlinx.coroutines.runBlocking +import java.time.Instant + +private const val backupFileName = "evmap-backup.db" + +class BackupAgent : BackupAgent() { + override fun onBackup( + oldState: ParcelFileDescriptor, + data: BackupDataOutput, + newState: ParcelFileDescriptor + ) { + // unused on Android M+, we don't support backups on older versions + } + + override fun onRestore( + data: BackupDataInput, + appVersionCode: Int, + newState: ParcelFileDescriptor + ) { + // unused on Android M+, we don't support backups on older versions + } + + override fun onFullBackup(data: FullBackupDataOutput) { + runBlocking { + // creates a backup of the app database to evmap-backup.db + AppDatabase.getInstance(applicationContext).createBackup( + applicationContext, + backupFileName + ) + } + super.onFullBackup(data) + val backupDb = applicationContext.getDatabasePath(backupFileName) + if (backupDb.exists()) backupDb.delete() + } + + override fun onRestoreFinished() { + super.onRestoreFinished() + // rename restored backup DB as evmap.db + val backupDb = applicationContext.getDatabasePath(backupFileName) + if (backupDb.exists()) { + backupDb.renameTo(applicationContext.getDatabasePath("evmap.db")) + } + // clear cache age + PreferenceDataSource(applicationContext).lastGeReferenceDataUpdate = Instant.EPOCH + PreferenceDataSource(applicationContext).lastOcmReferenceDataUpdate = Instant.EPOCH + } +} \ No newline at end of file diff --git a/app/src/main/java/net/vonforst/evmap/storage/Database.kt b/app/src/main/java/net/vonforst/evmap/storage/Database.kt index eb36de4e..e5eec253 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/Database.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/Database.kt @@ -4,6 +4,7 @@ import android.annotation.SuppressLint import android.content.ContentValues import android.content.Context import android.database.sqlite.SQLiteDatabase +import androidx.lifecycle.map import androidx.room.Database import androidx.room.RoomDatabase import androidx.room.TypeConverters @@ -18,6 +19,7 @@ import net.vonforst.evmap.api.openchargemap.OCMConnectionType import net.vonforst.evmap.api.openchargemap.OCMCountry import net.vonforst.evmap.api.openchargemap.OCMOperator import net.vonforst.evmap.model.* +import net.vonforst.evmap.viewmodel.await @Database( entities = [ @@ -446,4 +448,30 @@ abstract class AppDatabase : RoomDatabase() { } } } + + /** + * Creates a backup of the database to evmap-backup.db. + * + * The backup excludes cached data which can easily be retrieved from the network on restore. + */ + suspend fun createBackup(context: Context, fileName: String) { + val db = getInstance(context.applicationContext) + val backupDb = initDb( + SpatiaRoom.databaseBuilder( + context.applicationContext, + AppDatabase::class.java, + fileName + ) + ) + backupDb.clearAllTables() + + val favorites = db.favoritesDao().getAllFavoritesAsync() + backupDb.chargeLocationsDao().insert(*favorites.map { it.charger }.toTypedArray()) + backupDb.favoritesDao().insert(*favorites.map { it.favorite }.toTypedArray()) + backupDb.filterProfileDao().insert(*db.filterProfileDao().getAllProfiles().toTypedArray()) + backupDb.filterValueDao().insert(*db.filterValueDao().getAllFilterValues().toTypedArray()) + backupDb.recentAutocompletePlaceDao() + .insert(*db.recentAutocompletePlaceDao().getAllAsync().toTypedArray()) + backupDb.close() + } } \ No newline at end of file diff --git a/app/src/main/java/net/vonforst/evmap/storage/FilterProfileDao.kt b/app/src/main/java/net/vonforst/evmap/storage/FilterProfileDao.kt index 0674bf78..3d6b6652 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/FilterProfileDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/FilterProfileDao.kt @@ -19,7 +19,7 @@ data class FilterProfile( @Dao interface FilterProfileDao { @Insert(onConflict = OnConflictStrategy.REPLACE) - suspend fun insert(profile: FilterProfile): Long + suspend fun insert(vararg profile: FilterProfile) @Update suspend fun update(vararg profiles: FilterProfile) @@ -30,6 +30,9 @@ interface FilterProfileDao { @Query("SELECT * FROM filterProfile WHERE dataSource = :dataSource AND id != $FILTERS_CUSTOM ORDER BY `order` ASC, `name` ASC") fun getProfiles(dataSource: String): LiveData> + @Query("SELECT * FROM filterProfile") + suspend fun getAllProfiles(): List + @Query("SELECT * FROM filterProfile WHERE dataSource = :dataSource AND name = :name") suspend fun getProfileByName(name: String, dataSource: String): FilterProfile? diff --git a/app/src/main/java/net/vonforst/evmap/storage/FilterValueDao.kt b/app/src/main/java/net/vonforst/evmap/storage/FilterValueDao.kt index 02456bea..c04ac58f 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/FilterValueDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/FilterValueDao.kt @@ -26,6 +26,15 @@ abstract class FilterValueDao { dataSource: String ): List + @Query("SELECT * FROM booleanfiltervalue") + protected abstract suspend fun getAllBooleanFilterValuesAsync(): List + + @Query("SELECT * FROM multiplechoicefiltervalue") + protected abstract suspend fun getAllMultipleChoiceFilterValuesAsync(): List + + @Query("SELECT * FROM sliderfiltervalue") + protected abstract suspend fun getAllSliderFilterValuesAsync(): List + @Query("SELECT * FROM booleanfiltervalue WHERE profile = :profile AND dataSource = :dataSource") protected abstract fun getBooleanFilterValues( profile: Long, @@ -105,6 +114,11 @@ abstract class FilterValueDao { } } + open suspend fun getAllFilterValues(): List = + getAllBooleanFilterValuesAsync() + + getAllMultipleChoiceFilterValuesAsync() + + getAllSliderFilterValuesAsync() + @Transaction open suspend fun insert(vararg values: FilterValue) { values.forEach { diff --git a/app/src/main/java/net/vonforst/evmap/storage/RecentAutocompletePlaceDao.kt b/app/src/main/java/net/vonforst/evmap/storage/RecentAutocompletePlaceDao.kt index 6b0f38a1..54001b82 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/RecentAutocompletePlaceDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/RecentAutocompletePlaceDao.kt @@ -80,4 +80,7 @@ abstract class RecentAutocompletePlaceDao { dataSource: String, limit: Int? = null ): List + + @Query("SELECT * FROM recentautocompleteplace") + abstract suspend fun getAllAsync(): List } \ No newline at end of file diff --git a/app/src/main/res/xml/backup_rules.xml b/app/src/main/res/xml/backup_rules.xml index d5fbd5b3..870f43ef 100644 --- a/app/src/main/res/xml/backup_rules.xml +++ b/app/src/main/res/xml/backup_rules.xml @@ -8,5 +8,5 @@ path="encrypted_prefs.xml" /> + path="evmap-backup.db" /> \ No newline at end of file diff --git a/app/src/main/res/xml/backup_rules_api31.xml b/app/src/main/res/xml/backup_rules_api31.xml index d58e37d8..ab13a363 100644 --- a/app/src/main/res/xml/backup_rules_api31.xml +++ b/app/src/main/res/xml/backup_rules_api31.xml @@ -9,7 +9,7 @@ path="encrypted_prefs.xml" /> + path="evmap-backup.db" /> + path="evmap-backup.db" /> \ No newline at end of file