如何在ViewModel中通过Retrofit2与RxJava获取响应头?
如何在ViewModel中获取Retrofit+RxJava请求的响应头
要拿到服务响应的特定头,核心是让Retrofit返回包含完整响应信息的retrofit2.Response对象,而不是直接返回响应体。下面是具体的修改步骤:
1. 修改ApiService接口的返回类型
把原来直接返回Single<ServiceResponse>改成返回Single<retrofit2.Response<ServiceResponse>>,这样Retrofit会把响应头、状态码、响应体等所有信息封装进来:
interface ApiService { @GET("/repos/{owner}/data") fun loadData( @Path("owner") owner: String, @Query("page") page: Int, @Query("per_page") perPage: Int ): Single<retrofit2.Response<ServiceResponse>> // 调整返回类型 }
2. 更新NetworkProvider的方法返回类型
对应修改NetworkProvider中loadDataSingle的返回类型,和ApiService保持一致:
class NetworkProvider { private lateinit var authService: ApiService init { createService() } private fun createService() { // 原有的Retrofit初始化逻辑不需要改动 } // 调整返回类型 fun loadDataSingle(owner: String, page: Int, perPage: Int): Single<retrofit2.Response<ServiceResponse>> { return authService.loadData(owner, page, perPage) } }
3. 更新Repository的方法返回类型
同样修改Repository中loadDataSingle的返回类型:
class Repository { private val networkProvider = NetworkProvider() // 调整返回类型 fun loadDataSingle(owner: String, page: Int, perPage: Int): Single<retrofit2.Response<ServiceResponse>> { return networkProvider.loadDataSingle(owner, page, perPage) } }
4. 在ViewModel中读取响应头
现在在subscribe回调里,你会收到retrofit2.Response<ServiceResponse>对象,通过response.headers()可以获取所有响应头,用get("目标头名称")拿到特定头;响应体依然从response.body()获取:
class MyViewModel(val repository: Repository) : ViewModel { private val disposable = CompositeDisposable() val responseLiveData = MutableLiveData<SingleEvent<ServiceResponse>>() val errorLiveData = MutableLiveData<SingleEvent<Boolean>>() private fun loadDataPaged(owner: String, page: Int, perPage: Int) { disposable.add( repository.loadDataSingle(owner, page, perPage) .subscribeOn(Schedulers.io()) .subscribe({ response -> // 示例:获取名为"X-Total-Count"的响应头 val totalCount = response.headers().get("X-Total-Count") // 这里可以根据需求处理拿到的头信息,比如存入变量或其他LiveData // 获取原响应体并发送到LiveData response.body()?.let { serviceResponse -> responseLiveData.postValue(SingleEvent(serviceResponse)) } ?: run { // 处理响应体为空的异常情况 errorLiveData.postValue(SingleEvent(true)) } }, { exc -> errorLiveData.postValue(SingleEvent(true)) }) ) } }
内容的提问来源于stack exchange,提问作者vitiello.antonio
相关产品推荐
相关产品推荐

