我正在使用 Retrofit、OkHttp、Kotlin 协程来发出 HTTP 请求。
当服务器返回不成功的结果(例如 404)时,我会抛出一个自定义异常,它是
IOException
的子类型。问题:
如何确保当我抛出自定义异常(
IOException
的子类型)时,堆栈跟踪指向最初发出请求的代码(例如catApi.callThatReturns404()
)?
限制:
示例代码
fun main(): Unit = runBlocking {
val api = createCatApi()
api.callThatReturns404()
}
private fun createCatApi(): CatApi {
val url = "https://cat-fact.herokuapp.com/"
val httpClient = OkHttpClient.Builder()
.addInterceptor { chain ->
val response = chain.proceed(chain.request())
if (!response.isSuccessful) {
throw SubTypeOfIOException(response)
}
response
}
.build()
val retrofit = Retrofit.Builder()
.baseUrl(url)
.addConverterFactory(JacksonConverterFactory.create(ObjectMapper().registerKotlinModule()))
.client(httpClient)
.build()
return retrofit.create<CatApi>()
}
interface CatApi {
@GET("factss")
suspend fun callThatReturns404(): Collection<Any>
}
抛出
SubTypeOfIOException
时的堆栈跟踪
Exception in thread "main" com.SubTypeOfIOException: 404
at com.MainKt$createCatApi$$inlined$-addInterceptor$1.intercept(OkHttpClient.kt:1082)
我想要什么
Exception in thread "main" com.retrofit_test.SubTypeOfIOException: 404
at com.retrofit_test.Main.main(Main.kt:15)
Caused by: com.SubTypeOfIOException: 404
at com.MainKt$createCatApi$$inlined$-addInterceptor$1.intercept(OkHttpClient.kt:1082)
有趣的事情:当我从测试中调用此类代码并抛出
IOException
时,堆栈跟踪包含我想要的信息。如果在测试中我抛出 IOException
的子类型,则堆栈跟踪不包含此类信息
版本:
如果缺少框架与协程有关,https://github.com/Anamorphosee/stacktrace-decoroutinator可能会有所帮助。