Laden...

Plugins in einen Dienst laden: Besser per Assembly oder per COM?

Erstellt von wisher78 vor 11 Jahren Letzter Beitrag vor 11 Jahren 1.396 Views
wisher78 Themenstarter:in
101 Beiträge seit 2011
vor 11 Jahren
Plugins in einen Dienst laden: Besser per Assembly oder per COM?

Hallo,

da ich aus der Delphi Schiene komme und folgende Problematik dort mit COM lösen würde,
bitte ich um Rat, ob ich auf dem richtigen Weg bin.

Die Problemstellung ist wiefolgt:
Es soll ein Windows-Dienst als .NET C# Anwendung geschrieben werden. Dieser Dienst kommuniziert mit einer .NET GUI Anwendung. Diese Seite interessiert aber erstmal nicht weiter.
Des weiteren soll der Dienst mit n externen Hosts über ganz unterschiedliche Wege kommunizieren. z.B.: TCP/IP, Seriell, etc.
Der Plan ist zu diesen n Hosts eben so viele Kommunikationstreiber zu implementieren. Nennen wir sie mal "Protocoll Driver". Der Dienst soll also beliebige dieser Protocol Driver laden können.
Meine erste Idee war COM-DLL's im Dienst zu laden.
Nach ein bisschen googlen habe ich festgestellt, dass COM im .NET framework nicht mehr ganz up to date ist und hier wohl eher auf Assembly DLLs zurückgegriffen wird.

Bin ich hier auf dem richtigen Weg, oder gibt es besser Möglichkeiten?

Grüße
S.

C
1.214 Beiträge seit 2006
vor 11 Jahren

Wenn es reicht, die Plugins in einer .NET Sprache zu schreiben, dann kannst du reine.NET Plugins ganz leicht realisieren. Dazu gibts schon tausend Beispiele im Netz und auch hier im Forum. Wenn du die Plugins auch in nativen Sprachen, z.B. C++ oder Delphi schreiben willst, dann brauchst du COM. Würde aber eher darauf verzichten, wenns nicht unbedingt sein muss.
Für die Kommunikation gibts in .NET z.B. WCF, das kann schon über alle möglichen Kanäle kommunizieren. Würde es dir nicht reichen? Ich würds mir auf jeden Fall mal näher anschauen, wenn du es noch nicht kennst.

W
872 Beiträge seit 2005
vor 11 Jahren

Daneben wuerde ich mich an Deiner Stelle mit Dependency Injection Frameworks auseinandersetzen.
Castle Windsor, StructureMap, Spring.NET, AutoFac und Unity waeren Kandidaten.
Das Managed Extensibility Framework von MS geht auch in die Richtung.

wisher78 Themenstarter:in
101 Beiträge seit 2011
vor 11 Jahren

Hallo,

vielen Dank für die Antworten. Ich habe mich jetzt mal etwas in WCF eingelesen. Sieht auf den ersten Blick recht interessant für unsere Problemstellung aus. Allerdings scheint mir WCF ziemlich auf Internetdienste ausgelegt zu sein?

Die wichtigste Frage ist, macht es Sinn auf WCF zurückzugreifen, wenn die Kommunikation nicht nur unter SOAP, sondern diversen Protokollen laufen soll. Im Anhang ein Bild, was ich meine. Der hellblaue Kasten (LIMS Service) entspricht meinem Dienst. Er kommuniziert mit dem orangenen Teil (was erstmal nebensächlich ist) und kommuniziert über die erwähnten "Protocoll Driver", um die es geht, mit den Hosts. Jetzt ergibt sich aus der Anforderung allerdings, dass man flexibel beim Protokoll sein muss. Deshalb sind hier drei Kommunikationswege dargestellt. Das kann sein: TCP/IP, SOAP, aber auch RS232 oder andere.

WCF scheint von Hause aus via SOAP zu kommunizieren. Aber ich könnte mir vorstellen, dass man andere Protokolle einfach implementieren kann, ist das korrekt?

Vielen Dank ,
S.

6.911 Beiträge seit 2009
vor 11 Jahren

Hallo wisher78,

dann hast du dich bei WCF nicht gut genug eingelesen 😉
Standardmäßig wird SOAP, TCP, Named Pipes und jetzt auch REST unterstützt. Eigenen Bindungen können auch erstellt werden und somit könntest du RS232 bedienen - außer es gibt irgendwo (Codeplex, etc.) schon eine Bindung dafür.
Alternativ kannst du immer noch neben WCF einen extra "Stack" für RS232 umsetzen, dies wird wahrscheinlich einfacher sein.

Zu bedenken bei WCF ist, dass außer dem HTTP-Binding, die Clients auch .net sein müssen um die Nachrichten zu verstehen.

Es kommt als auf deine externen Hosts darauf an, ob nun WCF verwendet werden kann od. nicht. Wenn nicht kannst du ein Plug-In-System ganz einfach per Fabrik aufbauen od. wie weiter oben bereits vorschlagen mit DI-Systemen.

mfG Gü

Stellt fachliche Fragen bitte im Forum, damit von den Antworten alle profitieren. Daher beantworte ich solche Fragen nicht per PM.

"Alle sagten, das geht nicht! Dann kam einer, der wusste das nicht - und hat's gemacht!"

wisher78 Themenstarter:in
101 Beiträge seit 2011
vor 11 Jahren

Ich muss erstmal in Erfahrung bringen, ob die Host-Seite(hier Lims Host) als Blackbox zu verstehen ist, die via diverser Protokolle mit unserem Dienst kommuniziert, oder ob wir den Host selbst realisieren.

Bei letzterem interpretiere ich die bisherigen Erkenntnisse so, dass ich ein WCF Dienst (Client) und als Gegenpart einen WCF Host (Server) realisieren und beide um jeweils das gewünschte Protokoll (RS232, etc) erweitern kann. Korrekt?

6.911 Beiträge seit 2009
vor 11 Jahren

Hallo wisher78,

als Dienst wird üblicherweise der Host bezeichnet.

RS232 würde ich nicht über WCF laufen lassen, auch wenn es möglich ist, aber das wird doch zu Aufwändig werden und zuviel Overhead sein.

Sonst bietet der WCF-Server Bindungen an, der Client verbindet sich mit einer passenden davon. Das fällt aber unter [Hinweis] Wie poste ich richtig? Punkt 1.1.1 für WCF.

mfG Gü

Stellt fachliche Fragen bitte im Forum, damit von den Antworten alle profitieren. Daher beantworte ich solche Fragen nicht per PM.

"Alle sagten, das geht nicht! Dann kam einer, der wusste das nicht - und hat's gemacht!"

W
1 Beiträge seit 2012
vor 11 Jahren

Hallo wisher78,

evtl. wiederhole ich manches von den anderen, aber Fakt ist:

Du kannst mit WCF im Prinzip jedes Protokoll umsetzen, wie du möchtest. Die Gegenseite muss im Prinzip auch nicht in .NET geschrieben sein. Solang du auf der Gegenseite irgendwie schaffst Bytes auf egal welchem Weg zu empfangen, zu verarbeiten und evlt. zurückzusenden, kannst du ein beliebiges System bzw. Programmiersprache und an sich auch Betriebssystem, wenn ich mich nicht täusche, verwenden. Das würde allerdings bedeuten, dass du selber TransportChannels für WCF erstellst und die Gegenseite mit dem erzeugten Datenstrom etwas anfangen müsste. WCF würde eine SOAP-Nachricht mit dem Funktionsaufruf und evlt. mitgeschickten Daten generieren und dein Channel schickt sie lediglich "physisch" weiter, woraufhin die Gegenseite den so erzeugten Datenstrom bzw. das Datenpaket deserialisieren und verarbeiten müsste.

Im Idealfall hat man natürlich auf beiden Seiten WCF/.NET und entsprechend das Channel-Gegenstück zum einheitlichen Lesen und Verstehen des Bytearrays. Schließlich leitet man dann das interpretierte Paket bzw. die SOAP-Nachricht an WCF weiter hoch und WCF macht den Rest, ruft deine Methode mit den entsprechenden Parametern und Daten auf usw.

Und noch idealer ist es, wenn man mitgelieferte Bindings (die wiederum Channels beinhalten) verwendet, da man da dann tatsächlich kaum noch was programmieren muss und eine Client-/Serverarchitektur innerhalb nur kurzer Zeit für viele unterschiedliche Übertragungsprotokolle und auch Anzahl an Hosts und Clients erstellen kann.

RS232 ist kein so einfaches Protokoll für WCF. Einfach nur Daten senden und empfangen geht in den einfachsten Beispielen, die man überfall findet, ziemlich unkompliziert. Für WCF müsstest du jedoch so einiges implementieren, damit du RS232 genauso wie TCP/IP oder andere Protokolle verwenden und entsprechend per Konfiguration einfach austauschen oder parallel betreiben kannst (sozusagen ein Service, der auf unterschiedlichen Transportwegen erreichbar ist). RS232 hat die unschöne Eigenschaft, dass von Haus aus nur ein einziger Client und Service per Leitung verbunden sind. Es können sich nicht mehrere Instanzen auf eine Leitung verbinden und sie beide somit schreiben und lesen. Das geht mit irgendwelchen gemoddeden Treibern oder auch per virtuellen Ports über Drittsoftware. Du müsstest dann also entweder ein Binding und Channels bauen, die nur eine einzige Instanz auf jeweils einer Seite zulassen (wobei du dann immer noch verschiedene Portnummern/Leitungen und damit auch WCF-Instanzen verwenden könntest, um wenigstens mehr als eine Verbindung zu haben), oder aber du baust Bindings/Channels, die selbständig oder über eine Hilfsapplikation sich eine einzige RS232-Leitung teilen. Im zweiten Fall könntest du beliebig viele Clients und Services über eine einzige Leitung führen können, auch im Mischbetrieb. Der Sinn hinter vielen Clients und Services bei der geringen Datenrate von RS232 ist mal dahingestellt.

Weiterhin ist es so eine Sache mit RS232. In der Theorie ist alles schön und gut, in der Praxis kann es aber wegen schlechtem Kabel oder elektrischen/magnetfeldtechnischen Störungen zu Datenverlust kommen. Die im RS232 bereitgestellte Fehlerkorrektur/-Erkennung ist meiner Erfahrung nach nicht das Gelbe vom Ei. Wenn du kurze Kabel heißt, sollte es im Normalfall ganz gut gehen auch ohne Fehler.

Als WCF-Channel müsstest du dich auch um die ganze Organisation kümmern, z.B.: Was tun, wenn Kabel gezogen wurde? Was ist, wenn nur Kauderwelsch ankam bzw. nur ein halbes Paket? Der Gegenseite mitteilen, dass sie nochmal versuchen soll oder einfach lange warten? Teilst du WCF mit, dass was schief ging oder lässt du bis zum Timeout warten?

Ich hab mal am Ende des Studiums für ein Unternehmen ein Binding für RS232 erstellt, das per wiederum eigens erstellter Zwischenschicht eine einzige RS232 Leitung benutzt und die anfallenden Pakete an den jeweiligen Enden an die eigentlichen RS232-WCF-Channels verteilt werden. Damit waren beliebig viele Services und Clients möglich, egal auf welcher Seite. Ebenfalls konnte man Kompression hinzuschalten (bei der Datenrate von RS232 immer wieder echt nötig) und auch die Verschlüsselung, wenn man mochte. Die Zwischenapplikation nahm die Bytearrays von den WCF-Channels an, ergänzte sie um ein paar Bytes für die Wiedererkennung und Zuteilung am anderen Ende und schickte sie per RS232. Weiterhin war eine Priorisierung miteingebaut, die man in der ganz normalen WCF-Konfiguration einstellen konnte und die Zwischenapplikation daraufhin die hereinkommenden Pakete unterschiedlich behandelte. Sinnvoll bei (für RS232) größeren Datenübertragungen einzelner Hosts/Clients.

Das alles ist allerdings recht zeitaufwändig. Ich weiß daher nicht, ob du wirklich genau das suchst. Mit bestehenden Bindings/Channels ist es wirklich am einfachsten und auch sichersten 😃

Waldemar

wisher78 Themenstarter:in
101 Beiträge seit 2011
vor 11 Jahren

Vielen Dank für die ausführliche Antwort, Waldemar.
Wenn ich die Wahl hätte, würde ich die Kommunikation auf ein, oder zwei Protokolle beschränken. Aber wie das im Business leider manchmal so ist, man möchte ein breites Spektrum an Schnittstellen abdecken und anbieten und die Softwareentwicklung muss schauen, wie sie es realisiert bekommt. Jedenfalls habe ich mal einen ganz guten Einblick in WCF erhalten. Vielen Dank dafür!
Ich werde weiter recherchieren und mir eine passende Lösung zur Problemstellung einfallen lassen.

Viele Grüße
S.