Android中response未关闭异常,该在何处调用response.close()?
解决OkHttp拦截器中的
java.lang.IllegalStateException异常 问题原因
这个异常是因为OkHttp不允许在未关闭之前响应的情况下发起新请求。你的拦截器里有两处未正确关闭响应对象的问题:
- 首次请求得到的
initialResponse处理完401/403逻辑后没关闭 - 刷新令牌请求返回的
responseNewToken用完body后没关闭
修复后的代码
class AuthInterceptor() : Interceptor { @Throws(IOException::class) override fun intercept(chain: Interceptor.Chain): Response { val originalRequest = chain.request() val authenticationRequest = request(originalRequest) val initialResponse = chain.proceed(authenticationRequest) try { if (initialResponse.code == 401 || initialResponse.code == 403) { var responseNewToken: retrofit2.Response<*>? = null try { responseNewToken = SessionManager.refreshToken?.let { RetrofitBuilder.api(ApiService::class.java) .refreshAuthorizationToken(TokenRefreshRequest(it, it, null)) .execute() } // 修正逻辑判断:用&&替代||,避免空指针风险 if (responseNewToken != null && responseNewToken.code() == 200) { responseNewToken.body()?.let { response -> SessionManager.token = response.token SessionManager.refreshToken = response.refreshToken } } } finally { // 关闭刷新令牌的响应对象 responseNewToken?.close() } } } finally { // 关闭首次请求的响应对象(我们不会返回这个响应,必须手动释放) initialResponse.close() } val newAuthenticationRequest = request(originalRequest) return chain.proceed(newAuthenticationRequest) } private fun request(originalRequest: Request): Request { return originalRequest.newBuilder() .addHeader("Authorization", "Bearer ${SessionManager.token}") .addHeader("Accept", "application/json") .build() } }
关键修改说明
- 用
try-finally包裹响应对象的使用流程,确保无论是否出现异常,响应都会被关闭 - 修正刷新令牌后的判断逻辑,把
||改成&&,避免空指针异常 - 分别对
initialResponse和responseNewToken调用close()方法,释放OkHttp的响应资源
内容的提问来源于stack exchange,提问作者Lagos77
相关产品推荐
相关产品推荐

