Sunday, July 19, 2015

Blog has moved....

After seeing what I could get from Ghost as a blogging platform, I decided to move my blog to Ghost - blog.many-monkeys.com - I hope you like it.

Friday, April 3, 2015

Using GMock with Visual Studio CppUnitTestFramework

One of the things I have been a bit disappointed with myself during the development of OpenCover is the lack of unit testing around the C++ code that makes up the profiler. I did toy with GTest and got some decent tests around the instrumentation engine but I was never able to actually test the profiler callbacks, also I found the lack of GTest integration with Visual Studio quite irritating; I know I have been spoilt by ReSharper. Recently however, during handling Fakes through OpenCover, I had an opportunity to work out how to load the profiler using registry free loading and realised that perhaps such testing might be within my reach, what I was missing however was a mocking library and one that I could use with Visual Studio tooling.

Frankly GMock was the only candidate, the commercial alternatives being out as this was for an OSS project, but the instructions all seemed to want to build a number of libraries (64/32 bit Debug/Release) that I would have to statically link to and maintain these builds should the source or build options change. I decided to try a different tack that wouldn't involve building libraries and it has worked out reasonably successful, so I thought it would be worth commenting on here.

Step 1 

Get the latest GMock (1.7.0) library as a zip file and uncompress it somewhere within your repository.

Step 2

From within Visual Studio update the Additional Include Directories to include the following paths

$(SolutionDir)lib\gmock-1.7.0
$(SolutionDir)lib\gmock-1.7.0\include
$(SolutionDir)lib\gmock-1.7.0\gtest
$(SolutionDir)lib\gmock-1.7.0\gtest\include

Step 3

Add the following to your "stdafx.h"

#include "gmock/gmock.h"
#include "gtest/gtest.h"

Step 4

Add the following to your "stdafx.cpp"

// The following lines pull in the real gmock *.cc files.
#include "src/gmock-cardinalities.cc"
#include "src/gmock-internal-utils.cc"
#include "src/gmock-matchers.cc"
#include "src/gmock-spec-builders.cc"
#include "src/gmock.cc"

// The following lines pull in the real gtest *.cc files.
#include "src/gtest.cc"
#include "src/gtest-death-test.cc"
#include "src/gtest-filepath.cc"
#include "src/gtest-port.cc"
#include "src/gtest-printers.cc"
#include "src/gtest-test-part.cc"
#include "src/gtest-typed-test.cc"

Step 5

Now all you need to do is add initialise GMock and you are ready; as I am using the CppUnitTestFramework I do the following.

TEST_MODULE_INITIALIZE(ModuleInitialize)
{
    // enable google mock
    ::testing::GTEST_FLAG(throw_on_failure) = true;
    int argc = 0;
    TCHAR **argv = NULL;
    ::testing::InitGoogleMock(&argc, argv);
}

Now all you need to do is follow the GMock documentation and add some expectations etc you can as I discovered even mock COM objects and have expectations on them e.g.

EXPECT_CALL(*profilerInfo, SetEventMask(EVENT_MASK_WHEN_FAKES))
                .Times(1)
                .WillRepeatedly(Return(S_OK));

Bonus Round

There were a few little niggles however the first of which is that if an expectation fails, the Visual Studio test runner takes a little too long to close down (I suspect this may be something on my machine related to DrWatson). 

The second was that if an expectation did fail I could only initially see the result using DebugView - ugh - however I found a solution at http://www.durwella.com/post/96457792632/extending-microsoft-cppunittestframework which involves using some extra macros, which I added to my "stdafx.h" and voila the results are now available in Visual Studio.

Finally, I found the mocks were not very lightweight and in fact if I left them hooked in caused performance issues however replacing them with an admittedly less useful stub I could avoid this when necessary.

Sunday, February 22, 2015

Happy Birthday OpenCover

Happy Birthday


Today OpenCover is 4 (four) years old, where has the time gone? In that time it has had over 60,000 nuget downloads, been adopted by the SharpDevelop community as the coverage tool for their IDE, and, as I found out the other day, is also being used by the corefx team to supply coverage information on their tests.

Four years ago I started on OpenCover (first commit - not very interesting but a stake in the ground) in order to create a code coverage tool for the .NET platform that could be used by anyone, but especially so that those of us in the open source community could have a tool available to us to help enhance our testing feedback; in the past we have seen some tools go commercial, some just vanish and others just abandoned. I also wanted to share some of the knowledge I had picked up in this area but no longer used in my day-to-day activities and to ensure it remains within the community by making it maintainable and available without restriction.

It took nearly 6 months to get the first beta release and since that time we have added sequence and branch coverage, support for .NET 2 and .NET 4+, 32 and 64 bit support, and even Silverlight. Later features such as coverage by test and hooking into services and IIS support; not everything works as seamlessly as I would like but the community has either lived with it or improved it - which was the outcome I was seeking. Just recently we even added support for Microsoft.Fakes because some people wanted to use OpenCover for coverage with their tests that used Fakes rather than the coverage tool that they already had available; that was an interesting learning exercise, as well due to  some very fortuitous googling.

There even seems to be some movement to make a Mono version of OpenCover which was not something I saw coming but is also quite exciting, especially as Visual Studio now has support for Android and iPhone development, we knew about Xamarin/Mono but actual Visual Studio integration? Who 4 years ago would have seen that one coming ...?

Highlights


One of the highlights of the past few years was starting at my current place of work (MYOB) and then overhearing a conversation within the devops/build team who were discussing the coverage results of this free coverage tool they had found on github, imaging my delight when I realised it was OpenCover they were discussing and in mostly favourable terms; this was the first place I had seen OpenCover being used and it wasn't introduced by me. I even implemented a feature in response to their comments.

Another highlight is seeing that at least two Visual Studio integrations involving OpenCover are currently in play, both of these have been started independently, and though I am currently partly involved with one of them it will be interesting to see how they both progress.

I'd like to thank everyone who has contributed to OpenCover either through direct contribution, suggestions, free stuff (more please) and just using it. Here's to another 4+ interesting years and I wonder what will happen to OpenCover in that time - suggestions?