From bcefed46f232c33a273d9230d8b8d2a53edba076 Mon Sep 17 00:00:00 2001 From: Chris Banes Date: Mon, 22 Jun 2020 10:21:38 +0100 Subject: [PATCH] Fix related shows not loading correctly --- .../main/java/app/tivi/base/InvokeStatus.kt | 1 - .../src/main/java/app/tivi/ReduxViewModel.kt | 3 ++- .../data/repositories/shows/ShowsModule.kt | 27 +++++-------------- .../java/app/tivi/data/daos/TiviShowDao.kt | 9 +++++-- .../domain/interactors/UpdateRelatedShows.kt | 8 +++--- 5 files changed, 20 insertions(+), 28 deletions(-) diff --git a/base/src/main/java/app/tivi/base/InvokeStatus.kt b/base/src/main/java/app/tivi/base/InvokeStatus.kt index a90a2a9b6c..3aa13cabf0 100644 --- a/base/src/main/java/app/tivi/base/InvokeStatus.kt +++ b/base/src/main/java/app/tivi/base/InvokeStatus.kt @@ -17,7 +17,6 @@ package app.tivi.base sealed class InvokeStatus -object InvokeIdle : InvokeStatus() object InvokeStarted : InvokeStatus() object InvokeSuccess : InvokeStatus() data class InvokeError(val throwable: Throwable) : InvokeStatus() diff --git a/common-ui-view/src/main/java/app/tivi/ReduxViewModel.kt b/common-ui-view/src/main/java/app/tivi/ReduxViewModel.kt index 11244e3ef2..06324d23f7 100644 --- a/common-ui-view/src/main/java/app/tivi/ReduxViewModel.kt +++ b/common-ui-view/src/main/java/app/tivi/ReduxViewModel.kt @@ -27,6 +27,7 @@ import kotlinx.coroutines.flow.Flow import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.catch import kotlinx.coroutines.flow.collect +import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.map import kotlinx.coroutines.launch import kotlinx.coroutines.sync.Mutex @@ -78,7 +79,7 @@ abstract class ReduxViewModel( } private fun selectSubscribe(prop1: KProperty1): Flow { - return state.map { prop1.get(it) } + return state.map { prop1.get(it) }.distinctUntilChanged() } protected suspend fun setState(reducer: S.() -> S) { diff --git a/data-android/src/main/java/app/tivi/data/repositories/shows/ShowsModule.kt b/data-android/src/main/java/app/tivi/data/repositories/shows/ShowsModule.kt index abdfb6ec58..3d2966c9e3 100644 --- a/data-android/src/main/java/app/tivi/data/repositories/shows/ShowsModule.kt +++ b/data-android/src/main/java/app/tivi/data/repositories/shows/ShowsModule.kt @@ -25,8 +25,6 @@ import dagger.Module import dagger.Provides import dagger.hilt.InstallIn import dagger.hilt.android.components.ApplicationComponent -import kotlinx.coroutines.async -import kotlinx.coroutines.coroutineScope import javax.inject.Singleton typealias ShowStore = Store @@ -41,28 +39,17 @@ object ShowStoreModule { lastRequestStore: ShowLastRequestStore, traktShowDataSource: TraktShowDataSource ): ShowStore { - return StoreBuilder.fromNonFlow { showId: Long -> - val localShow = showDao.getShowWithId(showId) - ?: throw IllegalArgumentException("No show with id $showId in database") - - coroutineScope { - val traktResult = async { - traktShowDataSource.getShow(localShow) - } - - // Update our last request timestamp - if (traktResult is Success<*>) { - lastRequestStore.updateLastRequest(showId) - } - - traktResult.await().get() ?: TiviShow.EMPTY_SHOW - } + return StoreBuilder.fromNonFlow { id: Long -> + traktShowDataSource.getShow(showDao.getShowWithIdOrThrow(id)) + .also { if (it is Success<*>) lastRequestStore.updateLastRequest(id) } + .getOrThrow() }.persister( reader = showDao::getShowWithIdFlow, writer = { id, response -> showDao.withTransaction { - val local = showDao.getShowWithId(id) ?: TiviShow.EMPTY_SHOW - showDao.insertOrUpdate(mergeShows(local = local, trakt = response)) + showDao.insertOrUpdate( + mergeShows(local = showDao.getShowWithIdOrThrow(id), trakt = response) + ) } }, delete = showDao::delete, diff --git a/data/src/main/java/app/tivi/data/daos/TiviShowDao.kt b/data/src/main/java/app/tivi/data/daos/TiviShowDao.kt index 495ae9c4ef..821d42d040 100644 --- a/data/src/main/java/app/tivi/data/daos/TiviShowDao.kt +++ b/data/src/main/java/app/tivi/data/daos/TiviShowDao.kt @@ -49,6 +49,11 @@ abstract class TiviShowDao : EntityDao() { @Query("SELECT * FROM shows WHERE id = :id") abstract suspend fun getShowWithId(id: Long): TiviShow? + suspend fun getShowWithIdOrThrow(id: Long): TiviShow { + return getShowWithId(id) + ?: throw IllegalArgumentException("No show with id $id in database") + } + @Query("SELECT trakt_id FROM shows WHERE id = :id") abstract suspend fun getTraktIdForShowId(id: Long): Int? @@ -76,8 +81,8 @@ abstract class TiviShowDao : EntityDao() { // Great, the entities are matching idForTraktId } else { - val showForTmdbId = getShowWithId(idForTmdbId)!! - val showForTraktId = getShowWithId(idForTraktId)!! + val showForTmdbId = getShowWithIdOrThrow(idForTmdbId) + val showForTraktId = getShowWithIdOrThrow(idForTraktId) deleteEntity(showForTmdbId) return insertOrUpdate(mergeShows(showForTraktId, showForTraktId, showForTmdbId)) } diff --git a/domain/src/main/java/app/tivi/domain/interactors/UpdateRelatedShows.kt b/domain/src/main/java/app/tivi/domain/interactors/UpdateRelatedShows.kt index 401d47f75d..b5491d2721 100644 --- a/domain/src/main/java/app/tivi/domain/interactors/UpdateRelatedShows.kt +++ b/domain/src/main/java/app/tivi/domain/interactors/UpdateRelatedShows.kt @@ -40,15 +40,15 @@ class UpdateRelatedShows @Inject constructor( ) : Interactor() { override suspend fun doWork(params: Params) { withContext(dispatchers.io) { - relatedShowsStore.fetchCollection(params.showId, forceFresh = params.forceLoad) { + relatedShowsStore.fetchCollection(params.showId, params.forceLoad) { // Refresh if our local data is over 28 days old lastRequestStore.isRequestExpired(params.showId, Period.ofDays(28)) - }.forEach { + }.forEach { relatedShow -> // yield here to to let other calls potentially run yield() - showsStore.fetch(it.showId) - showImagesStore.fetchCollection(it.showId) + showsStore.fetch(relatedShow.otherShowId) + showImagesStore.fetchCollection(relatedShow.otherShowId) } } }