Получить удаленные данные или получить локальный через rxJava 2 - PullRequest
0 голосов
/ 27 апреля 2018

У меня очень простая задача отправить запрос на удаленные данные. Но нужно обработать мой запрос и получить локальный при удаленной ошибке. Способ функциональности подобно математике имеет много способов решения проблемы.

Итак, первым делом нужно прийти на ум:

val remote = remotePurchase
                .getAvailableUsersMaxCount()
                .subscribe({},{
                   //on failed            
                  getLocal()
        })

Но я думаю, что это новичок, и это обратный вызов в обратном вызове.

Также я думаю сделать это:

  override fun getActualUsersMaxCount(): Observable<Int> {
            return remotePurchase
                    .getAvailableUsersMaxCount()

                    .flatMap {
                        updateUsersCount(it)
                    }
                    .onErrorReturn {
                        userLocal.getById(PrefProvider.userId).map {
                            it.chatUsersCount?:0
                        }.blockingFirst()
                    }
        }

Бьют несколько раз ручку:

Вызвано: rx.exceptions.CompositeException: произошло 2 исключения.

Как этот github.com/ReactiveX/RxJava/issues/3679

Тогда я знаю, что использование toBlocking - не лучшая идея. Смотрите сообщение здесь .

Через некоторое время я решил намного лучше:

 override fun getActualUsersMaxCount(): Observable<Int> {

    val remote = remotePurchase
            .getAvailableUsersMaxCount()
            .flatMap {
                updateUsersCount(it)
            }.onErrorReturn { -1 }

    return zip(remote, userLocal.getById(PrefProvider.userId).map {
        it.chatUsersCount ?: 0
    }, { remoteCount, localCount ->

        if(remoteCount!= -1) remoteCount else localCount

    })
}

Так что теперь я почти контролирую ситуацию. Если я получил ошибку из сети, я могу проверить ее и получить локальный результат

Но какой вариант лучше, как вы думаете? Может быть, есть более простое решение?

1 Ответ

0 голосов
/ 27 апреля 2018

Вы можете использовать onErrorResumeNext, чтобы избежать вызова blockingFirst во втором решении. Это делает его лучшим решением, по моему мнению. Не уверен, о каких двух исключениях вы говорите. Могу дать больше контекста о том, что они есть, поскольку я не вижу проблемы.

override fun getActualUsersMaxCount(): Observable<Int> {
    return remotePurchase
        .getAvailableUsersMaxCount()
        .flatMap {
             updateUsersCount(it)
        }
        .onErrorResumeNext(
                 userLocal.getById(PrefProvider.userId).map {
                 it.chatUsersCount?:0
             })
}
...