Moq can Mock HubConnection but RhinoMocks can't?

c#, moq, rhino-mocks, signalr, unit-testing

Solution

My tip is to use the none concrete types from your code and inject the concrete types using a Ioc. The signalr dot net client however is missing a DependencyResolver unlike the server. I rolled my own to get around this, you can check out the code here (But in your case you can use any Ioc like Ninject, autofac etc)

https://github.com/AndersMalmgren/SignalR.EventAggregatorProxy/blob/master/SignalR.EventAggregatorProxy.Client.DotNet/Bootstrap/DependencyResolver.cs

The hub connection and proxy is a bit hard to abstract since you are dependent on the concrete types to create the proxy. I solved it with abstracting the creation of the hub proxy to a factory interface that returns a IHubProxy that can be easily mocked.

Look here https://github.com/AndersMalmgren/SignalR.EventAggregatorProxy/blob/master/SignalR.EventAggregatorProxy.Client.DotNet/Bootstrap/Factories/HubProxyFactory.cs

All examples are taken from my dot net client for this library https://github.com/AndersMalmgren/SignalR.EventAggregatorProxy

Problem

I'm looking at the unit tests for SignalR and noticed one of the tests uses Moq to create a mock HubConnection: ``` [Fact] public void HubCallbackClearedOnFailedInvocation() { var connection = new Mock<HubConnection>("http://foo"); var tcs = new TaskCompletionSource<object>(); tcs.TrySetCanceled(); connection.Setup(c => c.Send(It.IsAny<string>())).Returns(tcs.Task); var hubProxy = new HubProxy(connection.Object, "foo"); var aggEx = Assert.Throws<AggregateException>(() => { hubProxy.Invoke("foo", "arg1").Wait(); }); var ex = aggEx.Unwrap(); Assert.IsType(typeof(TaskCanceledException), ex); Assert.Equal(connection.Object._callbacks.Count, 0); } ``` However, when I try and do the same with a slightly different mocking framework, RhinoMocks, it complains that the method isn't virtual: ``` [Test] public void ShouldCreateBrokerWithHubConnection() { //Arrange var url = "http://localhost6790"; var hubProxy = MockRepository.GenerateMock<IHubProxy>(); var hubConnection = MockRepository.GenerateMock<HubConnection>(url); hubConnection.(c => c.CreateHubProxy("ArtemisClientHub")).Return(hubProxy); ... (more code) } ``` `System.InvalidOperationException : Invalid call, the last call has been used or no call has been made (make sure that you are calling a virtual (C#) / Overridable (VB) method).` Is this just a shortcoming of RhinoMocks compared to a newer library like Moq?

Original source