I use NUNIT and mostly Test with ValueSource to do assertions.
But i never try mocking.
I find a post os SO – What is Mocking?
It said :
To give an example: You can stub a database by implementing a simple in-memory structure for storing records. The object under test can then read and write records to the database stub to allow it to execute the test. This could test some behavior of the object not related to the database and the database stub would be included just to let the test run.
If you instead want to verify that the object under test writes some specific data to the database you will have to mock the database. Your test would then incorporate assertions about what was written to the database mock.
So, is it mean mocking framework act as a virtual database for read/write to satisfy the need of data source?
Not really. A mocking framework is something that allows you to generate mocks. A mock is generally an object that you can switch for a concrete implementation of something for test purposes. The mock will record which calls are made to it, and it can be configured to return specific values (or throw exceptions) when methods are called on it. Mocks can usually only be created for interfaces or abstract classes, so in order for you to reap the benefits of a mocking framework, your code base will have to adhere to some common OO best practices, such as:
Not making sense? Lets see an example.
Say you have class that fetches some webpage and determines if the page contains the word “hello”. It could look like this:
So how would you test this function, if your test machine was not connected to the internet? You could not, because
client.DownloadStringwould always throw an exception. This would be the same for other types of functions that require specific data in a database to work. They cannot be tested using mocks because they do not adhere to the “Program to an interface not an implementation” practice. So how can we change this? Well, we could make the code that provides theHasWordmethod with the string to search into a dependecy of theHelloFinderclass, so that we can mock it:This code does exactly the same as the example above, but it allows us to test the
HasWordmethod without worrying about internet connections. By using a mock instead of the actual implementation (StringDownloader).The code could be used like this in your live application:
But in order to test the
HasWordsmethod we don’t really care whether the string comes from google.com or anywhere else. We just need to test that given any string it behaves correctly, and that when the downloader throws an exception it also behaves correctly. And this is where the mock comes into play. Personally I use the mocking framework called Moq so the examples here use that aswell. Here is a test using a mock:So what is going on here?
First we create a new
Mockand ask it to mimic theIStringDownloaderinterface.We then call the
Setupmethod to tell to mock to return a hardcoded string every time theDownloadStringmethod is called, and we also tell it not to care what the argument is (achieved by theIt.IsAny<string>()argument.We now have a mock that behaves as we want it to, so we use it for the creation of the
HelloFinderclass and call theCountWordsmethod. To conclude the test, all we have to do is to check that result is correct.Other useful tests for this class could be:
To sum up
So back to your original question. Is a mocking framework something that acts like a virtual database? Not exactly. But it is something that you make act like anything you want. Do you need mocking for your unittests? Well, they are certainly helpful, but they require that your code is written in a certain way. Projects that use dependency injection are very easily tested with mocks. But since I don’t know about your specific code base, it’s hard to say. You say that you already have some unit tests. These would have to be rewritten to use mocks, and your entire code base may also have to be rewritten so that testing with mocks is even possible. So whether mocks are a good idea for your current project is up to you to decide. But make sure to have them in mind for future projects.
I hope this shed some light over the issue.