在一个位置将自定义异常映射到HTTP异常



在我的.NET Core Web API项目中,许多控制器端点都有类似以下示例的代码

public async Task<ActionResult<User>> UpdateUserUsernameAsync(/* DTOs */)
{
try
{
User user = null; // Update user here

return Ok(user);
}
catch (EntityNotFoundException entityNotFoundException) // map not found to 404
{
return NotFound(entityNotFoundException.Message);
}
catch (EntityAlreadyExistsException entityAlreadyExistsException) // map duplicate name to 409
{
return Conflict(entityAlreadyExistsException.Message);
}
catch (Exception exception) // map any other errors to 500
{
return new StatusCodeResult(StatusCodes.Status500InternalServerError);
}
}

我想为控制器创建一个映射,在将异常发送回客户端之前捕获异常并将其映射到HTTP响应。

4年前也提出过类似的问题

ASP.NET核心Web API异常处理

在NestJs中,可以通过扩展基类来定义自己的映射,例如

export class MyCustomException extends HttpException {
constructor() {
super('My custom error message', HttpStatus.FORBIDDEN);
}
}

从这里拍摄https://docs.nestjs.com/exception-filters#custom-例外

所以基本上,我想定义映射类,看起来像这个示例代码(这只是显示了我的伪实现(

// Map MyCustomException to NotFound
public class MyCustomExceptionMapping<TCustomException> : IExceptionMapping<TCustomException>
{
public ActionResult Map(TCustomException exception)
{
return NotFound(exception.Message);
}
}

接下来我可以将控制器端点方法清理到

public async Task<ActionResult<User>> UpdateUserUsernameAsync(/* DTOs */)
{
User user = null; // Update user here
return Ok(user);
}

每当抛出异常时,API都会试图找到正确的映射接口。否则,它会发回500。

定义这样的映射并避免项目中每个异常都出现巨大的切换情况,这将是一件很好的事情。

这样的东西存在吗?上一个问题的公认答案仍然是最新的吗?

使用异常过滤器当控制器抛出异常时会调用它,并且您可以定义自定义响应。Microsoft文档

public class MyExceptionFilter : IExceptionFilter
{
public void OnException(ExceptionContext context)
{
HttpStatusCode status;
var message = "";
var exceptionType = context.Exception.GetType();
if (exceptionType is EntityNotFoundException)
{
status = HttpStatusCode.NotFound;
message = context.Exception.Message;
}
else if (exceptionType is EntityAlreadyExistsException)
{
status = HttpStatusCode.Conflict;
message = context.Exception.Message;
}
else
{
status = HttpStatusCode.InternalServerError;
message = "Internal Server Error.";
}
//You can enable logging error
context.ExceptionHandled = true;
HttpResponse response = context.HttpContext.Response;
response.StatusCode = (int)status;
response.ContentType = "application/json";
context.Result = new ObjectResult(new ApiResponse { Message = message, Data = null });
}
}

要在所有控制器上使用筛选器,您必须在Startup.cs 的ConfigureServices方法中注册它

services.AddMvc(config =>
{
config.Filters.Add(typeof(MyExceptionFilter));
})

最新更新