Best way to check for inner exception?

老子叫甜甜 提交于 2020-01-09 04:13:40

问题


I know sometimes innerException is null

So the following might fail:

 repEvent.InnerException = ex.InnerException.Message; 

Is there a quick ternary way to check if innerException is null or not?


回答1:


Is this what you are looking for?

String innerMessage = (ex.InnerException != null) 
                      ? ex.InnerException.Message
                      : "";



回答2:


Great answers so far. On a similar, but different note, sometimes there is more than one level of nested exceptions. If you want to get the root exception that was originally thrown, no matter how deep, you might try this:

public static class ExceptionExtensions
{
    public static Exception GetOriginalException(this Exception ex)
    {
        if (ex.InnerException == null) return ex;

        return ex.InnerException.GetOriginalException();
    }
}

And in use:

repEvent.InnerException = ex.GetOriginalException();



回答3:


That's funny, I can't find anything wrong with Exception.GetBaseException()?

repEvent.InnerException = ex.GetBaseException().Message;



回答4:


The simplest solution is to use a basic conditional expression:

repEvent.InnerException = ex.InnerException == null ? 
    null : ex.InnerException.Message;



回答5:


Why so much recursion in these answers?

public static class ExceptionExtensions
{
    public static Exception GetOriginalException(this Exception ex)
    {
        while(ex.InnerException != null)ex = ex.InnerException;
        return ex;
    }
}

Seems like a much more straight forward way to implement this.




回答6:


Its an old question but for future readers:

In addition to the answers already posted I think the correct way to do this (when you can have more than one InnerException) is Exception.GetBaseException Method

If you want the exception instance you should do this:

repEvent.InnerException = ex.GetBaseException();

If you are only looking for the message this way:

repEvent.InnerException = ex.GetBaseException().Message;



回答7:


With C# 6.0 you can use:

string message = exception.InnerException?.Message ?? "";

This line of code is similar to:

string message = exception.InnerException == null ? "" : exception.InnerException.Message.

https://msdn.microsoft.com/en-us/library/ty67wk28.aspx

http://blogs.msdn.com/b/jerrynixon/archive/2014/02/26/at-last-c-is-getting-sometimes-called-the-safe-navigation-operator.aspx




回答8:


Sometimes also InnerException has an InnerException, so you can use a recursive function for it:

public string GetInnerException(Exception ex)
{
     if (ex.InnerException != null)
     {
        return string.Format("{0} > {1} ", ex.InnerException.Message, GetInnerException(ex.InnerException));
     }
   return string.Empty;
}



回答9:


With C# 6.0 you can do it in one line.

repEvent.InnerException = ex.InnerException?.Message; 

for other feature of C# 6.0 click here




回答10:


With this code you will be sure that you did't lose any inner exception messages

catch (Exception exception)
{
   Logger.Error(exception.Message);
   while (exception.InnerException != null)
   {
       exception = exception.InnerException;
       Logger.Error(exception);
   }
}



回答11:


Yes:

if (ex.InnerException == null) {
    // then it's null
}



回答12:


Here is another possible implementation that appends the messages and stack traces so we get them full:

private static Tuple<string, string> GetFullExceptionMessageAndStackTrace(Exception exception)
{
    if (exception.InnerException == null)
    {
        if (exception.GetType() != typeof(ArgumentException))
        {
            return new Tuple<string, string>(exception.Message, exception.StackTrace);
        }
        string argumentName = ((ArgumentException)exception).ParamName;
        return new Tuple<string, string>(String.Format("{0} With null argument named '{1}'.", exception.Message, argumentName ), exception.StackTrace);
    }
    Tuple<string, string> innerExceptionInfo = GetFullExceptionMessageAndStackTrace(exception.InnerException);
    return new Tuple<string, string>(
    String.Format("{0}{1}{2}", innerExceptionInfo.Item1, Environment.NewLine, exception.Message),
    String.Format("{0}{1}{2}", innerExceptionInfo.Item2, Environment.NewLine, exception.StackTrace));
}


[Fact]
public void RecursiveExtractingOfExceptionInformationOk()
{
    // Arrange
    Exception executionException = null;
    var iExLevelTwo = new NullReferenceException("The test parameter is null");
    var iExLevelOne = new ArgumentException("Some test meesage", "myStringParamName", iExLevelTwo);
    var ex = new Exception("Some higher level message",iExLevelOne);

    // Act 
    var exMsgAndStackTrace = new Tuple<string, string>("none","none");
    try
    {
        exMsgAndStackTrace = GetFullExceptionMessageAndStackTrace(ex);
    }
    catch (Exception exception)
    {
        executionException = exception;
    }

    // Assert
    Assert.Null(executionException);

    Assert.True(exMsgAndStackTrace.Item1.Contains("The test parameter is null"));
    Assert.True(exMsgAndStackTrace.Item1.Contains("Some test meesage"));
    Assert.True(exMsgAndStackTrace.Item1.Contains("Some higher level message"));
    Assert.True(exMsgAndStackTrace.Item1.Contains("myStringParamName"));

    Assert.True(!string.IsNullOrEmpty(exMsgAndStackTrace.Item2));

    Console.WriteLine(exMsgAndStackTrace.Item1);
    Console.WriteLine(exMsgAndStackTrace.Item2);
}



回答13:


class MyException : Exception
{
    private const string AMP = "\r\nInnerException: ";
    public override string Message
    {
        get
        {
            return this.InnerException != null ? base.Message + AMP + this.InnerException.Message : base.Message;
        }
    }

    public override string StackTrace
    {
        get
        {
            return this.InnerException != null ? base.StackTrace + AMP + this.InnerException.StackTrace : base.StackTrace;
        }
    }
}



回答14:


It is possible to use an exception filter to get more precise aiming.

catch (Exception ex) when (ex.InnerException != null) {...}

Please find more details here



来源:https://stackoverflow.com/questions/1456563/best-way-to-check-for-inner-exception

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!