首页 文章

AutoMapper与ValueInjecter [关闭]

提问于
浏览
209

每次我在StackOverflow上寻找AutoMapper的东西时,我都在读一些关于ValueInjecter的东西 .

有人能告诉我它们之间的优缺点(性能,功能,API使用,可扩展性,测试)吗?

4 回答

  • 170

    作为ValueInjecter的创造者,我可以告诉你我做了它因为我想要的东西 simple and very flexible

    我真的不喜欢写很多或写很多 monkey code 喜欢:

    Prop1.Ignore, Prop2.Ignore etc.
    CreateMap<Foo,Bar>(); CreateMap<Tomato, Potato>(); etc.
    

    ValueInjecter是 like mozilla with it's plugins, 您创建ValueInjections并使用它们

    有内置注射用于扁平化,不平整,以及一些旨在被遗传的注射剂

    它在 an aspect type of way 中工作得更多,您不必指定所有属性1对1,而是执行以下操作:

    获取源名称以"Id"结尾的所有int属性,转换值并将每个属性设置为源对象中具有相同名称但没有Id后缀的属性,并且它的类型是从Entity继承的,类似的东西

    so one obvious difference, ValueInjecter is used even in windows forms with flattening and unflattening, that's how flexible it is

    (从对象映射到表单控件并返回)

    Automapper,在Windows窗体中不可用,没有任何缺陷,但它有很好的东西,如集合映射,所以万一你需要使用ValueInjecter,你只需要做类似的事情:

    foos.Select(o => new Bar().InjectFrom(o));

    您还可以使用ValueInjecter从 anonymousdynamic 对象进行映射

    differences:

    • automapper为每个映射可能性创建配置CreateMap()

    • valueinjecter从任何对象注入任何对象(当从对象注入到valuetype时也存在这种情况)

    • automapper已经构建了扁平化,仅适用于简单类型或相同类型,并且没有不平整

    • valueinjecter只有你需要它才能做 target.InjectFrom<FlatLoopValueInjection>(source); also <UnflatLoopValueInjection> 如果你想从 Foo.Bar.Name of type StringFooBarName of type Class1 你继承FlatLoopValueInjection并指定这个

    • automapper默认映射具有相同名称的属性,其余的则必须逐个指定,并执行Prop1.Ignore(),Prop2.Ignore()等操作 .

    • valueinjecter有一个默认的注入.InjectFrom(),用于执行具有相同名称和类型的属性;对于其他一切,您使用单独的映射逻辑/规则创建自定义值注入,更像是方面,例如从Type Foo的所有道具到所有类型Bar的道具

  • 59

    由于我从未使用过任何其他工具,因此我只能谈论AutoMapper . 我有一些目标是构建AutoMapper:

    • 支持展平为哑DTO对象

    • 支持开箱即用的明显场景(集合,枚举等)

    • 能够轻松验证测试中的映射

    • 允许从其他位置解析值的边缘情况(自定义类型 - >类型映射,单个成员映射和一些非常疯狂的边缘情况) .

    如果您想要做这些事情,AutoMapper可以很好地为您服务 . AutoMapper做得不好的事情是:

    • 填充现有对象

    • Unflattening

    原因是我从来不需要做这些事情 . 在大多数情况下,我们的实体没有设置器,不暴露集合等,所以这就是为什么它不在那里 . 我们使用AutoMapper来展平DTO并从UI模型映射到命令消息等 . 这就是它真正起作用的地方,对我们来说非常好 .

  • 55

    我尝试过两者并且更喜欢ValueInjecter,因为它非常简单:

    myObject.InjectFrom(otherObject);
    

    对于我的绝大多数注射需求而言,这就是所有需要知道的 . 它不可能比这更简单和优雅 .

  • 27

    这是我一直在研究的一个问题,对于我的用例,它似乎是值得注意的 . 它不需要事先使用设置(可能会达到性能我猜,虽然如果巧妙地实现它可以缓存未来调用的映射而不是每次反映),所以在使用它们之前不需要预先定义任何映射 .

    但最重要的是,它允许反向映射 . 现在我可能在这里遗漏了一些东西,因为Jimmy提到他没有看到必要的用例,所以也许我的模式有问题,但我的用例是我正在从我的ORM创建一个ViewModel对象 . 然后我在我的网页上显示这个 . 一旦用户完成,我将ViewModel作为httppost返回,如何将其转换回原始的ORM类?我很想知道使用automapper的模式 . 使用ValueInjector它是微不足道的,它甚至会不平坦 . 例如,创建一个新实体

    entityframework创建的模型(模型优先):

    public partial class Family
    { 
        public int Id { get; set; }
        public string FamilyName { get; set; }
    
        public virtual Address Address { get; set; }
    }
    
    public partial class Address
    {
        public int Id { get; set; }
        public string Line1 { get; set; }
        public string Line2 { get; set; }
        public string TownCity { get; set; }
        public string County { get; set; }
        public string Postcode { get; set; }
    
        public virtual Family Family { get; set; }
    }
    

    ViewModel(我可以用验证器装饰):

    public class FamilyViewModel
    {
        public int Id { get; set; }
        public string FamilyName { get; set; }
    
        public int AddressId { get; set; }
        public string AddressLine1 { get; set; }
        public string AddressLine2 { get; set; }
        public string AddressTownCity { get; set; }
        public string AddressCounty { get; set; }
        public string AddressPostcode { get; set; }
    }
    

    ViewController:

    //
        // GET: /Family/Create
    
        public ActionResult Create()
        {
            return View();
        } 
    
        //
        // POST: /Family/Create
    
        [HttpPost]
        public ActionResult Create(FamilyViewModel familyViewModel)
        {
            try
            {
                Family family = new Family();
                family.InjectFrom<UnflatLoopValueInjection>(familyViewModel);
                db.Families.Add(family);
                db.SaveChanges();
                return RedirectToAction("Index");
            }
            catch
            {
                return View();
            }
        }
    

    在我看来,它并没有那么简单?

    (所以这引出了一个问题,我遇到的模式是错的(似乎很多其他人都这么做),它不被认为对AutoMapper有 Value 吗?)

    但是,如果这个模式被解释,是你想要使用的模式,那么我的投票就是一个国家英里的 Value .

相关问题