AutoFixture AutoMoq adding items to an ObservableCollection does not raise CollectionChanged event - c#

I'm just starting out using AutoFixture and I'm enjoying the features just now. But I've just created an AutoMoqDataAttribute as Mark Seemann describes here.
But now I'm trying to mock an object that contains an ObservableCollection of items and in my Sut I am subscribing to the CollectionChanged event and handling when new items are added.
My Sut looks like:
public class Foo
{
public Foo(IBar barWithObservableCollection)
{
barWithObservableCollection.Items.CollectionChanged += this.OnItemsChanged;
}
public ObservableCollection<IFooThing> FooThings
{
get;
private set;
}
private void OnItemsChanged(object sender, NotifyCollectionChangedEventArgs notifyCollectionChangedEventArgs)
{
// Handle the new object and build a new IFooThing with it.
...
this.FooThings.Add(fooThing);
}
}
My IBar interface is simple and basically only contains the ObservableCollection:
public interface IBar
{
ObservableCollection<IBarThings> Items
{
get;
}
}
So in my original implementation of the test to make sure that new items were handled was with full mocking of the objects using Moq and tying everything together myself (I'll leave this out as it's unnecessary for my question). But as said I've attempted to move this to using AutoFixture and now my tests looks like:
[Theory, AutoMoqData]
public void TestNewIBarThingsAreCorrectlyHandled([Frozen]IBar bar, [Frozen]IBarThing barThing, Foo sut)
{
bar.Items.Add(barThing);
Assert.Equal(1, sut.FooThings.Count);
}
So I was expecting that the IBar.Items was auto setting up an ObservableCollection which it is and this was being subscribed to, which it also is. But when I do the call to bar.Items.Add the collection changed handler is not not called, although I can see that the Items count is incremented on the IBar object.
Is there something that I'm doing wrong? Have I got the wrong end of the stick and I will have to manually setup the collection as before, I'd rather not have to do this as I'm enjoying the cleaner syntax?
EDIT:
After the comment below I checked that the IBar object provided to the tests and to the Sut were the same, but it turns out that these are not the same object. I was under the impression that the [Frozen] attribute specified that each time that object was requested the same object reference would be returned?

Related

Ninject - bind a List of types

I am using Ninject. What I want to do is to map a List of type, And then inject it in a constructor of my class:
private readonly IList<IDispatchFilter> m_Filters;
public DispatchFilteringManager(IList<IDispatchFilter> filters)
{
m_Filters = filters;
}
I have tried this binding:
Bind<IList<IDispatchFilter>>()
.ToMethod(bindDecoyDispatchFilters)
.InSingletonScope();
private IList<IDispatchFilter> bindDecoyDispatchFilters(IContext context)
{
Bind<IDispatchFilter>().To<WindowsXpFilter>();
IList<IDispatchFilter> result = context.Kernel.GetAll<IDispatchFilter>().ToList();
return result;
}
But in my constructor I get an empty List.
I can't seen to find a solution for this simple task.
The reason why you are receiving no items in your constructor is unfortunately due to the way Ninject's Multi Injection works. Ninject's resolution of IList<T> seems to non-intuitively look for all (independently) registered <T> and inject them into your class taking IList<T>, instead of actually using the explicitly registered method for resolving IList<T>.
As a result, bindDecoyDispatchFilters (as bound by .ToMethod(bindDecoyDispatchFilters)) will never be called, as Ninject will instead resolve the IList<T> based on the registered types T. (This is easily tested - put a breakpoint, or Assert.Fail() inside the method - it isn't ever called).
So if
Bind<IDispatchFilter>().To<WindowsXpFilter>();
is the only IDispatchFilter which ever needs to be resolved in the IList, then you can drop the registration, and as per #Fabjan's, directly register Bind<IDispatchFilter>().To<WindowsXpFilter>();. The multi injection will resolve this as a single element in the IList<T> passed to your constructor.
You can then remove the IList<T> binding altogether:
Bind<IList<IDispatchFilter>>() ... remove
.ToMethod(bindDecoyDispatchFilters)
.InSingletonScope();
and also drop the bindDecoyDispatchFilters method entirely.
However, if the list of filters changes after bootstrapping, and you do need a dynamic factory method to return the available Filters to your constructors, then you may to resort to a hack like this.
Alternatively, if you don't have many classes dependent on the IList<> you can also explicitly register each class, which again takes precedence over the multi-injection, so the Bootstrapping code becomes:
kernel.Bind<ResolveMe>()
.ToSelf()
.WithConstructorArgument<IEnumerable<IDispatchFilter>>(bindDecoyDispatchFilters);
private IList<IDispatchFilter> bindDecoyDispatchFilters(IContext context)
{
// Contract.Assert(1 == 0); // .. .ensure the method is called during resolution!
context.Kernel.Bind<IDispatchFilter>().To<WindowsXpFilter>();
return context.Kernel.GetAll<IDispatchFilter>().ToList();
}
The classes I used to test were:
public interface IDispatchFilter {}
public class WindowsXpFilter : IDispatchFilter { }
public class ResolveMe
{
public IEnumerable<IDispatchFilter> Stuff { get; set; }
public ResolveMe(IEnumerable<IDispatchFilter> stuff) { Stuff = stuff; }
}
And some tests:
var y = kernel.Get<ResolveMe>();
Assert.IsTrue(y.Stuff.Any());
Change:
Bind<IList<IDispatchFilter>>()
.ToMethod(bindDecoyDispatchFilters)
.InSingletonScope();
private IList<IDispatchFilter> bindDecoyDispatchFilters(IContext context)
{
Bind<IDispatchFilter>().To<WindowsXpFilter>();
...
}
To:
Bind<IDispatchFilter>().To<WindowsXpFilter>();
Bind<IList<IDispatchFilter>>()
.ToMethod(bindDecoyDispatchFilters)
.InSingletonScope();
private IList<IDispatchFilter> bindDecoyDispatchFilters(IContext context)
{
...
}
Explanation:
A method that we use in .ToMethod binding for let's say T will be executed only when we call container.Get<T> and not before that.
When Ninject tries to resolve IList<IDispatchFilter>> in the bindDecoyDispatchFilters method it looks for all bindings for IDispatchFilter registered before that and finds none. Therefore the ctor parameter is resolved as an empty collection.

Pass object into method without adding argument to method?

I have a simple interface called IEvent and it just contains this one method:
void Execute();
I have several derived classes from this interface and one of them needs access to an object that the caller of the method owns. The object is used in this fashion:
using (MyObject object = new MyObject(this.MessageService)
{
foreach (IEvent myEvent in eventList)
{
myEvent.Execute(); // <--- I need to pass object without adding argument here if possible?
}
}
I would add the object as a field in the derived class that needs access to it, but by the time I get to this part of the code, the IEvent objects are already constructed and running on a background thread. Currently, the only way I can think of is to add a setter in the IEvent interface for this object, but then I am exposing a field that most derived classes won't care about and doesn't seem like a clean solution.
I would add it as an argument to Execute(), but the problem is that the object belongs to an assembly that the assembly that contains IEvent doesn't know about (and don't want it to know about) and again 99% of the events don't care about this object anyway. Is there a better way to accomplish what I am trying to do here?
"If a class that implements IEvent does not/can not implement all the methods specified by IEvent the same way as they are declared in IEvent, that class should not implement IEvent in the first place." - Sweeper
So there's probably something wrong with your design of the whole program. I think you better revise your design a little bit and change some relationships between the classes and interfaces.
If you don't want to do that, there is another (not recommended) way to solve this problem.
Suppose your method caller is of type MethodCaller. You just change the declaration of Execute in the interface to this:
void Execute(MethodCaller obj = null);
And all the classes that implement IEvent can ignore the parameter except the class you mentioned in your question.
I'm going to piggyback on Jon Skeet's amazing knowledge of C#, .NET, CLR, IL and everything that surrounds any of those topics. You can't get to the instance of the calling object and especially the local varaible in the calling method. You can get its type, you can get the calling method through StackTrace, for example (StackTrace.GetFrames()), but none of those are going to do you any good in this situation. What you're trying to accomplish would require some heavy dive into the debugging API. As far as walking the stack, here's a quick sample I created to try see if I can figure something out for you (I made assumptions in regards to how your program is structured... obviously it's not a one to one sample):
using System;
using System.Collections.Generic;
using System.Diagnostics;
namespace SampleApp
{
class Program
{
static void Main(string[] args)
{
var eventList = new List<IEvent> { new SomeClass() };
using (MyObject obj = new MyObject(new MessageService()))
{
foreach (IEvent myEvent in eventList)
{
myEvent.Execute();
}
}
}
}
public interface IEvent
{
void Execute();
}
public class SomeClass : IEvent
{
public void Execute()
{
var stackTrace = new StackTrace();
var stackFrames = stackTrace.GetFrames();
var callingMethod = stackFrames[1].GetMethod();
var callingType = callingMethod.DeclaringType;
}
}
public class MyObject : IDisposable
{
public MessageService Service { get; }
public MyObject(MessageService service)
{
Service = service;
}
public void Dispose()
{
Service.Stop();
}
}
public class MessageService
{
public void Start() { }
public void Stop() { }
}
}
I like your question, because it presents an interesting and an unusual situation, but I'm afraid that you won't be able to accomplish your task without going outside of conventional routines that C# has in its arsenal. You may be able to pull something off with unmanaged code, but that's a different topic altogether.
However, aside from it being an interesting question... look at what you're trying to do. You have MyObject, which obviously implements IDisposable and will call Dispose() at the end of that using statement, and you're trying to grab its reference from a different assembly. I don't think this is a good idea.
I suggest revisiting your design and make use of things such as an optional parameter. May not be the "perfect" solution for your situation, as you'll pass it to every Execute in that foreach loop, but it's better than jumping through a thousand fiery hoops of debug API's.

Unit testing methods in the Presenter, MVP

Im trying to test a method which composes a collection of controls. It calls two methods:
Copies the original collection.
Sorts the new collection.
Ideally id like to be able to pass in a collection and test to see thats it sorts it correctly. Id also like to verify that method 1) is called twice, see below attempt based on the following:
Example using RhinoMock
The following test is producing errors when i try to create an instance of MainPresenter. General jist of the errors are "Can not convert from Moq.Mock to "FrazerMann.CsvImporter.UserInterface.IMainForm. + a similar one for IFileDialog.
[Test]
public void ComposeCollectionOfControls_CallSequence_4Calls()
{
var main = new Mock<IMainForm>();
var dialog = new Mock<IFileDialog>();
var temp = new Mock<IMainPresenter>();
temp.Setup(s => s.PopulateLists<Control>(It.IsAny<TableLayoutPanel>(), It.IsAny<List<Control>>()));
var testObject = new MainPresenter(main.Object, dialog.Object);
testObject.ComposeCollectionOfControls(It.IsAny<object>(), It.IsAny<EventArgs>());
temp.Verify(v => v.PopulateLists<Control>(It.IsAny<TableLayoutPanel>(), It.IsAny<List<Control>>()), Times.Once());
}
I would like to test the ComposeCollectionOfControls to ensure PopulateList() is called twice.
public interface IMainPresenter
{
void PopulateLists<T>(TableLayoutPanel userInputs, List<T> container) where T : Control;
int SortList<T>(T control1, T control2) where T : Control;
}
public class MainPresenter:IMainPresenter
{
UserInputEntity inputs;
IFileDialog _dialog;
IMainForm _view;
public MainPresenter(IMainForm view, IFileDialog dialog)
{
_view = view;
_dialog = dialog;
view.ComposeCollectionOfControls += ComposeCollectionOfControls;
view.SelectCsvFilePath += SelectCsvFilePath;
view.SelectErrorLogFilePath += SelectErrorLogFilePath;
view.DataVerification += DataVerification;
}
public void ComposeCollectionOfControls(object sender, EventArgs e)
{
PopulateLists<TextBox>(_view.ColumnNameCtrls, _view.SortedColumnNameCtrls);
_view.SortedColumnNameCtrls.Sort(SortList<TextBox>);
PopulateLists<ComboBox>(_view.ColumnDataTypeCtrls, _view.SortedColumnDataTypeCtrls);
_view.SortedColumnDataTypeCtrls.Sort(SortList<ComboBox>);
}
}
Could someone please give me some pointers as to how this should be done?
The error you are seeing is because your are passing the mock class itself (which is of type Moq.Mock) rather than the mocked object that Moq creates for you.
Instead of:
var testObject = new MainPresenter(main, dialog);
you need:
var testObject = new MainPresenter(main.Object, dialog.Object);
As an aside, it is usually considered bad practice to explicitly verify things like the number of calls made on a particular method. This leads to a tight coupling between your tests and a particular implementation, and consequently brittle tests.
By testing how many times you call a method you will often find a test failing after you refactor some code when the end result of the code is still correct.
It is much better to test the final state of the objects involved, and make your tests ignorant of how that state was reached.

TDD can force the creation of "fake" dependencies

I'm using a boilerplate implementation of Model-View-Presenter in an ASP.NET WebForms application. My View has two events of consequence, one that signals that the user has filled out enough fields on the domain model to initiate a duplication check, and the other is a regular Save event. My pseudo code looks like this:
public class ItemNewPresenter : PresenterBase<IItemNewView>
{
public IItemService Service { get; private set; }
public IItemNewView View { get; private set; }
public ItemNewPresenter(IItemService service, IItemNewView view)
{
Service = service;
View = view;
View.OnSave += DoItemSave;
View.OnItemIsDuplicateCheck+= DoItemIsDuplicateCheck;
}
private void DoItemIsDuplicateCheck(object sender, CheckItemDuplicateEventArgs e)
{
CheckForItemDuplication(e.Item);
}
private void CheckForItemDuplication(Item item){
if (Service.IsDuplicateItem(item))
{
View.RedirectWithNotification(BuildItemUrl(item), "This item already exists");
}
}
private void DoItemSave(object sender, SaveItemEventArgs e)
{
DoItemIsDuplicateCheck(this, e.ToItemDuplicateEventArgs());
Service.Save(e.Item);
}
}
Here's my test for ensuring that my presenter behaves properly when OnItemIsDuplicateCheck is raised from the view:
[Test]
public void presenter_checking_for_existing_item_should_call_redirect_if_found()
{
var service = new Mock<IItemService>();
var view = new Mock<IItemNewView>();
var presenter = new ItemNewPresenter (service.Object, view.Object);
var onCheckExistingHandler = view.CreateEventHandler <CheckItemDuplicateEventArgs>();
view.Object.OnExistingDenominatorCheck += onCheckExistingHandler;
var eventArgs = new CheckItemDuplicateEventArgs();
service.Setup(s => s.IsDuplicate(It.Is<CheckItemDuplicateEventArgs>(c => c.Equals(eventArgs)))).Returns(true);
onCheckExistingHandler.Raise(eventArgs);
view.Verify(v => v.RedirectWithNotification(It.IsAny<String>(), It.IsAny<string>()), Times.Once());
service.Verify();
}
For consistency, I would like to have the same duplicate check fired when the View raises the OnSave event. My question is around how I am supposed to write my test when one of the methods I want to verify (CheckForItemDuplication) is declared on the class under test. The alternative to verifying the method invocation on the SUT (bad) would be to write my save test with lots of duplicated code (setup and assertion of all my mocks would be copied from the above test) and it also makes the unit test less focused.
[Test]
public void presenter_saving_item_should_check_for_dupe_and_save_if_not_one() {
//duplicate mocks/setups/asserts from duplicate check fixture
//additional mocks/setups/asserts to test save logic
}
I think TDD would suggest pulling this private method out into a separate class that collaborates with my Presenter and would be injected via DI. But adding another dependency to my Presenter for functionality that doesn't seem worthy of being a freestanding abstraction *and*represents an internal implementation detail of my Presenter seems...well...crazy. Am I way off base here? There must be some design pattern or refactoring I can apply that would avoid the need to turn a private method into a dependency.
What I have done sometimes, when confronted with this dilemma, is to extract the function, make an internal constructor with the object as argument, AND a public constructor without. The public ctor is forwarded to the internal with a new object such as:
public class ClassThatUseInjection
{
private readonly SomeClass _injectedClass;
public ClassThatUseInjection(): this(new SomeClass()) {}
internal ClassThatUseInjection(SomeClass injectedClass)
{
_injectedClass = injectedClass;
}
}
public class SomeClass
{
public object SomeProperty { get; set; }
}
Thus, you can use the empty constructor from outside, and the other constructor for when you want to inject a stubbed argument for testpurposes. As long as the empty constructor only forwards the call without any logic of its own, you can still test it, like it has only one constructor.
I would go with testing the class as is by adding the duplicate setup code. Once that test is passing and you are confident all test cases are covered you can then refactor your test code to remove duplication.
You can move the dependencies (service and view) to private fields, then add a method to create the SUT:
private Mock<IItemService> _service;
private Mock<IItemNewView> _view;
private PresenterBase<IItemNewView> CreateSUT()
{
_service = new Mock<IItemService>();
_view = new Mock<IItemNewView>();
return new ItemNewPresenter (service.Object, view.Object);
}
(I think most people would prefer to initialize the Mock objects in the Setup method.)
Call the CreateSUT from your tests and now there is a little less duplication. Then you may want to add private method(s) for creating the event handler / raising the event as long as it is something that is being done the same or similar in more than one tests case.
Having this CreateSUT method cuts down on the amount of test code that is calling your constructor making it easier in the future if you were to add / remove / change dependencies. If you treat your test code like any other code and use the DRY principle when you see duplication it can result in more explicit, easier to read, maintainable test code. Dealing with very similar setup and test context is a common issue with unit testing and should not always change how the class being tested is/was designed.
I'll be interested if there are better answers, as I encounter this all the time.
The alternative to verifying the method invocation on the SUT (bad) would be to write my save test with lots of duplicated code (setup and assertion of all my mocks would be copied from the above test) and it also makes the unit test less focused.
I'm not sure why you feel it makes the test less focused, but in your shoes I would do exactly what it sounds like you don't want to do--have duplicated setup code to test isolated cases for the SUT. You are testing the external behavior of the SUT with the test you supplied, which seems exactly right to me.
I am personally not a fan of exposing more than is necessary from a class and/or making behavior that should be the responsibility of the SUT into a dependency just to facilitate testing. The "natural boundry" of the class's responsibility should not be violated just because you want to test it.
It is easier to unit-test the calculation of the url than to unit-test that redirection has occured.
If i understood you corretly you want to test that the mvp-s CheckForItemDuplication() redirects to a certain url by raising
the view-mock-s OnItemIsDuplicateCheck event.
private void CheckForItemDuplication(Item item)
{
if (Service.IsDuplicateItem(item))
{
View.RedirectWithNotification(BuildItemUrl(item),
"This item already exists");
}
}
In my opinion you are doing to much.
What if you rewrite your code as
internal protected GetErrorUrlForItem(Item item)
{
if (Service.IsDuplicateItem(item))
{
return BuildItemUrl(item,
"This item already exists");
}
return null;
}
private void CheckForItemDuplication(Item item)
{
var result = GetErrorUrlForItem(item);
if (result != null)
{
View.RedirectWithNotification(result);
}
}
In the unittest just test the internal method GetErrorUrlForItem(). You have to use the InternalsVisibleTo attribute to allow accessing the internal method.

Making mocks trigger PropertyChanged when changed

I am using RhinoMocks, and I have a Mock which has a property I need to behave as a real property - updating its value when set, and also trigger PropertyChanged when the property is changed.
The interface of the mocked object is in essence this:
public interface IFoo
{
event PropertyChangedEventHandler PropertyChanged;
int Bar { get; set; }
}
When creating the mock I set PropertyBehavior - which makes it actually update its faked value:
var mocks = new MockRepository();
var fakeFoo = mocks.DynamicMock<IFoo>();
SetupResult.For(fakeFoo.Bar).PropertyBehavior();
But when I update the value PropertyChanged isn't triggered. Now, the interface doesn't implement the INotifyPropertyChanged interface as it is an interface.. How can I make PropertyChanged triggered?
The role of listener and mutator may sometimes be combined in the same class (e.g. in an adapter), but both roles should not be tested together.
In one test, you merely verify that your listening class reacts to the PropertyChanged event as designed. You don't care about what caused the property to change in that test:
[Test]
public void Updates_Caption_when_Bar_PropertyChanged()
{
var foo = MockRepository.GenerateStub<IFoo>();
foo.Bar = "sometestvalue1";
var underTest = new UnderTest(foo);
// change property and raise PropertyChanged event on mock object
foo.Bar = "sometestvalue2";
foo.Raise(x=>x.PropertyChanged+=null,
foo,
new PropertyChangedEventArgs("Bar"));
// assert that the class under test reacted as designed
Assert.AreEqual("sometestvalue2", underTest.Caption);
// or if the the expected state change is hard to verify,
// you might just verify that the property was at least read
foo.AssertWasCalled(x => { var y = foo.Bar; } );
}
In another test, you verify that your class plays its mutator role as designed:
[Test]
public void Reset_clears_Foo_Bar()
{
var foo = MockRepository.GenerateStub<IFoo>();
foo.Bar = "some string which is not null";
var underTest = new UnderTest(foo);
underTest.Reset();
// assert that the class under test updated the Bar property as designed
Assert.IsNull(foo.Bar);
}
This way, it is never necessary to put real logic into your mock objects like you are trying to do. This does require that you design your classes for testability; it is hard to add such tests to existing classes. Hence the practice of test driven development.
I'm not an expert in RhinoMocks, but I wouldn't try to do that with any of the mock-framework I know (TypeMock I know the most).
I would implement something like:
public class FooFake: IFoo
{
public event PropertyChangedEventHandler PropertyChanged;
int _bar;
public int Bar
{
set
{
if( PropertyChanged != null )
PropertyChanged();
_bar = value;
}
get
{
return _bar;
}
}
}
Sorry. Nothing really clever. But I like this kind of stub as they can be resused.

Categories