2 // System.Runtime.Remoting.RemotingServices NUnit V2.0 test class
\r
4 // Author Jean-Marc ANDRE (jean-marc.andre@polymtl.ca)
\r
6 // ToDo: I didn't write test functions for the method not yep
\r
7 // implemented by Mono
\r
10 using System.Collections;
\r
11 using NUnit.Framework;
\r
12 using System.Reflection;
\r
13 using System.Runtime.Remoting;
\r
14 using System.Threading;
\r
15 using System.Runtime.Remoting.Activation;
\r
16 using System.Runtime.Remoting.Messaging;
\r
17 using System.Runtime.Remoting.Proxies;
\r
18 using System.Runtime.Remoting.Channels;
\r
19 using System.Runtime.Remoting.Channels.Tcp;
\r
21 using MonoTests.Helpers;
\r
23 namespace MonoTests.System.Runtime.Remoting.RemotingServicesInternal
\r
25 // We need our own proxy to intercept messages to remote object
\r
26 // and forward them using RemotingServices.ExecuteMessage
\r
27 public class MyProxy : RealProxy
\r
29 MarshalByRefObject target;
\r
31 MethodBase _mthBase;
\r
32 bool methodOverloaded = false;
\r
34 public MethodBase MthBase {
\r
35 get { return _mthBase; }
\r
38 public bool IsMethodOverloaded {
\r
39 get { return methodOverloaded; }
\r
42 public MyProxy (Type serverType, MarshalByRefObject target)
\r
45 this.target = target;
\r
47 IChannel [] registeredChannels = ChannelServices.RegisteredChannels;
\r
50 // A new IMessageSink chain has to be created
\r
51 // since the RemotingServices.GetEnvoyChainForProxy() is not yet
\r
53 foreach (IChannel channel in registeredChannels) {
\r
54 IChannelSender channelSender = channel as IChannelSender;
\r
55 if (channelSender != null) {
\r
56 _sink = (IMessageSink) channelSender.CreateMessageSink (RemotingServices.GetObjectUri (target), null, out ObjectURI);
\r
62 // Messages will be intercepted here and redirected
\r
63 // to another object.
\r
64 public override IMessage Invoke (IMessage msg)
\r
67 if (msg is IConstructionCallMessage) {
\r
68 IActivator remActivator = (IActivator) RemotingServices.Connect (typeof (IActivator), "tcp://localhost:1234/RemoteActivationService.rem");
\r
69 IConstructionReturnMessage crm = remActivator.Activate ((IConstructionCallMessage) msg);
\r
72 methodOverloaded = RemotingServices.IsMethodOverloaded ((IMethodMessage) msg);
\r
74 _mthBase = RemotingServices.GetMethodBaseFromMethodMessage ((IMethodMessage) msg);
\r
75 MethodCallMessageWrapper mcm = new MethodCallMessageWrapper ((IMethodCallMessage) msg);
\r
76 mcm.Uri = RemotingServices.GetObjectUri ((MarshalByRefObject) target);
\r
77 MarshalByRefObject objRem = (MarshalByRefObject) Activator.CreateInstance (GetProxiedType ());
\r
78 RemotingServices.ExecuteMessage ((MarshalByRefObject) objRem, (IMethodCallMessage) msg);
\r
79 IMessage rtnMsg = null;
\r
82 rtnMsg = _sink.SyncProcessMessage (msg);
\r
83 } catch (Exception e) {
\r
84 Console.WriteLine (e.Message);
\r
87 Console.WriteLine ("RR:" + rtnMsg);
\r
90 } catch (Exception ex) {
\r
91 Console.WriteLine (ex);
\r
97 // This class is used to create "CAO"
\r
98 public class MarshalObjectFactory : MarshalByRefObject
\r
100 public MarshalObject GetNewMarshalObject ()
\r
102 return new MarshalObject ();
\r
106 // A class used by the tests
\r
107 public class MarshalObject : ContextBoundObject
\r
109 public MarshalObject ()
\r
114 public MarshalObject (int id, string uri)
\r
122 set { id = value; }
\r
125 public string Uri {
\r
126 get { return uri; }
\r
129 public void Method1 ()
\r
132 methodOneWay = RemotingServices.IsOneWay (MethodBase.GetCurrentMethod ());
\r
135 public void Method2 ()
\r
137 methodOneWay = RemotingServices.IsOneWay (MethodBase.GetCurrentMethod ());
\r
140 public void Method2 (int i)
\r
142 methodOneWay = RemotingServices.IsOneWay (MethodBase.GetCurrentMethod ());
\r
146 public void Method3 ()
\r
148 methodOneWay = RemotingServices.IsOneWay (MethodBase.GetCurrentMethod ());
\r
151 public static int Called {
\r
152 get { return _called; }
\r
155 public static bool IsMethodOneWay {
\r
156 get { return methodOneWay; }
\r
159 private static int _called;
\r
160 private int id = 0;
\r
161 private string uri;
\r
162 private static bool methodOneWay = false;
\r
165 // Another class used by the tests
\r
166 public class DerivedMarshalObject : MarshalObject
\r
168 public DerivedMarshalObject () { }
\r
170 public DerivedMarshalObject (int id, string uri) : base (id, uri) { }
\r
181 public class CC : MarshalByRefObject
\r
185 public class DD : MarshalByRefObject
\r
190 } // namespace MonoTests.System.Runtime.Remoting.RemotingServicesInternal
\r
192 namespace MonoTests.Remoting
\r
194 using MonoTests.System.Runtime.Remoting.RemotingServicesInternal;
\r
196 // The main test class
\r
198 public class RemotingServicesTest
\r
200 private static int MarshalObjectId = 0;
\r
202 public RemotingServicesTest ()
\r
204 MarshalObjectId = 0;
\r
207 // Helper function that create a new
\r
208 // MarshalObject with an unique ID
\r
209 private static MarshalObject NewMarshalObject ()
\r
211 string uri = "MonoTests.System.Runtime.Remoting.RemotingServicesTest.MarshalObject" + MarshalObjectId.ToString ();
\r
212 MarshalObject objMarshal = new MarshalObject (MarshalObjectId, uri);
\r
219 // Another helper function
\r
220 private DerivedMarshalObject NewDerivedMarshalObject ()
\r
222 string uri = "MonoTests.System.Runtime.Remoting.RemotingServicesTest.DerivedMarshalObject" + MarshalObjectId.ToString ();
\r
223 DerivedMarshalObject objMarshal = new DerivedMarshalObject (MarshalObjectId, uri);
\r
230 // The two folling method test RemotingServices.Marshal()
\r
232 public void Marshal1 ()
\r
235 MarshalObject objMarshal = NewMarshalObject ();
\r
236 ObjRef objRef = RemotingServices.Marshal (objMarshal);
\r
238 Assert.IsNotNull (objRef.URI, "#A01");
\r
240 MarshalObject objRem = (MarshalObject) RemotingServices.Unmarshal (objRef);
\r
241 Assert.AreEqual (objMarshal.Id, objRem.Id, "#A02");
\r
244 Assert.AreEqual (objMarshal.Id, objRem.Id, "#A03");
\r
246 // TODO: uncomment when RemotingServices.Disconnect is implemented
\r
247 //RemotingServices.Disconnect(objMarshal);
\r
249 objMarshal = NewMarshalObject ();
\r
251 objRef = RemotingServices.Marshal (objMarshal, objMarshal.Uri);
\r
253 Assert.IsTrue (objRef.URI.EndsWith (objMarshal.Uri), "#A04");
\r
254 // TODO: uncomment when RemotingServices.Disconnect is implemented
\r
255 //RemotingServices.Disconnect(objMarshal);
\r
259 public void Marshal2 ()
\r
261 DerivedMarshalObject derivedObjMarshal = NewDerivedMarshalObject ();
\r
263 ObjRef objRef = RemotingServices.Marshal (derivedObjMarshal, derivedObjMarshal.Uri, typeof (MarshalObject));
\r
265 // Check that the type of the marshaled object is MarshalObject
\r
266 Assert.IsTrue (objRef.TypeInfo.TypeName.StartsWith ((typeof (MarshalObject)).ToString ()), "#A05");
\r
268 // TODO: uncomment when RemotingServices.Disconnect is implemented
\r
269 //RemotingServices.Disconnect(derivedObjMarshal);
\r
272 // Tests RemotingServices.GetObjectUri()
\r
274 public void GetObjectUri ()
\r
276 MarshalObject objMarshal = NewMarshalObject ();
\r
278 Assert.IsNull (RemotingServices.GetObjectUri (objMarshal), "#A06");
\r
280 RemotingServices.Marshal (objMarshal);
\r
282 Assert.IsNotNull (RemotingServices.GetObjectUri (objMarshal), "#A07");
\r
283 // TODO: uncomment when RemotingServices.Disconnect is implemented
\r
284 //RemotingServices.Disconnect(objMarshal);
\r
287 // Tests RemotingServices.Connect
\r
289 public void Connect ()
\r
291 var port = NetworkHelpers.FindFreePort ();
\r
292 MarshalObject objMarshal = NewMarshalObject ();
\r
294 IDictionary props = new Hashtable ();
\r
295 props ["name"] = objMarshal.Uri;
\r
296 props ["port"] = port;
\r
297 TcpChannel chn = new TcpChannel (props, null, null);
\r
298 ChannelServices.RegisterChannel (chn);
\r
301 RemotingServices.Marshal (objMarshal, objMarshal.Uri);
\r
302 MarshalObject objRem = (MarshalObject) RemotingServices.Connect (typeof (MarshalObject), $"tcp://localhost:{port}/" + objMarshal.Uri);
\r
303 Assert.IsTrue (RemotingServices.IsTransparentProxy (objRem), "#A08");
\r
305 ChannelServices.UnregisterChannel (chn);
\r
306 RemotingServices.Disconnect (objMarshal);
\r
310 // Tests RemotingServices.Marshal()
\r
312 public void MarshalThrowException ()
\r
314 var port = NetworkHelpers.FindFreePort ();
\r
315 MarshalObject objMarshal = NewMarshalObject ();
\r
317 IDictionary props = new Hashtable ();
\r
318 props ["name"] = objMarshal.Uri;
\r
319 props ["port"] = port;
\r
320 TcpChannel chn = new TcpChannel (props, null, null);
\r
321 ChannelServices.RegisterChannel (chn);
\r
324 RemotingServices.Marshal (objMarshal, objMarshal.Uri);
\r
325 MarshalObject objRem = (MarshalObject) RemotingServices.Connect (typeof (MarshalObject), $"tcp://localhost:{port}/" + objMarshal.Uri);
\r
326 // This line should throw a RemotingException
\r
327 // It is forbidden to export an object which is not
\r
330 RemotingServices.Marshal (objRem, objMarshal.Uri);
\r
331 Assert.Fail ("#1");
\r
332 } catch (RemotingException e) {
\r
335 ChannelServices.UnregisterChannel (chn);
\r
337 // TODO: uncomment when RemotingServices.Disconnect is implemented
\r
338 //RemotingServices.Disconnect(objMarshal);
\r
342 // Tests RemotingServices.ExecuteMessage()
\r
343 // also tests GetMethodBaseFromMessage()
\r
344 // IsMethodOverloaded()
\r
346 public void ExecuteMessage ()
\r
348 var port = NetworkHelpers.FindFreePort ();
\r
349 TcpChannel chn = new TcpChannel (port);
\r
350 ChannelServices.RegisterChannel (chn);
\r
352 MarshalObject objMarshal = NewMarshalObject ();
\r
353 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), objMarshal.Uri, WellKnownObjectMode.SingleCall);
\r
355 // use a proxy to catch the Message
\r
356 MyProxy proxy = new MyProxy (typeof (MarshalObject), (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/" + objMarshal.Uri));
\r
358 MarshalObject objRem = (MarshalObject) proxy.GetTransparentProxy ();
\r
362 // Tests RemotingServices.GetMethodBaseFromMethodMessage()
\r
363 Assert.AreEqual ("Method1", proxy.MthBase.Name, "#A09");
\r
364 Assert.IsFalse (proxy.IsMethodOverloaded, "#A09.1");
\r
367 Assert.IsTrue (proxy.IsMethodOverloaded, "#A09.2");
\r
369 // Tests RemotingServices.ExecuteMessage();
\r
370 // If ExecuteMessage does it job well, Method1 should be called 2 times
\r
371 Assert.AreEqual (2, MarshalObject.Called, "#A10");
\r
373 ChannelServices.UnregisterChannel (chn);
\r
377 // Tests the IsOneWay method
\r
379 public void IsOneWay ()
\r
381 var port = NetworkHelpers.FindFreePort ();
\r
382 TcpChannel chn = new TcpChannel (port);
\r
383 ChannelServices.RegisterChannel (chn);
\r
385 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), "MarshalObject.rem", WellKnownObjectMode.Singleton);
\r
387 MarshalObject objRem = (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/MarshalObject.rem");
\r
389 Assert.IsTrue (RemotingServices.IsTransparentProxy (objRem), "#A10.1");
\r
393 Assert.IsFalse (MarshalObject.IsMethodOneWay, "#A10.2");
\r
396 Assert.IsTrue (MarshalObject.IsMethodOneWay, "#A10.3");
\r
398 ChannelServices.UnregisterChannel (chn);
\r
403 public void GetObjRefForProxy ()
\r
405 var port = NetworkHelpers.FindFreePort ();
\r
406 TcpChannel chn = new TcpChannel (port);
\r
407 ChannelServices.RegisterChannel (chn);
\r
409 // Register le factory as a SAO
\r
410 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObjectFactory), "MonoTests.System.Runtime.Remoting.RemotingServicesTest.Factory.soap", WellKnownObjectMode.Singleton);
\r
412 MarshalObjectFactory objFactory = (MarshalObjectFactory) Activator.GetObject (typeof (MarshalObjectFactory), $"tcp://localhost:{port}/MonoTests.System.Runtime.Remoting.RemotingServicesTest.Factory.soap");
\r
415 MarshalObject objRem = objFactory.GetNewMarshalObject ();
\r
417 ObjRef objRefRem = RemotingServices.GetObjRefForProxy ((MarshalByRefObject) objRem);
\r
419 Assert.IsNotNull (objRefRem, "#A11");
\r
421 ChannelServices.UnregisterChannel (chn);
\r
425 // Tests GetRealProxy
\r
427 public void GetRealProxy ()
\r
429 var port = NetworkHelpers.FindFreePort ();
\r
430 TcpChannel chn = new TcpChannel (port);
\r
431 ChannelServices.RegisterChannel (chn);
\r
433 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), "MonoTests.System.Runtime.Remoting.RemotingServicesTest.MarshalObject.soap", WellKnownObjectMode.Singleton);
\r
435 MyProxy proxy = new MyProxy (typeof (MarshalObject), (MarshalByRefObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/MonoTests.System.Runtime.Remoting.RemotingServicesTest.MarshalObject.soap"));
\r
436 MarshalObject objRem = (MarshalObject) proxy.GetTransparentProxy ();
\r
438 RealProxy rp = RemotingServices.GetRealProxy (objRem);
\r
440 Assert.IsNotNull (rp, "#A12");
\r
441 Assert.AreEqual ("MonoTests.System.Runtime.Remoting.RemotingServicesInternal.MyProxy", rp.GetType ().ToString (), "#A13");
\r
443 ChannelServices.UnregisterChannel (chn);
\r
447 // Tests SetObjectUriForMarshal()
\r
449 public void SetObjectUriForMarshal ()
\r
451 var port = NetworkHelpers.FindFreePort ();
\r
452 TcpChannel chn = new TcpChannel (port);
\r
453 ChannelServices.RegisterChannel (chn);
\r
455 MarshalObject objRem = NewMarshalObject ();
\r
456 RemotingServices.SetObjectUriForMarshal (objRem, objRem.Uri);
\r
457 RemotingServices.Marshal (objRem);
\r
459 objRem = (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/" + objRem.Uri);
\r
460 Assert.IsNotNull (objRem, "#A14");
\r
462 ChannelServices.UnregisterChannel (chn);
\r
467 // Tests GetServeurTypeForUri()
\r
469 public void GetServeurTypeForUri ()
\r
471 var port = NetworkHelpers.FindFreePort ();
\r
472 TcpChannel chn = new TcpChannel (port);
\r
473 Type type = typeof (MarshalObject);
\r
474 ChannelServices.RegisterChannel (chn);
\r
476 MarshalObject objRem = NewMarshalObject ();
\r
477 RemotingServices.SetObjectUriForMarshal (objRem, objRem.Uri);
\r
478 RemotingServices.Marshal (objRem);
\r
480 Type typeRem = RemotingServices.GetServerTypeForUri (RemotingServices.GetObjectUri (objRem));
\r
481 Assert.AreEqual (type, typeRem, "#A15");
\r
483 ChannelServices.UnregisterChannel (chn);
\r
487 // Tests IsObjectOutOfDomain
\r
488 // Tests IsObjectOutOfContext
\r
490 [Category ("NotWorking")]
\r
491 public void IsObjectOutOf ()
\r
493 var port = NetworkHelpers.FindFreePort ();
\r
494 TcpChannel chn = new TcpChannel (port);
\r
495 ChannelServices.RegisterChannel (chn);
\r
497 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), "MarshalObject2.rem", WellKnownObjectMode.Singleton);
\r
499 MarshalObject objRem = (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/MarshalObject2.rem");
\r
501 Assert.IsTrue (RemotingServices.IsObjectOutOfAppDomain (objRem), "#A16");
\r
502 Assert.IsTrue (RemotingServices.IsObjectOutOfContext (objRem), "#A17");
\r
504 MarshalObject objMarshal = new MarshalObject ();
\r
505 Assert.IsFalse (RemotingServices.IsObjectOutOfAppDomain (objMarshal), "#A18");
\r
506 Assert.IsFalse (RemotingServices.IsObjectOutOfContext (objMarshal), "#A19");
\r
508 ChannelServices.UnregisterChannel (chn);
\r
513 public void ApplicationNameTest ()
\r
515 var port = NetworkHelpers.FindFreePort ();
\r
516 RemotingConfiguration.ApplicationName = "app";
\r
517 TcpChannel chn = new TcpChannel (port);
\r
518 ChannelServices.RegisterChannel (chn);
\r
520 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), "obj3.rem", WellKnownObjectMode.Singleton);
\r
522 MarshalObject objRem = (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/app/obj3.rem");
\r
523 MarshalObject objRem2 = (MarshalObject) Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/obj3.rem");
\r
525 Assert.IsTrue (RemotingServices.IsTransparentProxy (objRem), "#AN1");
\r
526 Assert.IsTrue (RemotingServices.IsTransparentProxy (objRem2), "#AN2");
\r
528 Assert.IsNotNull (RemotingServices.GetServerTypeForUri ("obj3.rem"), "#AN3");
\r
529 Assert.IsNotNull (RemotingServices.GetServerTypeForUri ("/app/obj3.rem"), "#AN4");
\r
530 Assert.IsNull (RemotingServices.GetServerTypeForUri ("//app/obj3.rem"), "#AN5");
\r
531 Assert.IsNull (RemotingServices.GetServerTypeForUri ("app/obj3.rem"), "#AN6");
\r
532 Assert.IsNull (RemotingServices.GetServerTypeForUri ("/whatever/obj3.rem"), "#AN7");
\r
533 Assert.IsNotNull (RemotingServices.GetServerTypeForUri ("/obj3.rem"), "#AN8");
\r
534 Assert.IsNull (RemotingServices.GetServerTypeForUri ("//obj3.rem"), "#AN9");
\r
536 ChannelServices.UnregisterChannel (chn);
\r
541 public void GetObjectWithChannelDataTest ()
\r
543 var port = NetworkHelpers.FindFreePort ();
\r
544 TcpChannel chn = new TcpChannel (port);
\r
545 ChannelServices.RegisterChannel (chn);
\r
547 RemotingConfiguration.RegisterWellKnownServiceType (typeof (MarshalObject), "getobjectwithchanneldata.rem", WellKnownObjectMode.Singleton);
\r
549 string channelData = "test";
\r
550 Assert.IsNotNull (Activator.GetObject (typeof (MarshalObject), $"tcp://localhost:{port}/getobjectwithchanneldata.rem", channelData), "#01");
\r
552 ChannelServices.UnregisterChannel (chn);
\r
557 [Ignore ("We cannot test RemotingConfiguration.Configure() because it keeps channels registered. If we really need to test it, do it as a standalone case")]
\r
558 public void ConnectProxyCast ()
\r
560 var port = NetworkHelpers.FindFreePort ();
\r
562 RemotingConfiguration.Configure (null);
\r
564 o = RemotingServices.Connect (typeof (MarshalByRefObject), $"tcp://localhost:{port}/ff1.rem");
\r
565 Assert.IsInstanceOfType (typeof (DD), o, "#m1");
\r
566 Assert.IsInstanceOfType (typeof (A), o, "#m2");
\r
567 Assert.IsInstanceOfType (typeof (B), o, "#m3");
\r
568 AssertHelper.IsNotInstanceOfType (typeof (CC), !(o is CC), "#m4");
\r
570 o = RemotingServices.Connect (typeof (A), $"tcp://localhost:{port}/ff3.rem");
\r
571 Assert.IsInstanceOfType (typeof (DD), o, "#a1");
\r
572 Assert.IsInstanceOfType (typeof (A), o, "#a2");
\r
573 Assert.IsInstanceOfType (typeof (B), o, "#a3");
\r
574 AssertHelper.IsNotInstanceOfType (typeof (CC), o, "#a4");
\r
576 o = RemotingServices.Connect (typeof (DD), $"tcp://localhost:{port}/ff4.rem");
\r
577 Assert.IsInstanceOfType (typeof (DD), o, "#d1");
\r
578 Assert.IsInstanceOfType (typeof (A), o, "#d2");
\r
579 Assert.IsInstanceOfType (typeof (B), o, "#d3");
\r
580 AssertHelper.IsNotInstanceOfType (typeof (CC), o, "#d4");
\r
582 o = RemotingServices.Connect (typeof (CC), $"tcp://localhost:{port}/ff5.rem");
\r
583 AssertHelper.IsNotInstanceOfType (typeof (DD), o, "#c1");
\r
584 Assert.IsInstanceOfType (typeof (A), o, "#c2");
\r
585 Assert.IsInstanceOfType (typeof (B), o, "#c3");
\r
586 Assert.IsInstanceOfType (typeof (CC), o, "#c4");
\r
588 // Don't add any tests that must create channels
\r
589 // after ConnectProxyCast (), because this test calls
\r
590 // RemotingConfiguration.Configure ().
\r
591 } // end class RemotingServicesTest
\r
592 } // end of namespace MonoTests.Remoting
\r