Recently, I published this article on copying a class dynamically. I then found that I could use the same approach to clear a class. Here’s the method:
private static void ClearClass<T>(T classToClear)
{
if (classToClear == null)
throw new Exception("Must not specify null parameters");
var properties = classToClear.GetType().GetProperties();
foreach (var p in properties.Where(prop => prop.CanWrite))
{
p.SetValue(classToClear, GetDefault(p.PropertyType));
}
}
/// <summary>
/// Taken from http://stackoverflow.com/questions/474841/dynamically-getting-default-of-a-parameter-type
/// </summary>
/// <param name="type"></param>
/// <returns></returns>
public static object GetDefault(Type type)
{
return type.IsValueType ? Activator.CreateInstance(type) : null;
}
As you can see, I had a little help from Jon Skeet with this one. Once I’d written it, I thought I’d have a play with the IntelliTest feature: if you right click the method and select “Create IntelliTest”, you’re presented with this:
It generated this:
/// <summary>This class contains parameterized unit tests for Program</summary>
[PexClass(typeof(Program))]
[PexAllowedExceptionFromTypeUnderTest(typeof(InvalidOperationException))]
[PexAllowedExceptionFromTypeUnderTest(typeof(ArgumentException), AcceptExceptionSubtypes = true)]
[TestClass]
public partial class ProgramTest
{
/// <summary>Test stub for ClearClass(!!0)</summary>
[PexGenericArguments(typeof(int))]
[PexMethod]
internal void ClearClassTest<T>(T classToClear)
{
Program.ClearClass<T>(classToClear);
// TODO: add assertions to method ProgramTest.ClearClassTest(!!0)
}
}
The interesting thing about this, is that it can’t be found as a test. What actually happens is this creates an intelli-test, which, as far as I can see, you have to right-click on the created test and select “Run Intelli-test”. This then creates you an actual unit test:
It looks something like this:
namespace ConsoleApplication13.Tests
{
public partial class ProgramTest
{
[TestMethod]
[PexGeneratedBy(typeof(ProgramTest))]
public void ClearClassTest861()
{
this.ClearClassTest<int>(0);
}
}
}
That then can be found and run:
Obviously, looking at the unit test, it’s not a particularly good one; it effectively tests that your code doesn’t crash, so it increases your code coverage, but doesn’t really test anything per-se.