C# Web API控制器中的异常处理和引发自定义错误消息
在我的一个项目中,我正在使用具有某种SOA架构的Web API。在控制器中,我希望捕获异常(由存储库引发)并返回C# Web API控制器中的异常处理和引发自定义错误消息,c#,asp.net-web-api,exception-handling,soa,C#,Asp.net Web Api,Exception Handling,Soa,在我的一个项目中,我正在使用具有某种SOA架构的Web API。在控制器中,我希望捕获异常(由存储库引发)并返回HttpResposeMessage 我想要的是应该有一个继承ApicController的BaseController(类BaseController:ApicController)并且我的每个控制器都应该由baseController继承,例如类TaskController:baseController,如果我的控制器中发生任何异常,那么它应该由baseController处理。
HttpResposeMessage
我想要的是应该有一个继承ApicController的BaseController(
类BaseController:ApicController
)并且我的每个控制器都应该由baseController继承,例如
类TaskController:baseController
,如果我的控制器中发生任何异常,那么它应该由baseController
处理。
演示:以下是VS解决方案中的项目:(项目结构) 代码: XYZ.模型
public class Error
{
public string Code { get; set; }
public string Message { get; set; }
}
XYZ.异常
// To create the custom exception as per our need
public class BaseException : Exception
{
private Error _error;
public Error Error
{
get { return _error; }
}
public BaseException()
{
_error = new Error();
}
public void SetErrorCode(string code)
{
_error.Code = code;
}
public void SetErrorMessage(string message)
{
_error.Message = message;
}
}
public class TaskNotFoundException : BaseException
{
public TaskNotFoundException()
{
string errorCode = "T0001";
base.SetErrorCode(errorCode);
base.SetErrorMessage((new ExceptionMessage()).GetExceptionMessage(errorCode));
}
}
存储库
public Task UpdateTaskDetails(Task task)
{
try
{
//--Task updating logic--//
}
catch (Exception ex)
{
throw new TaskUpdateFailedException();
}
return task;
}
XYZ.WebServices
public class BaseController : ApiController
{
public HttpResponseMessage CreateResponseMessage()
{
try
{
GetTasksByUserIdAndProjectId(new TaskQuery());
}
catch(BaseException exception)
{
return Request.CreateResponse(HttpStatusCode.InternalServerError, exception.Error);
}
}
public virtual List<Task> GetTasksByUserIdAndProjectId(TaskQuery query)
{
Console.WriteLine("I can be overridden");
}
}
public class TaskController : BaseController
{
[HttpPost]
public override List<Task> GetTasksByUserIdAndProjectId(TaskQuery query)
{
return _taskRepo.GetTasksByUserIdAndProjectId(query.UserId, query.ProjectId);
}
}
公共类BaseController:ApiController
{
公共HttpResponseMessage CreateResponseMessage()
{
尝试
{
getTaskByUserIDandProjectId(新任务查询());
}
catch(BaseException异常)
{
return Request.CreateResponse(HttpStatusCode.InternalServerError,exception.Error);
}
}
公共虚拟列表GetTaskByUserId和ProjectId(任务查询)
{
Console.WriteLine(“我可以被覆盖”);
}
}
公共类TaskController:BaseController
{
[HttpPost]
公共覆盖列表GetTaskByUserId和ProjectId(任务查询)
{
返回_taskRepo.gettasksbyuserid和ProjectId(query.UserId,query.ProjectId);
}
}
在TaskController
中,如果在gettasksbyuserid和projectid
方法中发生任何异常,它应该将异常抛出到BaseController CreateReponseMessage()
中,并在那里将HttpResponseMessage
返回给客户端。注意:在每个控制器中都有多个Get/Put/Post方法,因此不可能在
BaseController
中声明所有方法(web服务方法)来捕获项目当前结构中的子类异常。
在我的项目中,有没有更好的方法来处理Web API中的异常?我们使用的异常过滤器如下所示: 首先,我们创建自己的异常:
public class UserFriendlyException: Exception
{
public UserFriendlyException(string message) : base(message) { }
public UserFriendlyException(string message, Exception innerException) : base(message, innerException) { }
}
然后我们创建一个过滤器:
public class UserFriendlyExceptionFilterAttribute: ExceptionFilterAttribute
{
public override void OnException(HttpActionExecutedContext context)
{
var friendlyException = context.Exception as UserFriendlyException;
if (friendlyException != null)
{
context.Response = context.Request.CreateResponse(HttpStatusCode.BadRequest, new {Message = friendlyException.Message});
}
}
}
最后,在WebApi的配置中,我们添加了这个过滤器
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
...
config.Filters.Add(new UserFriendlyExceptionFilterAttribute());
...
}
}
使用此解决方案,您可以在代码中的任何位置抛出UserFriendlyException,并且响应将根据筛选器进行。我们使用的异常筛选器如下所示: 首先,我们创建自己的异常:
public class UserFriendlyException: Exception
{
public UserFriendlyException(string message) : base(message) { }
public UserFriendlyException(string message, Exception innerException) : base(message, innerException) { }
}
然后我们创建一个过滤器:
public class UserFriendlyExceptionFilterAttribute: ExceptionFilterAttribute
{
public override void OnException(HttpActionExecutedContext context)
{
var friendlyException = context.Exception as UserFriendlyException;
if (friendlyException != null)
{
context.Response = context.Request.CreateResponse(HttpStatusCode.BadRequest, new {Message = friendlyException.Message});
}
}
}
最后,在WebApi的配置中,我们添加了这个过滤器
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
...
config.Filters.Add(new UserFriendlyExceptionFilterAttribute());
...
}
}
使用此解决方案,您可以在代码中的任何位置抛出UserFriendlyException,响应将根据筛选器而定。使用异常筛选器可以更好地完成此操作。@Nkosi,感谢您的建议,我已经实现了异常筛选器,它工作正常。但我还有一个问题“我们可以在异常过滤器中处理一些验证失败错误之类的事情吗?因为验证失败不是异常,但我希望它在一个普通类中处理。”使用异常过滤器可以更好地做到这一点。@Nkosi,谢谢你的建议,我已经实现了异常过滤器,它工作正常。但我还有一个问题“我们能在异常过滤器中处理一些验证失败错误吗?因为验证失败不是异常,但我希望它在一个普通类中处理。”谢谢你的回答,我已经实现了异常过滤器,它工作得很好。但我还有一个问题“我们能在异常过滤器中处理一些验证失败错误吗?因为验证失败不是异常,但我希望它在一个普通类中处理。”。谢谢你的回答,我已经实现了异常过滤器,它工作得很好。但我还有一个问题,“我们可以在异常过滤器中处理一些验证失败错误之类的事情吗?因为验证失败不是异常,但我希望它在一个公共类中处理。”。