I want to do mock extension method, but it does not work. How can this be done?
public static class RandomExtensions
{
public static IEnumerable<int> NextInt32s(this System.Random random, int neededValuesNumber, int minInclusive, int maxExclusive)
{
// ...
}
}
[Fact]
public void Select()
{
var randomizer = Substitute.For<DefaultRandom>();
randomizer.NextInt32s(3, 1, 10).Returns(new int[] { 1, 2, 3 });
}
NSubstitute can not mock extension methods as per Sriram's comment, but you can still pass a mocked argument to an extension method. In this case, the Random class has virtual methods, so we can mock that directly with NSubstitute and other DynamicProxy-based mocking tools. (For NSubstitute in particular we need to be very careful mocking classes.
With NSubstitute the concept is similar but with one noticeable change. There is no wrapper for the mock, we directly manipulate an instance of the interface we want to substitute.
AFAIK you can't mock a extension method with free mocking frameworks. Because extension methods are just static methods, and you can't mock a static method with free mocking frameworks. TypeMock does this I think (but that's beyond the question).
You can create a non-static method on a class that implements an interface, mock the method on the interface, and then create a extension method that acts as a wrapper around either the original method or the mocked method. Allow a class to call an extension method where we can mock out the implementation of what happens in that extension method
NSubstitute can not mock extension methods as per Sriram's comment, but you can still pass a mocked argument to an extension method.
In this case, the Random
class has virtual methods, so we can mock that directly with NSubstitute and other DynamicProxy-based mocking tools. (For NSubstitute in particular we need to be very careful mocking classes. Please read the warning in the documentation.)
public static class RandomExtensions {
public static IEnumerable<int> NextInt32s(this System.Random random, int neededValuesNumber, int minInclusive, int maxExclusive) { /* ... */ }
}
public class RandomExtensionsTests {
[Test]
public void Select()
{
const int min = 0, max = 10;
var randomizer = Substitute.For<Random>();
randomizer.Next(min, max).Returns(1, 2, 3);
var result = randomizer.NextInt32s(3, 0, 10).ToArray();
Assert.AreEqual(new[] {1, 2, 3}, result);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With