Frage

Etwas, das mir wurde nervt, da ich eine Antwort auf eine andere Frage Stackoverflow lesen (die genauen man entzieht sich mir jetzt), wo ein Benutzer etwas wie „ angegeben Wenn Sie den Service Locator anrufen, werden Sie es zu tun falsch. "

Es war jemand mit einem guten Ruf (in den Hunderttausenden, glaube ich) so neige ich dazu, diese Person zu denken, vielleicht wissen, was sie reden. Ich habe für meine Projekte DI benutzen, da ich das Lernen über sie zum ersten Mal gestartet und wie gut sie sich auf Unit Testing und was nicht. Es ist etwas, das ich recht komfortabel bin mit jetzt und ich denken Ich weiß, was ich tue.

Allerdings gibt es viele Orte, wo ich habe zu lösen Abhängigkeiten in meinem Projekt des Service Locator verwenden. Sobald gutes Beispiel kommt aus meinen Modelbinder-Implementierungen.

Beispiel eines typischen Modell Bindemittel.

public class FileModelBinder : IModelBinder {
    public object BindModel(ControllerContext controllerContext,
                            ModelBindingContext bindingContext) {
        ValueProviderResult value = bindingContext.ValueProvider.GetValue("id");

        IDataContext db = Services.Current.GetService<IDataContext>();
        return db.Files.SingleOrDefault(i => i.Id == id.AttemptedValue);
    }
}

keine echte Implementierung - nur ein kleines Beispiel:

Da die Modelbinder Implementierung erfordert eine neue Instanz, wenn ein Binder ist zunächst angefordert wird, ist es unmöglich, Dependency Injection auf den Konstruktor für diese spezielle Implementierung zu verwenden.

Es ist auf diese Weise in vielen meiner Klassen. Ein anderes Beispiel ist das ein Cache Expiration Prozesses, der eine Methode ausgeführt wird, wenn ein Cache-Objekt in meiner Webseite abläuft. Ich betreibe eine Reihe von Datenbankaufrufe und was nicht. Auch dort ist ich einen Service Locator mit der erforderlichen Abhängigkeit zu erhalten.

Ein weiteres Problem, das ich vor kurzem hatte (die ich hier über eine Frage geschrieben) war, dass alle meine Controller benötigt eine Instanz von IDataContext die ich DI verwendet für - aber ein Aktionsmethode erforderlich, um eine andere Instanz IDataContext. Zum Glück Ninject kam die Rettung mit einer benannten Abhängigkeit. Dies ist jedoch wie ein kludge fühlte und keine wirkliche Lösung.

Ich dachte, mich zumindest verstanden, das Konzept der Trennung von Bereichen recht gut, aber es scheint etwas grundlegend falsch mit zu sein, wie ich verstehe, Dependency Injection und das Service Locator-Muster - und ich weiß nicht, was das ist <. / p>

So wie ich es noch verstehen - und das könnte falsch sein als auch - das ist zumindest in MVC, der Controller sucht einen Konstruktor für einen Controller und ruft den Service Locator selbst die erforderlichen Abhängigkeiten zu erhalten und übergibt sie dann in. ich kann aber, dass nicht alle Klassen verstehen und was eine Fabrik nicht haben, um sie zu erstellen. So scheint es mir, dass einige Muster Service Locator ist akzeptabel ... aber ...

  1. Wann ist es nicht akzeptabel?
  2. Welche Art von Muster sollte ich auf der Suche heraus, denn als ich sollte überdenken, wie ich den Service Locator Muster verwendet werden?
  3. Ist mein Modelbinder Implementierung falsch? Wenn ja, was muss ich lernen, es zu beheben?
  4. In einer anderen Frage nach dem Vorbild dieser einen Benutzer Mark Seemann ein Abstract Factory empfohlen - Wie funktioniert diese beziehen ?

Ich denke, das ist es. - Ich kann nicht wirklich, dass jede anderen Frage, mein Verständnis zu helfen, aber jede zusätzliche Information wird sehr geschätzt

Ich verstehe, dass DI nicht die Antwort auf alles sein könnte, und ich könnte in über Bord gehen, wie ich es umsetzen, jedoch scheint es so, wie ich es mit Unit Testing erwarten zu arbeiten und was nicht.

Ich bin nicht für die Code-Suche meines Beispiel-Implementierung zu beheben. - Ich bin auf der Suche zu lernen, um eine Erklärung suche mein fehlerhaftes Verständnis zu beheben

Ich wünsche stackoverflow.com hatte die Fähigkeit Entwurf Fragen zu speichern. Ich hoffe auch, wer auch immer diese Frage beantwortet für die Beantwortung dieser Frage die entsprechende Menge an Ruf bekommt, wie ich denke, dass ich für viele bin gefragt. Vielen Dank im Voraus.

War es hilfreich?

Lösung

Beachten Sie Folgendes:

public class MyClass
{
  IMyInterface _myInterface;
  IMyOtherInterface _myOtherInterface;

  public MyClass(IMyInterface myInterface, IMyOtherInterface myOtherInterface)
  {
    // Foo

    _myInterface = myInterface;
    _myOtherInterface = myOtherInterface;
  }
}

Mit diesem Design kann ich die Abhängigkeitsanforderungen für meine Art auszudrücken. Der Typ selbst nicht verantwortlich ist für die zu wissen, wie jede der Abhängigkeiten instanziieren, werden sie ihm gegeben (injiziert) durch ein beliebiges von Auflösungsmechanismus verwendet wird [typischerweise ein IoC Behälter]. Während:

public class MyClass
{
  IMyInterface _myInterface;
  IMyOtherInterface _myOtherInterface;

  public MyClass()
  {
    // Bar

    _myInterface = ServiceLocator.Resolve<IMyInterface>();
    _myOtherInterface = ServiceLocator.Resolve<IMyOtherInterface>();
  }
}

Unsere Klasse ist nun abhängig von den specfic Instanzen zu schaffen, sondern über eine Delegation zu einem Service-Locator. In diesem Sinne kann Service Lage ein anti-Muster wird in Betracht gezogen, weil Sie keine Abhängigkeiten auszusetzen, aber ermöglichen Sie es Probleme, die durch Kompilierung zu sprudeln in Laufzeit abgefangen werden können. (A good read ist hier ). Sie versteckte Komplexitäten.

Die Wahl zwischen dem einen oder anderen hängt wirklich davon ab, was Ihr Gebäude auf der Spitze und die erbrachten Leistungen. Normalerweise, wenn Sie eine Anwendung von Grund auf neu bauen würde ich DI ganze Zeit wählen. Es verbessert die Wartbarkeit, fördert die Modularität und macht Typen sehr viel einfacher zu testen. Aber unter ASP.NET MVC3 als Beispiel, könnte man leicht implementieren SL als in das Design gebacken.

Sie können immer für eine Verbundkonstruktion, wo Sie IoC / DI mit SL verwenden könnte, ähnlich wie mit dem Common Services Locator . Sie Komponententeile könnten verdrahtet durch DI, sondern durch SL ausgesetzt. Man könnte sogar Zusammensetzung in die Mischung und die Verwendung so etwas wie das Managed Extensibility Framework werfen (die selbst DI unterstützt, kann aber auch auf andere IoC Container oder Service Locators verdrahtet werden). Es ist eine große Design-Wahl zu machen, in der Regel meine Empfehlung für IoC / DI wäre, wenn möglich.

Ihr spezifisches Design würde ich nicht sagen, ist falsch. In diesem Fall ist der Code nicht verantwortlich eine Instanz des Modells Bindemittel selbst für die Erstellung, die den Rahmen ist, so dass Sie keine Kontrolle über das haben und , um Ihre Nutzung des Dienst Locator wahrscheinlich leicht geändert werden könnte einen IoC-Container zuzugreifen. Aber die Wirkung des Aufrufs Entschlossenheit auf dem Container IoC ... würden Sie nicht, dass die Service-Standort in Betracht ziehen?

Mit einer Abstrakte Fabrik der Fabrik ist spezialisiert auf bestimmte Arten zu schaffen. Sie registrieren nicht Typen für Auflösung, Sie im Wesentlichen ein abstraktes Werk registrieren und baut alle Arten, die Sie benötigen. Mit einem Service Locator ist es entworfen, um orten Dienste und diese Instanzen zurück. Ähnliche von einer Konvention Sicht, aber sehr verschieden im Verhalten.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top