2011-01-11 4 views
210

Каждый раз, когда я ищу AutoMapper материал на StackOverflow, я что-то читаю о ValueInjecter.AutoMapper vs ValueInjecter

Может ли кто-нибудь сказать мне «за» и «против» между ними (производительность, функции, использование API, расширяемость, тестирование)?

+2

Еще один, который я вижу много, - [EmitMapper] (http://emitmapper.codeplex.com/). – adrianbanks

+1

Как насчет клея? http://glue.codeplex.com/ Похоже, отличный проект, но я еще не пробовал. Я буду в течение следующего месяца. Я также видел проект под названием EmitMapper http://emitmapper.codeplex.com/ – Trygve

+0

См. Статью о двух инструментах: http://devproconnections.com/development/two-great-solutions-object-mapping?NL = 4S3A_News_DPC_UPDATE-ASP.NET_issue090414% 20-% 20Batch & E_ID = 7710159 & NLL = 5209 –

ответ

170

как создатель ValueInjecter, я могу вам сказать, что я сделал это, потому что я хотел что-то простой и очень гибкий

Я действительно не люблю писать много или писать много monkey code как:

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

ValueInjecter что-то как Mozilla с его плагинов, создавать ValueInjections и использовать их

есть встроенный в инъекциях для выпрямления, unflattening, а некоторые, которые предназначены для наследования

и он работает более типа аспекта пути, вы не должны указать все свойства 1-to 1, вместо этого вы делаете что-то вроде:

возьмите все свойства int из источника, имя которого заканчивается на «Id», преобразует значение и задает каждое свойство в исходном объекте с тем же именем без суффикса идентификатора, и это тип унаследован от Entity, например,

поэтому один obviou разница s, ValueInjecter используется даже в окнах форм с уплощением и unflattening, это как гибкая это

(отображение объекта для формирования управления и обратно)

Automapper, не могут быть использованы в Windows Forms, не unflatenning, но у него есть хорошие вещи, как отображение коллекций, поэтому в случае, если вам это нужно с ValueInjecter вы просто сделать что-то вроде:

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

вы также можете использовать ValueInjecter к карте от анонимной и динамических объектов

разница:

  • automapper создать конфигурацию для каждой отображения возможности CreateMap()

  • valueinjecter впрыснуть от любого объекта к любому объекту (есть также случаи, когда Вы вводите от объекта до valuetype)

  • automapper имеет уплощение, он построен, и только для простых типов или одного типа, и он не имеет unflattening

  • valueinjecter только если вам это нужно вы target.InjectFrom<FlatLoopValueInjection>(source); also <UnflatLoopValueInjection> , и если вы хотите от Foo.Bar.Name of type String к FooBarName of type Class1 наследованию FlatLoopValueInjection и указать

  • automapper отображает свойства с таким же именем по умолчанию, а для остальных вы должны указывать один за другим и делать такие вещи, как Prop1.Ignore(), Prop2.Ignore() и т. д.

  • valueinjecter имеет инъекцию по умолчанию.InjectFrom(), который выполняет свойства с тем же именем и типом; для всего остального вы создаете свои собственные инстинкты значений с индивидуальной логикой/правилами отображения, более похожими на аспекты, например. от всех опор типа Foo для всех реквизита типа Bar

+5

Для бога любви, пожалуйста, скажите мне, что ValueInjector может принимать глубокий график ViewModel и отображать на/из глубокого графика Business Entity и отображать все, что точно такое же, работа, и что мне нужно только указать, как обращаться с чем-то другим. Я надеялся, что AutoMapper добавит эту возможность, но она никогда не материализовалась, и у меня не было времени писать собственный авто-карппер. –

+3

@Chris Marisic, вы можете использовать его, если вы имеете в виду глубокое клонирование, я сделал одну инъекцию, как только это будет рекурсивно, но не будет работать для свойств коллекций. Http://valueinjecter.codeplex.com/Thread/View. aspx? ThreadId = 236126, или вы можете сделать Flat ViewModel и использовать сплющивание и unflattening, это было бы легко – Omu

+0

Объекты ViewModel и Domain были бы похожи, но разные, а не чистый клон. 90% свойств, как правило, являются точным типом и именем, ViewModels часто заканчиваются SelectLists и привязаны к ним, которые я хотел бы игнорировать, возвращаясь в домен. У обоих, скорее всего, есть коллекции объектов на них. –

55

Я пытался как и предпочитают ValueInjecter, потому что это так просто:

myObject.InjectFrom(otherObject); 

Это все, что нужно знать для подавляющего большинства мои потребности в инъекциях. Он не может быть более простым и элегантным, чем это.

+1

' этот объект' способ расширения есть? –

+0

@ Крис Марисич: Да. –

+2

Как я могу отделить мой код от ValueInjecter? Для меня, похоже, всегда есть зависимость от ValueInjecter, то есть в моем веб-проекте, потому что я использую ValueInjecter (метод расширения) для данного объекта DIRECTLY. – Rookian

59

Поскольку я никогда не использовал какие-либо другие инструменты, я могу говорить только об AutoMapper. У меня было несколько целей в виду, для построения AutoMapper:

  • Поддержка уплощение в немом DTO объекты
  • Поддержка очевидных сценариев из коробки (коллекции, перечислений и т.д.)
  • Уметь легко проверить отображения в a test
  • Разрешить краевые случаи для разрешения значений из других мест (настраиваемый тип-> сопоставление типов, отображение отдельных элементов и некоторые действительно сумасшедшие грани).

Если вы хотите сделать это, AutoMapper отлично работает для вас. Вещи AutoMapper не преуспевают являются:

  • Заполнение существующих объектов
  • Unflattening

Причина в том, я никогда не нужно делать эти вещи. По большей части наши сущности не имеют сеттеров, не выставляют коллекции и т. Д., Поэтому их нет. Мы используем AutoMapper для сглаживания к DTO и карты из моделей пользовательского интерфейса для управления сообщениями и тому подобное. Вот где это работает, действительно хорошо для нас.

+1

@Jimmy Bogard Видите ли, что заполнение существующих объектов когда-либо попадет в список функций для AutoMapper? – Roman

+0

Я не пробовал ValueInjecter, но для того, что нам было нужно, automapper очень мощный. – richb01

+0

Я думаю, что самое важное здесь - проверяемость. При переименовании и рефакторинге это огромная помощь. – Kugel

27

Это вопрос, который я тоже изучаю, и для моего прецедента, кажется, это значение для инъекций. Он не требует предварительной настройки для использования (может показаться удачной производительность, я думаю, хотя если бы она была реализована, она могла кэшировать сопоставления будущих вызовов, а не отражать каждый раз), поэтому вам не нужно заранее определять какие-либо сопоставления перед их использованием.

Самое главное, однако, это позволяет обратное картирование. Теперь у меня может быть что-то упущено, поскольку Джимми упоминает, что он не видит случая, когда это необходимо, поэтому, возможно, у меня неправильный шаблон, но мой вариант использования заключается в том, что я создаю объект ViewModel из своего ORM. Затем я показываю это на своей веб-странице. Как только пользователь закончит работу, я снова вернусь к ViewModel в качестве httppost, как это преобразуется обратно в исходные классы ORM? Мне бы хотелось узнать образец с автоматом. С 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?)

Однако, если это образец, который вы хотите использовать, то мой голос - это значение инжектора по сельской миле.

+1

, вероятно, вы также должны спросить об этом в отдельном вопросе с тегом asp.net-mvc и лучших практиках, ViewModel ..., atm. Я не вижу никаких проблем, если это хорошо работает для вас, но я уверен что у кого-то могут быть разные мнения – Omu

+0

Ну, узнав больше mvc. Теперь я могу ответить на мой вопрос. Способ обновления исходной модели при возврате модели с заполненным представлением заключается в использовании функции UpdateModel(), предоставляемой mvc. – DanH

+1

UpdateModel() используется для заполнения модели, представляющей представление, и аналогичен действию Action (модель MyModelClasss). – Omu