もうこれはテンプレ化しておきます。
Retrofit の話が中心となります。
Retrofit
Converter
JSON 形式のレスポンスをパースして変換するのは、Gson か Moshi が人気のように思います。
var retrofit = Retrofit. Builder ( )
. baseUrl ( "https://api.example.com" )
. addConverterFactory ( GsonConverterFactory. create ( ) )
. build ( )
var retrofit = Retrofit. Builder ( )
. baseUrl ( "https://api.example.com" )
. addConverterFactory ( MoshiConverterFactory. create ( ) )
. build ( )
retrofit/retrofit-converters at master · square/retrofit
今回は、Kotlin Serialization を利用した「Kotlin Serialization Converter」を使います。
ExperimentalSerializationApi なのですがね。
val contentType = "application/json" . toMediaType ( )
val retrofit = Retrofit. Builder ( )
. baseUrl ( "https://example.com/" )
. addConverterFactory ( Json. asConverterFactory ( contentType) )
. build ( )
JakeWharton/retrofit2-kotlinx-serialization-converter: A Retrofit 2 Converter.Factory for Kotlin serialization.
Call Adapter
通信の非同期処理はどれに任せるか。
var retrofit = Retrofit. Builder ( )
. baseUrl ( "https://api.example.com" )
. addCallAdapterFactory ( RxJavaCallAdapterFactory. create ( ) )
. build ( )
retrofit/retrofit-adapters at master · square/retrofit
Coroutine を使った Jake製の「Kotlin Coroutine Adapter」は 今では DEPRECATED。
JakeWharton/retrofit2-kotlin-coroutines-adapter: A Retrofit 2 adapter for Kotlin coroutine's Deferred type.
Retrofit は 2.6.0+ で、内部に suspend function をサポートしてるので、特に、.addCallAdapterFactory()
を使わなくてもよい。
@GET ( "users/{id}" )
suspend fun user ( @Path ( "id" ) id: Long) : User
retrofit/CHANGELOG.md at master · square/retrofit
HttpLoggingInterceptor
OkHttpClient に HTTP関連のログを吐かせます。
--> POST /greeting http/1.1
Host: example.com
Content-Type: plain/text
Content-Length: 3
Hi?
--> END POST
<-- 200 OK (22ms)
Content-Type: plain/text
Content-Length: 6
Hello!
<-- END HTTP
HttpLoggingInterceptor.Level (OkHttp Logging Interceptor 3.14.0 API)
val logging = HttpLoggingInterceptor ( )
logging. setLevel ( Level. BASIC)
val client = OkHttpClient. Builder ( )
. addInterceptor ( logging)
. build ( )
okhttp/okhttp-logging-interceptor at master · square/okhttp
まとめ
Dagger の Module にしておきます。
テンプレート化してください、と言わんばかりに
よく似たものをあちこちで見かけますよね。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@Module
@InstallIn(SingletonComponent::class)
object NetworkModule {
@Provides
@Singleton
fun provideOkHttpClient(): OkHttpClient {
val interceptor = HttpLoggingInterceptor().apply {
level = if (BuildConfig.DEBUG) Level.BODY else Level.NONE
}
return OkHttpClient.Builder()
.addInterceptor(interceptor)
.build()
}
@Provides
@Singleton
fun provideRetrofit(okHttpClient: OkHttpClient): Retrofit {
val contentType = "application/json".toMediaType()
val json = Json {
ignoreUnknownKeys = true
isLenient = true
} // *
return Retrofit.Builder()
.client(okHttpClient)
.baseUrl(BASE_URL)
.addConverterFactory(json.asConverterFactory(contentType))
.build()
}
@Provides
@Singleton
fun provideUserService(retrofit: Retrofit): UserService {
return retrofit.create(UserService::class.java)
}
@Provides
@Singleton
fun provideDetailService(retrofit: Retrofit): DetailService {
return retrofit.create(DetailService::class.java)
}
private const val BASE_URL = "https://api.example.com"
}
見通しも良くなります。
コピペでどうぞ。
(おわり)