Unit 5: ์ธํฐ๋ท์์ Retrofit Library๋ฅผ ํ์ฉํ์ฌ Image๋ฅผ ๊ฐ์ ธ์ค๋ ์ค์ต์ ํฉ๋๋ค.
private const val BASE_URL =
"https://android-kotlin-fun-mars-server.appspot.com"
private val retrofit = Retrofit.Builder().addConverterFactory(ScalarsConverterFactory.create())
private val retrofit =
Retrofit.Builder().addConverterFactory(ScalarsConverterFactory.create()).baseUrl(
BASE_URL
).build()
interface MarsApiService {
fun getPhotos() : String
}
interface MarsApiService {
@GET("photos")
fun getPhotos() : String
}
โ๏ธ์ฑ๊ธํค ์ ์ธ์ ์ธ์คํด์ค๊ฐ ํ๋๋ง ์์ฑ๋๋ ๊ฒ์ ๋ณด์ฅํด์ฃผ๋ฉฐ ์ด ๊ฐ์ฒด๋ ํ๋์ ์ ์ญ ํฌ์ธํฐ๋ฅผ ๊ฐ์ต๋๋ค. ๊ฐ์ฒด ์ด๊ธฐํ๋ ์ค๋ ๋ ์์ ์ ๋ณด์ฅ๋ฐ์ผ๋ฉฐ access์ ์คํ๋ฉ๋๋ค. ์ด ์ฑ์์ Retrofit ์ธ์คํด์ค๋ ํ๋๋ง ํ์ํ๋ฏ๋ก ์ฑ๊ธํค์ ํตํด ์์ฑํฉ๋๋ค.
object MarsApi {
val retrofitService: MarsApiService by lazy {
retrofit.create(MarsApiService::class.java)
}
}
โ๏ธViewModelScope
viewModelScope์ ์ฑ์ ๊ฐ ViewModel์ ๋์์ผ๋ก ์ ์๋ ๊ธฐ๋ณธ ์ ๊ณต ์ฝ๋ฃจํด ๋ฒ์์
๋๋ค. ์ด ๋ฒ์์์ ์คํ๋ ๋ชจ๋ ์ฝ๋ฃจํด์ ViewModel์ด ์ญ์ ๋๋ฉด ์๋์ผ๋ก ์ทจ์๋ฉ๋๋ค.
interface MarsApiService {
@GET("photos")
suspend fun getPhotos(): String
}
fun getMarsPhotos() {
viewModelScope.launch {
val listResult = MarsApi.retrofitService.getPhotos()
marsUiState = listResult
}
}
๊ทธ๋ผ ๋ค์๊ณผ ๊ฐ์ด ์๋ฒ๋ก๋ถํฐ Jsonํํ๋ก ์ ๋ณด๋ฅผ ๋ฐ์์ฌ ์ ์๊ฒ ๋ฉ๋๋ค.
ํ์ง๋ง ๋ง์ฝ ์ฌ์ฉ์๊ฐ ๋ฐ์ดํฐ๋ฅผ ๋๊ณ ์ฑ์ ์คํํ๋ค๋ฉด ์ฑ์ด ๊ณง๋ฐ๋ก ์ข ๋ฃ๋๋ ๋ฒ๊ทธ๊ฐ ๋จ์์์ต๋๋ค.์ฐ๋ฆฌ๋ ์ด๋ฌํ ์ํฉ์ ํด๊ฒฐํ ์ ์์ง๋ง ์ต๋ํ ์ฌ์ฉ์ ์นํ์ ์ด๊ฒ ์ฑ์ด ์คํ๋์ง ์๋ ์ด์ ๋ฅผ ์์ธ์ฒ๋ฆฌ๋ฅผ ์ฌ์ฉํด ๋ณด์ฌ์ค๋ค๋ฉด ์ข์ต๋๋ค.
์๋ฒ์ ์ฐ๊ฒฐํ๋ ๋์ ๋ฐ์ํ ์ ์๋ ์์ธ๋ ๋ค์๊ณผ ๊ฐ์ต๋๋ค.
viewModelScope.launch {
try {
val listResult = MarsApi.retrofitService.getPhotos()
marsUiState = listResult
} catch (e: IOException) {
}
}
์์ง ์ด ์ฑ์์๋ ์๋ฒ๋ก ๋ฐ์ดํฐ๋ฅผ ์์ฒญํ ๋ ์์ฒญ ์ํ๋ฅผ ๋ณด์ฌ์ฃผ์ง ๋ชปํฉ๋๋ค.
sealed interface MarsUiState {
data class Success(val photos: String) : MarsUiState
object Error : MarsUiState
object Loading : MarsUiState
}
var marsUiState: MarsUiState by mutableStateOf(MarsUiState.Loading)
private set
private fun getMarsPhotos() {
viewModelScope.launch {
marsUiState = try {
val listResult = MarsApi.retrofitService.getPhotos()
MarsUiState.Success(listResult)
} catch (e: IOException) {
MarsUiState.Error
}
}
}
fun HomeScreen(
marsUiState: MarsUiState,
modifier: Modifier = Modifier
) {
when (marsUiState) {
is MarsUiState.Loading -> LoadingScreen(modifier)
is MarsUiState.Success -> ResultScreen(marsUiState.photos, modifier)
is MarsUiState.Error -> ErrorScreen(modifier)
}
}
-์คํจ ํ๋ฉด-
-๋ก๋ฉ ํ๋ฉด-
-์ฑ๊ณต ํ๋ฉด-
@Serializable
data class MarsPhoto(
val id: String, val img_src: String
)
โ๏ธ @SerialName ์ด๋ ธํ ์ด์ : Json์ Key์ด๋ฆ์ด Kotlin ๊ฐ์ฒด์ ๋งค๊ฐ๋ณ์๋ค์ ์ด๋ฆ๊ณผ ๊ฐ์์ผ ๊ฐ๊ฐ์ ๋ง๊ฒ ํ์ฑ์ด ๋ฉ๋๋ค. ํ์ง๋ง Json๋ ๋ณ์๋ช ์ ์ค๋ค์ดํฌ ํ๊ธฐ๋ฒ์ผ๋ก ํ๋๋ฐ Kotlin์ ๊ฒฝ์ฐ Camel ํ๊ธฐ๋ฒ์ ์ฌ์ฉํฉ๋๋ค. Kotlin ๊ฐ์ฒด๊ฐ ๋ฌด์กฐ๊ฑด์ ์ผ๋ก Json์ Key์ด๋ฆ์ ๋ฐ๋ผํ๋ค๋ฉด Kotlin์ ์์ฑ์ ์ด์ง๋ฝ๊ฒ ํ๊ฑฐ๋ ๊ถ์ฅ ์์ฑ์ ๋ฒ์ด๋ ์ ์์ด @SerialName ์ด๋ ธํ ์ด์ ์ ์ฌ์ฉํ์ฌ Json์ Key์ด๋ฆ๊ณผ Kotlin ๊ฐ์ฒด์ ๋ณ์๋ช ์ ๋งตํํ ์ ์์ต๋๋ค.
@Serializable
data class MarsPhoto(
val id: String,
@SerialName(value = "img_src")
val imgSrc: String
)