Skip to content

Instantly share code, notes, and snippets.

@kohendrix
Created February 1, 2019 03:42
Show Gist options
  • Select an option

  • Save kohendrix/bfa0fe41c1d586b6e8c9825e282b3952 to your computer and use it in GitHub Desktop.

Select an option

Save kohendrix/bfa0fe41c1d586b6e8c9825e282b3952 to your computer and use it in GitHub Desktop.
HttpRequest client using Volley and Coroutines
import android.util.Log
import com.android.volley.Response
import com.android.volley.VolleyError
import com.android.volley.toolbox.JsonObjectRequest
import com.example.koheiando.twittervolleysample.TvsApplication
import kotlinx.coroutines.suspendCancellableCoroutine
import org.json.JSONObject
import kotlin.coroutines.resume
import kotlin.coroutines.resumeWithException
import kotlin.reflect.KClass
abstract class HttpRequest {
abstract val url: String
abstract val method: Int
abstract val queryParams: Map<String, String>
abstract fun headers(): Map<String, String>
companion object {
val TAG = this::class.java.simpleName
}
protected suspend fun <T : HttpResponse> request(responseClass: KClass<T>, jsonRequest: JSONObject?, retryCount: Int? = null): T {
return suspendCancellableCoroutine { continuation ->
val success = Response.Listener<JSONObject> { response ->
continuation.resume(
responseClass.java.newInstance().parseJson(response) as T
)
}
val error = Response.ErrorListener { error -> continuation.resumeWithException(error) }
val request = object : JsonObjectRequest(method, addQueryParams(), jsonRequest, success, error) {
override fun getHeaders(): Map<String, String> = headers()
override fun parseNetworkError(volleyError: VolleyError): VolleyError {
return volleyError.networkResponse?.let {
Log.e(TAG, volleyError.networkResponse.headers.toString())
Log.e(TAG, String(volleyError.networkResponse.data))
VolleyError(String(volleyError.networkResponse.data))
} ?: volleyError
}
}
request.retryPolicy = retryCount?.let { HttpRetryPolicy(it) } ?: HttpRetryPolicy()
continuation.invokeOnCancellation { request.cancel() }
try {
HttpRequestQueue.getInstance(TvsApplication.getAppContext()).addToRequestQueue(request)
} catch (e: Exception) {
continuation.resumeWithException(e)
}
}
}
protected suspend fun <T : HttpResponse> request(responseClass: KClass<T>, body: String, retryCount: Int? = null): T {
return suspendCancellableCoroutine { continuation ->
val success = Response.Listener<JSONObject> { response ->
continuation.resume(
responseClass.java.newInstance().parseJson(response) as T
)
}
val error = Response.ErrorListener { error -> continuation.resumeWithException(error) }
val request = object : JsonObjectRequest(method, addQueryParams(), null, success, error) {
override fun getHeaders(): Map<String, String> = headers()
override fun getBody(): ByteArray {
return body.toByteArray()
}
override fun parseNetworkError(volleyError: VolleyError): VolleyError {
return volleyError.networkResponse?.let {
Log.e(TAG, volleyError.networkResponse.headers.toString())
Log.e(TAG, String(volleyError.networkResponse.data))
VolleyError(String(volleyError.networkResponse.data))
} ?: volleyError
}
}
request.retryPolicy = retryCount?.let { HttpRetryPolicy(it) } ?: HttpRetryPolicy()
continuation.invokeOnCancellation { request.cancel() }
try {
HttpRequestQueue.getInstance(TvsApplication.getAppContext()).addToRequestQueue(request)
} catch (e: Exception) {
continuation.resumeWithException(e)
}
}
}
private fun addQueryParams(): String {
return url + if (queryParams.isNotEmpty()) queryParams.keys.fold("?") { pre, cur -> "$pre$cur=${queryParams[cur]!!}" } else ""
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment