add api cache cleanup
This commit is contained in:
+40
@@ -0,0 +1,40 @@
|
||||
package ru.shadowsparky.vbox.shared.data.api
|
||||
|
||||
import app.cash.sqldelight.async.coroutines.awaitAsOneOrNull
|
||||
import kotlinx.coroutines.withContext
|
||||
import kotlinx.serialization.json.Json
|
||||
import org.koin.core.annotation.Factory
|
||||
import ru.shadowsparky.domain.DispatcherProvider
|
||||
import ru.shadowsparky.vbox.domain.ApiCacheQueries
|
||||
import ru.shadowsparky.vbox.shared.data.AppDatabaseProvider
|
||||
|
||||
@Factory
|
||||
class ApiCache(
|
||||
val dbProvider: AppDatabaseProvider,
|
||||
val json: Json,
|
||||
val dispatcherProvider: DispatcherProvider
|
||||
) {
|
||||
|
||||
suspend inline fun <reified T> writeByKey(key: String, value: T) =
|
||||
withContext(dispatcherProvider.io) {
|
||||
getCache().insert(
|
||||
key,
|
||||
json.encodeToString(value)
|
||||
)
|
||||
}
|
||||
|
||||
suspend fun clear() {
|
||||
getCache().clear()
|
||||
}
|
||||
|
||||
suspend inline fun <reified T> getByKey(key: String): T? {
|
||||
val value = getCache().selectByKey(key)
|
||||
.awaitAsOneOrNull()?.cache_value
|
||||
?: return null
|
||||
return json.decodeFromString(value)
|
||||
}
|
||||
|
||||
suspend fun getCache(): ApiCacheQueries {
|
||||
return dbProvider.get().apiCacheQueries
|
||||
}
|
||||
}
|
||||
+8
-35
@@ -1,31 +1,23 @@
|
||||
package ru.shadowsparky.vbox.shared.data.api
|
||||
|
||||
import app.cash.sqldelight.async.coroutines.awaitAsOneOrNull
|
||||
import kotlinx.coroutines.withContext
|
||||
import kotlinx.serialization.json.Json
|
||||
import ru.shadowsparky.domain.DispatcherProvider
|
||||
import ru.shadowsparky.vbox.domain.ApiCacheQueries
|
||||
import ru.shadowsparky.vbox.shared.data.AppDatabaseProvider
|
||||
import ru.shadowsparky.vbox.shared.domain.VideoApi
|
||||
import ru.shadowsparky.vbox.shared.domain.model.VideoDetails
|
||||
import ru.shadowsparky.vbox.shared.domain.model.VideoLinksResponse
|
||||
import ru.shadowsparky.vbox.shared.domain.model.VideosResponse
|
||||
|
||||
class FallbackVideoApi(
|
||||
private val dbProvider: AppDatabaseProvider,
|
||||
private val wrapper: VideoApi,
|
||||
private val json: Json,
|
||||
private val dispatcherProvider: DispatcherProvider
|
||||
private val cache: ApiCache,
|
||||
private val wrapper: VideoApi
|
||||
) : VideoApi {
|
||||
|
||||
override suspend fun fetchNewVideos(query: String?): VideosResponse {
|
||||
val key = "fetchNewVideos_${query};1;date;"
|
||||
return try {
|
||||
wrapper.fetchNewVideos(query).apply {
|
||||
writeByKey(key, this)
|
||||
cache.writeByKey(key, this)
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
getByKey(key) ?: throw e
|
||||
cache.getByKey(key) ?: throw e
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,10 +25,10 @@ class FallbackVideoApi(
|
||||
val key = "fetchDetails_${id};"
|
||||
return try {
|
||||
wrapper.fetchDetails(id).apply {
|
||||
writeByKey(key, this)
|
||||
cache.writeByKey(key, this)
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
getByKey(key) ?: throw e
|
||||
cache.getByKey(key) ?: throw e
|
||||
}
|
||||
}
|
||||
|
||||
@@ -44,29 +36,10 @@ class FallbackVideoApi(
|
||||
val key = "fetchVideoLinks_${id};$seasonId;"
|
||||
return try {
|
||||
wrapper.fetchVideoLinks(id, seasonId).apply {
|
||||
writeByKey(key, this)
|
||||
cache.writeByKey(key, this)
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
getByKey(key) ?: throw e
|
||||
cache.getByKey(key) ?: throw e
|
||||
}
|
||||
}
|
||||
|
||||
private suspend fun getCache(): ApiCacheQueries {
|
||||
return dbProvider.get().apiCacheQueries
|
||||
}
|
||||
|
||||
private suspend inline fun <reified T> getByKey(key: String): T? {
|
||||
val value = getCache().selectByKey(key)
|
||||
.awaitAsOneOrNull()?.cache_value
|
||||
?: return null
|
||||
return json.decodeFromString(value)
|
||||
}
|
||||
|
||||
private suspend inline fun <reified T> writeByKey(key: String, value: T) =
|
||||
withContext(dispatcherProvider.io) {
|
||||
getCache().insert(
|
||||
key,
|
||||
json.encodeToString(value)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
+3
-7
@@ -1,11 +1,9 @@
|
||||
package ru.shadowsparky.vbox.shared.di
|
||||
|
||||
import io.ktor.client.HttpClient
|
||||
import kotlinx.serialization.json.Json
|
||||
import org.koin.core.annotation.Module
|
||||
import org.koin.core.annotation.Single
|
||||
import ru.shadowsparky.domain.DispatcherProvider
|
||||
import ru.shadowsparky.vbox.shared.data.AppDatabaseProvider
|
||||
import ru.shadowsparky.vbox.shared.data.api.ApiCache
|
||||
import ru.shadowsparky.vbox.shared.data.api.FallbackVideoApi
|
||||
import ru.shadowsparky.vbox.shared.data.api.PosterWithoutSuffixVideoApi
|
||||
import ru.shadowsparky.vbox.shared.data.api.VideoApiImpl
|
||||
@@ -19,13 +17,11 @@ class HttpModule {
|
||||
fun provideVideoApi(
|
||||
httpClient: HttpClient,
|
||||
serverConfigurationProvider: ServerConfigurationRepository,
|
||||
json: Json,
|
||||
dbProvider: AppDatabaseProvider,
|
||||
dispatcherProvider: DispatcherProvider
|
||||
apiCache: ApiCache
|
||||
): VideoApi {
|
||||
val impl = VideoApiImpl(httpClient, serverConfigurationProvider)
|
||||
return PosterWithoutSuffixVideoApi(
|
||||
FallbackVideoApi(dbProvider, impl, json, dispatcherProvider)
|
||||
FallbackVideoApi(apiCache, impl)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
+4
-1
@@ -6,6 +6,7 @@ import org.koin.core.annotation.Factory
|
||||
import org.koin.core.annotation.Named
|
||||
import ru.shadowsparky.http.domain.LogoutAction
|
||||
import ru.shadowsparky.http.domain.TokenStorage
|
||||
import ru.shadowsparky.vbox.shared.data.api.ApiCache
|
||||
import ru.shadowsparky.vbox.shared.di.DbType
|
||||
import ru.shadowsparky.vbox.shared.domain.tag.MovieTagRepository
|
||||
import ru.shadowsparky.vbox.shared.domain.tag.UserTagRepository
|
||||
@@ -21,7 +22,8 @@ class LogoutUseCase(
|
||||
private val bearerAuthProvider: BearerAuthProvider,
|
||||
private val tokenStorage: TokenStorage,
|
||||
private val authTokenRepository: AuthTokenRepository,
|
||||
private val pendingOperationRepository: PendingOperationRepository
|
||||
private val pendingOperationRepository: PendingOperationRepository,
|
||||
private val apiCache: ApiCache
|
||||
) : LogoutAction {
|
||||
|
||||
override suspend fun logout() {
|
||||
@@ -37,5 +39,6 @@ class LogoutUseCase(
|
||||
localUserTagRepository.clear()
|
||||
AggregateType.entries.forEach { syncRepository.set(it, false) }
|
||||
pendingOperationRepository.clear()
|
||||
apiCache.clear()
|
||||
}
|
||||
}
|
||||
|
||||
+3
@@ -12,3 +12,6 @@ deleteByKey:
|
||||
|
||||
selectByKey:
|
||||
SELECT * FROM ApiCache WHERE cache_key = ?;
|
||||
|
||||
clear:
|
||||
DELETE FROM ApiCache;
|
||||
|
||||
Reference in New Issue
Block a user