Ang OkHttp ay isang mataas na pagganap na HTTP-client para sa Android at Kotlin, na binuo ng kumpanyang Square bilang pundasyon para sa Retrofit at iba pang mga network library. Nagbibigay ito ng mahusay na pamamahala ng koneksyon, built-in na caching, at suporta para sa HTTP/2. Ayon sa datos ng Square, 2025, ang OkHttp ay nagpoproseso ng bilyun-bilyong mga request araw-araw sa mga aplikasyon sa buong mundo.
Mga Pangunahing Punto
OkHttp ay isang mahusay na HTTP-client para sa Java, Android at Kotlin, na binuo ng Square. Ang library ay nagbibigay ng low-level na API para sa pagsasagawa ng mga HTTP request na may suporta para sa HTTP/2, SPDY, WebSocket at awtomatikong pagpapanumbalik ng koneksyon sa mga pagkabigo ng network.
Ang OkHttp ay lumitaw noong 2013 bilang tugon sa pangangailangan para sa isang maaasahang HTTP-client na malulutas ang mga problema ng HttpURLConnection — kakulangan ng connection pool, mahinang suporta para sa HTTP/2 at hindi maginhawang API. Pagsapit ng 2025, ang OkHttp ay ginagamit sa antas ng system ng Android API: Ang OkHttp ay naka-embed sa implementasyon ng HttpURLConnection mula noong Android 4.4 (API 19).
Ayon sa Google I/O 2024, pinoproseso ng OkHttp ang higit sa 70% ng lahat ng HTTP request sa Android ecosystem. Ito ay posible dahil ang OkHttp ay ang transport layer para sa Retrofit, Apollo GraphQL, Firebase at marami pang ibang library. Ang mga developer ay awtomatikong nakakakuha ng functionality ng OkHttp nang hindi ito eksplicitong ikinokonekta.
Ang arkitektura ng OkHttp ay binuo sa isang chain ng mga interceptor (Interceptor chain). Ang bawat request ay dumadaan sa isang pagkakasunod-sunod ng mga interceptor na maaaring magbago ng Request, Response o huminto sa pagpapatupad. Ang arkitekturang ito ay kahawig ng pattern ng Chain of Responsibility at nagbibigay-daan sa flexible na pagpapalawak ng functionality.
Kapag ang aplikasyon ay nagpadala ng request, ginagawa ng OkHttp ang mga sumusunod na hakbang: nire-resolve ang DNS, pumipili ng koneksyon mula sa pool (o gumagawa ng bago), binubuksan ang TLS handshake (kung HTTPS), nagpapadala ng HTTP request, tumatanggap ng response at ibinabalik ito sa aplikasyon. Ang RealCall ay isang panloob na klase na namamahala sa buong lifecycle ng request mula sa paggawa hanggang sa pagkumpleto.
Awtomatikong hinahawakan ng OkHttp ang mga pag-redirect (302, 301), inuulit ang mga request sa mga pagkabigo ng network (retry), sumusunod sa keep-alive protocol at sumusuporta sa transparent gzip compression. Ang developer ay hindi kailangang magsulat ng code para sa mga operasyong ito — awtomatikong ginagawa ito ng OkHttp batay sa mga header ng server.
HTTP/2 ay nagbibigay-daan sa pagpapadala ng maraming request sa pamamagitan ng isang TCP connection nang sabay-sabay, nang walang pag-block (head-of-line blocking, na katangian ng HTTP/1.1). Awtomatikong ginagamit ng OkHttp ang HTTP/2 kung sinusuportahan ng server ang protocol na ito at transparent na lumilipat sa HTTP/1.1 kapag kinakailangan.
Ang multiplexing ng HTTP/2 ay lalong mahalaga para sa mga mobile application, kung saan ang pagkaantala ng pagtatatag ng koneksyon (TCP + TLS) ay maaaring 100–300 ms. Sa halip na 10 magkakasunod na koneksyon, gumagamit ang OkHttp ng isa, na nagbabawas ng kabuuang pagkaantala ng 40–60% sa mga tipikal na Android device na may hindi matatag na koneksyon.
Interceptor ay isang interface na may iisang pamamaraan na intercept(Chain) na tumatanggap ng Request, gumagawa ng mga aksyon at nagbabalik ng Response. Ang mga interceptor ay may dalawang uri: application interceptor (idinadagdag sa pamamagitan ng addInterceptor) at network interceptor (addNetworkInterceptor).
Ang mga application interceptor ay isinaaktibo bago mabuo ang HTTP request — nakikita nila ang orihinal na Request at ang panghuling Response pagkatapos ng lahat ng pagbabago. Ang mga network interceptor ay isinaaktibo sa antas ng network: nakikita nila ang request pagkatapos ng gzip compression, pagdagdag ng Content-Length headers, pag-redirect at pag-retry. Ang mga network interceptor ay hindi tinatawag kung ang response ay nakuha mula sa cache.
| Uri ng Interceptor | Paraan ng pagdagdag | Kailan tinatawag | Nakakakita ng cache |
|---|---|---|---|
| Application Interceptor | addInterceptor() | Bago at pagkatapos ng request | Oo |
| Network Interceptor | addNetworkInterceptor() | Sa antas ng network | Hindi |
Sa praktika, ang mga interceptor ng OkHttp ay lumulutas ng tatlong pangunahing gawain: awtorisasyon (pagdagdag ng Authorization header), pag-log (HttpLoggingInterceptor para sa debugging) at pag-retry (awtomatikong pag-uulit ng request sa mga pagkabigo ng network). Sa pamamagitan ng pagsasama ng maraming interceptor, maaaring bumuo ng kumpletong pipeline ng pagproseso ng request nang walang pagdoble ng code sa bawat HTTP tawag ng aplikasyon.
Ang pagkakasunud-sunod ng pagdagdag ng mga interceptor ay mahalaga: ang Interceptor na idinagdag una ay isinasagawa una sa pagpasok at huli sa paglabas. Para sa NetworkInterceptor, ang pagkakasunud-sunod ay tinutukoy ng network stack. Ang inirerekomendang pagkakasunud-sunod: AuthInterceptor (nagdadagdag ng token), LoggingInterceptor (nagla-log ng request), RetryInterceptor (umuulit sa mga pagkabigo).
Para sa debugging ng mga network request, ginagamit ang HttpLoggingInterceptor — isang handa na interceptor mula sa Square. Ito ay nagla-log ng pamamaraan, URL, mga header at katawan ng request at response. Mga antas ng pag-log: BASIC (pamamaraan + URL + code), HEADERS (may mga header) at BODY (buong request at response). Ang BODY ay kapaki-pakinabang sa pag-develop, ngunit sa produksyon ito ay hindi pinapagana para sa mga kadahilanang pangseguridad at pagganap.
Tingnan natin ang basic GET request sa pamamagitan ng OkHttp. Una, ginagawa ang OkHttpClient — isang mabigat na bagay na ginagawa nang isang beses at muling ginagamit. Pagkatapos, ang Request na may URL ay binubuo, at ang request ay isinasagawa nang sabaysabay sa pamamagitan ng execute o hindi sabaysabay sa pamamagitan ng enqueue.
val client = OkHttpClient.Builder()
.connectTimeout(15, TimeUnit.SECONDS)
.readTimeout(15, TimeUnit.SECONDS)
.build()
val request = Request.Builder()
.url("https://api.github.com/users/octocat")
.header("Accept", "application/vnd.github.v3+json")
.build()
val response = client.newCall(request).execute()
println(response.body()?.string())
Para sa asynchronous na pagpapatupad ginagamit ang pamamaraang enqueue, na tumatanggap ng Callback. Isinasagawa ng OkHttp ang request sa isang background thread at ibinabalik ang resulta sa callback sa parehong thread. Para lumipat sa pangunahing thread ng Android, gamitin ang Handler o mga coroutine.
client.newCall(request).enqueue(object : Callback {
override fun onFailure(
call: Call, e: IOException
) {
println("Nabigo ang request: ${e.message}")
}
override fun onResponse(
call: Call, response: Response
) {
println(response.body()?.string())
}
})
Ang isang custom na Interceptor ay nagdadagdag ng Bearer token sa bawat request. Sinusuri ng interceptor ang pagkakaroon ng Authorization header, at kung ang token ay hindi pa nakatakda, idinadagdag ito mula sa imbakan. Sa 401 response, maaaring i-update ng interceptor ang token sa pamamagitan ng Authenticator.
class AuthInterceptor(
private val tokenProvider: () -> String?
) : Interceptor {
override fun intercept(chain: Interceptor.Chain): Response {
val originalRequest = chain.request()
val token = tokenProvider.invoke()
val request = originalRequest.newBuilder()
.header("Authorization", "Bearer $token")
.build()
return chain.proceed(request)
}
}
Ang connection pool (ConnectionPool) — ang pangunahing optimisasyon ng OkHttp, na nagbibigay-daan sa muling paggamit ng mga TCP connection para sa maraming request. Sa halip na gumawa ng bagong socket para sa bawat request, nag-iimbak ang OkHttp ng hanggang 5 hindi aktibong koneksyon (bilang default) sa loob ng 5 minuto, na nagbabawas ng pagkaantala ng 30–70% para sa mga paulit-ulit na request sa parehong host.
Ang caching ng mga response ay ipinapatupad sa pamamagitan ng Cache class. Para i-activate ang cache, sapat na na tukuyin ang direktoryo at maximum na laki sa OkHttpClient.Builder. Awtomatikong ni-ca-cache ng OkHttp ang mga GET response ayon sa Cache-Control, Expires at ETag headers, na ibinabalik ang naka-cache na data nang walang network request kung hindi pa ito luma.
val cacheDir = File(context.cacheDir, "http-cache")
val cache = Cache(cacheDir, 10L * 1024 * 1024)
val client = OkHttpClient.Builder()
.cache(cache)
.connectionPool(ConnectionPool(5, 5, TimeUnit.MINUTES))
.build()
Ang tamang configuration ng pool at cache ay lalong mahalaga para sa mga application na may madalas na request — mga news feed, chat, data update. Kung walang pool, ang bawat TCP connection ay nangangailangan ng three-way handshake (SYN, SYN-ACK, ACK) at potensyal na TLS handshake (2–3 round-trip), na nagdaragdag ng 100–500 ms sa bawat request.
Sinusuportahan din ng OkHttp ang WebSocket sa pamamagitan ng RealWebSocket class. Ang WebSocket connection ay itinatag sa pamamagitan ng HTTP handshake (101 Switching Protocols) at pagkatapos ay lumipat sa isang two-way na protocol. Awtomatikong nagpapadala ang OkHttp ng mga ping frame upang mapanatiling buhay ang koneksyon at muling kumokonekta kapag naputol. Ang WebSocket mula sa OkHttp ay katugma sa mga karaniwang endpoint tulad ng wss://echo.websocket.org.
Paggawa ng OkHttpClient para sa bawat request — ang pinakakaraniwang pagkakamali. Ang OkHttpClient ay naglalaman ng connection pool, cache at thread pool. Ang paggawa ng bagong instance para sa bawat request ay hindi lamang nagsasayang ng memorya, ngunit inaalis din ang benepisyo ng muling paggamit ng koneksyon. Ang OkHttpClient ay dapat na isang singleton sa pamamagitan ng DI container.
Ang hindi pagpansin sa pagsasara ng Response.body() ay humahantong sa pagtagas ng resources. Ang ResponseBody ay naglalaman ng InputStream na dapat isara pagkatapos basahin. Kung gagamitin ang body().string() o body().bytes(), awtomatikong isinasara ng OkHttp ang stream, ngunit sa pagbabasa ng body().byteStream() o body().charStream(), kinakailangan ang eksplicitong tawag sa close() sa finally block.
Kawalan ng paghawak ng Timeout — isa pang problema. Bilang default, ang OkHttp ay walang mga timeout (connectTimeout = 10 segundo, readTimeout = 10 segundo, writeTimeout = 10 segundo). Para sa mga mobile application na may hindi matatag na koneksyon, inirerekomenda na itakda ang connectTimeout 15–30 segundo at readTimeout 15–30 segundo, kung hindi, ang user ay maghihintay nang masyadong mahaba kapag mahina ang signal.
Mga Madalas Itanong
OkHttp ay isang low-level na HTTP-client na may manu-manong pamamahala ng Request at Response. Ang Retrofit ay isang high-level na wrapper na may mga annotation. Ginagamit ang OkHttp bilang transport para sa Retrofit, ngunit maaaring gumana nang nakapag-iisa nang walang karagdagang library.
Gumagamit ang OkHttp ng SSLSocketFactory para sa TLS handshake. Sinusuportahan ng library ang CertificatePinner para sa pag-pin ng certificate (Certificate Pinning), TrustManager para sa custom na validation at HostnameVerifier para sa pagsuri ng host name laban sa certificate.
Ang mga synchronous request ay nagtatapon ng IOException sa mga problema sa network. Ang mga asynchronous request ay tumatanggap ng onFailure na tawag na may IOException. Para sa HTTP errors (4xx, 5xx), ang response ay itinuturing na matagumpay — ang error code ay sinusuri sa pamamagitan ng response.isSuccessful().
Oo, ang OkHttp ay may built-in na suporta para sa WebSocket sa pamamagitan ng WebSocket class at WebSocketListener. Pagkatapos maitatag ang koneksyon, ang WebSocket ay nagbibigay-daan sa pagpapadala at pagtanggap ng mga mensahe sa real-time nang walang paulit-ulit na HTTP request.
I-disable ang mga awtomatikong pag-redirect sa pamamagitan ng followRedirects(false) at followSslRedirects(false) sa OkHttpClient.Builder. Ito ay kapaki-pakinabang kapag kailangan mong manu-manong hawakan ang pag-redirect, halimbawa, upang kunin ang token mula sa redirect URL.
Buod
Gagawa kami ng mobile application na turnkey
Gumagawa ang IT Sectr ng mga iOS at Android application para sa mga startup at negosyo mula noong 2017. Magpapayo kami sa iyo at magmumungkahi ng pinakamahusay na solusyon.
Basahin din