8

App crashes on this line if response won't come.

chain.proceed(requestBuilder.build())

Here is my class for RetrofitClient

class RetrofitClient {

    private val apiService: ApiServiceInterface

    init {
        val builder = Retrofit.Builder()
        builder.baseUrl(RequestParameters.BASE_URL)
        builder.addConverterFactory(GsonConverterFactory.create())
        builder.addCallAdapterFactory(RxJava2CallAdapterFactory.create())//added for adapter
        builder.client(getClient())
        val retrofit = builder.build()
        apiService = retrofit.create(ApiServiceInterface::class.java)
    }

    companion object {
        private var clientInstance: RetrofitClient? = null
        lateinit var context: Context

        fun getInstance(): RetrofitClient {
            if (clientInstance == null) {
                clientInstance = RetrofitClient()
            }
            return clientInstance as RetrofitClient
        }
    }

    fun getApiInterface(): ApiServiceInterface {
        return apiService
    }

    private fun getClient(): OkHttpClient {

        val httpClient = OkHttpClient.Builder()
        httpClient.readTimeout(25, TimeUnit.SECONDS)
        httpClient.connectTimeout(25, TimeUnit.SECONDS)

        httpClient.addInterceptor { chain ->
            val original = chain.request()

            val requestBuilder = original.newBuilder()
                    .header(RequestParameters.X_API, RequestParameters.H_XAPI_KEY)
                    .method(original.method(), original.body())

            chain.proceed(requestBuilder.build())
        }

        // set your desired log level
        val logging = HttpLoggingInterceptor()
        logging.level = HttpLoggingInterceptor.Level.HEADERS
        logging.level = HttpLoggingInterceptor.Level.BODY
        httpClient.addInterceptor(logging)

        return httpClient.build()
    }
}

Here is the error in log:

1542609097.397 26572-26572/com.app.mylife W/System.err: java.net.SocketTimeoutException: timeout
1542609097.397 26572-26572/com.app.mylife W/System.err:     at okio.Okio$4.newTimeoutException(Okio.java:230)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okio.AsyncTimeout.exit(AsyncTimeout.java:285)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okio.AsyncTimeout$2.read(AsyncTimeout.java:241)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okio.RealBufferedSource.indexOf(RealBufferedSource.java:345)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okio.RealBufferedSource.readUtf8LineStrict(RealBufferedSource.java:217)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http1.Http1Codec.readHeaderLine(Http1Codec.java:212)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http1.Http1Codec.readResponseHeaders(Http1Codec.java:189)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.CallServerInterceptor.intercept(CallServerInterceptor.java:88)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.connection.ConnectInterceptor.intercept(ConnectInterceptor.java:45)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.cache.CacheInterceptor.intercept(CacheInterceptor.java:93)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.BridgeInterceptor.intercept(BridgeInterceptor.java:93)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RetryAndFollowUpInterceptor.intercept(RetryAndFollowUpInterceptor.java:125)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.logging.HttpLoggingInterceptor.intercept(HttpLoggingInterceptor.java:212)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
1542609097.398 26572-26572/com.app.mylife W/System.err:     at com.app.mylife.retrofit.RetrofitClient$getClient$1.intercept(RetrofitClient.kt:64)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:147)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okhttp3.internal.http.RealInterceptorChain.proceed(RealInterceptorChain.java:121)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okhttp3.RealCall.getResponseWithInterceptorChain(RealCall.java:200)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okhttp3.RealCall.execute(RealCall.java:77)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at retrofit2.OkHttpCall.execute(OkHttpCall.java:174)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at retrofit2.adapter.rxjava2.CallExecuteObservable.subscribeActual(CallExecuteObservable.java:41)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.Observable.subscribe(Observable.java:10179)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at retrofit2.adapter.rxjava2.BodyObservable.subscribeActual(BodyObservable.java:34)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.Observable.subscribe(Observable.java:10179)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.internal.operators.observable.ObservableSubscribeOn$1.run(ObservableSubscribeOn.java:39)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.Scheduler$1.run(Scheduler.java:134)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.internal.schedulers.ScheduledRunnable.run(ScheduledRunnable.java:59)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at io.reactivex.internal.schedulers.ScheduledRunnable.call(ScheduledRunnable.java:51)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.util.concurrent.FutureTask.run(FutureTask.java:266)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:301)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1162)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:636)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.lang.Thread.run(Thread.java:764)
1542609097.399 26572-26572/com.app.mylife W/System.err: Caused by: java.net.SocketException: Socket closed
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.net.SocketInputStream.read(SocketInputStream.java:203)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at java.net.SocketInputStream.read(SocketInputStream.java:139)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okio.Okio$2.read(Okio.java:139)
1542609097.399 26572-26572/com.app.mylife W/System.err:     at okio.AsyncTimeout$2.read(AsyncTimeout.java:237)
1542609097.400 26572-26572/com.app.mylife W/System.err:     ... 39 more
Rohit5k2
  • 17,948
  • 8
  • 45
  • 57
Kishan Solanki
  • 13,761
  • 4
  • 85
  • 82

2 Answers2

0

Try this code way.. make retrofit object creation part.

class ApiClient {

companion object {
    val BASE_URL = "https://simplifiedcoding.net/demos/"
    var retrofit: Retrofit? = null
    fun getClient(): Retrofit? {
        if (retrofit == null) {
            val interceptor = HttpLoggingInterceptor()
            interceptor.level = HttpLoggingInterceptor.Level.BODY
            val client = OkHttpClient.Builder().apply {
            readTimeout(20, TimeUnit.SECONDS)
            writeTimeout(20, TimeUnit.SECONDS)
            connectTimeout(20, TimeUnit.SECONDS)
            addInterceptor(interceptor)
            addInterceptor { chain ->
                var request = chain.request()
                request = request.newBuilder()
                        .build()
                val response = chain.proceed(request)
                response
            }
            }
            retrofit = Retrofit.Builder()
                    .baseUrl(BASE_URL)
                    .client(client.build())

                    .addConverterFactory(GsonConverterFactory.create())
                    .build()

        }

        return retrofit
    }
}

}

make interface for api calling..

interface ApiInterface {
@GET("marvel")
fun getData(): Call<List<Hero>>

}

In activity or fragment called api like this way i hope you create response pojo class

var apiInterface: ApiInterface = ApiClient.getClient()!!.create(ApiInterface::class.java)
    var hero: Call<List<Hero>>
    hero = apiInterface.getData()
    hero.enqueue(object : Callback<List<Hero>> {
        override fun onFailure(call: Call<List<Hero>>?, t: Throwable?) {
            closeDialog(dialog)
            Toast.makeText(mContext, t?.message, Toast.LENGTH_SHORT).show()
            Log.d("Error:::",t?.message)
        }

        override fun onResponse(call: Call<List<Hero>>?, response: Response<List<Hero>>?) {
           mHeroDataList.clear()
            if (response != null && response.isSuccessful && response.body() != null) {
                closeDialog(dialog)
                mHeroDataList .addAll(response.body()!!)
                setAdapter(mHeroDataList)
            }
        }

    })
  • This doesn't help because its the same code as I do. – Kishan Solanki Nov 19 '18 at 08:26
  • 1
    increase time out value. –  Nov 19 '18 at 08:27
  • 10
    Actually, the problem is app crashes if response won't come until timeout seconds. How could we handle this? My concern is app should not crash if response won't come(whether it is 30 secs or 60 secs). Increasing timeout value is not an ideal solution. – Kishan Solanki Nov 19 '18 at 08:47
0

This code throws Exception when there is no network. So you can catch the exception using try and catch block. You can put try and catch where your are calling the network. And it won't crash your App again.

Jeevan Rupacha
  • 3,055
  • 1
  • 15
  • 29