首页 > 解决方案 > 使用默认 {controller}/{id} 路由和 {controller}/{action}/{id} 路由时与路由冲突

问题描述

我有以下路线设置;

RouteTable.Routes.MapHttpRoute(
   name: "ActionApi",
   routeTemplate: "api/{controller}/{action}/{id}",
   defaults: new { id = RouteParameter.Optional });

RouteTable.Routes.MapHttpRoute(
    name: "DefaultApi",
    routeTemplate: "api/{controller}/{id}",
    defaults: new { id = System.Web.Http.RouteParameter.Optional },
    constraints: null,
    handler: new WebApiMessageHandler(GlobalConfiguration.Configuration));

以及以下控制器设置;

public class GetFileController : ApiController
{
    [HttpGet]
    public HttpResponseMessage Get(string id)
    {
        return Request.CreateResponse(HttpStatusCode.OK);
    }
}

我在这里遇到的问题是这个网址

/api/GetFile/id_is_a_string

返回此错误;

<Error>
    <Message>
        No HTTP resource was found that matches the request URI /api/GetFile/id_is_a_string.
    </Message>
    <MessageDetail>
        No action was found on the controller 'GetFile' that matches the name 'id_is_a_string'.
    </MessageDetail>
</Error>

有没有办法让它不认为字符串参数实际上是动作名称?

我知道我可以将我的请求 URL 更改为;

/api/GetFile?id=id_is_a_string

但是这种路由更改会影响我已经设置的许多其他控制器,并且真的不希望通过一切来切换它以以这种方式发送请求。

如果我重新排序路由,它似乎可以正常工作,但是对于我理想情况下希望在其中包含多个端点的新控制器,我会收到此错误;

ExceptionMessage=Multiple actions were found that match the request:

新控制器

public class GettingThingsController : ApiController
    {

        [HttpPost]
        public IHttpActionResult GetPeople()
        {
             return Ok();
        }

        [HttpPost]
        public IHttpActionResult GetProducts()
        {
            return Ok();
        }
    }

反正有没有达到我所需要的?!

标签: asp.net-mvcasp.net-web-apiasp.net-mvc-routing

解决方案


您可以尝试使用 Regex 指定参数:

routeTemplate: "api/{controller}/{action:regex([a-z]{1}[a-z0-9_]+)}/{id:regex([0-9]+)}",

routeTemplate: "api/{controller}/{id:regex([0-9]+)}",

这些正则表达式在Route属性中起作用。您可以在RouteTable映射中对其进行测试。


推荐阅读