I have a method like the following:
public void ExecuteSomeCommand()
{
new MyCommand( someInt, SomeEnum.EnumValue ).Execute();
}
I'd like to test that the enum value that is passed in to the constructor of the ICommand object I'm creating is the correct value. Is there any way I can do this with Rhino.Mocks?
The first step is to import Mockito dependencies into your code. Now let us see an example of how to test the class. Let us assume the below is the class that we want to test. Below is the sample class of the object that is instantiated in ClassToBeTested.
Using the verify() method. Whenever we mock a void method we do not expect a return value that is why we can only verify whether that method is being called or not. Features of verify(): Mockito provides us with a verify() method which lets us verify whether the mock void method is being called or not.
Unit Testing Techniques:Black Box Testing - Using which the user interface, input and output are tested. White Box Testing - used to test each one of those functions behaviour is tested. Gray Box Testing - Used to execute tests, risks and assessment methods.
Option 1: Use a Seam
The easiest way is to refactor that method with a seam:
public void ExecuteSomeCommand()
{
this.CreateCommand(someInt, SomeEnum.EnumValue).Execute();
}
// Your seam
protected virtual ICommand CreateCommand(int someInt,
SomeEnum someEnum)
{
return new MyCommand(someInt, SomeEnum.EnumValue);
}
This way you can intercept the creation of the 'new' operator by extending this class. When doing this by hand, it might look like this:
public FakeSomeService : SomeService
{
public int SomeInt;
public SomeEnum SomeEnum;
protected override Command CreateCommand(int someInt,
SomeEnum someEnum)
{
this.SomeInt = someInt;
this.SomeEnum = someEnum;
return new FakeCommand();
}
private sealed class FakeCommand : Command
{
public override void Execute() { }
}
}
This fake class can be used in your test methods.
Option 2: Separate behavior and data
A better way would be to separate the data from the behavior. You command has both data (the message) and the behavior (handling that message). If you are allowed to do such a change in your code base: separate this, for instance by defining commands and command handlers. Here is an example:
// Define an interface for handling commands
public interface IHandler<TCommand>
{
void Handle(TCommand command);
}
// Define your specific command
public class MyCommand
{
public int SomeInt;
public SomeEnum SomeEnum;
}
// Define your handler for that command
public class MyCommandHandler : IHandler<MyCommand>
{
public void Handle(MyCommand command)
{
// here your old execute logic
}
}
Now you can use dependency injection to inject a handler into the class you wish to test. This class will now look like this:
public class SomeService
{
private readonly IHandler<MyCommand> handler;
// Inject a handler here using constructor injection.
public SomeService(IHandler<MyCommand> handler)
{
this.handler = handler;
}
public void ExecuteSomeCommand()
{
this.handler.Handle(new MyCommand
{
SomeInt = someInt,
SomeEnum = someEnum
});
}
}
Since you now separated the data from the behavior, it will be very easy to create a fake command handler (or create it using Rhino mocks) that checks if the correct command was sent to the handler. Manually this would look like this:
public class FakeHandler<TCommand> : IHandler<TCommand>
{
public TCommand HandledCommand { get; set; }
public void Handle(TCommand command)
{
this.HandledCommand = command;
}
}
This fake handler can be reused throughout your unit testing project. A test using this FakeHandler
could look like this:
[TestMethod]
public void SomeTestMethod()
{
// Arrange
int expected = 23;
var handler = new FakeHandler<MyCommand>();
var service = new SomeService(handler);
// Act
service.ExecuteSomeCommand();
// Assert
Assert.AreEqual(expected, handler.HandledCommand.SomeInt);
}
Separating the data from the behavior not only makes your application more testable. It makes your application more resilient to change. For instance, cross-cutting concerns can be added to the execution of commands, without the need to make changes to any handler in the system. Because the IHandler<T>
is an interface with a single method, it is very easy to write a decorator that can wrap every handler and add things like logging, audit trailing, profiling, validation, transaction handling, fault tolerance improvents, etc. You can read more about it in this article.
None that I'm aware of. The closest thing that comes to my mind is to use a factory, then create a StrictMock
of that factory. Something like that:
readonly ICommandFactory factory;
public Constructor(ICommandFactory factory)
{
this.factory = factory;
}
public void ExecuteSomeCommand()
{
factory.Create( someInt, SomeEnum.EnumValue ).Execute();
}
then, you can place expectations on invokation to Create()
.
HTH
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With