You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

API请求失败时加载指示器未隐藏问题(需用指定ViewModel代码)

解决API请求失败时加载指示器无法隐藏的问题

问题场景

首次调用API获取条目列表时,初始阶段显示加载指示器;数据成功加载时,加载指示器可正常隐藏,但API请求失败时,加载指示器无法隐藏。

问题分析

从提供的代码来看,API请求失败时的错误回调中虽设置了Resource(Status.ERROR, it),但RxJava默认在IO线程执行订阅回调,而LiveData.setValue()必须在主线程调用才能触发UI状态更新,导致错误状态无法传递到UI层,加载指示器因此无法隐藏。

解决方案

通过以下两种方式确保LiveData的状态更新在主线程执行,让UI层能接收错误状态并隐藏加载指示器:

方案1:添加主线程调度器

在API请求的Observable链中加入observeOn(AndroidSchedulers.mainThread()),强制订阅回调在主线程执行:

private fun getIncomingStiDest() {
    val queries = mapOf(
        "last_status" to stiDest,
        "type" to incoming
    )

    getStiDestActionLiveData.value = Resource(Status.LOADING)
    getDashboardCounterUseCase.execute(queries)
        .asPageLoadEventSource()
        .observeOn(AndroidSchedulers.mainThread()) // 切换到主线程执行回调
        .subscribe({
            getStiDestActionLiveData.value = Resource(Status.SUCCESS, it)
        }, {
            getStiDestActionLiveData.value = Resource(Status.ERROR, null, it.message)
        })
        .also { disposables.add(it) } // 用CompositeDisposable管理订阅,避免内存泄漏
}

方案2:使用postValue()替代setValue()

postValue()会自动切换到主线程执行状态更新,无需额外调度器:

private fun getIncomingStiDest() {
    val queries = mapOf(
        "last_status" to stiDest,
        "type" to incoming
    )

    getStiDestActionLiveData.postValue(Resource(Status.LOADING))
    getDashboardCounterUseCase.execute(queries).asPageLoadEventSource().subscribe({
        getStiDestActionLiveData.postValue(Resource(Status.SUCCESS, it))
    }, {
        getStiDestActionLiveData.postValue(Resource(Status.ERROR, null, it.message))
    }).also { disposables.add(it) }
}

额外提示

  • 确保UI层能正确识别Resource类的Status.ERROR状态,执行隐藏加载指示器的逻辑。
  • 建议在ViewModel中维护CompositeDisposable,在ViewModel销毁时调用disposables.clear()清理所有订阅,避免内存泄漏。

内容的提问来源于stack exchange,提问作者Rizki Ramdhani

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 16:10:21