반응형
Retrofit
설명
- API 통신을 도와주는 라이브러리
- 기존의 HttpConnection을 활용한 방법보다 비동기 처리가 쉽고, 속도도 다른 라이브러리보다 빠른 장점을 갖는다.
- 내부적으로 OkHttp를 사용한다.
- 상세 사용법은 아래 참고
기본 예제
manifests/AndroidManifest.xml- INTERNET 퍼미션 추가 필요
<uses-permission android:name="android.permission.INTERNET" />
build.gradle
dependencies {
...
implementation 'com.squareup.retrofit2:retrofit:2.9.0'
implementation 'com.squareup.retrofit2:converter-gson:2.9.0'
}
Comment
data class Comment(
var postId: Int,
var id: Int,
var name: String,
var email: String,
var body: String
)
DemoApi
interface DemoApi {
@GET("todos/{id}/comments")
fun getComments(@Path("id") id: Int): Call<List<Comment>>
}
호출
val retrofit = Retrofit.Builder()
.baseUrl("https://jsonplaceholder.typicode.com/")
.addConverterFactory(GsonConverterFactory.create())
.build()
val demoApi = retrofit.create(DemoApi::class.java)
demoApi.getComments(1).enqueue(object: Callback<List<Comment>>{
override fun onResponse(call: Call<List<Comment>>, response: Response<List<Comment>>) {
Toast.makeText(this@MainActivity, response.body().toString(), Toast.LENGTH_SHORT).show()
}
override fun onFailure(call: Call<List<Comment>>, t: Throwable) {
TODO("Not yet implemented")
}
})
RxJava를 활용한 예제
- 기본적인 코드는 위 내용과 동일
dependencies {
...
implementation "com.squareup.retrofit2:adapter-rxjava2:2.3.0"
implementation "io.reactivex.rxjava2:rxandroid:2.0.1"
}
DemoApi
interface DemoApi {
@GET("todos/{id}/comments")
fun getComments(@Path("id") id: Int): Observable<List<Comment>> // Call에서 Observable로 변경
}
사용
fun callApi() {
val retrofit = Retrofit.Builder()
.baseUrl("https://jsonplaceholder.typicode.com/")
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.build()
val demoApi = retrofit.create(DemoApi::class.java)
val disposable = demoApi.getComments(1)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(
{ comments -> Toast.makeText(this, comments.toString(), Toast.LENGTH_SHORT).show() },
{ error -> Toast.makeText(this, error.toString(), Toast.LENGTH_SHORT).show() }
)
// disposable.dispose() // 호출시 HTTP 통신 도중 종료
}
OkHttp 사용 예제
fun callApi() {
val client = OkHttpClient.Builder()
.connectTimeout(15, TimeUnit.SECONDS)
.readTimeout(15, TimeUnit.SECONDS)
.build()
val retrofit = Retrofit.Builder()
.client(client) // okHttp 클라이언트 추가
.baseUrl("https://jsonplaceholder.typicode.com/")
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.build()
val demoApi = retrofit.create(DemoApi::class.java)
val disposable = demoApi.getComments(1)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(
{ comments -> Toast.makeText(this, comments.toString(), Toast.LENGTH_SHORT).show() },
{ error -> Toast.makeText(this, error.toString(), Toast.LENGTH_SHORT).show() }
)
// disposable.dispose() // 호출시 HTTP 통신 도중 종료
}
Interceptor 사용 예제
fun callApi() {
val client = OkHttpClient.Builder()
.connectTimeout(15, TimeUnit.SECONDS)
.readTimeout(15, TimeUnit.SECONDS)
.addInterceptor(CustomInterceptor()) // Interceptor 추가
.build()
val retrofit = Retrofit.Builder()
.client(client)
.baseUrl("https://jsonplaceholder.typicode.com/")
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(GsonConverterFactory.create())
.build()
val demoApi = retrofit.create(DemoApi::class.java)
val disposable = demoApi.getComments(1)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(
{ comments -> Toast.makeText(this, comments.toString(), Toast.LENGTH_SHORT).show() },
{ error -> Toast.makeText(this, error.toString(), Toast.LENGTH_SHORT).show() }
)
// disposable.dispose() // 호출시 HTTP 통신 도중 종료
}
inner class CustomInterceptor : Interceptor {
override fun intercept(chain: Interceptor.Chain): Response {
Log.d("TEST", "${chain.request().method()} - ${chain.request().url()}")
val request = chain.request().newBuilder().addHeader("token", "test-token").build()
val response = chain.proceed(request)
return response
}
}
Converter 사용 예제
fun callApi() {
val client = OkHttpClient.Builder()
.connectTimeout(15, TimeUnit.SECONDS)
.readTimeout(15, TimeUnit.SECONDS)
.build()
val retrofit = Retrofit.Builder()
.client(client)
.baseUrl("https://jsonplaceholder.typicode.com/")
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.addConverterFactory(CustomConverterFactory()) // Converter 설정
.build()
val demoApi = retrofit.create(DemoApi::class.java)
val disposable = demoApi.getComments(1)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(
{ comments -> Toast.makeText(this, comments.toString(), Toast.LENGTH_SHORT).show() },
{ error -> Toast.makeText(this, error.toString(), Toast.LENGTH_SHORT).show() }
)
// disposable.dispose() // 호출시 HTTP 통신 도중 종료
}
inner class CustomConverterFactory : Converter.Factory() {
override fun responseBodyConverter(type: Type, annotations: Array<Annotation>, retrofit: Retrofit): Converter<ResponseBody, *>? {
val gson = Gson()
val adapter = gson.getAdapter(TypeToken.get(type))
return object : Converter<ResponseBody, Any> {
override fun convert(value: ResponseBody): Any? {
try {
val jsonReader = gson.newJsonReader(value.charStream())
val result = adapter.read(jsonReader)
return result
} finally {
value.close()
}
}
}
}
}
참고
반응형
'Development > Android' 카테고리의 다른 글
[Android] SharedPreferences (0) | 2021.02.09 |
---|---|
[Android] Build APK (0) | 2021.02.09 |
[Android] Lottie (0) | 2021.02.09 |
[Android] Http Network (0) | 2021.02.09 |
[Android] File IO (0) | 2021.02.09 |