일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | ||||
4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 |
18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 | 26 | 27 | 28 | 29 | 30 | 31 |
- Di
- 운영체제
- JUnit
- JetPack
- markdown
- test
- O.S
- Compose
- 데드락
- Constraint Layout
- 더티비트
- 마크다운
- SOLID
- LiveData
- design pattern
- git
- Class.class
- 리드미
- readme
- spring
- Android
- github
- kotlin
- OS
- 다단계 큐
- Spring Boot
- 깃허브
- android study jam
- Data Binding
- coroutine flow
- Today
- Total
차지
[Android] LiveData -> Coroutine Flow 본문
MVVM 패턴을 적용하다보면 View와 ViewModel의 관심사 분리를 위해 노력하곤 합니다.
그 중 이벤트 처리와 데이터를 다루는 객체로 LiveData를 사용했습니다.
기존에 사용하던 LiveData에서 Coroutine Flow로 마이그레이션하며 개념을 정리하려 합니다.
짧은 사전 설명
xml에서 버튼을 클릭하면 Fragment에서는 원하는 화면으로 전환합니다.
해당 동작을 dataBinding을 사용해 아래처럼 구현했습니다.
Fragment에선 viewModel의 flow를 구독합니다.
flow 데이터의 값을 수신하면 원하는 화면으로 전환합니다.
xml에서 viewModel의 emit 함수를 실행시킵니다.
viewModel에선 flow 값을 발행시킵니다.
LiveData -> Flow
Domain Layer에서 반환값을 liveData로 사용하면 Android 패키지를 import하게 됩니다.
하지만 Domain Layer는 kotlin으로만 이루어져 있어 Coroutine Flow를 사용하게 되었습니다.
SharedFlow, StateFlow?
LiveData는 StateFlow와 유사하다는 얘기를 듣고 SharedFlow와 StateFlow의 차이가 궁금해 정리하게 되었습니다.
Hot Stream (SharedFlow)
Hot Stream은 방송국과 같습니다.
구독자가 없어도 값을 계속 방출한다는 특징이 있으며, 모든 구독자는 같은 데이터 스트림을 공유합니다.
이는 pub-sub 패턴과 유사하다고 볼 수 있습니다.
fun testSharedFlow(data: Flow<String>) {
val sharedFlow: SharedFlow<String> = data.sharedIn(
scope = viewModelScope,
started: SharingStarted.Eagerly,
replay = 0
)
}
일반 flow에 sharedIn 메서드를 붙여 SharedFlow로 사용할 수 있습니다.
sharedIn 메서드에는 매개변수가 세개 필요합니다.
- 어떤 코루틴 스코프에서 작동할지
- 데이터 방출 시작방식
- 각 새 collector로 재생할 항목의 수
여기서 2번째인 started 매개변수의 설명을 더하자면 세가지 방식이 존재합니다.
- 첫 구독자가 나타날 때 방출하는 Lazily 방식
- 선언과 함께 방출하는 Eagerly 방식
- 구독자가 존재하는 동안만 방출하는 등의 WhileSubscribed 방식
해당 SharingStarted 객체는 Cold Stream에서도 매개변수로 활용하게 됩니다.
Cold Stream (StateFlow)
Cold Stream은 Lazy합니다. LiveData의 쓰임새를 그대로 사용하려면 StateFlow를 사용하게 됩니다.
구독자가 생길 때마다 새 데이터 스트림을 생성한다는 특징이 있으며, 구독자가 생겨야 값을 방출하기 시작합니다.
이는 observer 패턴과 유사하다고 볼 수 있습니다.
fun testStateFlow(data: Flow<String>) {
val stateFlowExample: StateFlow<String> = data.stateIn(
scope = viewModelScope,
started = SharingStarted.Eagerly,
initialValue = ""
)
}
일반 flow에 stateIn 메서드를 붙여 StateFlow로 사용할 수 있습니다.
stateIn 메서드에는 매개변수가 세개 필요합니다.
- 어떤 코루틴 스코프에서 작동할지
- 데이터 방출 시작방식
- 디폴트값
References
'Android > Android' 카테고리의 다른 글
[Java] Reflection (0) | 2022.06.03 |
---|---|
[Kotlin] inline function (0) | 2022.02.23 |
[Android] Single Live Event & Event wrapper (0) | 2022.01.25 |
[Android] Two - way Data Binding (0) | 2022.01.19 |
[DI] Android에서의 DI 첫걸음 (0) | 2022.01.07 |