261

当我尝试使用 2 个“获取”方法时,我不断收到此错误

找到多个与请求匹配的操作:webapi

我一直在寻找关于堆栈的其他类似问题,但我不明白。

我有 2 个不同的名称并使用“HttpGet”属性

[HttpGet]
public HttpResponseMessage Summary(MyVm vm)
{
    return null;
}

[HttpGet]
public HttpResponseMessage FullDetails()
{
    return null;
}
4

18 回答 18

524

您的路线图在WebApiConfig.cs中可能是这样的:

routes.MapHttpRoute(
name: "API Default",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional });

但是为了使用相同的 http 方法进行多个操作,您需要通过如下路由向 webapi 提供更多信息:

routes.MapHttpRoute(
name: "API Default",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional });

请注意, routeTemplate 现在包含一个操作。更多信息在这里:http ://www.asp.net/web-api/overview/web-api-routing-and-actions/routing-in-aspnet-web-api

更新:

好吧,现在我想我明白了你在这里追求的是什么:

也许您不需要 action url 参数,应该以另一种方式描述您所追求的内容。既然您说这些方法从同一实体返回数据,那么只需让参数为您进行描述。

例如,您的两种方法可以变成:

public HttpResponseMessage Get()
{
    return null;
}

public HttpResponseMessage Get(MyVm vm)
{
    return null;
}

你在 MyVm 对象中传递什么样的数据?如果您只能通过 URI 传递变量,我建议您走这条路线。否则,您需要在请求的正文中发送对象,并且在执行 GET 时这不是您的 HTTP(尽管它有效,只需在 MyVm 前面使用 [FromBody])。

希望这说明您可以在单个控制器中拥有多个 GET 方法,而无需使用操作名称甚至 [HttpGet] 属性。

于 2013-01-26T06:48:24.063 回答
77

从 Web API 2 开始更新。

在您的 WebApiConfig.cs 文件中使用此 API 配置:

public static void Register(HttpConfiguration config)
{
    //// Web API routes
    config.MapHttpAttributeRoutes(); //Don't miss this

    config.Routes.MapHttpRoute(
        name: "DefaultApi",
        routeTemplate: "api/{controller}/{id}",
        defaults: new { id = System.Web.Http.RouteParameter.Optional }
    );
}

你可以像这样路由我们的控制器:

[Route("api/ControllerName/Summary")]
[HttpGet]
public HttpResponseMessage Summary(MyVm vm)
{
    return null;
}

[Route("api/ControllerName/FullDetails")]
[HttpGet]
public HttpResponseMessage FullDetails()
{
    return null;
}

其中 ControllerName 是您的控制器的名称(没有“控制器”)。这将允许您使用上面详述的路线获取每个操作。

进一步阅读:http ://www.asp.net/web-api/overview/web-api-routing-and-actions/attribute-routing-in-web-api-2

于 2016-01-21T21:10:44.353 回答
15

在 Web API(默认情况下)中,方法是根据HTTP 方法和路由值的组合选择的。

MyVm看起来像一个复杂的对象,由格式化程序从正文中读取,因此您在路由数据方面有两个相同的方法(因为它们都没有来自路由的任何参数) - 这使得调度程序 ( IHttpActionSelector) 无法匹配适当的.

您需要通过查询字符串或路由参数来区分它们以解决歧义。

于 2013-01-26T15:45:43.570 回答
14

经过大量的网络搜索并尝试找到最适合路由图的表格,如果找到以下内容

config.Routes.MapHttpRoute("DefaultApiWithId", "Api/{controller}/{id}", new { id =RouteParameter.Optional }, new { id = @"\d+" });
config.Routes.MapHttpRoute("DefaultApiWithAction", "Api/{controller}/{action}");

这些映射适用于动作名称映射和基本 http 约定(GET、POST、PUT、DELETE)

于 2014-10-23T04:40:41.537 回答
7

这是每个人都知道一切都是正确并检查了50次的答案.....

确保您没有反复查看RouteConfig.cs.

您要编辑的文件名为WebApiConfig.cs

此外,它应该看起来完全像这样:

using System.Web.Http;

namespace My.Epic.Website
{
    public static class WebApiConfig
    {
        public static void Register(HttpConfiguration config)
        {
          config.MapHttpAttributeRoutes();

          // api/Country/WithStates
          config.Routes.MapHttpRoute(
            name: "ControllerAndActionOnly",
            routeTemplate: "api/{controller}/{action}",
            defaults: new { },
            constraints: new { action = @"^[a-zA-Z]+([\s][a-zA-Z]+)*$" });

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

我本可以为自己节省大约 3 个小时。

于 2018-11-15T15:28:34.653 回答
5

您的 webmethod 可能被解析为相同的 url。看看以下链接:-

http://www.asp.net/web-api/overview/web-api-routing-and-actions/routing-in-aspnet-web-api

因此,您可能需要将您的方法名称添加到您的路由表中。

于 2013-01-26T05:35:22.433 回答
5

如果不使用操作,选项将是:

  1. 将其中一种方法移动到不同的控制器,以免它们发生冲突。

  2. 仅使用一种获取参数的方法,如果它为 null,请从您的代码中调用另一种方法。

于 2013-01-26T14:35:42.997 回答
4

这个解决方案对我有用。

请先将 Route2 放在 WebApiConfig 中。还要在每个方法之前添加 HttpGet 和 HttpPost,并在 url 中包含控制器名称和方法名称。

WebApiConfig =>

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

控制器 =>

public class ValuesController : ApiController
{

    [HttpPost]
    public string GetCustomer([FromBody] RequestModel req)
    {
        return "Customer";
    }

    [HttpPost]
    public string GetCustomerList([FromBody] RequestModel req)
    {
        return "Customer List";
    }
}

网址 =>

http://localhost:7050/api/Values/GetCustomer

http://localhost:7050/api/Values/GetCustomerList
于 2018-03-31T04:03:57.060 回答
3

我发现当我有两个 Get 方法时,一个是无参数的,一个是复杂类型的参数,我得到了同样的错误。我通过添加一个名为 Id 的 int 类型的虚拟参数作为我的第一个参数,然后是我的复杂类型参数来解决这个问题。然后我将复杂类型参数添加到路由模板中。以下对我有用。

首先得到:

public IEnumerable<SearchItem> Get()
{
...
}

第二次获得:

public IEnumerable<SearchItem> Get(int id, [FromUri] List<string> layers)
{
...
}

WebApiConfig:

config.Routes.MapHttpRoute(
    name: "DefaultApi",
    routeTemplate: "api/{controller}/{id}/{layers}",
    defaults: new { id = RouteParameter.Optional, layers RouteParameter.Optional }
);
于 2015-03-25T22:35:08.227 回答
3

这可能是由于使用 MVC 控制器而不是 Web API 控制器。检查 Web API 控制器中的命名空间,它应该如下所示

using System.Net;
using System.Net.Http;
using System.Web.Http;

如果命名空间如下,则在 web api 控制器方法调用中给出上述错误

using System.Web;
using System.Web.Mvc;
于 2015-11-27T11:45:00.360 回答
2

请检查您有两个名称不同但参数相同的方法。

如果是这样,请删除任何方法并尝试。

于 2013-07-10T18:16:17.110 回答
2

我在尝试通过额外的操作来增强我的 WebAPI 控制器时偶然发现了这个问题。

假设你会有

public IEnumerable<string> Get()
{
    return this.Repository.GetAll();
}

[HttpGet]
public void ReSeed()
{
    // Your custom action here
}

现在有两种方法可以满足触发 TS 描述的问题的 /api/controller 请求。

我不想在我的附加操作中添加“虚拟”参数,所以我查看了默认操作并想出了:

[ActionName("builtin")]
public IEnumerable<string> Get()
{
    return this.Repository.GetAll();
}

对于结合“双重”路由绑定的第一种方法:

config.Routes.MapHttpRoute(
    name: "DefaultApi",
    routeTemplate: "api/{controller}/{id}",
    defaults: new { action = "builtin", id = RouteParameter.Optional },
    constraints: new { id = @"\d+" });

config.Routes.MapHttpRoute(
    name: "CustomActionApi",
    routeTemplate: "api/{controller}/{action}");

请注意,即使第一个路由模板中没有“action”参数,您仍然可以配置默认操作,允许我们将“正常”WebAPI 调用的路由和对额外操作的调用分开。

于 2015-06-04T13:03:17.570 回答
2

在我的情况下,一切都是正确的

1) Web Config 配置正确 2) 路由前缀和路由属性正确

我仍然收到错误消息。在我的案例中,“Route”属性(通过按 F12)指向 System.Web.MVc 而不是 System.Web.Http 导致问题。

于 2019-03-12T07:01:31.443 回答
2

您可以添加[Route("api/[controller]/[action]")]到您的控制器类。

[Route("api/[controller]/[action]")]
[ApiController]
public class MySuperController : ControllerBase
{
 ...
}
于 2019-07-22T19:03:58.017 回答
0

我知道这是一个老问题,但有时,当您使用 AngularJS 等服务资源连接到 WebAPI 时,请确保您使用的是正确的路由,否则会发生此错误。

于 2017-06-20T15:40:37.137 回答
0

确保不要使用 [HttpPost/Put/Get/Delete] 属性为默认的 GET|PUT|POST|DELETE 操作装饰控制器方法。我已将此属性添加到我的香草后控制器操作中,它导致了 404。

希望这对某人有所帮助,因为它可能非常令人沮丧并导致进展停滞。

于 2017-09-06T00:47:20.590 回答
0

例如 => 测试控制器

        [HttpGet]
        public string TestMethod(int arg0)
        {
            return "";
        }

        [HttpGet]
        public string TestMethod2(string arg0)
        {
            return "";
        }

        [HttpGet]
        public string TestMethod3(int arg0,string arg1)
        {
            return "";
        }

如果只能更改 WebApiConfig.cs 文件。

 config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{action}/",
                defaults: null
            );

就是这样 :)

结果: 在此处输入图像描述

于 2019-01-15T10:29:28.043 回答
0

您是否尝试过:

[HttpGet("Summary")]
public HttpResponseMessage Summary(MyVm vm)
{
    return null;
}

[HttpGet("FullDetails")]
public HttpResponseMessage FullDetails()
{
    return null;
}
于 2019-05-15T02:36:05.590 回答