Skip to content

Commit

Permalink
Decouple verification methods from MethodCall
Browse files Browse the repository at this point in the history
This realises one of the two benefits claimed in an earlier commit
message: verification methods are modified to use `InvocationShape`
instead of newing up transient `MethodCall` instances (which represent
setups and are much heavier-weight).
  • Loading branch information
stakx committed Aug 24, 2018
1 parent a4beda3 commit 5a1f061
Show file tree
Hide file tree
Showing 3 changed files with 20 additions and 27 deletions.
34 changes: 14 additions & 20 deletions src/Moq/Mock.cs
Original file line number Diff line number Diff line change
Expand Up @@ -313,8 +313,8 @@ internal static void Verify<T>(
var (obj, method, args) = expression.GetCallInfo(mock);
ThrowIfVerifyExpressionInvolvesUnsupportedMember(expression, method);

var expected = new MethodCall(mock, null, expression, method, args) { FailMessage = failMessage };
VerifyCalls(GetTargetMock(obj, mock), expected, expression, times);
var expectation = new InvocationShape(method, args);
VerifyCalls(GetTargetMock(obj, mock), expectation, expression, times, failMessage);
}

internal static void Verify<T, TResult>(
Expand All @@ -335,11 +335,8 @@ internal static void Verify<T, TResult>(
var (obj, method, args) = expression.GetCallInfo(mock);
ThrowIfVerifyExpressionInvolvesUnsupportedMember(expression, method);

var expected = new MethodCallReturn<T, TResult>(mock, null, expression, method, args)
{
FailMessage = failMessage
};
VerifyCalls(GetTargetMock(obj, mock), expected, expression, times);
var expectation = new InvocationShape(method, args);
VerifyCalls(GetTargetMock(obj, mock), expectation, expression, times, failMessage);
}
}

Expand All @@ -353,11 +350,8 @@ internal static void VerifyGet<T, TProperty>(
var method = expression.ToPropertyInfo().GetGetMethod(true);
ThrowIfVerifyExpressionInvolvesUnsupportedMember(expression, method);

var expected = new MethodCallReturn<T, TProperty>(mock, null, expression, method, new Expression[0])
{
FailMessage = failMessage
};
VerifyCalls(GetTargetMock(((MemberExpression)expression.Body).Expression, mock), expected, expression, times);
var expectation = new InvocationShape(method, new IMatcher[0]);
VerifyCalls(GetTargetMock(((MemberExpression)expression.Body).Expression, mock), expectation, expression, times, failMessage);
}

internal static void VerifySet<T>(
Expand All @@ -369,14 +363,14 @@ internal static void VerifySet<T>(
{
Mock targetMock = null;
LambdaExpression expression = null;
var expected = SetupSetImpl<T, MethodCall<T>>(mock, setterExpression, (m, expr, method, value) =>
var expectation = SetupSetImpl(mock, setterExpression, (m, expr, method, value) =>
{
targetMock = m;
expression = expr;
return new MethodCall<T>(m, null, expr, method, value) { FailMessage = failMessage };
return new InvocationShape(method, value);
});

VerifyCalls(targetMock, expected, expression, times);
VerifyCalls(targetMock, expectation, expression, times, failMessage);
}

internal static void VerifyNoOtherCalls(Mock mock)
Expand Down Expand Up @@ -424,17 +418,18 @@ internal static void VerifyNoOtherCalls(Mock mock)

private static void VerifyCalls(
Mock targetMock,
MethodCall expected,
InvocationShape expectation,
LambdaExpression expression,
Times times)
Times times,
string failMessage)
{
var allInvocations = targetMock.MutableInvocations.ToArray();
var matchingInvocations = allInvocations.Where(expected.Matches).ToArray();
var matchingInvocations = allInvocations.Where(expectation.IsMatch).ToArray();
var matchingInvocationCount = matchingInvocations.Length;
if (!times.Verify(matchingInvocationCount))
{
var setups = targetMock.Setups.ToArrayLive(oc => AreSameMethod(oc.SetupExpression, expression));
throw MockException.NoMatchingCalls(expected, setups, allInvocations, expression, times, matchingInvocationCount);
throw MockException.NoMatchingCalls(failMessage, setups, allInvocations, expression, times, matchingInvocationCount);
}
else
{
Expand Down Expand Up @@ -617,7 +612,6 @@ private static TCall SetupSetImpl<T, TCall>(
Action<T> setterExpression,
Func<Mock, LambdaExpression, MethodInfo, Expression[], TCall> callFactory)
where T : class
where TCall : MethodCall
{
using (var context = new FluentMockContext())
{
Expand Down
4 changes: 2 additions & 2 deletions src/Moq/MockException.cs
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ internal static MockException MoreThanNCalls(MethodCall setup, int maxInvocation
/// Returns the exception to be thrown when <see cref="Mock.Verify"/> finds no invocations (or the wrong number of invocations) that match the specified expectation.
/// </summary>
internal static MockException NoMatchingCalls(
MethodCall expected,
string failMessage,
IEnumerable<MethodCall> setups,
IEnumerable<Invocation> invocations,
LambdaExpression expression,
Expand All @@ -112,7 +112,7 @@ internal static MockException NoMatchingCalls(
{
return new MockException(
MockExceptionReason.NoMatchingCalls,
times.GetExceptionMessage(expected.FailMessage, expression.PartialMatcherAwareEval().ToStringFixed(), callCount) +
times.GetExceptionMessage(failMessage, expression.PartialMatcherAwareEval().ToStringFixed(), callCount) +
Environment.NewLine + FormatSetupsInfo() +
Environment.NewLine + FormatInvocations());

Expand Down
9 changes: 4 additions & 5 deletions src/Moq/Obsolete/Mock.Legacy.cs
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@
using System;
using System.Linq.Expressions;

using Moq.Matchers;

namespace Moq
{
// Keeps legacy implementations.
Expand All @@ -57,11 +59,8 @@ internal static void VerifySet<T, TProperty>(
var method = expression.ToPropertyInfo().SetMethod;
ThrowIfVerifyExpressionInvolvesUnsupportedMember(expression, method);

var expected = new SetterMethodCall<T, TProperty>(mock, expression, method)
{
FailMessage = failMessage
};
VerifyCalls(GetTargetMock(((MemberExpression)expression.Body).Expression, mock), expected, expression, times);
var expectation = new InvocationShape(method, new IMatcher[] { AnyMatcher.Instance });
VerifyCalls(GetTargetMock(((MemberExpression)expression.Body).Expression, mock), expectation, expression, times, failMessage);
}
}
}

0 comments on commit 5a1f061

Please sign in to comment.