{{위키데이터 속성 추적}}
[[파일:MVVMPattern.png|500px|right|upright=1.5]]

'''모델-뷰-뷰 모델'''(model-view-viewmodel, MVVM)은 하나의 소프트웨어 [[아키텍처 패턴]]으로-[[마크업 언어]] 또는 GUI 코드로 구현하는-그래픽 사용자 인터페이스(뷰)의 개발을 [[비즈니스 로직]] 또는 [[프런트엔드와 백엔드 | 백-엔드 로직]](모델)로부터 분리시켜서 뷰가 어느 특정한 모델 플랫폼에 종속되지 않도록 해준다. MVVM의 뷰 모델은 값 변환기인데,<ref name="MVVM-eliminates-valueconverters">{{웹 인용|url=https://groups.google.com/forum/#!topic/wpf-disciples/P-JwzRB_GE8|title=Thought: MVVM eliminates 99% of the need for ValueConverters|author=Google groups}}</ref> 이는 뷰 모델이 모델에 있는 [[데이터 객체]]를 노출(변환)하는 책임을 지기 때문에 객체를 관리하고 표현하기가 쉬워진다는 것을 의미한다. 이러한 점에서, 뷰 모델은 뷰 보다는 더 모델인 것이며, 모든 뷰들의 디스플레이 로직을 제외한 대부분의 것들을 처리한다.<ref name="MVVM-eliminates-valueconverters"/> 뷰 모델은 '백-엔드 로직에 대한 접근'과 그 주변부의 '뷰에서 지원하는 [[유즈 케이스]] 집합'으로 구성되도록, [[중재자 패턴]]으로 구현할 수도 있다.

MVVM은 [[마틴 파울러]](Martin Fowler)의 '프레젠테이션 모델 디자인 패턴' 의 변형이다.<ref>{{웹 인용|url=http://martinfowler.com/eaaDev/PresentationModel.html|title=The Presentation Model Design Pattern|author=Martin Fowler|date=19 July 2004|publisher=Martin Fowler.com}}</ref><ref name="JoshSmith">{{저널 인용|last=Smith|first=Josh|date=February 2009|title=WPF Apps with the Model-View-ViewModel Design Pattern|url=http://msdn.microsoft.com/en-us/magazine/dd419663.aspx|journal=MSDN Magazine}}</ref> 이는 사용자 인터페이스의 [[사건 기반 프로그래밍|이벤트-기반 프로그래밍]]을 단순화하기 위해 [[마이크로소프트]]의 아키텍트인 켄 쿠퍼(Ken Cooper)와 테드 피터스(Ted Peters)에 의해 발명되었다. 이 패턴은 (마이크로소프트의 [[닷넷]] 그래픽 시스템인) [[윈도우 프레젠테이션 파운데이션|윈도우 프레젠테이션 파운데이션 (WPF)]] 및 (WPF의 인터넷 응용 프로그램 파생품인) [[실버라이트]]에 통합되었다.<ref name="JoshSmith" /> 마이크로소프트의 WPF 와 실버라이트 아키텍트인, 존 구스먼(John Gossman)은 2005년 [https://blogs.msdn.microsoft.com/johngossman/2005/10/08/introduction-to-modelviewviewmodel-pattern-for-building-wpf-apps/ 자신의 블로그에 MVVM을 발표]하였다.<ref name="JoshSmith" />

모델-뷰-뷰모델은 '''모델-뷰-바인더'''(model-view-binder)라고도 하는데, 특히 닷넷 플랫폼과 상관없이 구현된 경우를 지칭한다. ([[자바]]로 작성된 [[웹 프레임워크]]인) [[ZK]]와 ([[자바스크립트 라이브러리]]인) [[KnockoutJS]]는 모델-뷰-바인더를 사용한다.<ref name="JoshSmith"/><ref name="SMassey">{{웹 인용|last=Massey|first=Simon|title=Presentation Patterns in ZK|url=http://www.slideshare.net/simbo1905/design-patterns-in-zk-java-mvvm-as-modelviewbinder|accessdate=24 March 2012}}</ref><ref>{{웹 인용|author = Steve Sanderson |title = KnockoutJS |url = http://knockoutjs.com/documentation/observables.html}}</ref>

==MVVM 패턴의 구성 요소==
;모델 (Model)
:모델은 실제 상태 내용을 표현하는, [[도메인 모델]]을 참조하거나 (이는 객체-지향 접근법이라 한다), 또는 내용을 표현하는, [[데이터 접근 계층]]을 참조한다. (이는 데이터-중심 접근법이라 한다).
;뷰 (View)
:[[모델-뷰-컨트롤러]](MVC)와 [[모델-뷰-프리젠터]](MVP) 패턴에서와 같이, 뷰는 사용자가 화면에서 보는 것들에 대한 구조, 배치, 그리고 외관에 해당한다.<ref name="MSDN">{{웹 인용|url=https://msdn.microsoft.com/en-us/library/hh848246.aspx|title=The MVVM Pattern|website=msdn.microsoft.com|access-date=2016-08-29}}</ref> 모델을 보여서 표현하고 사용자와 뷰의 상호 작용(클릭, 키보드, 동작 등)을 수신하여, 이에 대한 처리를 뷰와 뷰 모델의 연결을 정의하고 있는 (속성, 이벤트 콜백 함수 등의) [[데이터 바인딩]](data binding, 데이터 연결)을 통하여 뷰 모델로 전달한다.
;뷰 모델 (View Model)
:뷰 모델은 공용 속성과 공용 명령을 노출하는 뷰에 대한 추상화(abstraction)이다. MVC 패턴의 컨트롤러나, MVP 패턴의 프리젠터(presenter, 발표자)를 대신하여, MVVM은 바인더(binder, 연결자)를 가지고 있는데, 이는 뷰 모델에 있는 뷰에 연결된 속성과 뷰 사이의 통신을 자동화 한다. 뷰 모델은 모델에 있는 데이터의 상태라고 설명했었다.<ref>{{웹 인용|author = Pete Weissbrod |title= Model-View-ViewModel Pattern for WPF: Yet another approach. |url = http://www.acceptedeclectic.com/2008/01/model-view-viewmodel-pattern-for-wpf.html |archiveurl = https://web.archive.org/web/20080201101909/http://www.acceptedeclectic.com/2008/01/model-view-viewmodel-pattern-for-wpf.html |archivedate = 2008-02-01}}</ref>
:뷰 모델과 MVP 패턴에 있는 프리젠터 사이의 주요한 차이점은 프리젠터는 뷰에 대한 참조를 가지고 있는 반면, 뷰 모델은 그렇지 않다는 것이다. 그 대신, 뷰는 뷰 모델의 속성에 직접 '연결된(binds)' 채로 업데이트를 주고 받는다. 효율적으로 작동하려면, '바인딩 기술(binding technology, 연결 기술)' 또는 '바인딩'을 하는 [[상용구 코드 | 상용구 코드 (boilerplate code)]]의 자동 생성이 필수이다.<ref name="MSDN" />
;바인더 (Binder, 연결자)
:MVVM 패턴에서는 선언적인 데이터와 '명령-바인딩(명령-연결)'이 내재되어 있다. 마이크로소프트 [[솔루션 스택]]에서, 바인더는 [[XAML]]이라는 [[마크업 언어]]이다.<ref>{{웹 인용|last=Wildermuth|first=Shawn|title=Windows Presentation Foundation Data Binding: Part 1|url=http://msdn.microsoft.com/en-us/library/aa480224.aspx|publisher=Microsoft|accessdate=24 March 2012}}</ref> 바인더는 뷰 모델과 뷰의 동기화를 위해 상용구 로직을 작성해야 하는 의무에서 개발자를 해방시켜 준다. 마이크로소프트 스택을 사용하지 않고 구현한다면, '선언적인 데이터 바인딩 기술' 이 있어야 이 패턴을 만들 수 있으며,<ref name="SMassey"/><ref>{{웹 인용|title=ZK MVVM|url=http://books.zkoss.org/wiki/Small_Talks/2012/February/New_Features_of_ZK_6#ZK_MVVM|publisher=Potix|accessdate=24 March 2012}}</ref> 바인더가 없다면, 그 대신 일반적인 MVP 나 MVC를 사용해야 할 것이고 더 많은 상용구 코드를 작성하게 (아니면 이를 다른 도구로 생성하게) 될 것이다.

== 근거 ==
MVVM은 뷰 계층에서 사실상 모든 [[GUI]] 코드를 제거하여, 뷰 계층의 개발을 패턴 나머지 부분에서 더 용이하게 분리하기 위해 WPF([[윈도 프리젠테이션 파운데이션]])의 [[데이터 바인딩]] 기능을 사용하도록 설계되어 있다.<ref name="JoshSmith" /> [[사용자 경험]](UX) 개발자는 GUI 코드를 직접 작성하는 대신, ([[XAML]] 같은) 프레임워크의 마크업 언어를 사용하여 뷰 모델에 대한 데이터 바인딩(연결)을 생성할 수 있으며, 이 뷰 모델은 응용 프로그램 개발자가 작성하고 관리하게 된다. 이러한 역할의 분리는 상호 작용 설계자가 비지니스 로직의 프로그래밍 보다는 UX 의 요구에 집중할 수 있도록 해준다. 그로 인해 응용 프로그램 계층별로 개발 흐름을 여러 개로 나누어서 생산성을 높일 수 있다. 설령 단일 개발자가 전체 코드 기반의 작업을 하게 되는 경우라 하더라도, 모델과 뷰를 적절히 분리하는 것이 더 생산적인데, 사용자 인터페이스는 일반적으로 최종-사용자의 피드백에 따라 개발 주기 과정에서 자주 그리고 뒤늦게 바뀌기 때문이다.

MVVM 패턴은 데이터를 가능한 순수한 응용 프로그램 모델에 가깝게 바인딩(연결)하는 [[데이터 바인딩]]과 프레임워크의 장점을 활용함과 동시에, MVC가 제공하는 기능 요소 개발의 분리라는 장점까지 해서, 이 둘을 다 얻으려고 시도한다.<ref name="JoshSmith" /><ref>{{저널 인용|author= John Gossman| title=Tales from the Smart Client: Introduction to Model/View/ViewModel pattern for building WPF apps| url= http://blogs.msdn.com/johngossman/archive/2005/10/08/478683.aspx}}</ref><ref>{{웹 인용|author = Karl Shifflett|title = Learning WPF M-V-VM.|url = http://karlshifflett.wordpress.com/2008/11/08/learning-wpf-m-v-vm/|access-date = 5 June 2009|archive-url = https://web.archive.org/web/20090413205731/http://karlshifflett.wordpress.com/2008/11/08/learning-wpf-m-v-vm/|archive-date = 13 April 2009|url-status = dead}}</ref> 이는 바인더(연결자), 뷰 모델, 그리고 어떤 비즈니스 계층에든 있는 데이터-검사 기능을 사용하여 들어오는 데이터를 검증한다. 결과적으로 모델과 프레임워크가 가능한 많은 작업을 수행하며, 뷰를 직접 조작하는 응용 프로그램 로직은 최소화하거나 아예 없애버린다.

== 비판 ==
이 패턴에 대한 비판은 MVVM 제작자인 존 구스만(John Gossman) 자신이 한 것인데,<ref>{{저널 인용|author= John Gossman| title= Tales from the Smart Client: Advantages and disadvantages of M-V-VM| url= https://docs.microsoft.com/en-gb/archive/blogs/johngossman/advantages-and-disadvantages-of-m-v-vm}}</ref> 단순한 UI 작업에서는 MVVM을 구현하는 부담이 "지나치게 과하다" 고 지적한다. 그가 말하길 응용 프로그램이 점점 더 커짐에 따라서, 뷰 모델을 폭 넓게 사용하기가 점점 더 어려워진다고 한다. 게다가 아주 큰 응용 프로그램에서 데이터 바인딩을 사용하게 되면 눈에 띄게 메모리를 소모하게 된다고 설명한다.

== 구현체 ==
=== 닷넷 프레임워크 ===
* [https://github.com/PrismLibrary/Prism/ Prism Library]
* [https://github.com/CaliburnFx/Caliburn Caliburn] / [https://caliburnmicro.com/ Caliburn.Micro]
* [https://github.com/DevExpress/DevExpress.Mvvm.Free DevExpress MVVM]
* [https://www.dotvvm.com/ DotVVM] open source project
* [http://www.mvvmlight.net/ MVVMLight Toolkit]
* [https://reactiveui.net/ ReactiveUI]
* [https://github.com/MugenMvvmToolkit/MugenMvvmToolkit Mugen MVVM Toolkit]
* [https://github.com/nventive/Uno Uno Framework - Open Source]
* [http://www.roboticarmsoftware.com/Rascl.aspx# Rascl]
* [https://www.mvvmcross.com/ MvvmCross]

=== 자바스크립트 프레임워크 ===
* [[앵귤러 (애플리케이션 플랫폼)|앵귤러]]
* [[리액트 (자바스크립트 라이브러리)]]
* [https://aurelia.io Aurelia]
* [http://durandaljs.com/ Durandal]
* [[Ember.js]]
* [[Ext JS]]
* [[Knockout.js]]
* [https://github.com/Tencent/omi/blob/master/tutorial/omi-mvvm.md Omi.js]
* [http://www.oracle.com/webfolder/technetwork/jet/index.html Oracle JET]
* [[Svelte]]
* [[Vue.js]]

== 같이 보기 ==
* [[다층 구조]]

== 각주 ==
{{각주}}

== 외부 링크 ==
* {{웹 인용 |url=https://code.msdn.microsoft.com/How-to-implement-MVVM-71a65441 |title=How to implement MVVM (Model-View-ViewModel) in TDD (test-driven development) |website=[[마이크로소프트 개발자 네트워크]] |publisher=Microsoft |확인날짜=2019-04-15 |archive-date=2019-04-15 |archive-url=https://web.archive.org/web/20190415052927/https://code.msdn.microsoft.com/How-to-implement-MVVM-71a65441 |url-status= }}
* {{웹 인용|url=https://blogs.msdn.microsoft.com/johngossman/2005/10/08/introduction-to-modelviewviewmodel-pattern-for-building-wpf-apps/ |title=Introduction to Model/View/ViewModel pattern for building WPF apps |website=[[마이크로소프트 개발자 네트워크]] |publisher=Microsoft}}
* [https://github.com/simbo1905/ZkToDo2/blob/b97b353d399ad012577bef7f880f9e3167ed70a3/src/main/java/org/zkforge/zktodo2/ZkToDoViewModel.java MVVM validation logic], written in Java by Tim Clare
* {{웹 인용|url=http://addyosmani.com/blog/understanding-mvvm-a-guide-for-javascript-developers/ |title=Understanding MVVM: A Guide for JavaScript Developers |website=AddysOnmani.com}}
* {{웹 인용 |url=http://www.learnmvvm.com/ |title=MVVM Step by step tutorial |website=learnmvvm.com |확인날짜=2019-04-15 |archive-date=2020-02-05 |archive-url=https://web.archive.org/web/20200205124851/http://www.learnmvvm.com/ |url-status=dead }}

{{기본정렬:모델-뷰-뷰모델}}

[[분류:소프트웨어 디자인 패턴]]
[[분류:아키텍처 패턴]]
[[분류:닷넷 용어]]