AutoMapper vs ValueInjecter

Jedes Mal, wenn ich in StackOverflow nach AutoMapper-Dingen suche, lese ich etwas über ValueInjecter .

Kann mir jemand die Vor- und Nachteile (performance, functionen, API-Nutzung, Erweiterbarkeit, Testen) mitteilen?

Als Schöpfer von ValueInjecter kann ich Ihnen sagen, dass ich es getan habe, weil ich etwas Einfaches und sehr Flexibles wollte

Ich mag es wirklich nicht viel zu schreiben oder viel monkey code schreiben wie:

 Prop1.Ignore, Prop2.Ignore etc. CreateMap(); CreateMap(); etc. 

ValueInjecter ist etwas wie Mozilla mit seinen Plugins, man erstellt ValueInjections und benutzt sie

Es gibt eingebaute Injektionen zum Abflachen, Verflachen und einige, die vererbt werden sollen

und es funktioniert mehr in einem Aspekt Art von Weg , Sie müssen nicht alle Eigenschaften 1 zu 1 angeben, stattdessen tun Sie etwas wie:

nimm alle Int-Eigenschaften von der Quelle, deren Name mit “Id” endet, transformiere den Wert und setze jede Eigenschaft in das Source-Objekt mit dem gleichen Namen ohne das Id-Suffix und der Typ wird von Entity geerbt

so ein offensichtlicher Unterschied, ValueInjecter wird sogar in Windows-Formularen mit Abflachung und Verflachung verwendet, so flexibel ist es

(Zuordnung von Objekt zu Formularsteuerelementen und zurück)

Automapper, nicht benutzbar in Windows Forms, keine Entflattern, aber es hat gute Sachen wie Collections Mapping, wenn Sie es mit ValueInjecter brauchen, machen Sie einfach etwas wie:

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

Sie können ValueInjecter auch zum Zuordnen von anonymen und dynamischen Objekten verwenden

Unterschiede:

  • automapper create Konfiguration für jede Zuordnungsmöglichkeit CreateMap ()

  • valueinjecter inject von einem beliebigen Objekt in ein beliebiges Objekt (es gibt auch Fälle, in denen Sie vom Objekt zum Werttyp injizieren)

  • automapper hat es flachgelegt, und nur für einfache Typen oder vom selben Typ, und es hat keine Verflachung

  • value injecter Nur wenn Sie es brauchen, tun Sie target.InjectFrom(source); also target.InjectFrom(source); also und wenn Sie von Foo.Bar.Name of type String zu FooBarName of type Class1 wollen, FooBarName of type Class1 Sie FlatLoopValueInjection und geben dies an

  • automapper mappt Eigenschaften mit dem gleichen Namen standardmäßig und für den Rest müssen Sie einzeln angeben und Sachen wie Prop1.Ignore (), Prop2.Ignore () etc. tun

  • valueinjecter verfügt über eine Standardinjektion .InjectFrom (), die die Eigenschaften mit dem gleichen Namen und Typ ausführt; Für alles andere erstellst du deine eigenen ValueInjections mit individueller Mapping-Logik / -Regeln, eher wie Aspekte, zB von allen Requisiten des Type Foo zu allen Requisiten des Typs Bar

Da ich noch keines der anderen Tools verwendet habe, kann ich nur über AutoMapper sprechen. Ich hatte einige Ziele für den Aufbau von AutoMapper:

  • Unterstützen Sie das Abflachen zu dummen DTO-Objekten
  • Unterstützung von offensichtlichen Szenarien (Sammlungen, Aufzählungen usw.)
  • In der Lage sein, Zuordnungen in einem Test einfach zu überprüfen
  • Erlaube Randfälle für das Auflösen von Werten von anderen Stellen (benutzerdefinierter Typ-> Typ-Mapping, individuelle Element-Zuordnung und einige wirklich verrückte Kantenfälle).

Wenn Sie diese Dinge tun möchten, funktioniert AutoMapper sehr gut für Sie. Dinge, die AutoMapper nicht gut macht, sind:

  • Bestehende Objekte füllen
  • Entflachung

Der Grund dafür war, dass ich diese Dinge nie tun musste. In den meisten Fällen haben unsere Entitäten keine Setter, stellen keine Sammlungen usw. offen, weshalb sie nicht dort sind. Wir verwenden AutoMapper, um DTOs zu glätten und von UI-Modellen zu Befehlsbefehlen und dergleichen zu mappen. Dort funktioniert es wirklich, sehr gut für uns.

Ich habe beides versucht und ValueInjecter vorgezogen, weil es so einfach ist:

 myObject.InjectFrom(otherObject); 

Das ist alles, was es für die große Mehrheit meiner Injektionsbedürfnisse zu wissen gibt. Es kann unmöglich einfacher und eleganter werden.

Dies ist eine Frage, die ich auch untersucht habe, und für meinen Anwendungsfall scheint es wertschöpfend zu sein. Es erfordert kein vorheriges Setup zu verwenden (kann performance treffen, denke ich, obwohl, wenn intelligent implementiert, könnte es die Zuordnungen für zukünftige Aufrufe zwischenspeichern, anstatt jedes Mal zu reflektieren), so dass Sie keine Zuordnungen vor der Verwendung von ihnen vordefinieren müssen.

Am wichtigsten ist jedoch, dass eine umgekehrte Zuordnung möglich ist. Jetzt kann ich hier etwas vermissen, da Jimmy erwähnt, dass er keinen Anwendungsfall sieht, wo es notwendig ist, also habe ich vielleicht das Muster falsch, aber mein Anwendungsfall ist, dass ich ein ViewModel-Objekt aus meinem ORM erstelle. Ich zeige das dann auf meiner Webseite an. Sobald der Benutzer fertig ist, bekomme ich das ViewModel als httppost zurück, wie wird es wieder in die ursprünglichen ORM-classn konvertiert? Ich würde gerne das Muster mit Auto-Mapper kennen. Mit ValueInjector ist es trivial, und es wird sogar flattern. zB Erstellen einer neuen Entität

Das Modell, das vom Entityframework (Modell zuerst) erstellt wurde:

 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; } } 

Das ViewModel (welches ich mit Validatoren dekorieren kann):

 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; } } 

Der 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(familyViewModel); db.Families.Add(family); db.SaveChanges(); return RedirectToAction("Index"); } catch { return View(); } } 

Meiner Meinung nach wird es nicht viel einfacher als das?

(Das wirft die Frage auf, was ist falsch mit dem Muster, dem ich begegne (und es scheint, dass viele andere es tun), dass es für AutoMapper nicht von Wert ist?)

Wenn dieses Muster jedoch als dekodiert gilt, dann ist meine Stimme wertmäßig um eine Landmeile.