About josekonoor

玄铁剑

成功的途径:抄,创造,研究,发明...
posts - 128, comments - 42, trackbacks - 0, articles - 174

Introduction

Dot Net Remoting is a simple programming model/framework which allows objects from different machines/processes/app-domains to communicate each other. It allows the flexibility of using different types of communication protocols (tcp, http etc..) and message formatters (binary, SOAP etc..). Communication among different app-domains is facilitated by Remoting objects. Remoting objects can be hosted using Managed Executables/IIS/.Net Component Services. It is also possible for .Net applications running on different machines to share the same instance of a remoting object hosted on a server. 

 

This document demonstrates how to handle events from a remote object using a real time ‘Message and file transfer’ application.

 

Technologies covered in this document

 

This document demonstrates the following pattern and technologies.

 

·         Publisher listener design pattern

·         Server activated singleton objects

·         Marshal by reference remote object access

·         Raising events from remote objects

·         Use of binary format over TCP channel

 

Publisher-Listener Design pattern.

Design patterns are an efficient way of reusing and sharing solutions to repeating problems. ‘Publisher-Listener’ is a behavioral design pattern. It is also known as ‘observer’ pattern. By definition, a ‘Publisher-listener’ pattern establishes a one-to-many dependency between objects so that when one object changes state , all it’s dependents are notified and updated automatically.

 

Sample screenshot 

 

As shown in the above diagram, in a ‘Publisher-Listener’ design pattern, when a publisher post a message, all the listeners are automatically get updated with the message. A publisher and listener can be the same object. There can be so many publishers and listeners. All the listeners have to register to the server to make them enable to listen to the messages.

 

Dot Net Remoting terminologies

 

Server-Activated Objects

Server-activated objects are objects whose lifetimes are controlled by the server. They are created by the server only as needed when the client invokes the first method on the object. Server-activated objects only support default constructors. To use a remote object with parameterized constructors you can use client activation or dynamic publication (see below). Server-activated objects are also referred to as well-known object types, as their location (URL) is published and known in advance. There are two activation modes for server-activated objects, Singleton and SingleCall, both of which are described below.

 

Single Call

Single Call objects service one and only one request coming in. Single Call objects are useful in scenarios where the objects are required to do a finite amount of work. Single Call objects are usually not required to store state information, and they cannot hold state information between method calls. However, Single Call objects can be configured in a load-balanced fashion.

 

Singleton Objects

Singleton objects are those objects that service multiple clients and hence share data by storing state information between client invocations. They are useful in cases in which data needs to be shared explicitly between clients and also in which the overhead of creating and maintaining objects is substantial.

For example, the following code snippet depicts a server-activated (wellknown) type with activation mode set to SingleCall.

 

<service>

  <wellknown mode="SingleCall" type="Hello.HelloService, Hello" objectUri="HelloService.soap" />

</service>

 

Client-Activated Objects (CAO)

Client-activated objects (CAO) are server-side objects that are activated upon request from the client. When the client submits a request for a server object using "new" operator or Activator.CreateInstance(), an activation request message is sent to the remote application. The server then creates an instance of the requested class and returns an ObjRef back to the client application that invoked it. A proxy is then created on the client side using the ObjRef. The client's method calls will be executed on the proxy. Client-activated objects can store state information between method calls for its specific client and not across different client objects. Each invocation of "new" returns a proxy to an independent instance of the server type. For example, the following code snippet depicts a ClientActivated type. Note that we no longer need an URL, as for client-activated types the type alone is sufficient for activation. Also, the wellknown tag has been replaced by the activated tag.

 

<service>

  <activated type="Hello.HelloService, Hello" objectUri="HelloService.soap" />

</service>

 

Types of Marshalling

Objects are valid only in the application domain where they are created. Any attempt to pass the object as a parameter or return it as a result will fail unless any of the following types of marshalling is used.

 

Marshal By Value (MBV)

For objects that are Marshal By Value (MBV), a complete copy of the object is made when the object is passed from one application to another. If the object is marked as Serializable, the object will automatically be serialized, transported from the one application domain to the other, and then deserialized to produce an exact copy of the object in the second application domain.

 

Marshal By Reference (MBR)

For objects that are Marshal By Reference (MBR), a reference to the object is made when passed from one application to another. When the object reference (ObjRef) arrives in the remote application, it is turned into a "proxy" back to the original object. In order to marshal a remoting object by reference, inherit it from MarshalByRefObject class.

 

Proxy objects.

 When a client creates an instance of a remote object, it receives a proxy to the class instance on the server. All methods called on the proxy will automatically be forwarded to the remote class and any results will be returned to the client. From the client's perspective, this process is no different than making a local call.

 

Stateless and Stateful objects.

 The .Net Framework makes a provision for creating remote objects as stateless. When an object is configured as SingleCall, it will be created when a method is called on that object. The object processes the call, returns an optional result, and is then collected by the garbage collector. This way the client is always connected to a fresh object with each call.

Configuring an object as a Singleton ensures that all clients will be connected to the same object whenever a call is made to that object.

 

Lease based Lifetime.

The lifetime of remote objects is controlled by a leasing mechanism. When an object is first created, it is given a lease time. When the lease time of the object reaches zero, the object will be disconnected from the Remoting infrastructure and when all references to the object has been freed within the AppDomain, it will be collected by the garbage collector. A number of mechanisms are provided that allow the client to extend the lease on the object, thereby sustaining its life.

 

Raising events from remote objects

As with any normal .Net class, event handlers can be attached to remoting objects so that a client can hook methods to serve the declared events. Whenever the event gets fired in the remote object, the event handler method is executed in the client. However delegates require that the receiving object be able to obtain the type information for the class whose function is being wrapped by the delegate. In the case of the remoting, it means that he client assembly be available to the server. If the client assembly is not available to the server, that type information cannot be loaded.

 

To make remoted delegates work, an abstract class (MustInherit in Visual Basic .NET, abstract in C#) that contains the callback function must be defined in a common assembly that both client and server have access to. The client can then derive a custom class from this abstract class to implement the logic in the callback. The abstract class needs to have a specific structure. The function to be used for callbacks must be a public function that cannot be overriden. This function must forward all calls to a protected abstract function that is overridden in the derived client classes. The reason for this architecture is that the delegate needs to be able to bind to a concrete implementation of the callback function, and this implementation must not be overridable.

 

Remoted delegates are implemented in the ‘Message and File Transfer Application’ (explained in section 6). You can refer the source code attached.

 

Message and File Transfer Application

 

Problem Definition

Basically, it is a chat application for intranet users of Windows network. The following screen shots explain the required functionality of this tool. When a user execute the client application, it the user gets automatically logged into the application. It then loads a Win-Form with a list of all the users who have already logged in. This list gets automatically updated in frequent intervals. In order to chat with a user, all that you have to do is to select the name of the user and type the message on the editable textbox. On entering the message, it get published to the remote object with the ‘from’ and ‘to’ addresses and all the listening clients get it. On receiving a message, each client checks the ‘to’ address and decide whether to display that message or not.

 

Step1:

User ‘Joser’ log in

 

Sample screenshot 

 

Step2:

User ‘Vijiths’ log in and send a few messages and file to user ‘Joser’

 

Sample screenshot 

 

Sample screenshot

 

Step3:

User – ‘Joser’ gets a down load-confirmation message.

 

Sample screenshot 

Sample screenshot

Sample screenshot

 

Solution architecture

The solution architecture is shown in the diagram below. There is class the object of which (the remote object) is hosted on a remote server by using a console application. Loading of this application can be configured using a windows service. As with any client-server application, it is must that the server application should be up running before the clients can access it. This object is a singleton object. The client application is a Winform which has reference to a local copy of the remote component. Using the local reference, the client application creates a proxy object. This proxy object then gets a reference of the remote object so that whenever the clients access the proxy object, it in turn accesses the remote object. Since the remote object is a singleton object, all the clients connecting to a single server is accessing the same instance of the remote class. This facilitates the communication among different clients.

 

The remote object exposes certain event handlers such as OnLogin, OnLogout, OnMessagePublish etc.. The client application can hook methods to these event handlers. So, whenever these events happen, all the clients get notified about it.

 

Whenever a user sends some message to another user, the ‘OnMessagePublish’ event is raised. The sender acts as a publisher. All the clients, who have registered (added) a method to the ‘OnMessagePublish’ event handler act as listeners. This is how ‘Publisher-Listener’ design pattern is being implemented in this design.

 

Sample screenshot

 

Configuration Files

 

Server Configuration File

<configuration>

   <system.runtime.remoting>

      <application>

<lifetime leaseTime="20D" sponsorshipTimeout="1H" renewOnCallTime="1D" leaseManagerPollTime="1H" />

         <service>

            <wellknown

               mode="Singleton"

               type="MessageShare.SharedMessage,MessageShare"

               objectUri="SharedMessage"/>

                                                </service>

                                                <channels>

                                                                <channel ref = "tcp" port = "8080">

 

                                                                <serverProviders>

                                                                                <formatter ref="binary" typeFilterLevel="Full" />

                                                                </serverProviders> 

                                                                </channel>

                                                </channels>

                                </application>

                </system.runtime.remoting>

</configuration>

 

Client Configuration File

<configuration>

   <system.runtime.remoting>

      <application>

      <lifetime leaseTime="20D" sponsorshipTimeout="1H" renewOnCallTime="1D" leaseManagerPollTime="1H" />

        <client>

        <wellknown type="MessageShare.SharedMessage,MessageShare" url="tcp://10.201.33.229:8080/SharedMessage" />                                       

        </client>

         <channels>

            <channel ref="tcp" port="0" clientConnectionLimit="20" >

           </channel>

         </channels>       

       </application>

   </system.runtime.remoting>

<appSettings>

   <add key="RemotingUrl" value="tcp://10.201.33.229:8080/SharedMessage"></add>

</appSettings>

</configuration>

 

Please note to change the IP address and port number - tcp://10.201.33.229:8080 to that of the server machine where the server application is running. The port number should be same as that configured in the server configuration file.

 

Code snippets

Remoting class

 

Download sourcecode - RemotingClassSource.zip 

  

Server Application

 

Download sourcecode - ServerAppSource.zip

 

Client application (Win-Form)

Download sourcecode - ClientAppSource.Zip

Installation Files

 

Download InstallationFiles - ServerAppExe.zip

Download InstallationFiles - ClientAppExe.zip

 

Installation Notes:

 

·         Please note to change the IP address and port number - tcp://10.201.33.229:8080 in the client configuration file to that of the server machine where the server application is running.

·         The port number in the client configuration file should be same as that configured in the server configuration file.

·         Manually start the server application (executable console application)

·         Use the client application only after ensuring the following

o        The configuration files are updated properly

o        The server application is started.

 

Reference

·         An Introduction to Microsoft .NET Remoting Framework

·         Remoting Events

·         Format for .NET Remoting Configuration Files

 

Abbreviations

Abbreviation

Expansion

MBV

Marshal By Value

MBR

Marshal By Reference

CAO

Client Activated Objects

SOAP

Simple Object Access Protocol

IIS

Internet Information Services


Pls visit my site at www.geocities.com/josekonoor

josekonoor@yahoo.com

Click here to view josekonoor's online profile.

Feedback

# re: Remote Events using Delegates – a real world example of 'chat and file send' application  回复  更多评论   

2008-02-21 13:34 by sonnian
Unfortunately,I can't get sample code.Please help me,may you give me new link?
Thanks a lot

# re: Remote Events using Delegates – a real world example of 'chat and file send' application  回复  更多评论   

2008-02-23 23:24 by 玄铁剑
you can get the www.codeproject.com and search the key: .net Remoting windows,after you will see many tips
只有注册用户登录后才能发表评论。