2010-05-23 5 views
10

J'utilise fréquemment AutoMapper pour mapper des objets Model (Domain) aux objets ViewModel, qui sont ensuite consommés par mes Views, dans un modèle Model/View/View-Model.Où vont les instructions 'CreateMap'?

Cela implique de nombreuses instructions 'Mapper.CreateMap', qui doivent toutes être exécutées, mais doivent être exécutées uniquement une fois dans le cycle de vie de l'application. Techniquement, alors, je devrais les garder tous dans une méthode statique quelque part, qui est appelée à partir de ma méthode Application_Start() (il s'agit d'une application ASP.NET MVC).

Cependant, il semble erroné de regrouper un grand nombre de problèmes de cartographie différents dans un même emplacement central.

Surtout lorsque le code de mappage devient complexe et implique un formatage et d'autres logiques.

Existe-t-il une meilleure façon d'organiser le code de mappage afin qu'il reste proche du ViewModel concerné?

(je suis venu avec une idée - ayant une méthode « CreateMappings » sur chaque ViewModel, et dans le BaseViewModel, appelant cette méthode sur instanciation Cependant, étant donné que la méthode ne doit être appelée une fois dans le cycle de vie de l'application,. il a besoin d'une logique supplémentaire pour mettre en cache une liste de types ViewModel pour lesquels la méthode CreateMappings a été appelée, puis l'appeler uniquement si nécessaire, pour ViewModels qui ne figurent pas dans cette liste.)

Répondre

2

Si vous utilisez des profils, vous peut y placer tous vos appels "CreateMap". En outre, vous pouvez créer une classe d'amorçage statique qui contient votre configuration et faire en sorte que la pièce de démarrage appelle simplement le programme d'amorçage.

+0

Mais cela ne marche toujours pas le problème d'avoir toutes les correspondances pour tous les différents vue-modèles lumped ensemble, quand je préfère avoir eux en quelque sorte liés aux classes auxquelles ils s'appliquent. – Jonathan

0

OK, la façon dont je suis actuellement le faire est la suivante:

ajouter une certaine logique au constructeur de mon BaseController, qui court la méthode 'CreateMappings de, mais seulement une fois par type de contrôleur:

public abstract class BaseController : Controller 
{  
    public BaseController() 
    { 
     if (!controllersWithMappingsCreated.Contains(GetType())) 
     { 
      CreateMappings(); 
      controllersWithMappingsCreated.Enqueue(GetType()); 
     } 
    } 

    protected virtual void CreateMappings() { } 
} 

Dans chaque contrôleur de béton, j'utilise CreateMappings pour déclarer les mappages de tous les Models/ViewModels pertinents pour ce contrôleur.

public class AccountController : BaseController 
{ 
    public AccountController() : base() { } 

    protected override void CreateMappings() 
    { 
     Mapper.CreateMap<Models.User, ViewModels.UserProfile>(); 
     Mapper.CreateMap<Models.User, ViewModels.ChangePassword>(); 
    } 
} 

Je trouve aussi quelques alternatives intéressantes impliquant Attributs here et here, mais ils me semblent un peu trop compliqué.

+2

Je disposerais toujours d'une classe d'amorçage statique, de sorte que vous pouvez désactiver vos mappages. – Martin

+0

Beau travail. Mais qu'est ce que 'controllersWithMappingsCreated' dans' BaseController'? – Blaise

6

Si vous ne voulez vraiment pas utiliser un programme d'amorçage, au moins un constructeur statique est un moyen facile de vous assurer que votre CreateMap est appelée au plus une fois. (Avec moins de déconner et preuve de plus de fil que la réponse de Jonathon.)

public class AccountController : Controller 
{ 
    static AccountController() 
    { 
     Mapper.CreateMap<Models.User, ViewModels.UserProfile>(); 
     Mapper.CreateMap<Models.User, ViewModels.ChangePassword>(); 
    } 
} 
+0

Je n'ai pas eu de chance de mettre les mappages dans le constructeur statique. Je trouve que je dois les mettre dans le constructeur d'instance. – AaronLS

+0

@AaronLS Oh non. Avez-vous une exception ou quelque chose comme ça? Quelles classes utilisez-vous pour les constructeurs et les mappings? –

Questions connexes