I'm using WebApi
. I have a custom ActionFilter
on my base controller and a custom ExceptionFilter
added globally. Both are inherited from the associated FilterAttributes in the System.Web.Http.Filters
namespace, not the mvc versions.
I've been getting an exception thrown from a private method within one of my services, this method is what resharper calls a method group, when it's used within a Linq statement (in this case a select
).
public IEnumerable<Foo> GetFoos()
{
IEnumerable<Bar> bars = _work.BarRepository.GetAll();
//throw new Exception("I'm visible to the filters");
IEnumerable<Foo> foos = bars.Select(MakeFooFromBar);
return foos;
}
private Foo MakeFooFromBar(Bar bar)
{
// an exception is being thrown here
// which is not being caught by the filers
throw new Exception("I am invisible to the filters");
}
This exception is not being caught by either filter (see filters below). My action filter says there was no exception and my exception filter is never hit. If I throw an exception prior to the Linq select (the one I've commented out), then the exception is caught as expected.
Using fiddler, what I end up with is this:
{
"message":"An error has occurred.",
"exceptionMessage":"The 'ObjectContent`1' type failed to serialize the response body for content type 'application/json; charset=utf-8'.",
"exceptionType":"System.InvalidOperationException",
"stackTrace":null,
"innerException":{
"message":"An error has occurred.",
"exceptionMessage":"I am invisible to the filters",
"exceptionType":"System.Exception",
"stackTrace":""
}
}
A portion of my action filter:
public override void OnActionExecuted(HttpActionExecutedContext actionExecutedContext)
{
Exception exception = actionExecutedContext.Exception;
if (exception == null)
{
// do things
}
else
{
// do some other things
}
}
and a portion of my exception filter:
public override void OnException(HttpActionExecutedContext actionExecutedContext)
{
// return early on certain kinds of exceptions...
_loggedErrorService.Log(actionExecutedContext.Exception);
}
From the documentation
You can customize how Web API handles exceptions by writing an exception filter. An exception filter is executed when a controller method throws any unhandled exception[...]
The problem is that if you return an IEnumerable<T>
from your WebAPI method, the error will occur during serialization, when the IEnumerable<T>
is iterated. This is the standard behavior of Select
(and most other query operators) it only call the method passed to it upon iteration ( MakeFooFromBar
in this case), so the exception will not be thrown when you invoke Select
but much later.
You could add a .ToList
to cause the exception to occur inside your method.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.