Netzprogrammierung: Microsoft .NET Remoting Robert Tolksdorf und Peter Löhr Überblick 1. Fernaufrufbare Objekte 2. Parameterübergabe 3. Konfigurationsdateien http://msdn.microsoft.com/en-us/library/72x4h507(VS.85).aspx (.NET Framework 3.0) Robert Tolksdorf und Peter Löhr 2 Fernaufrufbare Objekte Robert Tolksdorf und Peter Löhr .NET .NET („dotnet“) : von Microsoft eingeführte Plattform für verteilte Anwendungen: virtuelle Maschine „CLR“ (common language runtime) für die verteilte Ausführung von Programmen, deren Klassen in unterschiedlichen Sprachen geschrieben sein können C#, C++, J#, Visual Basic, Eiffel, Jscript, ... C# (dt. „Cis“, engl. „C-sharp“) : Referenzsprache für .NET, Microsoft‘s Antwort auf Java .NET Remoting : Robert Tolksdorf und Peter Löhr Fernaufrufe auf der .NET-Plattform 4 .NET Remoting • Fernaufrufbarkeit wird nicht an Schnittstellen, sondern an Klassen festgemacht: eine Klasse für fernaufrufbare Objekte wird als Unterklasse der Bibliotheksklasse System.MarshalByRefObject vereinbart, z.B. • class TextStore : MarshalByRefObject { ... } • statt interface Text extends Remote { ... } wie in Java. • Methoden von MarshalByRefObject : • geerbte Methoden von Object (Equals, toString, ...) • CreateObjectRef liefert ObjectRef-Objekt, das Informationen für die explizite Herstellung eines Objektvertreters (proxy) enthält • ..... Robert Tolksdorf und Peter Löhr 5 Objekterzeugung in 3 Varianten ... für fernaufrufbare Objekte auf einem Rechner R: • Fernerzeugung eines privaten Objekts: Objekt wird mit new erzeugt, aber auf anderem Rechner R; der Erzeuger erhält einen Fernverweis. • Fernerzeugung eines öffentlichen Objekts: Erzeugung wird auf R lokal vorbereitet, aber erst beim ersten Zugriff eines Klienten durchgeführt. • Bekanntmachung eines öffentlichen Objekts: Objekt wird auf R erzeugt und dann „veröffentlicht“. (Dies entspricht der Erzeugung bei Java RMI.) Robert Tolksdorf und Peter Löhr 6 Fernerzeugung eines privaten Objekts • Terminologie: client-activated object (CAO) • Der Anbieter vereinbart einen Port, über den er erreichbar ist, und registriert eine Klasse wie z.B. TextStore beim lokalen Fernaufrufsystem. • Der Klient stellt unter Angabe der gewünschten Klasse TextStore über sein lokales Fernaufrufsystem die Verbindung zum Anbieter her und kann mit new TextStore ein Objekt fernerzeugen. Robert Tolksdorf und Peter Löhr 7 Anbieter registriert Klasse using using using using System; // import library name spaces System.Runtime.Remoting; System.Runtime.Remoting.Channels; System.Runtime.Remoting.Channels.Tcp; public class TextStore : MarshalByRefObject { string text; public TextStore(string init) { text = init; } public void replace(string s) { text = s; return; } public string remove() { string result = text; text = null; return result; } public static void Main() { ChannelServices.RegisterChannel(new TcpServerChannel(4711)); RemotingConfiguration.RegisterActivatedServiceType( typeof(TextStore)); Console.WriteLine("press ENTER to stop server."); Console.ReadLine(); } } Robert Tolksdorf und Peter Löhr 8 Fernerzeugung durch Klienten using System; using System.Runtime.Remoting; public class Test { public static void Main() { RemotingConfiguration.RegisterActivatedClientType( typeof(TextStore), "tcp://localhost:4711"); TextStore text = new TextStore("initial text"); Console.WriteLine(text.remove()); // writes "initial text“ Console.WriteLine("press ENTER for another try:"); Console.ReadLine(); Console.WriteLine(text.remove()); // raises exception } } Beachte: Hier besteht kein Bedarf für ein rmiregistry . Robert Tolksdorf und Peter Löhr 9 Übersetzen und Testen (lokal) Übersetzen: C:\> csc server.cs C:\> csc /t:library server.cs Programm server erzeugen Klasse server.dll bereitstellen (Windows dynamic link library, .NET assembly) C:\> csc /r:server.dll client.cs Programm client erzeugen Testen: in separatem Fenster: C:\> server press ENTER to stop server. ... und dann: C:\> client initial text press ENTER for another try: Robert Tolksdorf und Peter Löhr ... ohne Aufsetzen eines Registry ! 10 Öffentliches Objekt bekanntmachen • Bereitstellung eines fernaufrufbaren Objekts - ebenfalls ohne Aufsetzen eines Registry: • Port registrieren: TcpChannel channel = new TcpServerChannel(4711); ChannelServices.RegisterChannel(channel); • Objekt erzeugen: Server server = new Server(); • Objekt mit mnemonischem Namen registrieren: RemotingServices.Marshal(server, "ServerObject"); • Nachdem dies auf dem Rechner host ausgeführt wurde, beschaffen Klienten sich einen Fernverweis wie folgt: Server s = (Server)Activator.GetObject( typeof(Server), "tcp://host:4711/ServerObject"); Robert Tolksdorf und Peter Löhr 11 Schnittstellen verwenden! C:\> csc /r:server.dll client.cs Programm client erzeugen (von S. 10) mit Bezugnahme auf den Anbieter-Code ist nur für einfache lokale Tests praktikabel. Falls Implementierung des Dienstes (Klasse Server) nicht beim Klienten bekannt, Schnittstelle verwenden: public interface Service { ... } public class Server : Service , MarshalByRefObject { public static void Main(string[] arg) { ..... } ......... public class Client { ..... ..... Service s = (Service )Activator.GetObject( typeof(Service), "tcp://taos:4711/ServerObject"); ..... Robert Tolksdorf und Peter Löhr 12 Parameterübergabe Robert Tolksdorf und Peter Löhr Parametermechanismen in C# • op(int i) Wertparameter (call-by-value) Bei Fernaufrufen: call-by-value • op(ref int i) Variablenparameter (call-by-reference) Bei Fernaufrufen: call-by-value-result ! • op(out int i) Variablenparameter, evtl. nicht belegt Bei Fernaufrufen: call-by-result ! • Beim Aufruf auch ref bzw. out, z.B. op(ref n) • --> Bei ref drohen Verletzungen der Verteilungsabstraktion! Robert Tolksdorf und Peter Löhr 14 Variablenparameter Beispiel für abweichende Sematik: public void inc(bool cond, ref int x, ref int y) { if(cond) x++; else y++; } ? Effekt von ob.inc(cond, ref a[i], ref a[k]); ? Jedenfalls sollte ein Element des Feldes a erhöht sein (auch im Fall i==k). ! Bei Fernaufruf kein Effekt falls cond && i==k ! Robert Tolksdorf und Peter Löhr 15 Verweistypen Bei Verweistypen zusätzlich beachten (bei Argument- und Ergebnis-Objekten): • Wenn Objekt fernaufrufbar (MarshalByRefObject): Fernverweis wird übergeben; • sonst, wenn Objekt serialisierbar ( [Serializable] *): Objektkopie wird übergeben; • sonst: Ausnahmemeldung. • --> Verletzungen der Verteilungsabstraktion drohen ! (vgl. Java RMI) * ein der Klassenvereinbarung vorangestelltes Attribut: [Serializable] class ... Robert Tolksdorf und Peter Löhr 16 Verweistypen • Wenn von einem Objekt nur eine Schnittstelle bekannt ist, kann sich dahinter ein MarshalByRefObject verbergen oder auch nicht. • Wenn ja, kann es tatsächlich in einem anderen Rechner liegen - oder auch nicht. (Vgl. Java RMI, Parametersemantik) • Ohne genauere Typanalyse kann daher nicht entschieden werden, ob für einen zum/vom Objekt übertragenen Serializable Parameter ein Verweis oder eine Kopie übertragen wird. interface IStack { ... } class Stack : IStack { ... } class RemoteStack : IStack, MarshalByRefObject { ... } ..... void op(IStack stack) { ... a = stack.dump(); ... } Robert Tolksdorf und Peter Löhr 17 Konfigurationsdateien Robert Tolksdorf und Peter Löhr Auslagerung der netzspezifischen Daten wie Rechnernamen und Portnummern u.a. aus dem Programmtext in Konfigurationsdateien (XML) • erlaubt deren Änderung ohne Neuübersetzung, • flexibilisiert die Installation, • verbessert die Verteilungsabstraktion. Robert Tolksdorf und Peter Löhr 19 Struktur Typische Struktur einer Konfigurationsdatei: <configuration> <system.runtime.remoting> <application> <channels> ..... </channels> <service> ..... </service> <client> ..... </client> </application> </system.runtime.remoting> </configuration> Robert Tolksdorf und Peter Löhr 20 Beispiel Fernerzeugung eines öffentlichen Objekts (SAO - server-activated object) Beim Anbieter wird Objekterzeugung vorbereitet: ChannelServices.RegisterChannel(new TcpServerChannel(4711)); RemotingConfiguration.RegisterWellKnownServiceType( typeof(Server), "ServerObject", WellKnownObjectMode.Singleton); Klient beschafft sich Fernverweis (impliziert ggfls. Erzeugung): Server s = (Server)Activator.GetObject( // wie Klient auf s. 11 typeof(Server), "tcp://host:4711/ServerObject"); Robert Tolksdorf und Peter Löhr 21 Benutzung einer Konfigurationsdatei Im Anbieter wird ChannelServices.RegisterChannel(new TcpServerChannel(4711)); RemotingConfiguration.RegisterWellKnownServiceType( typeof(Server), "ServerObject", WellKnownObjectMode.Singleton); ersetzt durch RemotingConfiguration.Configure("server.exe.config"); Name einer Konfigurationsdatei für das Programm (in Datei server.exe) Robert Tolksdorf und Peter Löhr 22 Konfigurationsdatei für den Anbieter Inhalt der Konfigurationsdatei server.exe.config : <configuration> <system.runtime.remoting> <application> <channels> <channel ref="tcp" port="4711"/> </channels> Klasse <service> <wellknown mode="Singleton" type="Server, server" objectUri="ServerObject"/> </service> Assembly (server.dll) </application> </system.runtime.remoting> </configuration> Robert Tolksdorf und Peter Löhr 23 ... und beim Klienten Im Klienten wird Server s = (Server)Activator.GetObject( // wie Klient auf s. 11 typeof(Server), "tcp://host:4711/ServerObject"); ersetzt durch RemotingConfiguration.Configure("client.exe.config"); Name einer Konfigurationsdatei für das Programm (in Datei client.exe) Robert Tolksdorf und Peter Löhr 24 Konfigurationsdatei für den Klienten Inhalt der Konfigurationsdatei client.exe.config : <configuration> <system.runtime.remoting> <application> <client> <wellknown type="Server, client" url="tcp://host:4711/ServerObject"/> </client> </application> </system.runtime.remoting> </configuration> Robert Tolksdorf und Peter Löhr 25 Zusammenfassung Robert Tolksdorf und Peter Löhr Zusammenfassung • Objekterzeugung - 3 verschiedene Techniken: • Fernerzeugung eines privaten Objekts (CAO) • Fernerzeugung eines öffentlichen Objekts (SAO) • Bekanntmachung eines lokal erzeugten Objekts • Kein separates Registry erforderlich • stattdessen explizite Port-Angabe nötig • Parameterübergabe: Abstraktionsschwächen • Variablenparameter: Wert/Ergebnis-Übergabe • Serializable: statt Verweis wird Objektkopie übergeben • Konfigurationsdateien • formuliert in XML • entlasten den Programmcode • ermöglichen Änderung der Konfigurationsdaten ohne Neuübersetzung • (offen geblieben: Sicherheit, Leasing, HTTP, ... ) Robert Tolksdorf und Peter Löhr 27 Literatur S. McLean: .NET Remoting. Microsoft Press 2002 I. Rammer: Advanced .NET Remoting. apress 2002 (2. ed. 2006) M. Kuhrmann, E. Horn, J. Calame: Verteilte Systeme mit .NET Remoting. Spektrum 2004 http://msdn.microsoft.com/en-us/library/72x4h507(VS.85).aspx (.NET Framework 3.0) Robert Tolksdorf und Peter Löhr 28