Model View ViewModel
![](http://upload.wikimedia.org/wikipedia/commons/thumb/8/87/MVVMPattern.png/440px-MVVMPattern.png)
Model View ViewModel (MVVM) ist ein Entwurfsmuster und eine Variante des Model-View-Controller-Musters (MVC). Es dient zur Trennung zwischen Darstellung und Logik der Benutzerschnittstelle (UI) und des Software-Backends. Das Entwurfsmuster ist die Standardimplementierung von UI-Plattformen wie Cocoa (Apple), Windows Presentation Foundation (WPF, Microsoft) und JavaFX (Oracle). Im Webbrowser wird das Muster durch bestimmte JavaScript-Frameworks wie React oder Knockout.js verfügbar, welche den Zustand einer HTML5-Benutzeroberfläche verwalten können. Die Unterteilung der Benutzeroberfläche in Komponenten, die aufeinander aufbauen und schlussendlich als View die gesamte Applikationsoberfläche darstellen, wird Compositing genannt und ist typisch für MVVM-Anwendungen.
Das MVVM-Entwurfsmuster erfordert neben dem Kompositum-Entwurfsmuster auch das Beobachter-Entwurfsmuster, da das ViewModel den Zustand der UI abbildet, der sich wiederum durch Eingabe- und andere Ereignisse ändert. Die unmittelbare Reaktion der UI auf Änderungen im ViewModel und umgekehrt realisiert die Echtzeit-Datenbindung des Musters.
MVVM erlaubte bei seiner Einführung die heute gebräuchliche Rollentrennung von UI-Designern im Frontend und Entwicklern im Backend, wodurch Anwendungsschichten von verschiedenen Arbeitsgruppen entwickelt werden konnten. Im Desktop-Umfeld eingeführt, findet sich das MVVM-Entwurfsmuster heute in den meisten webbasierten Clients.
Geschichte
Das MVVM wurde 2005 von Microsoft MVP John Gossman veröffentlicht. Es ist eine Spezialisierung des Presentation Model von Martin Fowler[1] und ist mit diesem insofern identisch, als beide Muster Zustand und Verhalten der View in ein separates UI-Model (Presentation bzw. View Model) verschieben. Das Presentation Model ermöglicht allerdings das Erzeugen einer View unabhängig von der UI-Plattform, wohingegen das MVVM ursprünglich auf UIs mittels WPF abzielt. Es findet allerdings inzwischen auch in anderen Bereichen Anwendung, ähnlich wie bei MVC.
Beschreibung
Das MVVM nutzt die funktionale Trennung des MVC-Musters von Model und View. Zum Erreichen einer losen Kopplung zwischen diesen Komponenten wird ein Datenbindungsmechanismus verwendet. Das MVVM-Muster enthält folgende drei Komponenten:
- Model: Datenzugriffsschicht für die Inhalte, die dem Benutzer angezeigt und von ihm manipuliert werden. Dazu benachrichtigt es über Datenänderungen und führt eine Validierung der vom Benutzer übergebenen Daten durch. Es enthält die gesamte Geschäftslogik und ist für sich alleine durch Unit Tests überprüfbar.
- View: Alle durch die grafische Benutzeroberfläche (GUI) angezeigten Elemente. Es bindet sich an Eigenschaften des ViewModel, um Inhalte darzustellen und zu manipulieren sowie Benutzereingaben weiterzuleiten. Durch die Datenbindung ist die View einfach austauschbar und ihr Code-Behind gering.
- ViewModel: Enthält die UI-Logik (Model der View) und dient als Bindeglied zwischen View und obigem Model. Einerseits tauscht es Information mit dem Model aus, ruft also Methoden oder Dienste auf. Andererseits stellt es der View öffentliche Eigenschaften und Befehle zur Verfügung. Diese werden von der View an Steuerelemente gebunden, um Inhalte auszugeben bzw. UI-Ereignisse weiterzuleiten. Das ViewModel darf dabei keinerlei Kenntnis der View besitzen.
Das MVVM-Muster kann als technologie-spezifisch bezeichnet werden, da für die Verknüpfung von View und ViewModel ein Datenbindungsmechanismus benötigt wird. Diese Infrastruktur wird häufig als Binder bezeichnet[2]. Im Detail handelt es sich hierbei um einen bidirektionalen Einsatz des Beobachter-Musters. Binder, welche eine Datenbindung auf Basis von deklarativen Angaben etablieren können, sind für verschiedene Techniken vorhanden.
.NET und JavaFX
In Bezug auf WPF und Silverlight bedeutet MVVM, dass die View aus rein deklarativem XAML-Markup besteht. Sie kann von UI-Designern etwa mittels Expression Blend entworfen werden, wobei lediglich Datenbindungen zum ViewModel erzeugt werden müssen, aber kein Code-Behind. Die Logik wird in einer Programmiersprache wie C# oder VB.NET implementiert. Die Abhängigkeiten zwischen Markup und Code werden minimiert. Gleiches gilt für JavaFX. Hier kann die View mittels FXML und beispielsweise SceneBuilder entwickelt und dann im ViewModel per Property Binding uni- oder bidirektional mit der Geschäftslogik verbunden werden.
JavaScript/HTML
Das MVVM-Muster bzw. der hierzu benötigte Datenbindungsmechanismus wurden im Jahr 2010 von dem Microsoft-Entwickler Steve Sanderson nach JavaScript portiert. Die entstandene JavaScript-Bibliothek trägt den Namen Knockout.js. Mittlerweile findet das MVVM-Muster ebenfalls Einsatz in anderen JavaScript-Frameworks, wie z. B. Angular, Vue.js oder React. Durch die Verwendung des MVVM-Muster bei client-lastigen Webanwendungen wird der Implementierungsaufwand reduziert, da sonst übliche manuelle DOM-Zugriffe durch die Datenbindung stark reduziert werden können. Die Beschreibung der Datenbindung erfolgt ebenfalls deklarativ, wie bei XAML-basierten Microsoft-Produkten.
Android
Das MVVM-Muster und die Datenbindung kann ebenfalls bei der Implementierung mobiler Android-Anwendungen verwendet werden.[3]
Vor- und Nachteile
Vorteile
- Die Geschäftslogik kann unabhängig von der Darstellung bearbeitet werden. MVVM „erbt“ die leichtere Austauschbarkeit der View vom MVC-Muster.
- Die Testbarkeit verbessert sich, da die ViewModel die UI-Logiken enthalten und unabhängig von der View instanziiert werden können. Hierdurch sind keine UI-Tests nötig. Stattdessen genügen codebasierte Modultests des ViewModel.
- Die Menge von Glue Code zwischen Model und View wird durch den Verzicht von Controller-Instanzen gegenüber dem MVC-Muster reduziert.[4]
- Views können von reinen UI-Designern gestaltet werden, während Entwickler unabhängig davon die Models und ViewModels implementieren.
- Es können unterschiedliche Views erstellt werden, die alle an dasselbe ViewModel gebunden werden, ohne dass dort Änderungen an der Programmierung vorgenommen werden müssen.
Nachteile
- Als Nachteil kann der höhere Rechenaufwand aufgrund des enthaltenen bi-direktionalen Beobachters gewertet werden.
- Der generische Datenbindungsmechanismus erspart die Implementierung von verschiedenen Controllern. Allerdings ist dieser Mechanismus zur Umsetzung des MVVM-Muster zwingend erforderlich.
MVVM-Frameworks
Es existieren verschiedene Frameworks, welche MVVM umsetzen.
- Windows Presentation Foundation
- Knockout.js – MVVM in JavaScript
- Vue.js
- JavaFX
- SwiftUI
Siehe auch
Literatur
- Raffaele Garofalo: Building Enterprise Applications with Windows Presentation Foundation and the Model View ViewModel Pattern, Microsoft Press 2011, ISBN 978-0735650923
Weblinks
- Norbert Eder: Model-View-ViewModel Die Serie – Codebeispiel
Einzelnachweise
- ↑ Presentation Model
- ↑ Binder-Definition aus dem ZK-Framework
- ↑ Android Data Binding Guide (englisch)
- ↑ John Gossman: Tales from the Smart Client: Advantages and disadvantages of M-V-VM. Abgerufen am 28. Mai 2012.
Erzeugungsmuster | Abstrakte Fabrik | Erbauer | Fabrikmethode | Prototyp | Singleton | Multiton | Objektpool |
Strukturmuster | Adapter | Brücke | Decorator | Fassade | Fliegengewicht | Kompositum | Stellvertreter |
Verhaltensmuster | Beobachter | Besucher | Interpreter | Iterator | Kommando | Memento | Schablonenmethode | Strategie | Vermittler | Zustand | Zuständigkeitskette | Interceptor | Nullobjekt | Protokollstapel |
Muster für objektrelationale Abbildung | Datentransferobjekt | Table Data Gateway | Row Data Gateway | Active Record | Unit of Work | Identity Map | Lazy Loading | Identity Field | Dependent Mapping | Embedded Value | Serialized LOB | Inheritance Mapper | Metadata Mapping | Query Object | Command-Query-Responsibility-Segregation |
Nachrichtenübermittlungsmuster | Message | Command Message | Document Message | Event Message | Request-Reply | Return Address | Correlation Identifier | Message Sequence | Message Expiration | Format Indicator | Message Channel | Point-to-Point Channel | Publisher-Subscriber Channel | Datatype Channel | Invalid Message Channel | Dead Letter Channel | Guaranteed Delivery | Channel Adapter | Messaging Bridge | Message Bus | Pipes-and-Filters | Message Router | Content-based Router | Message Filter | Dynamic Router | Recipient List | Splitter | Aggregator | Resequencer | Composed Message Processor | Scatter-Gather | Routing Slip | Process Manager | Message Broker | Message Translator | Envelope Wrapper | Content Enricher | Content Filter | Claim Check | Normalizer | Canonical Data Model | Message Endpoint | Messaging Gateway | Messaging Mapper | Transactional Client | Polling Consumer | Event-driven Consumer | Competing Consumers | Message Dispatcher | Selective Consumer | Durable Subscriber | Idempotent Receiver | Service Activator | Control Bus | Detour | Wire Tap | Message History | Message Store | Smart Proxy | Test Message | Channel Purger |
Andere | Application Controller | Business Delegate | Data Access Object | Dependency Injection | Extension Interface | Fluent Interface | Inversion of Control (IoC) | Lock | Model View Controller (MVC) | Model View Presenter (MVP) | Model View Update (MVU) | Model View ViewModel (MVVM) | Page Controller | Registry | Remote Facade | Repository | Service Locator | Session State | Table Module | Template View | Threadpool | Transaction Script | Transform View | Two-Step View | Value Object |