How to moq a property that will be indirectly modified? - c#

I am trying to do a very simple thing: Set an initial value to a property, call a method which callback should modify the property value, and read the property at the end.
Class Test2 is using ITest1 to automatize some actions.
public interface ITest1
{
decimal Value { get; set; }
void Increment();
}
public class Test2
{
ITest1 test1;
public Test2(Itest1 test1)
{
this.test1 = test1;
}
public void Increment()
{
this.test1.Increment();
}
public Get()
{
return this.test1.Value;
}
}
In order to achieve this behaviour I setted up this test:
[TestClass]
public class Test2Test
{
private Test2 test2;
private decimal value;
[TestInitialize]
public void Setup()
{
var test1Mock = new Mock<ITest1>();
test1Mock.SetupGet(m => m.Value).Returns(value);
test1Mock
.Setup(m => m.Increment())
.Callback(() => value++);
this.test2= new Test2(test1Mock.Object);
}
[TestMethod]
public void Get_Returns0()
{
Assert.AreEqual(0, this.test2.Get());
}
[TestMethod]
public void Get_AfterIncrement_Returns1()
{
this.test2.Increment();
Assert.AreEqual(1, this.test2.Get());
}
}
The second test is returning always 0. Why is this happening?

The solution is to return actions instead of variables as:
.Return(() => value) instead of .Return(value)
Answer found here.

Related

Can we create a global variable whose value can be accessed in any where in the application?

I have a class library project, I want to create a variable and assign a value to it through MethodA() whose value can be access through MethodB().
Just like we have a session in ASP.NET.
I cannot pass as a parameter to MethodB() because MethodB() is being used in many places and if I change it, all the other methods will get affected.
Public Void MethodA()
{
string value ="Hello";
}
public Void MethodB()
{
-- I want to read the value which is set in MethodA()
}
I need to dispose the value as well after reading it in MethodB().
Both of these methods are in different classes inside the same project.
First try to create a property with a private setter:
public class A
{
public string Value { get { return MethodA(); } }
public string MethodA()
{
return "Hello";
}
public void MethodB()
{
var value = Value;
}
}
If you have two classes:
public class A
{
public string FooMethod()
{
return string.Empty;
}
}
public class B
{
public string BarMethod()
{
var result = new A().FooMethod();
return result;
}
}
You can get idea to handle your exception
public class test
{
public static int value = 0; //Global variable
public void MethodA()
{
//you can assign here as well
value++;
}
}
public class HomeController : Controller
{
test t = new test();
public IActionResult Index()
{
t.MethodA();
int d = test.value;
//you can assign here as well
test.value = 100;
int dd = test.value;
return View();
}
}

Reduce duplication in NUnit tests for different implementations of interface

I have the following interface:
public interface IStack
{
int Peek();
void Push(int i);
}
And two implementations:
public class LinkedListStack : IStack
{
public void Push(int x)
{
...
}
public int Peek()
{
...
}
}
public class ArrayStack : IStack
{
public void Push(int i)
{
...
}
public int Peek()
{
...
}
}
For my unit tests - I currently have something like this, two files containing the same tests - the only difference being the implementation:
LinkedListStackTest.cs:
public class LinkedListStackTest
{
[Test]
public void PushToStack()
{
//Arrange
IStack stack = new LinkedListStack();
//Act
stack.Push(1);
//Assert
Assert.AreEqual(1, stack.Peek());
}
}
ArrayStackTest.cs
public class ArrayStackTest
{
[Test]
public void PushToStack()
{
//Arrange
IStack stack = new ArrayStack();
//Act
stack.Push(1);
//Assert
Assert.AreEqual(1, stack.Peek());
}
}
Given the tests for the implementations should be the same - is there a way I can write a single set of NUnit tests that will run against all my implementations of IStack?
You can use the TestCaseSourceAttribute:
[Test]
[TestCaseSource(typeof(StackTestCases))]
public void PushToStack(IStack stack)
{
//Arrange/Act
stack.Push(1);
//Assert
Assert.AreEqual(1, stack.Peek());
}
Implementation of StackTestCases:
internal class StackTestCases : IEnumerable
{
public static IEnumerable TestCases
{
get
{
yield return new TestCaseData(new LinkedListStack());
yield return new TestCaseData(new ArrayStack());
}
}
/// <inheritdoc />
public IEnumerator GetEnumerator()
{
return TestCases.GetEnumerator();
}
}
Please note that the test method will take an IStack as a parameter:
[Test]
[TestCaseSource(typeof(StackTestCases))]
public void PushToStack(IStack stack)
...And you can return the different implementations of IStack in TestCases property of StackTestCases:
yield return new TestCaseData(new LinkedListStack());
yield return new TestCaseData(new ArrayStack());
You will have to use generics for this purpose with TextFixture attributes having the implementations of your interface.
[TestFixture(typeof(LinkedListStack))]
[TestFixture(typeof(ArrayStack))]
class IStack_Contract<T> where T : IStack, new()
{
}
You just pass the types to your tests and then they will execute for the respective implementations.
You can use abstract classes to achieve this.
First, create an abstract class where you will define all your common/share tests among all your implementations:
public abstract class MyClassShould
{
protected abstract MyInterface Initialize();
protected MyInterface myInterface;
[SetUp]
public void SetUp()
{
myInterface = Initialize();
}
[Test]
public void FirstTest()
{
// do something with myInterface
// assert results
}
}
Then create a test class for your Implemenetation1
public abstract class MyFirstImplementationShould
{
protected override MyInterface Initialize()
{
return new MyFirstImplementation();
}
}
And the same for your Implementation2 which may have extra tests. For example, this implementation has a TTL expiration while the first one doesn't.
public abstract class MySecondImplementationShould
{
protected override MyInterface Initialize()
{
return new MySecondImplementation();
}
[Test]
public void TtlTest()
{
// do something with myInterface
// assert results
}
}

Moq an object in a static class

I can't get Moq to mock an object that gets created in a static method.
Here is my moq and code
code:
public interface IConfigHelper
{
string GetConfiguration(string sectionName, string elementName);
}
public class ConfigHelper : IConfigHelper
{
public ConfigHelper() { }
public virtual string GetConfiguration(string sectionName, string elementName)
{
string retValue = String.Empty;
//Does things to get configuration and return a value
return retValue;
}
}
public class myRealClass
{
public myRealClass(){}
public string myworkingMethod()
{
var retValue = String.Empty;
retValue = utilSvc.GetConfigurationValue();
return retValue;
}
}
public static class utilSvc
{
public static string GetConfigurationValue()
{
ConfigHelper configUtil = new ConfigHelper(); //NOT BEING MOCKED
return configUtil.GetConfiguration("sectionName/sectionElement", "ClinicalSystem");
}
}
the Test using Moq
[TestFixture(TestName = "Tests")]
public class Tests
{
private Mock<IConfigHelper> configHelperMOCK;
[SetUp]
public void Setup()
{
configHelperMOCK = new Mock<IConfigHelper>();
}
[Test]
public void serviceIsBPManagementForValidSource()
{
//Arrange
string sectionName = "sectionName/sectionElement";
string clinicalElementName = "ClinicalSystem";
string clinicalElementValue = "Zedmed";
configHelperMOCK.Setup(s => s.GetConfiguration(sectionName, clinicalElementName)).Returns(clinicalElementValue);
//act
// the call to myRealClass
//assert
// test assertions
}
}
The issue that I am having is with this line:
ConfigHelper configUtil = new ConfigHelper(); //NOT BEING MOCKED
I cannot get the moq to Mock the object.
I do not want the code to read the config file. I wish to moq away this instance of ConfigHelper
You can't wrap the static class/method but you can redirect it
public static class UtilSvc
{
static UtilSvc()
{
CreatorFunc = () => new ConfigHelper();
}
public static Func<IConfigHelper> CreatorFunc { get; set; }
public static string GetConfigurationValue()
{
var configUtil = CreatorFunc();
return configUtil.GetConfiguration("sectionName/sectionElement",
"ClinicalSystem");
}
}
and then in the test
//...
private Mock<IConfigHelper> configHelperMOCK;
[SetUp]
public void Setup()
{
configHelperMOCK = new Mock<IConfigHelper>();
UtilService.CreatorFunc = () => configHelperMOCK.Object;
}
//...
You cannot mock static class. I would rather propose to inject that IConfigHelper into the myRealClass. That is the usual way how to decouple dependencies and use DI.
public class myRealClass
{
private IConfigHelper _configHelper;
public myRealClass(IConfigHelper configHelper)
{
_configHelper = configHelper;
}
public string myworkingMethod()
{
var retValue = String.Empty;
retValue = _configHelper.GetConfigurationValue();
return retValue;
}
}
Avoid coupling your code to static classes, which in most cases cause you code be to difficult to maintain and test.
Follow the Explicit Dependencies Principle
Methods and classes should explicitly require (typically through
method parameters or constructor parameters) any collaborating objects
they need in order to function correctly.
Give the article a read. It is short and very informative.
If you want to keep the static class then you wrap the static class behind an abstraction.
public interface IUtilSvc {
string GetConfigurationValue();
}
public class utilSvcWrapper : IUtilSvc {
public string GetConfigurationValue() {
return utilSvc.GetConfigurationValue(); //Calling static service
}
}
Or another option is that utlSvc does not have to be static if can be injected into dependent classes
public class utilSvc : IUtilScv {
private readonly IConfigHelper configUtil;
public utilSvc(IConfigHelper configHelper) {
configUtil = configHelper;
}
public string GetConfigurationValue() {
return configUtil.GetConfiguration("sectionName/sectionElement", "ClinicalSystem");
}
}
Inject the IUtilScv into the dependent class so that it is no longer dependent on static class.
public class myRealClass {
private readonly IUtilScv utilSvc;
//Explicit dependency inject via constructor
public myRealClass(IUtilScv utilSvc) {
this.utilSvc = utilSvc;
}
public string myworkingMethod() {
var retValue = utilSvc.GetConfiguration();
return retValue;
}
}
In that case you don't even need IConfigHelper when testing as it has also been abstracted away. And you only need to mock the dependencies needed for the test.
[TestFixture(TestName = "Tests")]
public class Tests {
private Mock<IUtilScv> utilScvMOCK;
[SetUp]
public void Setup() {
utilScvMOCK = new Mock<IUtilScv>();
}
[Test]
public void serviceIsBPManagementForValidSource() {
//Arrange
var expectedClinicalElementValue = "Zedmed";
utilScvMOCK
.Setup(s => s.GetConfiguration())
.Returns(expectedClinicalElementValue)
.Verifiable();
var sut = new myRealClass(utilScvMOCK.Object);
//Act
var actualClinicalElementValue = sut.myworkingMethod();
//Assert
configHelperMOCK.Verify();
Assert.AreEqual(expectedClinicalElementValue, actualClinicalElementValue);
}
}

verifying setup on a passed in mocked object

I am testing my class
public class myclass
{
private IAwesome awesomeObject;
public myclass(IAwesome awesomeObject)
{
this.awesomeObject = awesomeObject;
}
public void MethodUnderTest()
{
this.awesomeObject.RunSomething(); //I want to verify that RunSomething was called
}
}
The way I am doing this is:
//Arrange
var mockAwesome = new Mock<IAwesome>();
mockAwesome.Setup(x=>x.RunSomething()).Returns ... Verify()...;
//Act
var sut = new myclass(mockAwesome.object);
sut.MethodUnderTest();
//Assert
mockAwesome.Verify();
The exception I am getting is:
System.NotSupportedException : Expression references a method that
does not belong to the mocked object: x => x.RunSomething
Is it not possible to test that a specific method was executed on a mocked object that I passed into a class, that is now part of a private member of that class?
Modify set up line to mockAwesome.Setup(x=>x.RunSomething()).Verifiable() and it should work for the example you provided.
[TestClass]
public class MoqVerificationTest {
[TestMethod]
public void Moq_Should_Verify_Setup() {
//Arrange
var mockAwesome = new Mock<IAwesome>();
mockAwesome.Setup(x => x.RunSomething()).Verifiable();
//Act
var sut = new myclass(mockAwesome.Object);
sut.MethodUnderTest();
//Assert
mockAwesome.Verify();
}
public interface IAwesome {
void RunSomething();
}
public class myclass {
private IAwesome awesomeObject;
public myclass(IAwesome awesomeObject) {
this.awesomeObject = awesomeObject;
}
public void MethodUnderTest() {
this.awesomeObject.RunSomething(); //I want to verify that RunSomething was called
}
}
}
To confirm, comment out this.awesomeObject.RunSomething() in your sample class and run the test again. It will fail because you setup the RunSomething as Verifiable() and it was not used.
When testing, works perfectly fine for me...
Try this approach see if anything different results...
void Main()
{
IAwesome awesome = Mock.Of<IAwesome>();
Mock<IAwesome> mock = Mock.Get(awesome);
mock.Setup(m => m.RunSomething());
MyClass myClass = new MyClass(awesome);
myClass.MethodUnderTest();
mock.Verify(m => m.RunSomething(), Times.Once);
}
public interface IAwesome
{
void RunSomething();
}
public class MyClass
{
private IAwesome awesomeObject;
public myclass(IAwesome awesomeObject)
{
this.awesomeObject = awesomeObject;
}
public void MethodUnderTest()
{
this.awesomeObject.RunSomething();
}
}

Moq to verify certain value not predicable

To make it easy to explain, I have following codes
public interface IAnother
{
void DoAnotherJob(DateTime date);
}
public class MainJob
{
private IAnother another;
public MainJob(IAnother another)
{
this.another = another;
}
public void FunctionA()
{
this.FunctionB(DateTime.Now);
}
public void FunctionB(DateTime date)
{
this.another.DoAnotherJob(date);
}
}
I need to write a unit test code to make sure when FunctionA() is called the underlying IAnother.DoAnotherJob() is called to use the current date time.
I can write the testing code
[TestMethod()]
public void FunctionATest()
{
var mockAnother = new Mock<IAnother>();
var mainJob = new MainJob(mockAnother.Object);
mainJob.FunctionA();
mockAnother.Verify(x => x.DoAnotherJob(It.IsAny<DateTime>()), Times.Once);
}
to make sure the function is called with any date time, but I have no way to specify the exact value since the real value of DateTime is not predictable.
Any ideas?
You are always going to struggle when you want to verify anything regarding DateTime.Now as the property value will most likely change between calls. The best you can do is something like this:
mockAnother.Verify(x => x.DoAnotherJob(It.Is<DateTime>(d > DateTime.Now.AddSeconds(-1))), Times.Once);
The alternative is to introduce another class and abstraction which you use to resolve the DateTime:
public interface ITimeProvider
{
DateTime Now { get; }
}
public class TimeProvider : ITimeProvider
{
DateTime Now { get { return DateTime.Now ; } }
}
Which you would then use instead of DateTime.Now directly:
public class MainJob
{
private IAnother another;
private ITimeProvider timeProvider;
public MainJob(IAnother another, ITimeProvider timeProvider)
{
this.another = another;
this.timeProvider = timeProvider;
}
public void FunctionA()
{
this.FunctionB(this.timeProvider.Now);
}
public void FunctionB(DateTime date)
{
this.another.DoAnotherJob(date);
}
}
Then, your Unit Test becomes:
[TestMethod()]
public void FunctionATest()
{
var now = DateTime.Now;
var mockAnother = new Mock<IAnother>();
var mockTimeProvider = new Mock<ITimeProvider>();
mockTimeProvider.Setup(x => x.Now).Returns(now);
var mainJob = new MainJob(mockAnother.Object, mockTimeProvider.Object);
mainJob.FunctionA();
mockAnother.Verify(x => x.DoAnotherJob(now), Times.Once);
}

Categories

Resources