Introduction
This is a simple .NET Remoting example in three parts: the interface, the server, and the client. The client asks for your name, then sends it to the server. The server returns a personal greeting.
Background
I wanted to see the simplest .NET Remoting project possible. Although there are many resources that explain .NET Remoting, I found many examples were either incomplete, or got convoluted by configuration files, sinks, or activation modes. This example is by no means comprehensive, but it's a good place to start if you're new to .NET Remoting or C#.
Using the code
Download the code, and open the solution in Visual Studio 2005. Build the solution. The tricky part is starting both the client and the server application in the debugger. Select Project in the menu, and choose "Select Startup projects...". Then, select Multiple Startup Projects, and set the RemoteClient and RemoteServer actions to start. Click OK, and hit F5.
The interface
The RemoteInterface project contains just one source file, HelloInterface.cs. It simply identifies the methods that will be performed by the remote object. This file will be compiled into an assembly (a DLL) that contains the meta-data needed by both the client project and the server project to talk to one another.
using System;
namespace RemoteInterface
{
public interface HelloInterface
{
String HelloMethod(String name);
}
}
The server
The server waits for the clients to introduce themselves. When you open the solution, note that RemoveServer contains a project reference to RemoteInterface. This tells the compiler that anything defined in the RemoteInterface project (in our case, the HelloInterface
class) is used by the HelloServer project.
You should also notice two source files: HelloServer.cs and RemoteServerMain.cs. In the example below, HelloServer
implements the HelloInterface
we just defined, plus inherits from another class: MarshalByRefObject
. If we want to use a class with .NET Remoting, we have to inherit from MarshalByRefObject
.
using System;
using RemoteInterface;
namespace RemoteServer
{
public class HelloServer : MarshalByRefObject, HelloInterface
{
public HelloServer()
{
Console.WriteLine("HelloServer activated");
}
public String HelloMethod(String name)
{
Console.WriteLine("HelloServer.HelloMethod : {0}", name);
return "Hi there " + name;
}
}
}
In the next file, the Main
method sets up the .NET Remoting infrastructure. It opens a listening TCP/IP port, and associates our HelloServer
class with a URI, SayHello
. This is the neat part: you can have as many classes as you want, all on the same port, each using a different URI.
using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Channels.Tcp;
namespace RemoteServer {
public class RemoteServer {
public static int Main(string [] args) {
Console.Title = "RemoteServer";
TcpChannel chan = new TcpChannel(8084);
ChannelServices.RegisterChannel(chan, false);
RemotingConfiguration.RegisterWellKnownServiceType(
typeof(HelloServer),
"SayHello",
WellKnownObjectMode.SingleCall);
System.Console.WriteLine("Hit enter to exit...");
System.Console.ReadLine();
chan.StopListening(null);
return 0;
}
}
}
The client
The client below prompts you for your name, then sends it off to the server. Notice that there's no mention of HelloServer
here at all. The code points to the HelloInterface
we defined earlier, and the URI refers to the port and the URI we created for the listener. When this call reaches the server, the server checks its own .NET Remoting configuration and finds the class that matches the URI.
using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Channels.Tcp;
using RemoteInterface;
namespace RemoteClient
{
public class Client
{
public static int Main(string[] args)
{
Console.Title = "RemoteClient";
TcpChannel chan = new TcpChannel();
ChannelServices.RegisterChannel(chan, false);
HelloInterface obj = (HelloInterface)Activator.GetObject(
typeof(RemoteInterface.HelloInterface),
"tcp://localhost:8084/SayHello");
if (obj == null)
System.Console.WriteLine("Could not locate " +
"HelloServer type in RemoteServer.exe asembly");
else
{
while (true)
{
System.Console.WriteLine(
"What is your name? (just hit enter to quit)");
String strName = System.Console.ReadLine();
if (String.IsNullOrEmpty(strName))
break;
Console.WriteLine(obj.HelloMethod(strName));
}
}
return 0;
}
}
}
Where to go next
This is almost the simplest .NET Remoting example possible. The RemoteInterface project and the HelloInterface
class are not really required; the RemoteClient may reference the RemoteServer assembly directly, and use the HelloServer
class in place of the HelloInterface
. However, I prefer to define interfaces someplace other than the client or the server.
This article omitted the issue of activation modes, which you had better read about. I also found the examples of configuration files in the Microsoft Help difficult to understand at first. Having read this example, I hope you can see the basic elements that the configuration files control: classes, network endpoints, and protocols.
There is no exception handling in this example. Clearly, you will need to read the help files on each method called to see just what its possible outcomes are and how you should catch and handle them.
History
- August 28, 2007 - Initial revision.
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.