Ich versuche, ein Lambda mit einer Funktion für mehrere Parameter zu verwenden, aber Moq löst diese Ausnahme zur Laufzeit aus, wenn ich versuche, die Zeile mock.Object.Convert(value, null, null, null);
aufzurufen.
System.Reflection.TargetParameterCountException: Nicht übereinstimmende Parameteranzahl
Der Code lautet:
var mock = new Mock<IValueConverter>();
mock.Setup(conv => conv.Convert(It.IsAny<Object>(), It.IsAny<Type>(),
It.IsAny<Object>(), It.IsAny<CultureInfo>())).Returns((Int32 num) => num + 5);
var value = 5;
var expected = 10;
var actual = mock.Object.Convert(value, null, null, null);
Was ist der richtige Weg, um es zu implementieren?
Es ist Ihre Returns
-Klausel. Sie haben eine 4-Parameter-Methode, die Sie einrichten, aber Sie verwenden nur ein 1-Parameter-Lambda. Ich habe Folgendes ohne Probleme ausgeführt:
[TestMethod]
public void IValueConverter()
{
var myStub = new Mock<IValueConverter>();
myStub.Setup(conv => conv.Convert(It.IsAny<object>(), It.IsAny<Type>(), It.IsAny<object>(), It.IsAny<CultureInfo>())).
Returns((object one, Type two, object three, CultureInfo four) => (int)one + 5);
var value = 5;
var expected = 10;
var actual = myStub.Object.Convert(value, null, null, null);
Assert.AreEqual<int>(expected, (int) actual);
}
Keine Ausnahmen, Test bestanden.
Keine Antwort für OP, aber vielleicht für zukünftige Googler:
Ich hatte ein Callback
, das nicht mit der Signatur der einzurichtenden Methode übereinstimmte
Mock
.Setup(r => r.GetNextCustomerNumber(It.IsAny<int>()))
.Returns(AccountCounter++)
.Callback<string, int>(badStringParam, leadingDigit =>
{
// Doing stuff here, note that the 'GetNextCustomerNumber' signature is a single int
// but the callback unreasonably expects an additional string parameter.
});
Dies war das Ergebnis einiger Umgestaltungen und das Umgestaltungswerkzeug konnte natürlich nicht erkennen, dass die Signatur Callback
falsch war
In meinem Fall dachte ich, dass der Typ in Returns<>
Der Ausgabetyp ist, aber tatsächlich der/die Eingabetyp (en).
Also, wenn Sie eine Methode haben
public virtual string Foo(int a, int b) { ... }
Die korrekte Klausel ist .Returns<int, int>(...)
, NOT .Returns<string>(...)
, was ich anfangs gedacht habe.
Mein Fehler war, dass ich eine Funktion mit dem gleichen Eingabe- und Rückgabetyp getestet habe - zum Beispiel public virtual string Foo(string a)
.
Vielleicht liegt es daran, dass Sie null
übergeben, aber It.IsAny<Object>()
erwartet object
mit Ausnahme von null
? Was passiert, wenn Sie Folgendes tun:
var actual = mock.Object.Convert(value, new object(), typeof(object), CultureInfo.CurrentCulture);
Dies ist nur ein Stich in die Dunkelheit von mir, ich kenne Rhino.Mocks besser.
Meine 2. Vermutung:
Nachdem Sie sich das Moq.chm angesehen haben, das mit dem Download geliefert wird,
Sie verwenden die Setup(Expression<Action<T>>)
-Methode, die "ein Setup für den verspotteten Typ für einen Aufruf einer void
-Methode angibt."
Sie möchten die Methode Setup<TResult>(Expression<Func<T,TResult>>)
, die "ein Setup für den verspotteten Typ für einen Aufruf einer Wertrückgabemethode angibt".
Sie könnten also versuchen:
mock.Setup<Int32>(
conv => {
conv.Convert(
It.IsAny<Object>(),
It.IsAny<Type>(),
It.IsAny<Object>(),
It.IsAny<CultureInfo>());
return num + 5;
});