skip to main | skip to sidebar
Showing posts with label moles. Show all posts
Showing posts with label moles. Show all posts

Tuesday, April 20, 2010

Disabling Moles Pre-Compilation

One thing about Moles that I've found a bit annoying is that the Mole types always get compiled into an assembly. This is fine when you mole something like mscorlib because it's not going to be changing, but when you mole your own code, the result is that you have a dependency on a binary file that keeps changing over and over. If you check your code into source control, this is a nuisance.

It turns out that if you open a .moles file and add <Compilation Disable="true"/>, Moles won't generate an assembly and will instead put the source directly into your test project. In my opinion, this is much cleaner. Now you don't have binary files to keep track of and fewer assembly references in your test project.

Wednesday, April 7, 2010

Moles and InternalsVisibleTo

The InternalsVisibleTo assembly-level attribute is a pretty cool little bit of wizardry. By adding one (typically to your AssemblyInfo.cs file), you can declare a “friend” assembly that gets access to all types and members marked “internal.” If you’ve ever right clicked an internal type or member in VS and selected “Create Unit Test,” you know that VS will generate this for you. It’s great for unit testing – while some people believe that you should only unit test the external interfaces of your types, I don’t see any reason not to break it down further when you can.

Moles assemblies can take advantage of InternalsVisibleTo as well, but they need their own InternalsVisibleTo attribute in your assembly specifically for them. Fortunately, it’s not too tough.

For unsigned assemblies, giving Moles access to the internals is as simple as creating an InternalsVisibleTo attribute in your AssemblyInfo pointing to the Moles assembly name:

[assembly: InternalsVisibleTo(“MyProject.MyClasses.Moles”)]

An assembly can have more than one InternalsVisibleTo attribute, so you can point one to your test project and one to the Moles assembly.

If your assembly is signed, there are a couple other hoops to jump through. Information floating around on the Internet confuses things a bit, but the fact of the matter is that if the assembly you want to increase visibility to is signed, the friend assembly has to be signed as well, and the InternalsVisibleTo attribute has to include the public key of the friend assembly. Not the public key token, but the entire public key. Unfortunately, the IntelliSense documentation for InternalsVisibleTo has absolutely no reference to this and does not show how to format things properly. The correct format is like so (with an example of a real public key, so as not to confuse you with brackets and other things, and to show you just how long they are):

[assembly: InternalsVisibleTo(“MyProject.MyClasses.MyFriendAssembly, PublicKey=0024000004800000940000000602000000240000525341310004000001000100b3a1f96b163680bfd8f36cd4a2ee94accb680d97d407ed8898abc1710662205878d27c138902bd3a08a19c6b2afacdf95a4de2cbd3b6fd2cc18e08540ad79cdea4ab5e81ea3c8191fbfdb72efa90c6d750224ae05fae6ab9fe1ebc6958423dbb644a36c7019dc8388e925a802e33d1902ed293fd0f420a1dcb4e135cff7ee8c5”)]

But how do you sign a Moles assembly, and how do you get the public key from it? It’s actually pretty simple. If you mole a signed assembly, the Moles assembly will be signed with a key packaged up in the framework and used specifically for this purpose. To get the key, first generate the Moles assembly without trying to use InternalsVisibleTo. Once you’ve got it, open up a Visual Studio command prompt, and do (case sensitive) “sn –Tp MyProject.MyClasses.Moles.dll”. This will spit out the public key, which you can use to create the InternalsVisibleTo attribute on your assembly. Finally, rebuild both projects to regenerate the Moles assembly, and you’re good to go.

Mole Instances and Moling Instance Methods

So far, we’ve seen how to mole static methods and how to stub interfaces and abstract and virtual methods. What’s left? Moling instance methods that can’t be overridden by following the rules. Moles aren’t just for static methods – you can also create mole instances that override methods that normally can’t be overridden and swap them in for the real thing.

Here’s the context for today’s post:
public class Example
{
 MyDependency m_dependency;
 public Example()
 : this(new MyDependency(10))
 {
 }
 public Example(MyDependency dependency)
 {
 m_dependency = dependency;
 }
 public string Execute()
 {
 return "Dependency string is: " + m_dependency.MyDependencyMethod();
 }
}
public class MyDependency
{
 int m_dependencyInt;
 public MyDependency(int myInt)
 {
 m_dependencyInt = myInt;
 }
 public string MyDependencyMethod()
 {
 return "MyInt times 2 = " + m_dependencyInt * 2;
 }
}
Here we’ve got a class, Example, that takes a dependency of a specific type into its constructor. The type specified isn’t an interface, but a concrete, non-abstract type. It’s not sealed (although it could be for purposes of this example), but it doesn’t have any virtual methods, so it can’t be replaced with a stub. Something like this could happen in practice when a developer gets a bright idea about constructor dependency injection, but never ends up finding a need to abstract the type of the dependency out to an interface (in real life, what’s more likely is that the developer would just new up an instance of the dependency right within the class – I’ll get to that soon). We’d like to test Example.Execute isolated from its dependencies, so we create a mole instance in our test and hand that in to the Example constructor instead.
[TestMethod()]
[HostType("Moles")]
public void ExecuteTest()
{
 MMyDependency mole = new MMyDependency
 {
 MyDependencyMethod = () => "Moled method!";
 };
 Example target = new Example(mole);
 string actual = target.Execute();
}
I gave MyDependency a little bit of state to give you something to think about – notice that the moled version of MyDependency has no concept of state. When you mole a class, it loses its “classiness” and becomes nothing more than a collection of methods. If you want to give a mole state, you can store that state within variables inside the test method, and then refer to those variables from within your lambda expressions. This works because of closures (warning: that link goes to a piece written by Jon Skeet, meaning that if you read it and keep exploring his other stuff, you will lose most of your day), one of the most beautiful ideas in all of programmingdom. However, think hard before doing this – it’s likely to be way more than you actually need for purposes of your test. One thing you can do, if you want to put the work in, is use state to make a mole or a stub into a mock, with expectations about what methods will be called and with what parameters.

What if your class under test doesn’t let you inject the dependency? Check the next post for information about how to mole constructors, use a mole type to affect all calls to a given instance method on all instances, and a little bit of insight as to how moles work.

Tuesday, April 6, 2010

Why Use Stubs?

If the code under test is nicely abstracted out, with dependencies represented as interfaces that can be injected, why use stubs generated by Pex/Moles and not just implement and derive test doubles yourself? Because it makes a mess! You end up spinning up new classes for every test to customize the behavior and get what you want. Using stubs generated by moles, you get this nice generic “harness” that you can plug lambda expressions into inline, right in your unit test.

One question I’ve seen on the community forums a couple times is, to paraphrase, “why would I ever use stubs?” Moles are powerful, easy, expressive and global. Why screw around with other tools? The answers in those threads are pretty good, but I’d like to expand on them a little bit. There are three “technical” reasons and one “religious” reason (not to imply it’s only presented by zealots – I just wanted to discriminate between reasons that are scientific in nature and those that are more design-centric).

The easy first reason is “performance”. Moles do runtime code rewriting, whereas stubs are simple derivatives of classes, so moles add a lot of overhead. Additionally, if you’re using Moles, you have to use the Moles host, which also adds overhead. Stubs do not require it. With all that said, I’m not really convinced that this is a solid reason to prefer stubs over moles unless you’re doing a lot of stubbing/moling in a lot of test cases – unit tests will still only take a second or two to run otherwise.

The next, more interesting reason is that there is one important thing stubs can do that moles cannot: provide implementations for interfaces and abstract methods. Moles require that method implementations exist in the first place so you can detour them. If there’s no implementation, you need to create one with a stub.

The last technically-oriented reason is related to deployment. You can use stubs simply by GACing or “binning” the Moles framework assemblies, but using Moles requires that the Moles installer has been run on the machine to install and register the rewriting CLR profiler. If you have a build machine you’re running tests on and you have limitations as to how you can modify it, you may want to avoid using moles.

The “religious” reason is that you should use the simplest possible thing that does the job. If a stub can do the job, use a stub, unless it makes lots of hoops to jump through and using a mole results in fewer hoops. Stubs may use code generation, but they don’t use “magic” and they are built on standard object-oriented principles that are easy to explain. They represent a process that you can easily implement without them (by spinning up new implementations of interfaces and derivations of abstract classes), but they result in less code and easier to read code that’s all in one place.

An interesting corollary: if you find yourself using a lot of moles in a given unit test, it likely means that your code is very tightly coupled to a lot of external dependencies. Perhaps you should consider refactoring a bit so that stubs are a more realistic option.

Stubs!

Stubs are the boring, old-fashioned cousins of moles. They don’t break any rules and don’t do anything you couldn’t technically do yourself. However, this doesn’t mean that they don’t have their place. I’m going to be talking about stubs in this post, largely because I’ve used the word “mole” so much in the last few days that it’s starting to lose meaning!

If you look back to the post about rules for generating moles and stubs, you’ll see that you can only generate stubs for interfaces and for classes that can be derived from and instantiated: this means no sealed classes and no static classes. A stub type by itself is useless – you have to create an instance of it, and then set delegates for methods and set properties on that instance for it to be useful. You can then hand that stub in as a parameter to a constructor for a class under test, or as a parameter for a method under test.

The basic behavior of a stub when you call a method on it is as follows:

1. If a custom delegate has been set for the method, that’s what gets called.
2. If not, and if the CallBase property on the stub is set to true, the base implementation will be called. This only applies to virtual methods that your stub overrides: abstract method declarations and method declarations in interfaces have no implementation.
3. If neither of the above applies, the Behavior of the instance is used to determine the course of action.

Like moles, stubs have behaviors too. They are in the BehavedBehaviors class and there are only a couple: DefaultValue and NotImplemented. These behave just like the behaviors with the same names on moles. Unlike static methods on mole types, the default behavior for a stub instance is NotImplemented, so if you forget to mole an instance method that gets called, your test will fail with an exception. Also, if you want, you can set the BehavedBehaviors.Current property to a given behavior to globally set behaviors for all stubs whose behavior hasn’t been explicitly set.

Stubs seem a lot less powerful than moles, so why would you ever use them? See the next post!

Wednesday, March 31, 2010

How To Get Moles Into Your Test Project

In my last post, I talked about what Moles can do for your testing capabilities. In this one, I’m going to give a quick overview of what you need to do to start using Moles in your project. For this post and most others, I’ll be talking from the viewpoint of Visual Studio 2008 (all of the stuff on the Pex page trumpets VS 2010, but it works fine with 2008) Team Suite, so I’ll be using the VS Team Test unit test tools as opposed to something like NUnit, although Pex and Moles come out of the box with a few switches you can flip to make them friendly to NUnit and a couple other testing frameworks.
Like most things, you’re going to need to install it first. I recommend the full Pex + Moles installer - you can grab it from here. I try to be careful with what I install and avoid installs that make a mess or require a lot of steps, and I can report that the Pex + Moles installer is simple and clean as can be.
Once the installer finishes, fire up VS with your test project. In your test project (as opposed to the project-under-test), do an Add > New Item. You should find a new template called “Moles and Stubs for Testing.” Before you fire away and click OK, there’s a small bit to understand about what adding a .moles file does and what effect the name has.


Running this template will add a .moles file and subfiles to your solution and add two references to your project: one to the newly compiled Moles.dll and another to the Moles framework types A .moles file is a small XML file in your solution that contains configuration for a set of MSBuild tasks that also get added to your project when you add a mole. Most importantly, it points to the assembly that you want to mole. A .moles file only moles a single assembly, so if you want to mole types in multiple assemblies, you’ll need to add multiple moles. The .moles file has three subfiles when viewed in Solution Explorer:
  1. A designer.cs file. To be honest, I have no idea what this does, as it contains nothing but a commented-out Base64 string.
  2. A Moles.xml file. This contains generated documentation for all the mole types generated.
  3. A Moles.dll file. This is a compiled assembly that contains the mole types. When your test project is built, this assembly is generated by MSBuild, and a reference to it is automatically added to your project. If you mole a big assembly, like mscorlib, it can add a good chunk of time to your build process, but it will only rebuild the assembly if the assembly being moled has changed since the last build.

When you add your .moles file, the name you use (minus the .moles part) will be the name of the assembly that it moles by default. It has visibility to everything in the GAC plus everything referenced by the containing project. You can change the assembly by opening the .moles file in an XML editor, but it’s easier to just name it correctly to begin with. One tweaky thing I’ve noticed is that, unlike a lot of other VS template items, you really should explicitly include “.moles” at the end of the filename, otherwise it will get confused if the targeted assembly contains dots in its name.

Just like that, you’re done. You now have access to moles and stubs for all the types in the referenced assembly. Now, what exactly does that mean? Check out the next post for information about how mole and stub types are generated.

Monday, March 29, 2010

Moles!

As I write more of them, I'm finding that these "unit test" things aren't so bad, especially if you write them properly. That means getting rid of your external dependencies - code that's not yours, code that is yours but isn't being tested, networks, file systems, and all that other junk.

If you're working in the ivory tower of Objectorientedland, this is always dead simple: the dependencies of every class you use are abstracted away as interfaces, and concrete implementations of those interfaces are controlled by either the caller, who provides them to the class' constructor, or a dependency-injection framework, which I admittedly haven't messed around with. Your test should provide suitable test doubles of those dependencies.

There are lots of ways of thinking about test doubles - the two most common that I've seen are stubs and mocks. Stubs are little dummy objects with methods that basically do the simplest thing possible to make your test run. For example, if I have an object with a method that takes a DataSet and returns a scalar value, my stub implementation of that method will be a one-liner that just returns the value I'm expecting. Another kind of test double is a mock. A mock performs the same actions as a stub when it comes to the code that's calling it, but it also has "expectations:" you set up a mock to expect method calls with certain parameters in a certain order, because that's what you're expecting your code-under-test to do. If the mock's expectations aren't met, the test fails.

Back to Objectorientedland - parachuting down from the ivory tower and making our way to the swamp of spaghetti code, we see that things aren't always that simple. Sometimes corners are cut, sometimes refactoring never happens, sometimes it's just simpler to use that static filesystem accessor method, and sometimes creating a zillion classes and interfaces to accomplish a simple task (aka "enterprise design") is just overkill.

Enter Moles.

Moles are part of Microsoft Research's new test tool Pex. I'm not going to go into Pex just yet - I'm really excited about it but I haven't explored it fully enough. Both Moles and Pex help you to write better and more complete test cases for your code. Pex does it by "exploring" your code, literally finding ways to take all the branches and break it if possible. Moles gives you a way to easily stub out methods, even methods you shouldn't technically be able to stub out, without writing a ton of code.

I'm going to be writing a bunch of posts about Moles and Pex, but just to get started, I'm going to toss out a perfect use case for Moles: getting around the static File methods. In a properly built OO application, the file system will be abstracted away through a set of classes, abstracted away to interfaces, that can be swapped out so your tests can effectively "fake it." However, we all know that File.Open is way too tasty, and sometimes it's really all that's called for. The problem with File.Open is that you have inexorably chained your code to the filesystem - have fun trying to make a test suite that doesn't refuse to run on any machine but yours without 20 minutes of setup. The whole point of unit tests is that you could be able to click a couple buttons and watch the green checkmarks roll in within seconds.

With Moles, you can literally rewrite File.Open and any other static methods you like, right in your test case, to make them do whatever you want. Check out the following code and the test method for it:

public int SumNumbersFromAFile(string filename)
{
 string fileText = File.ReadAllText(filename);
 string[] numbers = fileText.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
 return numbers.Select((str) => Int32.Parse(str)).Sum();
}
[TestMethod()]
[HostType("Moles")]
public void SumNumbersFromAFileTest()
{
 Class1 target = new Class1();
 string input = "filename";
 string textFromFile = "1, 2, 3, 4";
 MFile.ReadAllTextString = path =>
 {
 Assert.AreEqual(input, path);
 return textFromFile;
 };
 int actual = target.SumNumbersFromAFile(input);
 Assert.AreEqual(10, actual);
}


SumNumbersFromAFile is the method under test. As you can see, it reads the text from a file, expecting to find a list of numbers separated by commas, and sums them. It's a pretty contrived example, and one without a lot of error handling or checking of assumptions, but it does the job for illustrating Moles as I'm doing here.

The test case looks like a pretty standard test case - setup of input and expected results, method call, and an assertion - with the exception of that "MFile" sitting there. MFile is actually the Mole of the static file class. As a mole of a static class, it has a static property for each method. The type of each property is a delegate type that matches the signature of the method being moled. By providing an implementation for the delegate, you are overriding the behavior of the method. When my method under test calls "File.ReadAllTextFromString("filename");", it will call my delegate implementation. The assert in there is a poor man's mock-like expectation: it checks to see if the method was called with the expected parameter. Then it returns my nicely prepared string to execute on.

How does this sorcery work? The key is the [HostType("Moles")] attribute at the top. This causes the test to run in a host that can overwrite the compiled IL as it executes. The debugger behaves just a little bit funny when you debug inside a Moles-hosted test - it looks like it's jumping around a bit but it actually is working properly - but if you step through SumNumbersFromAFile you can see it call out to my Mole delegate to get my pre-prepared string, bypassing the file system entirely.

You can use Moles to bypass most anything, and also included is a simple little stubbing framework for doing regular ol' stubs of interfaces, abstract classes and classes with virtual methods. For stuff where a regular stub won't cut it, you use a mole.

In the coming weeks I'll be posting some more about how to actually get Pex and Moles into your test project, neat examples of how to use Moles and stubs, and how to do things like mole constructor methods, create mole instances (for classes that can't be stubbed because they're sealed or have no virtual methods), and create nested stubs.
Subscribe to: Comments (Atom)
 

AltStyle によって変換されたページ (->オリジナル) /