MVVM은 Model(모델), View(뷰), ViewModel(뷰모델)의 약자로, 사용자 인터페이스(UI)와 비즈니스 로직을 분리하여 개발의 효율성과 유지보수성을 높이는 아키텍처 패턴
특히 Android 개발에서 MVVM은 Jetpack의 ViewModel, LiveData, Data Binding과 같은 아키텍처 컴포넌트와 함께 사용되어 구조화된 앱 개발을 가능
역할: 데이터와 비즈니스 로직을 담당
예시: Room 데이터베이스, Retrofit을 통한 네트워크 통신, Repository 패턴 등이 포함
역할: 사용자에게 UI를 표시하고, 사용자 입력을 처리
예시: Activity, Fragment, XML 레이아웃 등이 해당
역할: Model과 View 사이의 중재자로서, UI 관련 데이터를 관리하고, View에 필요한 데이터를 제공
특징: ViewModel은 View의 생명주기와 독립적으로 존재하며, LiveData를 통해 데이터 변화를 관찰할 수 있음
사용자가 View에서 액션을 취함
View는 ViewModel에 해당 액션을 전달
ViewModel은 Model을 통해 데이터를 요청하거나 처리
Model은 데이터를 반환하고, ViewModel은 이를 가공하여 LiveData에 설정
View는 LiveData를 관찰하고 있다가 데이터가 변경되면 UI를 업데이트
data class User(val id: Int, val name: String, val email: String)
class UserRepository {
fun getUsers(): List<User> {
// 실제로는 Retrofit이나 Room을 통해 데이터를 가져옴
return listOf(
User(1, "원형", "1hyung@example.com"),
User(2, "홍길동", "hong@example.com")
)
}
}
class UserViewModel : ViewModel() {
private val repository = UserRepository()
private val _users = MutableLiveData<List<User>>()
val users: LiveData<List<User>> get() = _users
fun fetchUsers() {
_users.value = repository.getUsers()
}
}
class MainActivity : AppCompatActivity() {
private lateinit var viewModel: UserViewModel
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
// setContentView 및 뷰 바인딩 설정
viewModel = ViewModelProvider(this).get(UserViewModel::class.java)
viewModel.users.observe(this, Observer { users ->
// RecyclerView 어댑터에 데이터 설정
})
viewModel.fetchUsers()
}
}
관심사의 분리: UI와 비즈니스 로직을 분리하여 코드의 명확성과 유지보수성을 높임
테스트 용이성: ViewModel과 Model은 UI와 독립적으로 테스트할 수 있음
재사용성: ViewModel은 여러 View에서 재사용이 가능하여 코드 중복을 줄임
생명주기 관리: ViewModel은 Activity나 Fragment의 생명주기와 독립적으로 존재하여 데이터 손실을 방지
복잡성 증가: 간단한 앱에서는 MVVM의 구조가 오히려 복잡할 수 있음
데이터 바인딩의 남용: 과도한 데이터 바인딩은 디버깅을 어렵게 할 수 있음
ViewModel의 역할 초과: ViewModel에 너무 많은 로직을 담으면 또 다른 문제를 야기할 수 있음
MVVM 아키텍처는 Kotlin과 Android 개발에서 코드의 구조화와 유지보수성을 높이는 데 큰 도움이 됨. Jetpack의 아키텍처 컴포넌트와 함께 사용하면 더욱 효과적이며, 특히 중대형 프로젝트에서 그 진가를 발휘함. 하지만 프로젝트의 규모와 복잡도를 고려하여 적절하게 적용하는 것이 중요.
소프트웨어 아키텍처 패턴은 애플리케이션의 구조를 정의하여 유지보수성과 확장성을 향상
Android 개발에서 주로 사용되는 세 가지 패턴은 다음과 같음
Model: 데이터와 비즈니스 로직을 관리
View: 사용자 인터페이스를 담당하며, 사용자 입력을 Controller에 전달
Controller: 사용자 입력을 처리하고, Model과 View를 연결
특징:
간단한 구조로 이해하기 쉬움
View와 Controller 간의 결합도가 높아, 테스트와 유지보수가 어려울 수 있음
Model: 데이터와 비즈니스 로직을 관리
View: 사용자 인터페이스를 담당하며, 사용자 입력을 Presenter에 전달
Presenter: Model과 View 사이의 중재자로서, 로직을 처리하고 View를 업데이트
특징:
View와 Presenter 간의 명확한 분리로 테스트 용이성이 향상
Presenter와 View 간의 강한 결합으로 인해 복잡성이 증가할 수 있음
Model: 데이터와 비즈니스 로직을 관리
View: 사용자 인터페이스를 담당하며, ViewModel을 관찰
ViewModel: Model과 View 사이의 중재자로서, 데이터를 가공하여 View에 제공
특징:
View와 ViewModel 간의 결합도가 낮아 유지보수가 용이
데이터 바인딩을 통해 UI 업데이트가 자동화
| 패턴 | 테스트 용이성 | 결합도 | 복잡성 | 사용 사례 |
|---|---|---|---|---|
| MVC | 낮음 | 높음 | 낮음 | 간단한 앱 |
| MVP | 중간 | 중간 | 중간 | 중간 규모 앱 |
| MVVM | 높음 | 낮음 | 높음 | 대규모 앱 |