Net6最小API中的自定义结果



在ASP中。NET Core 5我有一个自定义的操作结果如下:

public class ErrorResult : ActionResult {
private readonly IList<Error> _errors;
public ErrorResult(IList<Error> errors) {
_errors = errors;
}
public override async Task ExecuteResultAsync(ActionContext context) {
// Code that creates Response
await result.ExecuteResultAsync(context);
}
}

然后在控制器操作上,我会有:

return new ErrorResult(errors);

如何在NET 6 Minimal API中执行类似操作?

我一直在研究它,我认为我应该实现IResult。

但我不确定这是否是解决方案或如何做到这一点

我最近一直在使用最小API,并致力于全局异常处理。以下是我到目前为止的想法。

  1. 创建IResult的类实现
  • 创建一个构造函数,该构造函数将接受您希望进入IResult响应的详细信息的参数。APIErrorDetails是我的一个自定义实现,类似于MVC中ProblemDetails中的内容。无论您的需求是什么,方法实现都是开放的
public class ExceptionAllResult : IResult
{
private readonly ApiErrorDetails _details;
public ExceptionAllResult(ApiErrorDetails details)
{
_details = details;
}
public async Task ExecuteAsync(HttpContext httpContext)
{
var jsonDetails = JsonSerializer.Serialize(_details);
httpContext.Response.ContentType = MediaTypeNames.Application.Json;
httpContext.Response.ContentLength = Encoding.UTF8.GetByteCount(jsonDetails);
httpContext.Response.StatusCode = _details.StatusCode;
await httpContext.Response.WriteAsync(jsonDetails);
}
}
  1. 在Program.cs文件中返回异常处理中间件的结果

app.UseExceptionHandler(
x =>
{

x.Run(
async context =>
{
// https://learn.microsoft.com/en-us/aspnet/core/fundamentals/error-handling?view=aspnetcore-6.0
var exceptionFeature = context.Features.Get<IExceptionHandlerPathFeature>();
// Whatever you want for null handling
if (exceptionFeature is null) throw new Exception(); 
// My result service for creating my API details from the HTTP context and exception. This returns the Result class seen in the code snippet above
var result = resultService.GetErrorResponse(exceptionFeature.Error, context);
await result.ExecuteAsync(context); // returns the custom result
});
}
);

如果您仍然想使用MVC(模型-视图-控制器(,您仍然可以使用Custom ActionResult。

如果您只想使用MinimalAPI来执行响应,那么您必须实现IResult、Task<IResult>ValueTask<IResult>

app.MapGet("/hello", () => Results.Ok(new { Message = "Hello World" }));

以下示例使用内置的结果类型来自定义响应:

app.MapGet("/api/todoitems/{id}", async (int id, TodoDb db) =>
await db.Todos.FindAsync(id) 
is Todo todo
? Results.Ok(todo) 
: Results.NotFound())
.Produces<Todo>(StatusCodes.Status200OK)
.Produces(StatusCodes.Status404NotFound);

您可以在此处找到更多IResult实现示例:https://github.com/dotnet/aspnetcore/tree/main/src/Http/Http.Results/src

链接:最小API概述|Microsoft Docs

最新更新