AOP

Parameter Checking with PostSharp

Guard TowerLast time, I started off my PostSharp series by adding some logging coming in and out of a method. It was very easy to do and it was nice to have a single point of code that wasn’t copy-paste repeated all over the codebase. This time, I want to look at what it might take to check the parameters that come into the method.

As Matt Groves pointed out in the comments of my last post, Phil Haack created something called NullGuard to do the kind of thing that I’m endeavoring to do here. In addition, PostSharp themselves created the ability to do just this very thing with the release of PostSharp 3, but it is only available in the paid editions. You can see an explanation in detail here.

Smart people don’t roll their own code for things that are already “solved problems” (I ranted about this in a recent podcast). However, I’m going to tackle this simple problem a few different ways in order to demonstrate how you can create your own more complex rules with PostSharp.

I created a class called NoNullParamsAttribute.cs and its code is as follows

using PostSharp.Aspects;
using System;
using System.Text;

namespace IntroToAop2
{
    [Serializable] 
    public class NoNullParamsAttribute : OnMethodBoundaryAspect 
    {
        public override void OnEntry(MethodExecutionArgs args)
        {
            var messages = new StringBuilder();

            for (int i = 0; i < args.Arguments.Count; i++)
            {
                if (args.Arguments.GetArgument(i) == null)
                {
                    messages.AppendFormat("Parameter \"{0}\" cannot be null. ", args.Method.GetParameters()[i].Name);
                }
            }

            if (messages.Length > 0)
            {
                throw new ArgumentException(messages.ToString());
            }
        }
    }
}

Now, we can call that above one of our methods from last week like this

[NoNullParams]
public string ReverseString(string input)
{
    var inputArray = input.ToCharArray();
    Array.Reverse(inputArray);
    return new string(inputArray);
}

Now when I call it passing in null, I get an argument exception with the message ‘Parameter “input” cannot be null.’. I could obviously do the same check to make sure that it was not empty, or that all integers were greater than zero, and so on. Of course, the examples I mentioned earlier are much more sophisticated, however today we’ve seen how to iterate over method parameters, get their name, and examine them. Not too bad for a day’s work!

All of the code can be found on my GitHub repo for this series under IntroToAop2.