August 03 2010

Detecting nested exceptions (because of CSLA)

CSLA is a pretty good middle-tier framework (though not without it’s complexity or problems).  A colleague and I were discussing that for small organisations, it’s just not worth implementing it if you’re not going to be running the factory methods on one server and the executions method on another server…. but that is not what I’m here to talk about!

So my problem with CSLA today is that when I want to invoke an exception from the bowels of an internal method, it is wrapped up nicely in a CSLA defined exception.  This means I can’t catch my exception like this:

try
{
    user = UserCsla.GetById(userId);
}
catch (DataNotFoundException dNFExc) // !!! THIS WON'T WORK !!!
{
    //user not found
    user = new User();
}

I know my exception is in there somewhere, but I don’t want to catch ALL exceptions in case something unexpected happens.  In that case I want the exception to keep bubbling.

My solution is to write an extension method for class Exception, that will recursively plumb the depths of .InnerException and see if it contains a certain type.

Extension Method:

public static class ExceptionExtender
{
    /// 
    /// Recurses Inner Exceptions and returns true if 
    /// the exception type is found in the stack
    /// 
    public static bool Contains(this Exception exception, 
                                Type exceptionType)
    {
        if (exception.GetType().Equals(exceptionType))
        {
            return true;
        }
        if (exception.InnerException != null)
        {
            return exception.InnerException
                               .Contains(exceptionType);
        }
        return false;
    }
}

Using it:

try
{
    user = UserCsla.GetById(userId);
}
catch (Exception exc)
{
    if (exc.Contains(typeof(DataNotFoundException)))
    {
        //user not found
        user = new User();
    }
    else
    {
        throw;
    }
}

Extra Note: I am aware that a better way to consume this data would be to have .GetById(userId) return a null value if the user isn’t found.  The method was created by another developer with that behaviour intentionally, and to consume it, I had to live by its rules.

Comments (View)
blog comments powered by Disqus

Please...

Leave a comment if this has helped or offended you.

StackOverflow Id