阻止调用Web API方法

时间:2013-01-30 18:01:53

标签: c# asp.net asp.net-web-api asp.net-web-api-routing

我正在使用ASP.NET Web API创建Web API。我目前在我的端点上存在功能,以便我可以开始针对它进行开发。

我的WebApiConfig.cs文件如下所示:

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

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

在我的UsersController.cs文件中,我有以下方法:

//Maps to /Users endpoint
[HttpGet]
public IEnumerable<User> GetAllUsers()
{
   //Code
}

//Maps to /Users/{id} endpoint
[HttpGet]
public User GetUser(int id)
{
   //Code
}

//Maps to /Users/{id}/Enrollments endpoint
[HttpGet, ActionName("Enrollments")]
public IEnumerable<Enrollment> GetUserEnrollments(int id)
{
   //Code
}

//Maps to /Users/{id}/Enrollments/{id}
[HttpGet, ActionName("Enrollments")]
public IEnumerable<Enrollment> GetUserEnrollment(int userid, int id)
{
   //Code
}

如何阻止/Users/GetUser成为有效路线?

[NonAction]上使用GetUser(int id)会阻止其完全正常工作。

编辑:以下是/Users/GetUser

的当前输出
<Error>
    <Message>An error has occurred.</Message>
    <ExceptionMessage>
        Multiple actions were found that match the request: Byui.ILearnAPI2.Business.Entities.User GetUser(Int32) on type Byui.ILearnAPI2.API.Controllers.UsersController System.Collections.Generic.IEnumerable`1[System.String] GetUserEnrollments(Int32) on type Byui.ILearnAPI2.API.Controllers.UsersController
    </ExceptionMessage>
    <ExceptionType>System.InvalidOperationException</ExceptionType>
    <StackTrace>
at System.Web.Http.Controllers.ApiControllerActionSelector.ActionSelectorCacheItem.SelectAction(HttpControllerContext controllerContext) at System.Web.Http.Controllers.ApiControllerActionSelector.SelectAction(HttpControllerContext controllerContext) at System.Web.Http.ApiController.ExecuteAsync(HttpControllerContext controllerContext, CancellationToken cancellationToken) at System.Web.Http.Dispatcher.HttpControllerDispatcher.SendAsyncInternal(HttpRequestMessage request, CancellationToken cancellationToken) at System.Web.Http.Dispatcher.HttpControllerDispatcher.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    </StackTrace>
</Error>

5 个答案:

答案 0 :(得分:2)

再次审核您的帖子后,我认为您没有正确查看错误。

由于您配置控制器的方式,存在不明确的路线。

找到了符合请求的多项操作:

类型为Byui.ILearnAPI2.API.Controllers.UsersController

GetUser(Int32) 类型为Byui.ILearnAPI2.API.Controllers.UsersController

GetUserEnrollments(Int32)

GetUser和GetUserEnrollments共享相同的路线。据我所知,如果你传递一个int或一个字符串或其他东西,GetUser将无法工作,因为它不知道如何正确解析。

您可以在默认值之前添加路由配置以解决问题。

config.Routes.MapHttpRoute(
    name: "GetUsers",
    routeTemplate: "api/users/{id}",
    defaults: new { controller = "Users", action = "GetUser" }
);

答案 1 :(得分:2)

试试这个。

  1. 评论GetUserEnrollments(int id)
  2. 致电/Users/GetUser - 您将获得
  3.   The request is invalid.
      The parameters dictionary contains a null entry for parameter 'id' of 
      non-nullable type 'System.Int32' for method 'so14610664.Models.User 
      GetUser(Int32)' in 'so14610664.Controllers.UsersController'. An optional 
      parameter must be a reference type, a nullable type, or be declared as an 
      optional parameter.
    
    1. 现在拨打/User/abcdefg - 您会收到与上述相同的消息。 "The request is invalid..."
    2. 请注意,并不是GetUser被曝光,而是它试图将/Users/之后的任何内容映射到id并失败,因为GetUser和{{ 1}}无效"abcdefg"值;换句话说:它认为你忘了Int32


      试用AttributeRouting包。这是一个位于MVC路由(id中的路由)和/或Web API路由之上的包(你是什么的)正在做 - App_Start/RouteConfig

      中的路线

      使用该软件包, 替换 App_Start/WebApiConfig中的路由映射与代码示例中的路由映射:

      App_Start

答案 2 :(得分:1)

您可以使用IHttpRouteConstraint验证{id}是否为整数,并在路线中指定路线约束。

可以找到样本here

答案 3 :(得分:0)

GetUsers返回404,这是处理它的Restful方式。

答案 4 :(得分:0)

您可以执行以下操作来验证提供的ID。如果找不到Id,您可以使用您想要的任何代码返回自定义响应消息。

[HttpGet]
public User GetUser(int id)
{
    if (id > 0 && validIds.Contains(id))
    {
        //Go do something fun...
    }
    else
        throw new HttpResponseException(
            new HttpResponseMessage(HttpStatusCode.NotFound)
                {
                    ReasonPhrase = String.Format("A valid id is required. {0} is most definitely not a valid id.", id);
                }


  );

}