Reputation: 175
I have achieved a solution to mock test the public virtual method using FakeItEasy Framework. Below I have a Test class with Private method and private method cannot be virtual. So please help me t mock the Private method using FakeItEasy Framework
Class To be tested
public class XYZ
{
public static int nValue = 0;
private void AddInetegers()
{
int i = 3;
int j = i * 100;
int k = j * 30 / 100;
Show(String.Format("Value Here {0}", k.ToString()));
nValue = k;
}
public virtual void Show(string message)
{
MessageBox.Show(message);
}
}
Test Class
[TestMethod]
public void Test_Using_FakeItEasy()
{
var instance = A.Fake<XYZ>();
A.CallTo(() => instance.Show("Hello"));
//A.CallTo(() => instance.AddInetegers(3)).CallsBaseMethod();
A.CallTo(instance).Where(x => x.Method.Name.Contains("AddInetegers")).MustHaveHappened();
Assert.AreEqual(90, XYZ.nValue);
}
Error:
Result Message: Test method PrjMSTest.Test.Test_Using_FakeItEasy threw exception: FakeItEasy.ExpectationException:
Assertion failed for the following call:
Any call made to the fake object.
where x => x.Method.Name.Contains("AddInetegers")
Expected to find it at least once but no calls were made to the fake object.
Upvotes: 2
Views: 4904
Reputation: 3097
As they told you in the comments, you can't easily test private methods and, in the vast majority of cases, probably you shouldn't.
If, for some reason, you still want to test AddInetegers()
, there's a "dirty" way to keep some kind of information hiding and to test your method.
First, you have to make AddInetegers
internal; it won't be visible outside your assembly and you will be able to test it.
Then find the Properties\AssemblyInfo.cs file of the project to which your XYZ
class belongs to; supposing your project is named MyProject
and your test project is MyProjectTests
, you can add
using System.Runtime.CompilerServices;
to the top of AssemblyInfo.cs and
[assembly: InternalsVisibleTo("MyProjectTests")]
to the bottom. This will make your method testable. More info here or here.
PrivateObject
, which has been around since 2004 as per this article by James Newkirk himself
var CurrentInstance = new XYZ();
var PrivateObject= new PrivateObject(CurrentInstance);
PrivateObject.Invoke("AddInetegers");
Assert.AreEqual(90, XYZ.nValue);
sometimes it is simply safest to just test the private functionality
You're in a rush, and have to do the fastest thing possible for here and now. In the long run, you don't want to test private methods. But I will say that it usually takes some time to refactor to address design issues. And sometimes you have to ship in a week. That's okay: do the quick and dirty and test the private methods using a groping tool if that's what you think is the fastest and most reliable way to get the job done. But understand that what you did was suboptimal in the long run, and please consider coming back to it (or, if it was forgotten about but you see it later, fix it).
Upvotes: 1