Set Expectation that any overload of a method is called

621 views
Skip to first unread message

Sam

unread,
Nov 12, 2008, 12:18:49 PM11/12/08
to Moq Discussions
How's this for an idea for creating more robust tests?

I've just had a case where I'm mocking the ILog interface in Log4Net.
Basically I want to ensure that my class logs a Warning in a
particular case. Problem is, ILog has multiple overloads of the the
WarnFormat, and I have to set the exectation on the one that my class
is using; if, for example, my message needs another parameter, I'll
need to remember to change the expectation to point to a different
overload of WarnFormat. Not very robust!

Would it be possible to allow verifiable Expectations to be set for
any overload of a method? Obviously you couldn't set expectations for
individual parameters: it would just allow you to assert that a method
call had been made.

Suggested syntax:

Mock<ILog> mockLog = new Mock<ILog>();
mockLog.Expect(m => m.WarnFormat(It.IsAny<string>(), It.IsAny<object>
())).AnyOverload().Verifiable();

Daniel Cazzulino

unread,
Nov 12, 2008, 3:16:55 PM11/12/08
to moq...@googlegroups.com
Ahh... this just gave me a cool idea!

The following compiles just fine (not with current moq, but plain C#):

            mock.Expect<int, string, bool>(m => m.Do);

So you could do away with the It.IsAny<T> that way !!! :D:D:D

Adding an AnyOverload() might be interesting. 
What do others think?

Brian J. Cardiff

unread,
Nov 12, 2008, 3:39:27 PM11/12/08
to moq...@googlegroups.com
I like it.

Overloads will be tricky.
Some overload appends arguments, others prepend.
Overload detection should be argument-name-based match, because type-based match won't work, think of String.format.

Brian J. Cardiff
bcardiff(?)gmail.com
.

Brian J. Cardiff

unread,
Nov 12, 2008, 3:41:53 PM11/12/08
to moq...@googlegroups.com
It's even better than defining overloads like extension methods and leave the more generic as the actual method.
Which is the other alternative for supporting call to 'overloads'


Brian J. Cardiff
bcardiff(?)gmail.com
.


Sam

unread,
Nov 13, 2008, 5:25:06 AM11/13/08
to Moq Discussions
Brian,
I'm not quite sure what you mean about overloads being tricky
because of appending or prepending arguments.

In my example I intended that the particular WarnFormat call should be
an example of one possible overload of the WarnFormat method, and Moq
should then expect a call to any overload, not just to ones that
extended the parameter list of the example I specified. I agree that
the syntax I suggested doesn't make this clear.

In your second post you suggested that the interface should just
define the most generic form, and then extension methods should
provide the more compact overloads. I agree that this is a good way to
define interfaces, and certainly would make my situation easier
because there's then only one interface call to expect. Trouble is, I
don't control the ILog interface - it's part of the Log4Net project.

Sam

On Nov 12, 8:41 pm, "Brian J. Cardiff" <bcard...@gmail.com> wrote:
> It's even better than defining overloads like extension methods and leave
> the more generic as the actual method.
> Which is the other alternative for supporting call to 'overloads'
>
> Brian J. Cardiff
> bcardiff(?)gmail.com
> .
>
> On Wed, Nov 12, 2008 at 6:39 PM, Brian J. Cardiff <bcard...@gmail.com>wrote:
>
> > I like it.
>
> > Overloads will be tricky.
> > Some overload appends arguments, others prepend.
> > Overload detection should be argument-name-based match, because type-based
> > match won't work, think of String.format.
>
> > Brian J. Cardiff
> > bcardiff(?)gmail.com
> > .
>
> > On Wed, Nov 12, 2008 at 6:16 PM, Daniel Cazzulino <dan...@cazzulino.com>wrote:
>
> >> Ahh... this just gave me a cool idea!
> >> The following compiles just fine (not with current moq, but plain C#):
>
> >>             mock.Expect<int, string, bool>(m => m.Do);
>
> >> So you could do away with the It.IsAny<T> that way !!! :D:D:D
>
> >> Adding an AnyOverload() might be interesting.
> >> What do others think?
>

Sam

unread,
Nov 13, 2008, 5:26:05 AM11/13/08
to Moq Discussions
Daniel,
I think the new Expect syntax would be a valuable addition to Moq.

Sam

On Nov 12, 8:16 pm, "Daniel Cazzulino" <dan...@cazzulino.com> wrote:
> Ahh... this just gave me a cool idea!
> The following compiles just fine (not with current moq, but plain C#):
>
>             mock.Expect<int, string, bool>(m => m.Do);
>
> So you could do away with the It.IsAny<T> that way !!! :D:D:D
>
> Adding an AnyOverload() might be interesting.
> What do others think?
>

Daniel Cazzulino

unread,
Nov 13, 2008, 6:59:59 AM11/13/08
to moq...@googlegroups.com, moq...@googlegroups.com
Overload resolution in .net is based on argument position and type, so if you specify those in the Expect, I don't see why they will be tricky

Sent from my iPod

Daniel Cazzulino

unread,
Nov 13, 2008, 9:40:29 AM11/13/08
to moq...@googlegroups.com
Ok, we sorted it out :)

AnyOverload() would only have to be valid if you use either It.IsAny<> for all specified arguments, or if you use the new syntax that specifies only the method "name"

makes sense?

Brian J. Cardiff

unread,
Nov 13, 2008, 9:50:42 AM11/13/08
to moq...@googlegroups.com
I was having in mind scenarios where I would want to constraint allowed values, for example, ensure that the warning message explains something of the invalid status of the model.

Then, if some arguments can be restricted, an overload shouldn't be just a method with same name, but a method that can be extended with "optional" parameters. In this thought I express an "parameter-name-based". Because an overload could be Bar(int, int) and Bar(string, string), If an expectation is set on the former, how a call to the later would be treated?

Although Kzu and I have talked and agree that the most common scenario would to not restrict arguments in overloads.


Brian J. Cardiff
bcardiff(?)gmail.com
.


On Thu, Nov 13, 2008 at 9:59 AM, Daniel Cazzulino <dan...@cazzulino.com> wrote:

Sam

unread,
Nov 14, 2008, 9:31:51 AM11/14/08
to Moq Discussions
Daniel,
That sounds good to me. When can I start using it ;-)

Sam

On Nov 13, 2:50 pm, "Brian J. Cardiff" <bcard...@gmail.com> wrote:
> I was having in mind scenarios where I would want to constraint allowed
> values, for example, ensure that the warning message explains something of
> the invalid status of the model.
>
> Then, if some arguments can be restricted, an overload shouldn't be just a
> method with same name, but a method that can be extended with "optional"
> parameters. In this thought I express an "parameter-name-based". Because an
> overload could be Bar(int, int) and Bar(string, string), If an expectation
> is set on the former, how a call to the later would be treated?
>
> Although Kzu and I have talked and agree that the most common scenario would
> to not restrict arguments in overloads.
>
> Brian J. Cardiff
> bcardiff(?)gmail.com
> .
>
> On Thu, Nov 13, 2008 at 9:59 AM, Daniel Cazzulino <dan...@cazzulino.com>wrote:
>
>
>
> > Overload resolution in .net is based on argument position and type, so if
> > you specify those in the Expect, I don't see why they will be tricky
>
> > Sent from my iPod
>
> > On Nov 12, 2008, at 6:39 PM, "Brian J. Cardiff" <bcard...@gmail.com>
> > wrote:
>
> > I like it.
>
> > Overloads will be tricky.
> > Some overload appends arguments, others prepend.
> > Overload detection should be argument-name-based match, because type-based
> > match won't work, think of String.format.
>
> > Brian J. Cardiff
> > bcardiff(?)gmail.com
> > .
>
> > On Wed, Nov 12, 2008 at 6:16 PM, Daniel Cazzulino < <dan...@cazzulino.com>
> > dan...@cazzulino.com> wrote:
>
> >> Ahh... this just gave me a cool idea!
> >> The following compiles just fine (not with current moq, but plain C#):
>
> >>             mock.Expect<int, string, bool>(m => m.Do);
>
> >> So you could do away with the It.IsAny<T> that way !!! :D:D:D
>
> >> Adding an AnyOverload() might be interesting.
> >> What do others think?
>
> >> On Wed, Nov 12, 2008 at 3:18 PM, Sam < <samuel.j...@gmail.com>
> >> samuel.j...@gmail.com> wrote:
>
> >>> How's this for an idea for creating more robust tests?
>
> >>> I've just had a case where I'm mocking the ILog interface in Log4Net.
> >>> Basically I want to ensure that my class logs a Warning in a
> >>> particular case. Problem is, ILog has multiple overloads of the the
> >>> WarnFormat, and I have to set the exectation on the one that my class
> >>> is using; if, for example, my message needs another parameter, I'll
> >>> need to remember to change the expectation to point to a different
> >>> overload of WarnFormat. Not very robust!
>
> >>> Would it be possible to allow verifiable Expectations to be set for
> >>> any overload of a method? Obviously you couldn't set expectations for
> >>> individual parameters: it would just allow you to assert that a method
> >>> call had been made.
>
> >>> Suggested syntax:
>
> >>>  Mock<ILog> mockLog = new Mock<ILog>();
> >>> mockLog.Expect(m => m.WarnFormat(It.IsAny<string>(), It.IsAny<object>
> >>> ())).AnyOverload().Verifiable();- Hide quoted text -
>
> - Show quoted text -
Reply all
Reply to author
Forward
0 new messages