How do you create a Moq mock for a Func - c#

I have the following Func method which i need to mock off
Func<Owned<ISomeInterface>> someMethod { get; set; }
but cant figure out how to mock it off using 'Moq' framework.
I have read a similar post on SO but still cant seem to mock it off, it always comes back with
Expression is not a method invocation: x => Invoke(x.someMethod )
or
A matching constructor for the given arguments was not found on the
mocked type. ----> System.MissingMethodException : Constructor on
type 'Owned`1Proxy40a9bf91815d4658ad2453298c903652' not found.

The Funct is defined as a property so you should use SetupSet within Moq
public interface IPersona
{
string nome { get; set; }
string cognome { get; set; }
Func<Owned<ISomeInterface>> somemethod { get; set; }
}
. In your test :
You create a mock for the Func:
Func<Owned<ISomeInterface>> somemethodMock = () => new Mock<Owned<ISomeInterface>>().Object;
THen you setup the mock for the Class containing the Func as a property and you setup the expectation on the Set method :
var obj = new Mock<IMyInterface>();
obj.SetupSet(x => x.somemethod = somemethodMock).Verifiable();
You create the container object for the mock:
//We pass the mocked object to the constructor of the container class
var container = new Container(obj.Object);
container.AnotherMethod(somemethodMock);
obj.VerifyAll();
Here is the definition of Another method of the Container class, if get the func as an input parameter and set it to the property of the contained object
enter public class Container
{
private IPersona _persona;
public Container(IPersona persona)
{
_persona = persona;
}
public void AnotherMethod(Func<MyClass<IMyInterface>> myFunc)
{
_persona.somemethod = myFunc;
}
}

Related

Mocking a concrete class with a virtual method

I want to test a class that depends on another class with the virtual method.
class DepClass
{
public virtual string Get() => "";
}
class HostClass
{
private _c;
public Host(DepClass c){ _c = c; }
public string Magic() => _c.Get();
}
Now I want to test the HostClass with Autofixture + NSubstitute.
My expectation:
Fixture.Freeze<DepClass>().Get().ReturnsForAnyArg("123");
var sut = Fixture.Create<HostClass>();
var res = sut.Magic(); //should be 123
As a fact, when I do Freeze().Get().Returns() the real Get method is being called.
How to customize Autofixture to mock all virtual methods?
Would be great not to discuss interface vs virtual methods, etc
Update
This does not work:
Fixture.Freeze<DepClass>().Get().ReturnsForAnyArgs("123");
At the same time, this works:
Substitute.For<DepClass>().Get().ReturnsForAnyArgs("123");
In addition to the answer
Another approach that might be not fit your needs: in my case, I expect that only direct dependencies can have virtual methods. all dependencies of the lower level will be mocked.
As result, I decided to go in a bit more specific way. The code below is an example, so you might be want to modify it before using it in your solution.
abstract class UnitTestBase<T>
{
protected IFixture Fixture { get; private set; }
protected IList<Type> ProxyTypes {get; private set;}
protected CreateSut(): T => Fixt.Create<T>();
[SetUp]
protected virtual Setup()
{
ProxyTypes = new List<Type>();
Fixture = new Fixture().Customize(new CompositeCustomization(
new AutoNSubstituteCustomization {
ConfigureMembers = true,
GenerateDelegates = true
})
);
SetupTypesToProxy();
Fixture.Customizations.Add(new SubstituteRelay(new ProxyExactTypesSpecification(ProxyTypes)));
}
protected virtual void SetupTypesToProxy()
=> typeof(T)
.GetConstructors(BindingFlags.Public | BindingFlags.Instance)
.SelectMany(ctorInfo => ctorInfo
.GetParameters()
.Select(paramInfo => paramInfo.ParameterType)
.Where(ShouldProxy))
.ForEach(t => ProxyTypes.Add(t));
private static bool ShouldProxy(Type type)
=> !type.GetTypeInfo().IsInterface && !type.GetTypeInfo().IsAbstract;
}
internal class ProxyExactTypesSpecification: IRequestSpecification
{
public ProxyExactTypesSpecification(
IEnumerable<Type> types
)
{
_proxyTypes = types ?? Type.EmptyTypes;
}
public bool IsSatisfiedBy(
object request
)
{
Argument.NotNull(request, nameof(request));
if (request is Type type)
return _proxyTypes.Contains(type);
return false;
}
private readonly IEnumerable<Type> _proxyTypes;
}
Because DepClass is neither an interface nor an abstract type, by default, AutoFixture will not rely on a mocking framework to create the instance, and will use the actual constructor from the type.
Since NSubstitute does not have the equivalent of Mock<T> or Fake<T> from other popular mocking frameworks, AutoFixture had to provide a special specimen builder, called SubstituteRelay, to fill in the gap. You can use this class as any other specimen builder to instruct the Fixture to return a mock when a specific type instance is requested.
var fixture = new Fixture().Customize(new AutoNSubstituteCustomization());
fixture.Customizations
.Add(new SubstituteRelay(new ExactTypeSpecification(typeof(DepClass))));
This construction is a bit lengthy so you could create a generic relay to shorten the syntax.
public class SubstituteRelay<T> : CompositeSpecimenBuilder
{
public SubstituteRelay()
: base(new SubstituteRelay(new ExactTypeSpecification(typeof(T))))
{
}
}
You should be able to write your test something like.
[Fact]
public void ReturnsExpectedValue()
{
var fixture = new Fixture().Customize(new AutoNSubstituteCustomization());
fixture.Customizations.Add(new SubstituteRelay<DepClass>());
fixture.Freeze<DepClass>().Get().ReturnsForAnyArgs("1234");
var sut = fixture.Create<HostClass>();
var actual = sut.Magic();
Assert.Equal("1234", actual);
}
To get closer to your intended API, you can create your own extension method that abstracts away the two lines of code that register the relay and freeze the instance.

Original method still getting called in Moq even after CallBase = true/false

Here's my code:
public class Bar { }
public class Foo { public string Name { get; set; } public Bar TheBar { get; set; } }
public class Dependency
{
public Foo DoSomething(Expression<Func<Foo, bool>> exp1) { return new Foo(); }
}
public class Base
{
public Dependency Dependency { get; set; }
public virtual Foo MethodA(Expression<Func<Foo, bool>> exp1,
params Expression<Func<Foo, object>>[] exp2)
{
return Dependency.DoSomething(exp1);
}
}
public class Derived : Base
{
public Foo DerviedMethod(string str)
{
return base.MethodA(e1 => e1.Name.Equals(str), e2 => e2.TheBar);
}
}
And my Unit Test code:
var mock = new Mock<Derived> { CallBase = true }; // Same result with false
mock
.Setup(m => m.MethodA(
It.IsAny<Expression<Func<Foo, bool>>>(),
It.IsAny<Expression<Func<Foo, object>>>()
))
.Returns(new Foo());
// Act
var result = mock.Object.DerviedMethod("test");
// Assert
Assert.IsNotNull(result);
But it still calls the original method and not the mocked one. Both classes exist in same assembly.
I have searched about it and almost all people got it right with CallBase = true or false.
Any ideas what is wrong with above code?
As has been suggested by #Pierre-Luc in the comments, extracting the base class and injecting it as a dependency is probably the better approach (I always think mocking the class you're actually trying to test feels wrong).
That said, for you to be able to mock a call of a class, it needs to be made via the VTable. Essentially, the mocking framework creates a new implementation of the virtual method. When you call it normally, this version of the method is run and can then intercept calls. The problematic line is this one:
return base.MethodA(e1 => e1.Name.Equals(str), e2 => e2.TheBar);
Because you're explicitly calling MethodA, via the base keyword, it tells the compiler to call a particular version of the method. It's always going to call the base implementation. This means that the mock can't intercept the call.
Changing the method to:
public Foo DerviedMethod(string str) {
return MethodA(e1 => e1.Name.Equals(str), e2 => e2.TheBar);
}
Allows the MethodA method to be mocked. Whether or not this is the right thing from a design perspective is up to you.

TDD How to Assert that a property of a POCO is set within a method that is being tested

We are creating a C# application using TDD and DI methodologies and NSubstitute.
We are writing a CreateThing method:
name and description strings as parameters
create a new Thing object
set the Name and Description properties of Thing from the method parameters
set the Status to Active
pass the Thing to a method on another class (via constructor injection) for further processing
We know how to write a test for the call to the other class by using Substitute.For and .Received().
How do we write tests for the Thing properties being set?
You can use Argument matchers namely Conditional matcher which looks like Arg.Is<T>(Predicate<T> condition). Your matcher could look like:
anotherClass.Received().Process(Arg.Is<Thing>(thing => !string.IsNullOrEmpty(thing.Name)));
Full listing:
public class Thing
{
public string Name { get; set; }
}
public class AnotherClass
{
public virtual void Process(Thing thing)
{
}
}
public class CreateThingFactory
{
private readonly AnotherClass _anotherClass;
public CreateThingFactory(AnotherClass anotherClass)
{
_anotherClass = anotherClass;
}
public void CreateThing()
{
var thing = new Thing();
thing.Name = "Name";
_anotherClass.Process(thing);
}
}
public class CreateThingFactoryTests
{
[Fact]
public void CreateThingTest()
{
// arrange
var anotherClass = Substitute.For<AnotherClass>();
var sut = new CreateThingFactory(anotherClass);
// act
sut.CreateThing();
// assert
anotherClass.Received().Process(Arg.Is<Thing>(thing => !string.IsNullOrEmpty(thing.Name)));
}
}

Moq behaviour with virtual property and parameter constructor

while mocking an object using parametrized constructor, if the property being initialized within the constructor is virtual, Moq does not set property value. But if it is non-virtual property, Moq sets the value.
Following is my class I wants to mock.
public class Activity
{
private Activity() {}
public Activity(string code, string description, string option)
{
if(string.IsNullOrEmpty(code)) throw new ArgumentNullException("code");
if (string.IsNullOrEmpty(option)) throw new ArgumentNullException("option");
Code = code;
Description = description;
Option = option;
}
public virtual string Code { get; private set; }
public virtual string Description { get; private set; }
public virtual string Option { get; private set; }
}
This is how I try to mock it:
[TestMethod]
public void It_Creates_Mock_For_A_Class()
{
var mock = new Mock<Activity>("Code 1", null, "Option");
Assert.IsNotNull(mock.Object);
Assert.AreEqual("Code 1", mock.Object.Code);
}
The test method fails saying:
Assert.AreEqual failed. Expected:. Actual:<(null)>.
But if I remove the virtual keyword from all the property, it works and passes the test case.
I have to keep the properties virtual because of Entity Framework.
Any clue? How to get around this problem?
Found out that if "CallBase" property is set to true, it solved the problem.
By looking at the assembly in Object Browser, the summary says:
Summary:
Whether the base member virtual implementation will be called for mocked classes if no setup is matched. Defaults to false.
The code that works:
[TestMethod]
public void It_Creates_Mock_For_A_Class()
{
var mock = new Mock<Activity>("Code 1", null, "Option");
mock.CallBase = true;
Assert.IsNotNull(mock.Object);
Assert.AreEqual("Code 1", mock.Object.Code);
}

How to Mock a readonly property whose value depends on another property of the Mock

(As indicated by the tags, I am using moq).
I have an interface like this:
interface ISource
{
string Name { get; set; }
int Id { get; set; }
}
interface IExample
{
string Name { get; }
ISource Source { get; set; }
}
In my application, concrete instances of IExample accept a DTO (IDataTransferObject) as the Source. Some properties on the concrete implementation of IExample are simply delegated to the Source. Like this...
class Example : IExample
{
IDataTransferObject Source { get; set; }
string Name { get { return _data.Name; } }
}
I would like to create a standalone mock of IExample (standalone meaning that I cannot use a captured variable because several instances of the IExample mock will be created in the course of a test) and setup the Mock such that IExample.Name returns the value of IExample.Source.Name. So, I would like to create a mock something like this:
var example = new Mock<IExample>();
example.SetupProperty(ex => ex.Source);
example.SetupGet(ex => ex.Name).Returns(what can I put here to return ex.Source.Name);
Essentially, I want to configure the mock to return, as the value of one property, the value of a property of a subobject of the mock.
Thanks.
You could probably use:
example.SetupGet(ex => ex.Name).Returns(() => example.Object.Source.Name);
The value to be returned will then be determined when the property is accessed, and will be taken from Name property of the mock's Source property.

Categories

Resources