Willkommen bei ASP.NET Zone. Anmelden | Registrieren | Hilfe

DI / IoC Container LightCore Teil 2: Registrierung über Xml Modul

LightCore Xml Registration moduleWie bereits im ersten Teil erwähnt, wird es einer mehr Schichten Architektur immer wichtiger, Abhängigkeiten zu minimieren. Dabei einen ersten Schritt zu setzen, ist die Implementierung eines IoC Containers. Dieser hilft dabei, den Code in den diversen Projekten unabhängiger zu halten.

1. LightCore – Einführung
2. LightCore – Registrierung über Xml Module
3. LightCore – Registrierung von Generics

Mich persönlich hat Peter Bucher mit seinem neusten Projekt LightCore darauf aufmerksam gemacht. Anfangs war dies nur als Unit Testing Spielwiese gedacht, hat sich aber zu einem konkurrenzfähigen Micro Kernel entwickelt. Dessen weitere Entwicklung wird in Zukunft per Community gesteuert. Der Source Code wurde veröffentlicht und ist auf jeden Fall einen Blick Wert! (Stichwort: Codequalität)



Zurück zum Thema. Viele werden sich denken, was bringt mir das Ganze eigentlich?
  • Abhängigkeiten verringern und Kontrolle der Abhängigkeiten (Interface / Basisklasse - also Abstraktion) und dadurch auf die Instanziierung (Die sonst auf den konkreten Typen geht), rausziehen.
  • Dadurch bessere Testbarkeit und Aufbrechung der Anwendung in mehr Einzelteile, wodurch die Komplexität sinkt.
  • Außerdem globale Konfigurierbarkeit, was genutzt werden soll um Änderungen an vielen, unnötigen Stellen vorzunehmen.
Nun wird anhand eines Beispiels wird gezeigt, wie man Lightcore in einer drei Schichten Architektur einsetzen bzw. integrieren kann.
Gleichzeitig wird die Registrierung über das integrierte Xml Modul erklärt

Was eine drei Schichten Architektur (Tier 3 layer) ist, erklärt Robert Mühsig in seinem Post.

Das folgende Beispiel wird eine Solution mit mehreren Projekten beinhalten, die eine Anwendung mit mehreren Schichten darstellt.

Die Klassische Struktur sieht wie folgt aus:
  • Data Access Layer
  • Business Layer
  • Presentation Layer
Folglich könnten die Projekte so benannt werden:

Data: beinhaltet eine User Klasse sowie das dazugehörige Repository.

Service: beinhaltet einen User Service mit dem Repository als Member, der per Constructor Injection injiziert wird.

Web: Die Präsentation

LightCore Xml Registration Project Tree

Im ersten Teil des Posts wurde gezeigt, wie man Kontrakte einfach per code (global.asax) registrieren kann. Der erste Schritt wird sein, die Registrierung in die Web/App.config bzw. einer eigenen Konfigurationsdatei auszulagern.

Wer achte gibt sieht, dass beim heruntergeladenen Paket unter Anderem eine XML Schema Datei (LightCore.xsd), sowie eine Beispiel Konfiguration (SampleConfiguration.xml) dabei ist.
Nun die Datei LightCore.xsd dem aktuellen Web Projekt hinzufügen.

Es kann eine eigene Konfigurationsdatei erstellt werden, oder aber einfach den entsprechenden Block in die Web/App.config hinzufügen.
Wer sich für letzteres entscheidet, den Block, der innerhalb der SampleConfiguration.xml zu finden ist, einfach in den <configuration> Abschnitt packen.

<configuration>
    …
    <LightCoreConfiguration xmlns="clr-namespace:LightCore.Configuration;assembly=LightCore.Configuration">


Als erstes kommt die Einstellung über den genutzten Lebenszyklus, also ob Singleton, Transient oder HttpRequest.

<LightCoreConfiguration.TypeAliases>
    <TypeAlias Alias="HttpRequest" Type="LightCore.Integration.Web.HttpRequestLifecycle, LightCore.Integration.Web"/>
</LightCoreConfiguration.TypeAliases>


Jetzt die eigentliche Registrierung.
Einfache Registrierungen ohne Gruppen kommen in die LightCoreConfiguration.Registrations Sektion:

<LightCoreConfiguration.Registrations>
    <Registration Name="MyRepository" ContractType="MyAssembly.IUserRepository, MyAssembly" ImplementationType="MyAssembly.Repository, MyAssembly" />
</LightCoreConfiguration.Registrations>


Sollte selbsterklärend sein, Namensangabe um den registrierten Kontrakt wiederzufinden, der Kontrakttyp sowie die Klasse mit jeweiliger Angabe des Assembly Namens. Optionale Argumente für den Konstruktor können über Arguments=“Value1, Value2“ mitgegeben werden. Wenn die LightCore.xsd im Projekt eingebunden wurde, sollte auch IntelliSense zur Verfügung stehen!

Ist eine gruppierte Registrierung gewollt, um bspw. die Repositories zu sammeln, gibt es auch hierfür eine Sektion:

<LightCoreConfiguration.RegistrationGroups>
    <RegistrationGroup Name="Repositories">
        <RegistrationGroup.Registrations>
            <Registration Name="MyRepository" ContractType="MyAssembly.IUserRepository, MyAssembly" ImplementationType="MyAssembly.Repository, MyAssembly" />
        </RegistrationGroup.Registrations>
    </RegistrationGroup>
</LightCoreConfiguration.RegistrationGroups>


Jetzt wo die Registrierung der Repositories gemacht wurde, muss der Container erstellt und das Konfigurationsmodul zugewiesen werden.

Dies sollte in der Globalen Anwendungsdatei (global.asax) in der Application_Start methode gemacht werden:

protected void Application_Start(object sender, EventArgs e)
{
    var builder = new ContainerBuilder();
    var module = new XamlRegistrationModule();
    builder.RegisterModule(module);
    _container = builder.Build();
}


Wenn gewollt, kann die Konfigurationsdatei im Konstruktor des XamlRegistrationModules angegeben werden:

var module = new XamlRegistrationModule("~/MyConfiguration.xml")

Die Objekte können wie gehabt mit resolve aufgelöst werden

var myRepository = _container.Resolve<IRepository>("MyRepository");

Fazit: Welche Variante ist nun besser?

Registrierung per Code hat den Vorteil, dass weniger Fehler auftreten können.
Da es kompiliert werden muss, wird überprüft ob der Kontrakt implementiert ist oder nicht.

Somit ist es intuitiver und Refactoring-sicher. Wenn eine Klasse umbenannt wird – wird sie auch hier übernommen.

Allerdings hat die Registrierung per Code einen riesen Haken: Es ist eine harte – also feste – Referenz.
Wenn eine Assembly, aus welchem Grund auch immer, ausgetauscht wird, muss das komplette Projekt neu kompiliert werden.

Sollte das bei einer Produktivumgebung der Fall sein, kann das ein großer Nachteil sein. Dadurch muss ein komplettes Deployment gemacht werden.

Was also „besser“ ist, hängt vom Anwendungsfall ab.
Ich persönlich finde die „per Code“ Variante bei nicht allzu vielen Klassen übersichtlich.
Eine gut durchdachte Anwendungsstruktur von Anfang an ist natürlich Voraussetzung :-)

Anbei gibt’s wie immer das oben gezeigte Beispiel als Download.

Veröffentlicht Sonntag, 21. Februar 2010 17:02 von Roberto
Abgelegt unter: , , ,

Attachment(s): LightCore.DemoPartTwo.zip

Kommentare

# Roberto's Blog : DI / IoC Container LightCore Teil 2: Registrierung &#252;ber Xml Modul

# re: DI / IoC Container LightCore Teil 2: Registrierung über Xml Modul

Eine weitere typsichere Lösung wäre das einbinden einer "Configuration Assembly", die nichts anderes macht als die Konfiguration. Die Interfaces leben sowieso alle in in jeweils eigenen, separaten Assemblie, abgetrennt von der Implementierung, wenn man Komponenten orientiert arbeitet/ bzw. einer gesammelten separaten Interface Assembly. Diese besitzt ein eigenes Interface zum Konfigurieren der Assembly die ein mapping auf alle notwenigen Kompontent durchfürht. Somit bekommen wir über Indirektion und quasi einen Konfigurationsproxy bzw. -gateway auch den gewünschten Effekt hin.

Nächste Variante, die ich schon in Postsvgesehen habe, über die ich auch schon nachdenke ist eine Container Konfigurations DSL, die ähnlich dem ServiceLocator funktioniert.

Und last but not least könnte z.B. IronRuby, Python, Boo order irgend ein anderer hostbarer Interpreter/Compiler in die Applikation eingebettet wird und dann wieder über eine Codedatei/Skriptdatei das Konfigurationsmanagement durchgeführt werden.

Das sind für mich persöhnlich noch bessere Alternativen, als XML. Ausser jemand will die Konfiguration per Tools durchführen. Dann punktet XML wieder, ausser die gehostet Sprache besittz ein CodeDom Model und lässt Codegenerierung und Refactoring zu. Als Tipp sei mal auf NRefactory aus SharpDevelop hingewiesen.

Dienstag, 23. Februar 2010 23:26 by Rainer Schuster

# BASTA! Spring 2010: Das wars …

Ich habe es tatsächlich geschafft und über jede besuchte Session einen Beitrag geschrieben und ich habe

Montag, 1. März 2010 10:32 by Jürgen Gutsch

# re: DI / IoC Container LightCore Teil 2: Registrierung über Xml Modul

Salute Rainer

Die XML-Registierung ist eine Möglichkeit, kein Muss. Komplett abgetrennt vom LightCore-"Kern".

Du kannst gerne eine eigene Implementation von "RegistrationModule" erstellen, wo du eine deiner interessanten, genannten Ideen umsetzen könntest :-)

Montag, 1. März 2010 12:11 by Peter Bucher

# re: DI / IoC Container LightCore Teil 2: Registrierung über Xml Modul

Hallo Rainer und Peter,

Vielen Dank erstmal für eure Kommentare!

Ja, Xml kann - muss aber nicht immer evil sein.

Ich finde eine eigene Configuration Assembly grundsätzlich keine schlechte Idee.

Ich bin immer mehr für code Lösungen - bzw. nutze ich die Registrierung momentan auch per code in eigenen Projekten.

Wenn Du vor hast eine deiner Ideen umzusetzten, wär ich sehr gespannt darauf diese zu sehen!

Viele Grüße,

Roberto

Montag, 1. März 2010 12:21 by Roberto
Anonyme Kommentare sind nicht zugelassen