在.NET Core 3.1 Web API中按查询参数处理多个端点 [英] Handle multiple endpoints in .NET Core 3.1 Web API by Query Params

查看:68
本文介绍了在.NET Core 3.1 Web API中按查询参数处理多个端点的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在将控制器从.NET Framework迁移到.NET Core,并希望与以前版本的API调用兼容。我在处理来自查询参数的多个路由时遇到问题。

我的示例控制器:

[Route("/api/[controller]")]
[Route("/api/[controller]/[action]")]
public class StaticFileController : ControllerBase
{
    [HttpGet("{name}")]
    public HttpResponseMessage GetByName(string name)
    {
    }

    [HttpGet]
    public IActionResult Get()
    {
    }
}

调用api/StaticFile?name=someFunnyName将引导我执行Get()操作,而不是预期的GetByName(string name)

我要实现的目标:

  • 调用getapi/StaticFile->;转到Get()操作
  • 调用GET api/StaticFile?name=someFunnyName->;转到GetByName()操作

我的app.UseEndpoints()发件人Startup.cs只有以下几行:

endpoints.MapControllers();
endpoints.MapDefaultControllerRoute();

如果我在任何地方都使用[HttpGet]并添加([FromQuery] string name),则会得到AmbiguousMatchException: The request matched multiple endpoints

感谢您抽出时间帮助我(也可能帮助其他人)

推荐答案

我要实现的目标:

  • 调用Get API/StaticFile->;转到get()操作
  • 调用Get API/StaticFile?Name=omeFunnyName->;转到GetByName()操作

要实现基于查询字符串将请求与预期操作匹配的上述要求,您可以尝试实现自定义ActionMethodSelectorAttribute并将其应用于您的操作,如下所示。

[AttributeUsage(AttributeTargets.Method, AllowMultiple = true)]
public class QueryStringConstraintAttribute : ActionMethodSelectorAttribute
{
    public string QueryStingName { get; set; }
    public bool CanPass { get; set; }
    public QueryStringConstraintAttribute(string qname, bool canpass)
    {
        QueryStingName = qname;
        CanPass = canpass;
    }
    public override bool IsValidForRequest(RouteContext routeContext, ActionDescriptor action)
    {
        StringValues value;

        routeContext.HttpContext.Request.Query.TryGetValue(QueryStingName, out value);

        if (QueryStingName == "" && CanPass)
        {
            return true;
        }
        else
        {
            if (CanPass)
            {
                return !StringValues.IsNullOrEmpty(value);
            }

            return StringValues.IsNullOrEmpty(value);
        }
    }
}

应用于操作

[Route("api/[controller]")]
[ApiController]
public class StaticFileController : ControllerBase
{
    [HttpGet]
    [QueryStringConstraint("name", true)]
    [QueryStringConstraint("", false)]
    public IActionResult GetByName(string name)
    {
        return Ok("From `GetByName` Action");
    }

    [HttpGet]
    [QueryStringConstraint("name", false)]
    [QueryStringConstraint("", true)]
    public IActionResult Get()
    {
        return Ok("From `Get` Action");
    }
}

测试结果

这篇关于在.NET Core 3.1 Web API中按查询参数处理多个端点的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆