-
Notifications
You must be signed in to change notification settings - Fork 101
Closed
Description
Current implementation with BubbleExceptionContainer
have issue of changing original stacktrace.
Consider following code. Semantically it's identical to current behavior - if exception is throw, store it to some field and throw it elsewhere.
void ThrowSomeException() => throw new InvalidOperationException();
void StoreAndThrowExample()
{
try
{
try
{
ThrowSomeException();
}
catch (Exception ex)
{
var storedEx = ex;
throw ex;
}
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
}
Result of invoking StoreAndThrowExample
is
System.InvalidOperationException: Operation is not valid due to the current state of the object.
at Program.<<Main>$>g__StoreAndThrowExample|0_2()
Notice that original source is not listed in stacktrace.
Now look at this method that uses ExceptionDispatchInfo
:
void ExceptionDispatchInfoExample()
{
try
{
try
{
ThrowSomeException();
}
catch (Exception ex)
{
var exInfo = ExceptionDispatchInfo.Capture(ex);
exInfo.Throw();
}
}
catch (Exception ex)
{
Console.WriteLine(ex);
}
}
which produces following stacktrace:
System.InvalidOperationException: Operation is not valid due to the current state of the object.
at Program.<<Main>$>g__ThrowSomeException|0_0()
at Program.<<Main>$>g__ExceptionDispatchInfoExample|0_1()
--- End of stack trace from previous location ---
at Program.<<Main>$>g__ExceptionDispatchInfoExample|0_1()
This approach is used in async-await