Being fairly new to unit testing, I find myself discovering all kinds of interesting challenges when trying to test my data access layer (DAL). I had decided early on in one of my projects (with the tutelage of my supervisor and mentor) to take on the task of writing my DAL from scratch.
Disclaimer: I realize that data access is a problem that has already been solved (many times over), this was more of a learning exercise for me.
Part of my DAL deals with the IDbCommand.CreateParameter() method. I ran into a problem where I wanted each subsequent call of CreateParameter() to return a different mock IDbDataParameter. After some brief searching, I ran into a thread on Moq Discussions from someone with the same problem, and a very elegant solution.
var parameters = new Queue<IDbDataParameter>(new[] { mockFirstParam.Object, mockSecondParam.Object });
mockCommand.Expect(c => c.CreateParameter()).Returns(() => pq.Dequeue());
First we set up a generic Queue of IDbDataParameters, initialized with an array of mock IDbDataParameter objects that have already been created.
Then we set the behavior of our mock IDbCommand’s CreateParameter() method to the queue's Dequeue() method so that each subsequent call will return the next mock in the queue.
We use TypeMock Isolator in our shop, so here's the same code using TypeMock Isolator's AAA syntax:
var parameters = new Queue<IDbDataParameter>(new[] { mockFirstParam, mockSecondParam });
Isolate.WhenCalled(() => command.CreateParameter()).DoInstead(param => parameters.Dequeue());
This code behaves the same as its Moq counterpart, the only difference is how we use the API.
Hope someone else finds this useful. Thanks to the original author!