AAC ViewModel과 MVVM ViewModel

이윤설·2024년 12월 10일
0

안드로이드 연구소

목록 보기
7/33

서론

안드로이드로 앱 개발을 하다보면, ViewModel 이라는 단어를 자주 접하게 된다.
ViewModel의 종류에는 2가지, MVVM 뷰모델과 AAC 뷰모델이 있다.
하지만 두 단어가 모두 "뷰모델" 이라는 단어를 포함한다고 해서, 비슷한 개념이라고 착각하기 쉬운데, 그렇지 않다.

예를 들어 "파스타" 라는 대분류 안에 "토마토 파스타", "오일 파스타", "까르보나라" 등 다양한 파스타 종류가 소분류로서 존재하는 것이 아니다.

마치 "배" 라는 단어가 먹는 배, 타는 배, 사람의 배, 계산할 때의 배 등등 완전히 다른 것처럼 뷰모델도 이름만 같을 뿐 다른 역할을 한다고 생각하면 좋을 것이다.

MVVM ViewModel

  • MVVM 패턴은 마틴 파울러에 의해 나온 MVP 패턴에서 파생된 패턴이다. MVVM 패턴의 목표는 비즈니스 로직과 프레젠테이션 로직을 UI로부터 분리하는 것이다. 비즈니스 로직과 프레젠테이션 로직을 UI로부터 분리하게 되면 테스트, 유지 보수 측면에서 용이하다.

  • MVVM 패턴에서의 ViewModel은 View에 연결될 데이터와 메서드를 구현하고, 상태가 변화하게 되면 변경 알림 이벤트를 통해 View에게 상태 변화를 알려준다.

  • View는 ViewModel의 상태 변화를 옵저빙 한다.
    옵저버 패턴을 사용하기 때문에 View에서는 ViewModel을 알고 있지만, ViewModel은 View를 알지 못한다.

  • ViewModel과 Model 사이의 관계는 1:n의 관계다. 따라서 View는 자신이 이용할 ViewModel을 선택하여 상태 변화 알림을 받게 된다. ViewModel은 View가 쉽게 사용할 수 있도록 Model의 데이터를 가공하여 View에게 제공한다.

AAC ViewModel

1. AAC ViewModel의 역할

AAC의 ViewModel은 안드로이드 애플리케이션의 화면 회전 같은 환경 변화에서 UI 데이터를 유지하는 데 집중하는 클래스다. 예를 들어, 사용자가 로그인한 정보를 화면 회전 후에도 유지할 수 있도록 도와준다. 화면 회전 시 Activity는 새로 생성되지만, ViewModel은 데이터를 그대로 유지하여 불필요한 데이터 재로딩을 방지해준다.
AAC Viewmodel은 딱 이 역할만 담당한다.
ViewModel을 생성하고 거기에 유저 로그인 정보를 넣었을 뿐, 그렇다고 이게 MVVM 패턴이 되지는 않는다.

2. AAC의 ViewModel을 MVVM의 ViewModel로써 사용할 수 있다.

대부분의 예제를 보면, MVVM을 구현할 때 AAC ViewModel을 사용한다.
AAC ViewModel은 MVVM의 ViewModel과 전혀 상관이 없다고 했는데, 인터넷에 올라온 예제들이 모두다 잘못된 예제일까?

그렇지 않다. AAC의 ViewModel을 MVVM의 ViewModel로써 사용할 수 있다.
MVVM의 뷰모델의 역할은 위에서 보았듯이 뷰와 모델 사이에서 데이터를 관리하고 바인딩해주는 것이다. 뷰모델이 가지고 있는 데이터를 옵저버블하게 해주고, 뷰에서는 데이터 바인딩으로 그것을 구독하고 있으면 되는 것이다.

AAC ViewModel이라고 그게 안될리가 없다. 오히려 화면 회전시 데이터를 유지시켜주는 기능까지 있으므로 더 좋다. AAC ViewModel에 LiveData를 사용하여 바인딩 시킬 수 있다.

3. 주의할 점

안드로이드 개발을 하면서 MVVM패턴을 사용하려고 한다면, 꼭 AAC의 ViewModel을 사용하지 않아도 MVVM구현은 가능하다.

그러나 놓치지 말아야 할 것은, AAC의 뷰모델은 MVVM에서 말하는 ViewModel과 다르다는 것을 아는 것이다. 이걸 모르고 AAC ViewModel을 MVVM ViewModel처럼 사용한다면 개발 도중 어려움이 생길 가능성이 크다. 예를 들어, AAC ViewModel은 ViewModelProviders를 사용해서 ViewModel을 만드는데, 이렇게 만들어진 뷰모델은 그 액티비티에서 딱 하나만 존재하게 된다.
액티비티 한 개 내에서만 유효한 싱글톤인 셈이다. 이런 특성은 일반적인 MVVM에서는 강제되는 것이 아니기 때문에 혼란이 올 수 있다.

4. 뷰와 뷰모델의 관계 -> 1대n 혹은 1대1

  • 안드로이드 권장사항: 뷰 한개에 1개 또는 필요에 따라서는 n개를 사용해도 좋다고 한다.
    어차피 MVVM 패턴에서는 뷰와 뷰모델은 1:n 관계이기 때문이다. 개발자는 필요에 따라서 얼마든지 UserPersonalDataViewModel, UserAccountViewModel 등등 여러가지 뷰모델로 나눠서 사용이 가능하다. 다만 UserPersonalDataViewModel을 한번 생성하면, 그 액티비티에서 UserPersonalDataViewModel을 여러번 생성해도 그것은 싱글톤이기 때문에 하나의 객체만 계속 사용된다는 것이다.
  • 구글: 구글은 하나의 뷰에 하나의 뷰모델만 두고 사용하는 것을 권장한다. SignUpActivity가 있다면, SignUpViewModel 하나만 놔두고, 그 안에 여러 Model과 LiveData를 사용하는 것을 권장하고 있다.
    • 이것은 원래의 MVVM 원칙과 맞지 않는 내용이다. 그렇다고 해서 구글의 방식이 나쁘다는 것은 아니다. 구글이 추천하는 방식과 원래 MVVM의 원칙 중 어떤것이 더 자신의 프로젝트에 맞는지는 개발자가 판단할 몫이다.

5. AAC ViewModel과 MVVM ViewModel의 차이점

구분AAC ViewModelMVVM에서의 ViewModel
주요 역할화면 회전 등 환경 변화에서 UI 데이터를 유지UI와 모델을 분리하고, 데이터를 관리하고 바인딩
기능데이터를 화면 회전 후에도 유지데이터 바인딩, LiveData/StateFlow 등을 통해 UI 상태 관리
사용 목적UI 상태 유지, 화면 회전 후 데이터 복원UI와 비즈니스 로직 분리, 데이터 처리 및 상태 관리
권장 사항UI 상태 유지가 중요한 경우 사용UI와 비즈니스 로직을 명확히 분리하는 경우 사용

의문점

MVVM이나 AAC 둘 다 똑같은 ViewModel(import androidx.lifecycle.ViewModel)을 import 해서 사용한다. 그런데 어떻게 ViewModel이 2개로 나뉜다는건지 이해가 가지 않는다. import 하는게 각각 다르면 이해가 가는데, aac나 mvvm 둘 다 같은 뷰모델을 import 한다!

해답

실제로 두 방식은 본질적으로 동일한 ViewModel 클래스를 사용한다.
차이점은 "사용 방식"과 "아키텍처 패턴"에 있다.

AAC ViewModel vs MVVM ViewModel

공통점

  • 같은 androidx.lifecycle.ViewModel import
  • 같은 생명주기 관리 메커니즘
  • viewModelScope 등 동일한 기능

차이점

  1. 데이터 관리 방식

    • AAC: LiveData 중심
    • MVVM: StateFlow/Flow 중심
  2. 상태 표현 방법

    • AAC: 단일 데이터 노출
    • MVVM: 상태 클래스를 통한 복합적 상태 관리

코드로 비교

// AAC ViewModel
class UserViewModel : ViewModel() {
    // LiveData 사용
    private val _users = MutableLiveData<List<User>>()
    val users: LiveData<List<User>> = _users
}

// MVVM ViewModel
class UserViewModel : ViewModel() {
    // StateFlow 사용
    private val _uiState = MutableStateFlow<UiState>(UiState.Loading)
    val uiState: StateFlow<UiState> = _uiState
}

즉, 같은 ViewModel 클래스를 사용하지만 "어떻게 상태를 관리하고 표현하느냐"의 차이이다.

결론: 기술적으로 같은 ViewModel, 패러다임만 다를 뿐이다.

정리

  1. AAC ViewModel과 MVVM ViewModel은 서로 다른 역할을 한다.
  2. MVVM ViewModel은 옵저버 패턴을 사용한다. 그래서 View에서는 ViewModel을 알고 있지만, ViewModel은 View를 알지 못한다.
  3. AAC ViewModel은 MVVM ViewModel의 역할을 대체할 수 있다.
    • 하지만 중요한 것은, AAC ViewModel의 특성을 명확히 알아야 한다는 것이다.
    • 대표적인 AAC ViewModel의 특성은 "Singleton"이라는 점이다.
  4. 뷰와 뷰모델의 관계 -> 1대n 혹은 1대1 둘 중 아무거나 사용해도 상관없다. 개발자가 판단할 몫이다.

https://leveloper.tistory.com/216
https://medium.com/@jungil.han/%EC%95%84%ED%82%A4%ED%85%8D%EC%B2%98-%EC%BB%B4%ED%8F%AC%EB%84%8C%ED%8A%B8-viewmodel-%EC%9D%B4%ED%95%B4%ED%95%98%EA%B8%B0-2e4d136d28d2
https://medium.com/kenneth-android/android-mvvm-viewmodel%EA%B3%BC-aac-viewmodel%EC%9D%98-%EC%B0%A8%EC%9D%B4-8c0d54922e07
https://wooooooak.github.io/android/2019/05/07/aac_viewmodel/

profile
화려한 외면이 아닌 단단한 내면

0개의 댓글

관련 채용 정보