web-dev-qa-db-ja.com

インターセプターで例外をスローすると、レトロフィットがクラッシュします

私はいくつかの認証を処理するインターセプターを持っています。認証が失敗すると、例外がスローされます。私が見つけたものによると、例外をスローすると、例外を処理する場所でonFailureが呼び出されるはずです。残念ながら、これは発生せず、アプリは完全にクラッシュします。私は何かが欠けているに違いないと確信していますが、私はそれを理解できないようです。ここの誰かが助けてくれることを願っています:)

以下のコードとスタックトレース:

val client = OkHttpClient.Builder()
     // Add interceptor that throws
     .addInterceptor { chain ->
         throw Exception("test")
     }
     .build()

retrofit = Retrofit.Builder()
                .baseUrl(baseURL)
                .client(client)
                .build()

api = retrofit.create(ApiInterface::class.Java)


// Create api call...

apicall.enqueue(object : Callback<T> {
    override fun onResponse(call: Call<T>?, response: retrofit2.Response<T>?) {
        // ....
    }

    override fun onFailure(call: Call<T>?, t: Throwable?) {
        // Expect to go here to handle the Exception. But the app crashes
    }
})

スタックトレース:

E/AndroidRuntime: FATAL EXCEPTION: OkHttp Dispatcher
                  Process: com.testapp.test.debug, PID: 28891
                  Java.lang.Error: Java.lang.Exception: test
                      at Java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.Java:1168)
                      at Java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.Java:636)
                      at Java.lang.Thread.run(Thread.Java:764)
                   Caused by: Java.lang.Exception: test
                      at com.testapp.test.data.networking.RetrofitWebApi$client$1.intercept(RetrofitWebApi.kt:90)
                      at com.testapp.test.data.networking.RetrofitWebApi$client$1.intercept(RetrofitWebApi.kt:76)
                      at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.Java:92)
                      at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.Java:67)
                      at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.Java:185)
                      at okhttp3.RealCall$AsyncCall.execute(RealCall.Java:135)
                      at okhttp3.internal.NamedRunnable.run(NamedRunnable.Java:32)
                      at Java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.Java:1162)
                      at Java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.Java:636) 
                      at Java.lang.Thread.run(Thread.Java:764) 
16
Djangow

OkHttpは、Interceptorの場合にのみ、IOExceptionで発生する例外をキャッチします。これを行うコードを見ることができます ここ 、関連する部分(簡略化)は次のとおりです:

try {
  Response response = getResponseWithInterceptorChain();
} catch (IOException e) {
  responseCallback.onFailure(RealCall.this, e);
}

したがって、コードを次のように変更すると、期待どおりにonFailureメソッドでコールバックが返されます。

val client = OkHttpClient.Builder()
     // Add interceptor that throws
     .addInterceptor { chain ->
         throw IOException("test")
     }
     .build()
25
zsmb13