c00000fd
c00000fd

Reputation: 22327

How to go from one exception handler to another?

The best way to explain my question is with the following pseudo-code:

try
{
    //Do work
}
catch (SqlException ex)
{
    if (ex.Number == -2)
    {
        debugLogSQLTimeout(ex);
    }
    else
    {
        //How to go to 'Exception' handler?
    }
}
catch (Exception ex)
{
    debugLogGeneralException(ex);
}

Upvotes: 0

Views: 130

Answers (3)

Roy Ashbrook
Roy Ashbrook

Reputation: 854

I do not believe there is any way to do this as the catch blocks are in different scopes. There's no way to re-throw without exiting the try block and no way to 'call' the final catch block because it's only triggered during an exception.

I would suggest the same as roman m above and just make the same call. Otherwise you have to do something really bad. Like the below crazy code which you should never ever use but i included because it does something like what you want.

In general I think what you are doing is controlling normal flow via exceptions which isn't recommended. If you are trying to track for timeouts, you should probably just handle that another way.

Note that you could do something like the code below with the insanity of a goto statement, but i included it so no one can forget what a bad idea this is. =)

void Main()
{
    Madness(new NotImplementedException("1")); //our 'special' case we handle
    Madness(new NotImplementedException("2")); //our 'special' case we don't handle
    Madness(new Exception("2")); //some other error
}

void Madness(Exception e){
    Exception myGlobalError;

    try
    {
        throw e;
    }
    catch (NotImplementedException ex)
    {
        if (ex.Message.Equals("1"))
        {
            Console.WriteLine("handle special error");
        }
        else
        {
            myGlobalError = ex;
            Console.WriteLine("going to our crazy handler");
            goto badidea;
        }
    }
    catch (Exception ex)
    {
        myGlobalError = ex;
        Console.WriteLine("going to our crazy handler");
        goto badidea;
    }
    return;

    badidea:
    try{
        throw myGlobalError;
    }
    catch (Exception ex)
    {
        Console.WriteLine("this is crazy!");
    }
}
// Define other methods and classes here

Upvotes: 0

Eric Lloyd
Eric Lloyd

Reputation: 519

The first catch clause that matches is the only one that can possibly run on the same try block.

The best way I can think of to do what you're attempting is to include casts and conditionals in the more general type:

try
{
    //Do work
}
catch (Exception ex)
{
    var sqlEx = ex as SqlException;
    if (sqlEx != null && sqlEx.Number == -2)
    {
        debugLogSQLTimeout(ex);
    }
    else
    {
        debugLogGeneralException(ex);
    }
}

If you find yourself writing this over and over again throughout your data layer, at least take the time to encapsulate it in a method.

Upvotes: 1

Jeremy Thompson
Jeremy Thompson

Reputation: 65702

Exception ex = null;
try
{
    //Do work
}
catch (SqlException sqlEx)
{
    ex = sqlEx;
    if (ex.Number == -2)
    {
       //..
    }
    else
    {
        //..
    }
}
catch (Exception generalEx)
{
  ex = generalEx;
}
finally()
{
  if (ex != null) debugLogGeneralException(ex);
}

Upvotes: 3

Related Questions