I keep seeing this referred to on DotNetKicks etc... Yet cannot find out exactly what it is (In English) or what it does? Could you explain what it is, or why I would use it?
Moq is a mocking framework for C#/.NET. It is used in unit testing to isolate your class under test from its dependencies and ensure that the proper methods on the dependent objects are being called. For more information on mocking you may want to look at the Wikipedia article on Mock Objects.
Other mocking frameworks (for .NET) include JustMock, TypeMock, RhinoMocks, nMock, .etc.
In simple English, Moq is a library which when you include in your project give you power to do Unit Testing in easy manner.
Why? Because one function may call another, then another and so on. But in real what is needed, just the return value from first call to proceed to next line.
Moq helps to ignore actual call of that method and instead you return what that function was returning. and verify after all lines of code has executed, what you desired is what you get or not. Too Much English, so here is an example:
String Somethod()
{
IHelper help = new IHelper();
String first = help.firstcall();
String second= secondcall(first);
return second;
}
Now, here first is needed to for secondcall(), but you can not actually call help.firstcall() as it in some other layer. So Mocking is done, faking that method was called:
[TestMethod]
public void SomeMethod_TestSecond
{
mockedIHelper.Setup(x=>x.firstcall()).Returns("Whatever i want");
}
Here, think, SetUP as faking method call, we are just interested in Returns.
Moq is a mocking engine for doing .Net TDD.
Related
How do I test the following code?
public void CreateRentalIfNecessary(int? rentalId)
{
if (rentalId.HasValue) { CreateRental(rentalId.Value); }
}
I need to write a simple unit test to verify that CreateRental is called when the rentalId is not null. How do I test this?
Then answer here seems way too complicated: how to assert if a method has been called using nunit
Taking the example at face value, you are trying to simultaneously test two methods of the same object, CreateRentalIfNecessary and CreateRental. Since they are both in the same object, you can't use a mock. This leads me to several alternative conclusions...
One of the methods may be unneeded. Do you really want to create a method when it's not necessary? Perhaps you can just remove the ...IfNecessary variant and always check for necessity in CreateRental. Whether this is possible, of course, depends on how the methods are being called.
As a variant, simply have clients make the test to see if the call is needed.
If both are really needed, I presume you are testing CreateRental. In that case, you should be able to reuse the same test cases for CreateRentalIfNeeded.
My preference would be to go for something like (1). It's possible that your tests are telling you to refactor the SUT.
I have various methods that I would like to unit test using Visual Studio's built in unit testing capability for C#. Things have been going pretty smoothly, but I've run into a scenario where I want to "stub out" a dependency on a particular function call.
Namely, I have some methods that are in the following format:
public class ClassWithMethodsIWantToUnitTest
{
public void myFcn(object someArg)
{
...
LoggerService.Instance.LogMessage("myMessage");
...
}
}
So basically, I want my unit test to simply verify that the call to "LogMessage" has occurred. I don't want to actually check a log file or anything. I want a way to see if the LoggerService line has been hit and executed.
LoggerService is a singleton, and if possible, I don't want to modify the code just for unit testing.
Based on the format of this problem, it seems to me that it should be possible to somehow take control of the code in my unit test. In other words, is there a way for me to make a fake version of LogMessage such that I can use it for my unit test? I don't want the "real" LogMessage function to be called if possible. I just want to test that the code hit the path that called the function.
Does this make any sense? Is this possible?
It certainly makes sense and is not an unknown problem.
Unfortunately you will probably need to change the code, so that it accepts dependency injection. That is, when testing you should be able to inject a specially crafted test object (a mock) instead of the real thing. In your case it probably means being able to set LoggerService.Instance to a special mock object.
The second thing you need is the fake logger instance that you will test against. You probably want a mock, which is a special object that can be set up to check behaviour of the caller. There are several mock frameworks around and I really recommend that you use one instead of trying to roll your own.
Anders' answer was definitely the "canonical" way of approaching the problem, but in .NET 4.5, there's a second option:
The Fakes framework.
It lets you add a "fakes" assembly to your unit test project that accepts a delegate to perform in place of the actual implementation of a method. Here's an example using File.ReadAllText
[TestMethod]
public void Foo()
{
using (ShimsContext.Create())
{
ShimFile.ReadAllTextString = path => "test 123";
var reverser = new TextReverser();
const string expected = "321 tset";
//Act
var actual = reverser.ReverseSomeTextFromAFile(#"C:\fakefile.txt");
//Assert
Assert.AreEqual(expected, actual);
}
}
What that test method is doing is temporarily (within the scope of the ShimsContext) replacing the implementation of File.ReadAllText with the lambda I provided. In this case, any time ReadAllText is called, it returns the string "test 123".
It's slower than regular DI, but if you're absolutely tied to a specific implementation of a singleton, it could be exactly what you need. Read more about it here.
What Anders said.
Several popular mocking frameworks are Moq and RhinoMocks
And you'd change your code so that the logger dependency was injected to your class:
public class ClassWithMethodsIWantToUnitTest
{
public ClassWithMethodsIWantToUnitTest(ILoggerService logger)
{}
public void myFcn(object someArg)
{
...
logger.LogMessage("myMessage");
...
}
}
Or something similar. A DI framework could inject the logger automatically into the class when it needs it. Esentially a DI framework automatically calls
new ClassWithMethodsIWantToUnitTest(LoggerService.Instance);
Here's my example:
[TestMethod]
public void NewAction_should_return_IndexAction()
{
NewViewModel viewModel = new NewViewModel()
{
Name = "José Inácio Santos Silva",
Email = "joseinacio#joseinacio.com",
Username = "joseinacio"
};
//IsUserRegistered is used to validate Username, Username is unique.
_mockAuthenticationService.Setup(x => x.IsUserRegistered(viewModel.Username )).Returns(false);
//IsUserRegistered is used to validate Email, Email is unique.
_mockUsuarioRepository.Setup(x => x.GetUserByEmail(viewModel.Email));
_mockDbContext.Setup(x => x.SaveChanges());
_mockUsuarioRepository.Setup(x => x.Add(It.IsAny<User>()));
_userController = new UserController(_mockUsuarioRepository.Object, _mockDbContext.Object, _mockAuthenticationService.Object);
ActionResult result = _userController.New(viewModel);
result.AssertActionRedirect().ToAction("Index");
_mockAuthenticationService.VerifyAll();
_mockUsuarioRepository.VerifyAll();
_mockDbContext.VerifyAll();
}
I have read some tutorials and they say that we should use only one mock per test.
But look at my test, it use 3 mocks, to check if my Action is working the right way I need to check these 3 mocks, do not agree?
How do I make this test in the correct way?
Each unit test should test only one thing.
In your unit test you are testing three mock objects. If the mockAuthenticationService fails, this will be reported and the unit test will stop there. Any errors with the other Mock objects are not reported and are effectively hidden.
In this situation you should create three unit tests, and in each one verify only one of the Mock objects. The rest are just used as stubs. (A stub is exactly the same as a Mock object, except you dont call VerifyAll on it at the end)
To avoid duplication and wasted effort, you should refactor that unit test so that most of the code is in a separate method. Each of the three unit tests calls this method and then verifies a single Mock.
You also have a test to ensure the correct redirect is called. This should also be in a separate test.
Quite simply:
[TestMethod]
public void NewAction_should_checkUserRegistered()
{
SetupTest();
_mockAuthenticationService.VerifyAll();
}
[TestMethod]
public void NewAction_should_GetUserByEmail()
{
SetupTest();
_mockUsuarioRepository.VerifyAll();
}
[TestMethod]
public void NewAction_should_SaveDBContext()
{
SetupTest();
_mockDbContext.VerifyAll();
}
[TestMethod]
public void NewAction_should_return_Redirects_Action()
{
var novoActionResult = SetupTest();
novoActionResult.AssertActionRedirect().ToAction("Index");
}
Short answer: "only one mock per test." is ambiguous. Use as many fakes as you need to isolate the code under test to a "unit" that is testing one condition.
It should be phrased: Only test one thing per test. If you are checking the state of more than one mock object you are probably testing more than one thing.
Long answer:
There is a lot to answer here to get the unit test written according to the best practices I have come across.
Common terminology from (The Art of Unit Testing), which I hope will come to be common:
Fake - an object that isolates the code under test from the rest of the application.
Stub - a simple fake object.
Mock - a fake object that stores what is passed to it, that you can inspect to verify the test.
Stubs and Mocks are both types of fake.
"only one mock per test." is wrong. You use as many fakes as you need to fully isolate the code under test from the rest of the application. If a method takes no parameters, there's nothing to fake. If a method takes a simple data type e.g. int, string, that doesn't have any complex behaviour, you don't need to fake it. If you have 2 repositories, context, a service object passed in, fake all of them, so no other production methods are being called.
You should have one condition per test as #Mongus Pong has said.
Test naming convention: MethodUnderTest_Condition_ExpectedBehaviour in this case you cannot do that as you have got more than one condition tested.
Test pattern: Arrange, Act, Assert. From your test, it seems as that is what you have done, but you have are arranging using private members. You should replace these with variables in each test, since the running order of tests is not always enforced, the state of these variables cannot be guaranteed, making your tests unreliable.
Buy a copy of "The Art of Unit Testing" http://artofunittesting.com/ it will answer a lot of more of your questions and is a great investment; one of the books that I'd grab if the office caught fire.
IMHO mocks and stubs are not that unique defined - every author uses them slightly different.
As I understand stubs "mock" behavior or "output" while you use mocks for example to check "input" into the mocked object/interface (like the Verify-Methods in MOQ).
If you see it this way then yes I too think you should only use one Mock because you should only test one thing - if you see it more like the stubs to inject testable interfaces then it's impossible to do.
If the VerifyAll is really needed here you indeed use 3 mocks, but I don't think they are nedded.
The best way to use Mock and stubs with Dev Magic Fake, so you can mock the UI and the DB for more information see Dev Magic Fake on codePlex
http://devmagicfake.codeplex.com/
Thanks
M.Radwan
In the past, I have only used Rhino Mocks, with the typical strict mock. I am now working with Moq on a project and I am wondering about the proper usage.
Let's assume that I have an object Foo with method Bar which calls a Bizz method on object Buzz.
In my test, I want to verify that Bizz is called, therefore I feel there are two possible options:
With a strict mock
var mockBuzz= new Mock<IBuzz>(MockBehavior.Strict);
mockBuzz.Setup(x => x.Bizz()); //test will fail if Bizz method not called
foo.Buzz = mockBuzz
foo.Bar();
mockBuzz.VerifyAll();
With a loose mock
var mockBuzz= new Mock<IBuzz>();
foo.Buzz = mockBuzz
foo.Bar();
mockBuzz.Verify(x => x.Bizz()) //test will fail if Bizz method not called
Is there a standard or normal way of doing this?
I used to use strict mocks when I first starting using mocks in unit tests. This didn't last very long. There are really 2 reasons why I stopped doing this:
The tests become brittle - With strict mocks you are asserting more than one thing, that the setup methods are called, AND that the other methods are not called. When you refactor the code the test often fails, even if what you are trying to test is still true.
The tests are harder to read - You need to have a setup for every method that is called on the mock, even if it's not really related to what you want to test. When someone reads this test it's difficult for them to tell what is important for the test and what is just a side effect of the implementation.
Because of these I would strongly recommend using loose mocks in your unit tests.
I have background in C++/non-.NET development and I've been more into .NET recently so I had certain expectations when I was using Moq for the first time. I was trying to understand WTF was going on with my test and why the code I was testing was throwing a random exception instead of the Mock library telling me which function the code was trying to call. So I discovered I needed to turn on the Strict behaviour, which was perplexing- and then I came across this question which I saw had no ticked answer yet.
The Loose mode, and the fact that it is the default is insane. What on earth is the point of a Mock library that does something completely unpredictable that you haven't explicitly listed it should do?
I completely disagree with the points listed in the other answers in support of Loose mode. There is no good reason to use it and I wouldn't ever want to, ever. When writing a unit test I want to be certain what is going on - if I know a function needs to return a null, I'll make it return that. I want my tests to be brittle (in the ways that matter) so that I can fix them and add to the suite of test code the setup lines which are the explicit information that is describing to me exactly what my software will do.
The question is - is there a standard and normal way of doing this?
Yes - from the point of view of programming in general, i.e. other languages and outside the .NET world, you should use Strict always. Goodness knows why it isn't the default in Moq.
I have a simple convention:
Use strict mocks when the system under test (SUT) is delegating the call to the underlying mocked layer without really modifying or applying any business logic to the arguments passed to itself.
Use loose mocks when the SUT applies business logic to the arguments passed to itself and passes on some derived/modified values to the mocked layer.
For eg:
Lets say we have database provider StudentDAL which has two methods:
Data access interface looks something like below:
public Student GetStudentById(int id);
public IList<Student> GetStudents(int ageFilter, int classId);
The implementation which consumes this DAL looks like below:
public Student FindStudent(int id)
{
//StudentDAL dependency injected
return StudentDAL.GetStudentById(id);
//Use strict mock to test this
}
public IList<Student> GetStudentsForClass(StudentListRequest studentListRequest)
{
//StudentDAL dependency injected
//age filter is derived from the request and then passed on to the underlying layer
int ageFilter = DateTime.Now.Year - studentListRequest.DateOfBirthFilter.Year;
return StudentDAL.GetStudents(ageFilter , studentListRequest.ClassId)
//Use loose mock and use verify api of MOQ to make sure that the age filter is correctly passed on.
}
Me personally, being new to mocking and Moq feel that starting off with Strict mode helps better understand of the innards and what's going on. "Loose" sometimes hides details and pass a test which a moq beginner may fail to see. Once you have your mocking skills down - Loose would probably be a lot more productive - like in this case saving a line with the "Setup" and just using "Verify" instead.
This question already has answers here:
How do I start unit testing?
(8 answers)
Closed 10 years ago.
So I'm starting to write a class library of useful methods I've written and picked up over the years, I'll start with two examples of code, then ask my specific questions:
I'd also like to make the argument that this is not a duplicate of some of the other, "where do I start unit testin questions."
Check network connectivity (not internet, just netwok)
public static Boolean IsNetworkConnected()
{
Boolean ret = false;
try
{
String HostName = System.Net.Dns.GetHostName();
System.Net.IPHostEntry thisHost = System.Net.Dns.GetHostEntry(HostName);
String thisIpAddr = thisHost.AddressList[0].ToString();
ret = thisIpAddr != System.Net.IPAddress.Parse("127.0.0.1").ToString();
}
catch (Exception)
{
return false;
}
return ret;
}
And my IsValiEmail method (note, I didn't write the regex)
public const String MatchEmailPattern = #"^(([\w-]+\.)+[\w-]+|([a-zA-Z]{1}|[\w-]{2,}))#"
+ #"((([0-1]?[0-9]{1,2}|25[0-5]|2[0-4][0-9])\.([0-1]?[0-9]{1,2}|25[0-5]|2[0-4][0-9])\."
+ #"([0-1]?[0-9]{1,2}|25[0-5]|2[0-4][0-9])\.([0-1]?[0-9]{1,2}|25[0-5]|2[0-4][0-9])){1}|"
+ #"([a-zA-Z]+[\w-]+\.)+[a-zA-Z]{2,4})$";
public static bool IsValidEmail(string email)
{
if (email != null && email != string.Empty)
return Regex.IsMatch(email, MatchEmailPattern);
else
return false;
}
So, my question is how do I test that these methods actually work, obviously I want to start Unit Testing more of my code which is more complex than these quick examples.
I'd like to avoid installing additional tools/frameworks if possible, but I'm open to your ideas.
update
Where should this new Unit-Test code (via the links already posted) live? In the same assembly? A seperate assembly?
Check out the book. The art of unit testing. The wiki page has a lot of great resources.
NUnit is probably the unit testing framework that best suits your need. Have a look at their quick start tutorial.
You can certainly do unit testing without a framework -- just make an app with a "test" button that runs your tests. However, I've found that it's much nicer to use an existing framework -- They're set up to allow you to easily add tests, see success/failure, and run tests automatically. Nunit is fine, or really, anything will do. MSTest is OK, if you have a version of Visual Studio that comes with it.
IsValidEmail should be easy to test: test with null, "", a valid email, and an invalid email. Then put on a black hat and try sneaking pernicious garbage in: can you make it break? But since this function only operates on its inputs, it is pretty easy to test.
IsNetworkConnected is harder to test. You call GetHostName and GetHostEntry, and you can't control what they return. This makes it hard to check all of the possible modes. Unit testing exerts strong pressure on you to separate your logic from your data retrieval. One option here would be to pass in the IPHostEntry. Of course, this would makes your exception trapping less useful, and push some of it on to the caller.
You could build a function to make the calls to GetHostName and GetHostEntry for you, then pass a delegate to the real one in your app and a fake* one in your test. At some point this strategy costs more than it delivers in value -- You'll have to make that judgment yourself, and don't waste effort on work that doesn't produce value.
*Followers of the Mock Objects technique will note that you should not mock out GetHostName and GetHostEntry, since you do not own them. If you have a mocking framework and wish to use it, feel free; Just don't mistake using their tools with following their design methods.
Testing IsNetworkConnected
Sean McMillan is right in his response that there is not much of a benefit in testing IsNetworkConnected method. It does not encapsulate much logic but only the dependencies which are not worth abstracting. However, let us pretend that it is important to unit test that method due to some reason. The following is the way in which I would go about:
public static Boolean IsNetworkConnected(IIPAddressProvider ipAddressProvider)
{
Boolean ret = false;
try
{
IPAddress thisIpAddr = ipAddressProvider.GetIPAddressOFLocalHost();
ret = thisIpAddr.ToString() != System.Net.IPAddress.Parse("127.0.0.1").ToString();
}
catch (Exception)
{
return false;
}
return ret;
}
After doing that I would write the following unit test:
Throw exception from the mock of IIPAddressProvider
Return Null IPAddress from the mock of IIPAddressProvider
Return 127.0.0.1 from the mock of IIPAddressProvider
Return different IPAddress other than 127.0.0.1 from the mock of IIPAddressProvider
Testing IsValidEmail
There is a definite value in writing unit tests for this method. You need to try postive, negative and boundary test cases. Also unit testing is form of white box testing. From your method it is clear that you need to exercise on pre-condition of the method and the regular expression while doing unit testing. The important thing here is to exercise the regular expression. There are not many code paths in the method. In my opinion you need to write the above mentioned test case scenarios. Additionally, some third party tools for doing regular expression validation should be used before you use it in your production code.
Where should the test code be located
In my opinion it should always be located in a different assembly from the production code. That is the best choice.
For the first bit of code you'll want to look into introducing Dependency Inversion so that you can mock out those dependencies and control when the method returns true and when it returns false.
For the second I'd create some NUnit tests that each pass in either valid or invalid emails and verify that the correct result is returned. You do this by either creating one test per email you're wanting to test or creating one test as a row-test (which is possible with NUnit 2.5+).
As for where the tests should live....well they can live in the same assembly or in another assembly... Best practice, at the moment, seems to be to put them in a separate assembly. If you have a project called MyProject you then create a project for your unit tests called MyProject.Tests....and as an added extra it's good to put your integration tests in another assembly called MyProject.Integration.Tests.
Some additional unit testing frameworks can be found here.
You can start with Junit, and you can use mocking framework (like mockito) to mock parts of your code that involves using Frameworks. But to use mock framework you need to isolate part of your code that uses external framework into a seperate class or interface and use mock framework to mock the external dependency.
Also in your code you are using a "==" operator for String comparision.
ret = thisIpAddr != System.Net.IPAddress.Parse("127.0.0.1").ToString();
But you should use "equals" method for String comparision .
Agreed with Asaph, NUnit is most widely used framework. That being said, if you do not want to use additional frameworks, VStudio Professional does have unit testing tools built in.
I recommend putting your tests in the same solution, in a separate project, so that you don't have to ship your tests with your assembly.
Your first case is actually not the most obvious to unit test, because your class has an external dependency which will be difficult to replicate: obviously, if the class tests that the machine is connected, the result itself will be dependent on the state of the machine. In other words, if the test fails, you don't know if it is because of your code, or because of something which is outside of the control of your code. These situations are typically approached through Mocking, but that's probably not the easiest thing to start with if you are new to unit testing!
The second case is a much better starting point; essentially you will have to create valid and invalid addresses, and pass them to your method, and check that the result is what it should be.