C'est un problème auquel je suis confronté depuis que j'ai commencé à utiliser MVVM, d'abord dans WPF et maintenant dans Silverlight.
J'utilise un conteneur IOC pour gérer la résolution des Views et ViewModels. Les Views ont tendance à être très basiques, avec un constructeur par défaut, mais les ViewModels ont tendance à accéder à de vrais services, qui sont tous nécessaires à leur construction. Encore une fois, j'utilise un conteneur IOC pour la résolution, donc l'injection de services n'est pas un problème.
Ce qui devient un problème, c'est de transmettre les données requises au ViewModel en utilisant l'IOC. À titre d'exemple simple, considérons un écran qui permet de modifier un client. En plus de tous les services dont il pourrait avoir besoin, le ViewModel de cet écran nécessite un objet client pour afficher/modifier les données du client.
Lors de tout type de développement de bibliothèque (non-MVVM), je considère comme une règle inflexible que les invariants de classe soient passés par le constructeur. Dans les cas où j'ai besoin de données spécifiques au contexte lors de la construction de la classe y la classe en question est gérée par un conteneur, j'ai tendance à utiliser une fabrique abstraite* comme pont. En MVVM, cela semble excessif, car la plupart des ViewModels auront besoin de leur propre fabrique.
Parmi les autres approches que j'ai essayées/envisagées, citons (1) une méthode d'initialisation/de chargement dans laquelle je passe les données, ce qui enfreint la règle consistant à forcer les invariants de classe par le biais du constructeur, (2) le passage des données par le conteneur en tant que paramètres superposés (Unity), et (3) le passage des données par un sac d'état global (ugh).
Quelles sont les autres façons de faire passer des données spécifiques au contexte d'un ViewModel à un autre ? L'un des cadres MVVM aborde-t-il ce problème spécifique ?
* ce qui peut avoir ses propres problèmes, comme le fait de devoir choisir entre un appel à Container.Resolve() ou de ne pas avoir votre ViewModel géré par conteneur. Castle Windsor a une bonne solution à ce problème, mais aucun autre framework ne le fait.
Edit :
J'ai oublié d'ajouter : certaines des options que j'ai énumérées ne sont même pas possibles si vous faites du MVVM "View First", à moins que vous ne passiez les données d'abord à la vue et ensuite au ViewModel.