C# 是否通过AutoMapper将域模型映射到视图模型
我想用视图模型代替域模型进行显示。我想定制一个用于展示的属性,我应该如何做?使用AutoMapper进行显示是一种良好的做法吗 下面是代码示例:C# 是否通过AutoMapper将域模型映射到视图模型,c#,asp.net-mvc-4,automapper,C#,Asp.net Mvc 4,Automapper,我想用视图模型代替域模型进行显示。我想定制一个用于展示的属性,我应该如何做?使用AutoMapper进行显示是一种良好的做法吗 下面是代码示例: public class BookController : BaseController { private IBookService bookService; public BookController(IBookService bookService) { this.
public class BookController : BaseController
{
private IBookService bookService;
public BookController(IBookService bookService)
{
this.bookService = bookService;
}
public ActionResult Details(int id)
{
var book = bookService.GetBookById(id);
return View(Mapper.Map<BookView>(book));
}
}
public class Book
{
public virtual int Id { get; set; }
public virtual string Name { get; set; }
}
public class BookView
{
public int Id { get; set; }
public string Name { get; set; }
}
我该怎么做?使用AutoMapper进行显示是一种良好的做法吗
更新
在下面的场景中使用automapper似乎更合适。例如,将视图模型映射到域模型,如下所示。有什么意见吗
[HttpPost]
public ActionResult Create(BookView bookView)
{
try
{
var book = Mapper.Map<Book>(bookView); //this is wrong
bookService.SaveOrUpdate(book);
return RedirectToAction("Index");
}
catch
{
return View();
}
}
更新3
引自:
我认为使用AutoMapper是因为您不想使用“=”
接线员有点懒。相反,我们用它来展平和重塑,
针对目标类型的环境进行优化。记住,我的
AutoMapper最初的动机是:
通过映射到,启用从其他层保护域层
DTOs
感谢@AndrewHitaker的链接这是AutoMapper的一个很好的使用案例(我已经在许多项目中广泛使用了这种方式,并取得了成功)。通常,您不希望将域实体公开给视图(在MVC中,这将是将模型直接公开给视图,这是不正确的) 域实体和viewmodel之间不需要1-1映射。您可以使它们看起来完全不同,并在
CreateMap
调用中自定义映射。要使用您的示例:
Mapper.CreateMap<Book, BookView>()
.ForMember(dest => dest.Name, opt => opt.MapFrom(src => src.Name + " this is for display purpose"));
Mapper.CreateMap<Book, BookView>()
.ForMember(dest => dest.Name, opt => opt.MapFrom(src => src.Name + " Decorated"));
Mapper.CreateMap()
.ForMember(dest=>dest.Name,opt=>opt.MapFrom(src=>src.Name+“装饰”);
最糟糕的情况是,对于复杂的情况,您可以放弃automapper,或者使用带有automapper的自定义类型解析器来完成工作
其实,。他特别提到了从域实体到ASP.NET MVC ViewModels的映射,以用于强类型视图
另一个优点是,您可以对映射配置文件进行单元测试。这样,如果您最终发现ViewModel和Model之间不匹配,您将得到一个失败的单元测试
更新:
我认为您添加到问题中的引用进一步支持使用AutoMapper从域模型映射到视图模型:
相反,我们使用它来展平和重塑,优化目标类型的环境
因此,在我的示例中,您肯定会针对目标类型的环境(在本例中为视图)进行优化
此外,根据我上面引用的链接,您不应该使用automapper映射到域,仅从。考虑到这一点,您必须编写一些逻辑来根据从视图中接收到的内容创建/更新域实体,而不管是什么。请记住,控制器操作不应直接获取域实体(您不应信任直接来自视图的数据——让模型确定域实体是否有效)。根据更新2,它是如何混合不同用途的?ViewModel的目的不是显示域模型吗?Automapper只是一个实现这一点的工具。它与其他映射(例如域到dto)相比,不显示,而且更可能是干净的。您可以为域
-->
dto创建一个完全不同的映射。此外,您不应该使用AutoMapper从任何内容映射到域。根据您的更新(有用),是否有任何示例或链接用于将视图模型转换为域模型,并进行视图模型验证?我不明白您的最后一段。您的意思是我们不应该使用automapper从ViewModel映射到域(POCO)?如果是,如何将用户输入(视图)保存到数据库(模型)?通过手动映射?@Willy:是的,通过手动映射。我们的想法是,域太重要了,不能进行自动映射。为什么域太重要了,不能进行自动映射?我仍然感到困惑。我在患者表上有50个或更多字段。大多数字段必须在注册时填写。如果我手工绘制地图,那是多么无聊。这就是automapper简化映射的目的吗?@Willy:你当然可以随意使用automapper。我认为Jimmy Bogard在我上面链接的文章中更好地解释了这个问题
public BookView(Book book){
//mapping here
}
Mapper.CreateMap<Book, BookView>()
.ForMember(dest => dest.Name, opt => opt.MapFrom(src => src.Name + " Decorated"));