我正在开发一个WebAPI 2项目,并且我实现了一个全局错误过滤器属性,如下所示:
public class MyExceptionFilterAttribute: ExceptionFilterAttribute
{
public override void OnException(HttpActionExecuteContext context)
{
if (context.Exception is MyException)
{
// Handle MyException
}
else if (context.Exception is UnauthorizedAccessException)
{
// Handle UnauthorizedAccessException
}
}
}
当我调用外部API并收到错误响应时,我抛出MyException
。
var httpResponseMessage = _httpClient.GetAsync(request).Result;
if (!httpResponseMessage.IsSuccessStatusCode)
{
var message = "Error calling external API";
var except = new MyException(message);
throw except;
}
我想将API返回的状态代码作为MyException
的一部分传递给全局错误过滤器。我的第一次尝试是将状态代码添加为MyException
的属性。
public class MyException : Exception
{
public HttpStatusCode statusCode;
public MyException() : base() { }
public MyException(string message, HttpStatusCode statusCode) : base(message)
{
this.statusCode = statusCode;
}
}
在抛出异常中:
var httpResponseMessage = _httpClient.GetAsync(request).Result;
if (!httpResponseMessage.IsSuccessStatusCode)
{
var message = "Error calling external API";
var except = new MyException(message, httpResponseMessage.StatusCode);
throw except;
}
然后在我的过滤器中,我将context.Exception
投回到MyException
并尝试访问该属性,但该属性始终以null
的形式返回。
var ex = context.Exception as MyException;
var code = ex.statusCode; // Always comes back as null
我的第二次尝试是将状态代码添加到Data
继承自MyException
的{{1}}媒体资源。
Exception
但是,当我尝试在过滤器中访问它时,var httpResponseMessage = _httpClient.GetAsync(request).Result;
if (!httpResponseMessage.IsSuccessStatusCode)
{
var message = "Error calling external API";
var except = new MyException(message);
except.Data.add("status", httpResponseMessage.StatusCode);
throw except;
}
没有密钥。我知道我可以在我的异常消息中包含状态代码,然后在过滤器中解析它,但我宁愿不这样做,因为我认为它是错误的解决方案。如何将状态代码提供给我的异常过滤器,以便在处理异常时可以使用它?
答案 0 :(得分:0)
异常可能会在调用堆栈中被包含在更高的位置。然后它将处于内部异常中。您可以迭代所有内部异常以查看它们中是否有任何异常,但访问属性的代码应该按预期工作。
var ex = context.Exception;
while (ex != null)
{
if (ex is MyException)
{
// Do work
break;
}
ex = ex.InnerException;
}