对象映射工具AutoMapper介绍
AutoMapper是用来解决对象之间映射转换的类库。对于我们开发人员来说,写对象之间互相转换的代码是一件极其浪费生命的事情,AutoMapper能够帮助我们节省不少时间。
一. AutoMapper解决了什么问题?
要问AutoMapper解决了什么问题? 难道不是对象映射转换的问题吗?
当然是,不过我们可以问深入一些,为什么项目中会出现大量的对象映射转换?(以下对于非MVC项目也适用)
在现代的软件开发中,项目的层级更加的细分,而不同层级之间对于对象的需求是有区别的,这就需要在不同层级间传递数据的时候,必须要转换数据。
举一些实际具体的例子:
在持久层(数据访问层), 我们的User对象,可能是一个包含User表中所有字段的数据的对象,甚至包含了用户的Password信息。而在界面层,我们只是需要显示用户的name, email,不需要Password这些额外的信息,同时,它还需要用户的考勤信息,而这个信息来自于另外一张表。
这个例子中,能够发现不同层之间,我们对于数据对象的需求是不同的。
每个层都做了它们职责范围内的事情:
持久层关注数据,所以只提供数据对象,它无需知道外层如何使用这些数据对象,也无法知道。
界面层关注数据的呈现,它只关注它要显示的数据。
那么问题是,谁来弥补它们之间的鸿沟?DTO(Data Transfer Object)——数据传输对象。而AutoMapper就是解决其中涉及到的数据对象转换的工具。

在实际开发中,如果你还可以直接在Business层或者界面层直接使用持久层的对象,因为你认为这个关系不大,整个项目都是你自己控制的,虽然dirty,但是quick. 作为一个有些洁癖的程序员,我还是建议使用DTO在不同层级之间传递数据。因为当你做更高层级开发的时候,比如开发web service,WCF,Web API这些为系统外部提供接口的开发时候,你就回明白这些好的习惯和思维能够帮助你更加好的设计这些外部接口。
二. AutoMapper如何使用?
先来看一个简单的例子,这个例子是定义Order对象到OrderDto对象之间的映射。(我们把Order称呼为源类,OrderDto称呼为目标类)
Mapper.CreateMap<Order, OrderDto>();//创建映射关系Order –> OrderDto
OrderDto dto = Mapper.Map<OrderDto>(order);//使用Map方法,直接将order对象装换成OrderDto对象
智能匹配
AutoMapper能够自动识别和匹配大部分对象属性:
- 如果源类和目标类的属性名称相同,直接匹配
- 目标类型的CustomerName可以匹配源类型的Customer.Name
- 目标类型的Total可以匹配源类型的GetTotal()方法
自定义匹配规则
AutoMapper还支持自定义匹配规则
Mapper.CreateMap<CalendarEvent, CalendarEventForm>()
//属性匹配,匹配源类中WorkEvent.Date到EventDate
.ForMember(dest => dest.EventDate, opt => opt.MapFrom(src => src.WorkEvent.Date))
.ForMember(dest => dest.SomeValue, opt => opt.Ignore())//忽略目标类中的属性
.ForMember(dest => dest.TotalAmount, opt => opt.MapFrom(src => src.TotalAmount ?? ))//复杂的匹配
.ForMember(dest => dest.OrderDate, opt => opt.UserValue<DateTime>(DateTime.Now));固定值匹配
测试
当定义完规则后,可以使用下面的代码来验证配置是否正确。不正确抛出异常AutoMapperConfigurationException.
Mapper.AssertConfigurationIsValid();
三. AutoMapper处理多对一映射
我们开篇提到的问题中,说到界面显示User的name, email, 还有用户的考勤信息,而这些信息来自于2张不同的表。这就涉及到了多对一映射的问题,2个持久层对象需要映射到一个界面显示层的对象。
假设我们的持久层对象是这样的:
public class User
{
public int Id { get; set; }
public string Name { get; set; }
public string Email { get; set; }
public string Passworkd { get; set; }
public DateTime Birthday { get; set; }
} public class Evaluation
{
public int Id { get; set; }
public int Score { get; set; }
}
在Asp.net MVC中,我的界面显示层的ViewModel是这样的
public class UserViewModel
{
public int Id { get; set; }
public string Name { get; set; }
public string Email { get; set; }
public int Score { get; set; }
}
接下来,为了达到多对一的映射的目的,我们创建这个EntityMapper类
public static class EntityMapper
{
public static T Map<T>(params object[] sources) where T : class
{
if (!sources.Any())
{
return default(T);
} var initialSource = sources[];
var mappingResult = Map<T>(initialSource); // Now map the remaining source objects
if (sources.Count() > )
{
Map(mappingResult, sources.Skip().ToArray());
}
return mappingResult;
} private static void Map(object destination, params object[] sources)
{
if (!sources.Any())
{
return;
}
var destinationType = destination.GetType();
foreach (var source in sources)
{
var sourceType = source.GetType();
Mapper.Map(source, destination, sourceType, destinationType);
}
} private static T Map<T>(object source) where T : class
{
var destinationType = typeof(T);
var sourceType = source.GetType();
var mappingResult = Mapper.Map(source, sourceType, destinationType);
return mappingResult as T;
}
}
为了实现多个源对象映射一个目标对象,我们使用了AutoMapper的方法,从不同的源对象逐一匹配一个已经存在的目标对象。下面是实际使用在MVC中的代码:
public ActionResult Index()
{
var userId = ,
var user = _userRepository.Get(userId);
var score = _scoreRepository.GetScore(userId);
var userViewModel = EntityMapper.Map<UserViewModel>(user, score);
return this.View(userViewModel);
}
四. 使用Profile在Asp.net MVC项目中配置AutoMapper
Profile是AutoMapper中用来分离类型映射定义的,这样可以让我们的定义AutoMapper类型匹配的代码可以更加分散,合理和易于管理。
利用Profile, 我们可以更加优雅的在MVC项目中使用我们的AutoMapper. 下面是具体的方法:
1. 在不同层中定义Profile,只定义本层中的类型映射
继承AutoMapping的Profile类,重写ProfileName属性和Configure()方法。
public class ViewModelMappingProfile: Profile
{
public override string ProfileName
{
get
{
return GetType().Name;
}
} protected override void Configure()
{
Mapper.CreateMap......
}
}
2. 创建AutoMapperConfiguration, 提供静态方法Configure,一次加载所有层中Profile定义
public class AutoMapperConfiguration
{
public static void Configure()
{
Mapper.Initialize(x => x.AddProfile<ViewModelMappingProfile>());
Mapper.AssertConfigurationIsValid();
}
}
3. 在Global.cs文件中执行
最后,在Global.cs文件中程序启动前,调用该方法
AutoMapperConfiguration.Configuration()
对象映射工具AutoMapper介绍的更多相关文章
- .NET的对象映射工具AutoMapper使用笔记
AutoMapper是一个.NET的对象映射工具. 项目地址:https://github.com/AutoMapper/AutoMapper. 帮助文档:https://github.com/Aut ...
- EF架构~AutoMapper对象映射工具简化了实体赋值的过程
回到目录 AutoMapper是一个.NET的对象映射工具,一般地,我们进行面向服务的开发时,都会涉及到DTO的概念,即数据传输对象,而为了减少系统的负载,一般我们不会把整个表的字段作为传输的数据,而 ...
- .NET之AutoMapper对象映射工具运用
AutoMapper对象映射工具:主要是将某一个实体转成另一个实体. 1.引用NuGet包;搜索:AutoMapper 2.创建实体类 using System; using System.Colle ...
- .NET的DTO映射工具AutoMapper
.NET的DTO映射工具AutoMapper 原文:https://github.com/AutoMapper/AutoMapper/wiki/Getting-started 参考:http://ww ...
- 【5min+】 对象映射只有AutoMapper?试试Mapster
系列介绍 [五分钟的dotnet]是一个利用您的碎片化时间来学习和丰富.net知识的博文系列.它所包含了.net体系中可能会涉及到的方方面面,比如C#的小细节,AspnetCore,微服务中的.net ...
- 对象转换工具 MapStruct 介绍
前言 在我们日常开发的分层结构的应用程序中,为了各层之间互相解耦,一般都会定义不同的对象用来在不同层之间传递数据,因此,就有了各种 XXXDTO.XXXVO.XXXBO 等基于数据库对象派生出来的对象 ...
- ASP.NET Core 中的对象映射之 AutoMapper
目录 AutoMapper 简介 AutoMapper 使用 初始化 Profile设置 扁平化映射 集合映射 投影 条件映射 值转换 设置转换前后行为 配置验证及设置 反向映射 自定义转换器 自定义 ...
- [转]对象映射类AutoMapper的使用
由于原文太长了,此处就直接贴上原文的超链接,大家自行学习. codeproject中的一篇文章: AutoMapper
- 基于 abp vNext 和 .NET Core 开发博客项目 - 用AutoMapper搞定对象映射
上一篇文章(https://www.cnblogs.com/meowv/p/12961014.html)集成了定时任务处理框架Hangfire,完成了一个简单的定时任务处理解决方案. 本篇紧接着来玩一 ...
随机推荐
- JS只能输入数字,数字和字母等的正则表达式
1.只能输入英文 <input type="text" onkeyup="value=value.replace(/[^a-zA-Z]/g,'')"> ...
- Azure Application Gateway (3) 设置URL路由
<Windows Azure Platform 系列文章目录> 在之前的文章中,笔者介绍了Azure Web App可以设置URL路由.如下图: 在这里笔者简单介绍一下,首先我们还是创建以 ...
- 重温Servlet学习笔记--response对象
在用户浏览网页时,服务器对于客户端浏览器做出的响应被封装成一个HttpServletResponse对象,要对浏览器操作只需要操作这个response对象即可.response的功能分类及介绍: 响应 ...
- Ubuntu下搭建Mininet环境
Mininet环境搭建分为两个步骤,如下: 1.从GITHUB上获取mininet源码到本地的opt目录下 打开Linux终端,切换目录到根目录 cd / 切换到Linux的opt目录下 cd opt ...
- 浅尝ECMAScript6
浅尝ECMAScript6 简介 ECMAScript6 是最新的ECMAScript标准,于2015年6月正式推出(所以也称为ECMAScript 2015),相比于2009年推出的es5, es6 ...
- Web App 向上滑动动态加载数据 2015-06-11 09:36 20人阅读 评论(0) 收藏
好久没有写博客了 - - ,个人原因 个人原因.. 宣传一下...自己的.NET群:252713569 欢迎各位大神加入 嗯..最近在公司开发微信平台的东西..需要做一个WebAPP(PS:其实就是 ...
- spring boot 调试 - 热部署
maven gradle Maven: 命令行方式: mvn spring-boot:run -Drun.jvmArguments="-Xdebug -Xrunjdwp:transport= ...
- 优化MySchool数据库设计
第一章 数据库的设计 1.E-R图中: 矩形:实体 椭圆:属性 菱形:关系 直线:连接实体,属性和关系 2.映射基数 一对多 多对一 多对多 3.范式: 第一范式:确保每列的原子性 第二范式:确保表中 ...
- 【shell 大系】Linux Shell常用技巧
在最近的日常工作中由于经常会和Linux服务器打交道,如Oracle性能优化.我们数据采集服务器的资源利用率监控,以及Debug服务器代码并解决其效率和稳定性等问题.因此这段时间总结的有关Linux ...
- 21、ASP.NET MVC入门到精通——ASP.NET MVC4优化
本系列目录:ASP.NET MVC4入门到精通系列目录汇总 删除无用的视图引擎 默认情况下,ASP.NET MVCE同时支持WebForm和Razor引擎,而我们通常在同一个项目中只用到了一种视图引擎 ...