In typical unit testing scenarios
, mocking property getters and setters isn't high on the list of areas of concern. Where it usually comes into play is when an entity’s properties’ values (or the act of setting them) are part of the scaffolding, or behavior for the system under test.
An example is a scenario where entities are publishers of events and the system under test is the subscriber. WPF and Silverlight (as well as Windows 8 development with .NET) make common use of the INotifyPropertyChanged interface on models to facilitate the MVVM pattern. The INotifyPropertyChanged interface contains a single event, as shown in Listing 1.
Listing 1 – INotifyPropertyChanged Interface
The premise of the pattern is that any time a property changes on the model, the PropertyChanged event gets raised, notifying any subscribers of the change. One of the subscribers in .NET is the XAML data binding engine, and together they can provide a very rich and responsive user interface.
By implementing this interface on the models in your application (in addition to the benefits that you get from the XAML databinding engine), you can build an “IsDirty” flag that gets set if any property on your model changes. One use for this flag in the XAML world is to pass it into commands as parameters to enable Save and Cancel buttons, for example.
For our example, we are going to create an IEntity interface as well as a EntityBase class that implements the IEntity interface. Both the interface and base class are shown in Listing 2.
Listing 2 – IEntity Interface and BaseEntity base class
Mocking Property Getters
Property getters are mocked the same way traditional methods are mocked (minus the parenthesis and parameters, of course!). To show this in action, I’ve created a simple implementation of an ICommand. For those of you familiar with XAML, this is old hat. If you aren’t a familiar with the ICommand pattern, it works like this:
- The command takes a parameter to the CanExecute and Execute methods
- If the CanExecute method returns false, the Execute method won’t be able to be executed
- If the CanExecute method returns true, the Execute method is able to be executed.
Of course, there’s a lot more to it than that, but that’s enough for what we are testing. The implementation of ICommand is shown in Listing 3. Listing 3 – ICommand Implementation
For our first test, we want to ensure that the CanExecute method returns true if the parameter is not null, it’s an IEntity, and IsDirty is true. Skipping over the tests for is null and the parameter is not an IEntity since they don’t need mock objects to execute, Listing 4 shows the test that creates a mock of the IEntity interface, creates an expectation that IsDirty will be called, and when it is called, it will return true as the property value.
Listing 4 – Mocking the getter for a property
Mocking Property Setters
Mocking property setters work a little differently than getters and regular methods. Instead of “Arrange”, we use “ArrangeSet”. A very simple example just meant to show the syntax is shown in Listing 5.
Listing 5 – Demonstration Test for Mock.ArrangeSet
The real need for this type of test is to test our implementation of OnPropertyChanged. Remember that the INotifyPropertyChanged mechanism raises an event whenever a value changes on the class the implements the interface? Well, it doesn’t happen for free. It has to be coded. And if not coded correctly, the benefit of the pattern will be lost. A typical implementation that I use when developing XAML based applications is shown in Listing 6. The BaseEntity is the core functionality with the implementation of the IEntity interface (which contains the INotifyProertyChanged interface as well as the IsDirty property) and the OnPropertyChanged method, which set’s the IsDirtyFlag to true. What’s missing is the call to raise the PropertyChanged event, which I omitted for brevity.
Listing 6 – Base Entity and a Customer Entity
When the Name property of the Customer model gets changed, the OnPropertyChanged method in the base class gets called. This sets the IsDirty flag to true. We want to make sure that changing the value of the Name really does set the IsDirty flag correctly. NOTE:
There is a lot more to implementing the pattern here, such as error checking, handling rewinds, etc. If this was a post on the implementation of INotifyPropertyChanged, we’d be covering them. As it is, those details would just add a lot of noise to the message we are trying to convey. I cover those details and more in this blog post
To test this, we create a mock of the concrete Customer class. We are using the concrete class here because we want to make sure that the derived property IsDirty in the base class gets set. This is a little different than using mock objects to fill in the blanks for scaffolding (which is much more common).
NOTE: If you are using JustMock Lite
, you will need to make sure that you set the IsDirty property in the base entity class to virtual (as I did in Listing 6). If you are using the profiled version of JustMock (the commercial edition) that step is not necessary.
As you can see from the test in Listing 7, the syntax for arranging the setter is a little bit different. We use “ArrangeSet” instead of arrange, and the right hand of the lamba is an assignment statement instead of a method (or property) call.
Listing 7 – Testing the IsDirty setter
Mocking property getters and setters are typically an infrequent need. But still a need. When your code requires mocking properties, JustMock
provides a very clean mechanism for mocking both setters and getters, and allows you to cover even more of your code simply and cleanly. Instead of hiding the behavior of the scaffolding (in this case the entity), it is very apparent to the reader of the test what is going on.