Peu importe, tant qu'il s'agit d'une classe statique. Tout est question de convention .
Notre convention est que chaque "couche" (web, services, données) a un seul fichier appelé AutoMapperXConfiguration.cs
, avec une seule méthode appelée Configure()
, où X
est la couche.
La Configure()
méthode appelle ensuite des private
méthodes pour chaque zone.
Voici un exemple de notre configuration de niveau Web:
public static class AutoMapperWebConfiguration
{
public static void Configure()
{
ConfigureUserMapping();
ConfigurePostMapping();
}
private static void ConfigureUserMapping()
{
Mapper.CreateMap<User,UserViewModel>();
}
// ... etc
}
Nous créons une méthode pour chaque "agrégat" (utilisateur, publication), afin que les choses soient bien séparées.
Alors votre Global.asax
:
AutoMapperWebConfiguration.Configure();
AutoMapperServicesConfiguration.Configure();
AutoMapperDomainConfiguration.Configure();
// etc
C'est un peu comme une "interface de mots" - ne peut pas l'imposer, mais vous vous y attendez, vous pouvez donc coder (et refactoriser) si nécessaire.
ÉDITER:
Je pensais juste mentionner que j'utilise maintenant des profils AutoMapper , donc l'exemple ci-dessus devient:
public static class AutoMapperWebConfiguration
{
public static void Configure()
{
Mapper.Initialize(cfg =>
{
cfg.AddProfile(new UserProfile());
cfg.AddProfile(new PostProfile());
});
}
}
public class UserProfile : Profile
{
protected override void Configure()
{
Mapper.CreateMap<User,UserViewModel>();
}
}
Beaucoup plus propre / plus robuste.
Mapper.Initialize
dans chaque classe de configuration écrase-t-il les profils précédents ajoutés? Dans l'affirmative, que faut-il utiliser au lieu d'initialiser?Mapper.CreateMap()
est désormais obsolète.'Mapper.Map<TSource, TDestination>(TSource, TDestination)' is obsolete: 'The static API will be removed in version 5.0. Use a MapperConfiguration instance and store statically as needed. Use CreateMapper to create a mapper instance.'
. Comment mettriez-vous à jour votre exemple pour vous conformer aux nouvelles exigences?Vous pouvez vraiment le placer n'importe où tant que votre projet Web fait référence à l'assembly dans lequel il se trouve. Dans votre situation, je le mettrais dans la couche service car il sera accessible par la couche web et la couche service et plus tard si vous décidez de faites une application console ou vous faites un projet de test unitaire, la configuration de mappage sera également disponible à partir de ces projets.
Dans votre Global.asax, vous appellerez ensuite la méthode qui définit toutes vos cartes. Voir ci-dessous:
Fichier AutoMapperBootStrapper.cs
Global.asax au démarrage de l'application
il suffit d'appeler
Maintenant, certaines personnes vont argumenter contre cette méthode qui viole certains principes SOLIDES, dont ils ont des arguments valides. Les voici pour la lecture.
Configurer Automapper dans Bootstrapper viole le principe ouvert-fermé?
la source
Mettre à jour: l'approche publiée ici n'est plus valide car elle
SelfProfiler
a été supprimée à partir d'AutoMapper v2.Je prendrais une approche similaire à Thoai. Mais j'utiliserais le intégré
SelfProfiler<>
classe pour gérer les cartes, puis utiliserais laMapper.SelfConfigure
fonction pour initialiser.Utilisation de cet objet comme source:
Et ceux-ci comme destination:
Vous pouvez créer ces profils:
Pour initialiser dans votre application, créez cette classe
Ajoutez cette ligne à votre fichier global.asax.cs:
AutoMapperConfiguration.Initialize()
Vous pouvez maintenant placer vos classes de mappage là où elles ont du sens pour vous et ne pas vous soucier d'une seule classe de mappage monolithique.
la source
Pour ceux d'entre vous qui adhèrent à ce qui suit:
J'ai fait un combo entre les profils et en exploitant mon conteneur ioc:
Configuration IoC:
Exemple de configuration:
Exemple d'utilisation:
Le compromis est que vous devez référencer le mappeur par l'interface IMappingEngine au lieu du mappeur statique, mais c'est une convention avec laquelle je peux vivre.
la source
Toutes les solutions ci-dessus fournissent une méthode statique pour appeler (depuis app_start ou n'importe où) qu'elle doit appeler d'autres méthodes pour configurer des parties de la configuration de mappage. Mais, si vous avez une application modulaire, que les modules peuvent se connecter et se déconnecter à tout moment, ces solutions ne fonctionnent pas. Je suggère d'utiliser une
WebActivator
bibliothèque qui peut enregistrer certaines méthodes pour s'exécuterapp_pre_start
etapp_post_start
n'importe où:Vous pouvez installer
WebActivator
via NuGet.la source
MyModule1
projet (ou quel que soit le nom de votre projet), créez simplement une classe nomméeInitMapInModule1
et mettez le code dans le fichier; pour les autres modules, faites de même.En plus de la meilleure réponse, un bon moyen consiste à utiliser Autofac IoC liberary pour ajouter une certaine automatisation. Avec cela, vous définissez simplement vos profils indépendamment des initiations.
et en appelant cette ligne dans la
Application_Start
méthode:Le code ci-dessus trouve toutes les sous-classes de profil et les lance automatiquement.
la source
Mettre toute la logique de mappage en un seul endroit n'est pas une bonne pratique pour moi. Parce que la classe de mappage sera extrêmement grande et très difficile à maintenir.
Je recommande de regrouper les éléments de mappage avec la classe ViewModel dans le même fichier cs. Vous pouvez facilement accéder à la définition de mappage que vous souhaitez en suivant cette convention. De plus, lors de la création de la classe de mappage, vous pouvez faire référence aux propriétés ViewModel plus rapidement car elles se trouvent dans le même fichier.
Ainsi, votre classe de modèle de vue ressemblera à:
la source
À partir de la nouvelle version d'AutoMapper utilisant la méthode statique Mapper.Map () est obsolète. Vous pouvez donc ajouter MapperConfiguration en tant que propriété statique à MvcApplication (Global.asax.cs) et l'utiliser pour créer une instance de Mapper.
App_Start
Global.asax.cs
BaseController.cs
https://github.com/AutoMapper/AutoMapper/wiki/Migrating-from-static-API
la source
Pour ceux qui sont (perdus) en utilisant:
Voici comment j'ai réussi à intégrer AutoMapper de la " nouvelle façon ". Aussi, un grand merci à cette réponse (et question)
1 - Création d'un dossier dans le projet WebAPI appelé "ProfileMappers". Dans ce dossier je place toutes mes classes de profils qui créent mes mappages:
2 - Dans mon App_Start, j'ai un SimpleInjectorApiInitializer qui configure mon conteneur SimpleInjector:
3 - Startup.cs
4 - Ensuite, dans votre contrôleur, injectez simplement comme d'habitude une interface IMapper:
la source
Pour les programmeurs vb.net utilisant la nouvelle version (5.x) d'AutoMapper.
Global.asax.vb:
AutoMapperConfiguration:
Profils:
Cartographie:
la source
Protected Overrides Sub Configure()
c'est obsolète. Tout reste le même mais cette ligne devrait être:Public Sub New()