ASP.NET Web API 属性路由到错误操作
ASP.NET Web API Attribute Routing To Wrong Action
我在我的控制器上应用了属性路由,但它路由到错误的操作。我不知道我哪里弄错了。
这是我的控制器:
using System.Collections.Generic;
using System.Web.Http;
using System.Web.Http.Description;
using System.Linq;
using System;
namespace Iboo.API.Controllers
{
public class ClientsController : ApiController
{
private readonly IClientRepository _repository;
public ClientsController(IClientRepository repository)
{
_repository = repository;
}
// GET: api/Clients
[Route("api/v1/clients")]
public IEnumerable<Client> Get()
{
//code
}
// GET: api/Clients/5
[HttpGet]
[ResponseType(typeof(Client))]
[Route("api/v1/clients/get/{id}")]
public IHttpActionResult GetClientById(int id)
{
//code
}
// GET: api/Clients/5
[HttpGet]
[ResponseType(typeof(string))]
[Route("api/v1/clients/{id}/emailid")]
public IHttpActionResult GetClientEmailId(int id)
{
//code
}
}
}
我对 GetClientEmailId 方法特别感兴趣。下面是我的 WebApiConfig
public static void Register(HttpConfiguration config)
{
// Web API configuration and services
var container = new UnityContainer();
container.RegisterType<IClientRepository, ClientRepository>(new
HierarchicalLifetimeManager());
// Web API routes
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/v1/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
我的Global.asax.cs如下
public class WebApiApplication : System.Web.HttpApplication
{
protected void Application_Start()
{
AreaRegistration.RegisterAllAreas();
GlobalConfiguration.Configure(WebApiConfig.Register);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
}
在浏览器中如果我输入 http://localhost:54919/api/v1/clients/?id=1/getemailid it's taking me to http://localhost:54919/api/v1/clients 这不是我想要的。
如果我尝试 http://localhost:54919/api/v1/clients/1/getemailid 我收到 404 错误。
我不确定我弄错了什么。
您可以尝试在控制器上使用路由前缀。
[RoutePrefix("api/v1/clients")]
public class ClientsController : ApiController
{
// GET: api/Clients/5
[ResponseType(typeof(string))]
[Route("{id:int}/emailid"),HttpGet]
public IHttpActionResult GetClientEmailId(int id)
{
//code
}
}
你说:
In the browser If I type http://localhost:54919/api/v1/clients/?id=1/getemailid it's taking me to http://localhost:54919/api/v1/clients which is not what I want.
从你的路线设置方式来看,你似乎需要去 http://localhost:54919/api/v1/client/1/emailid
才能到达你想要的路线
为了解释差异,当您调用 http://localhost:54919/api/v1/clients/?id=1/getemailid
时,匹配的路由类似于:
[Route("api/v1/clients")]
public IHttpActionResult GetClientEmailId(string id)
{
//code
}
因为您已将 id
参数添加为查询字符串参数。在这种情况下,id
参数的值为 1/getemailid
,这没有多大意义。
通过使用路由参数(通过将 ?id=1/getemailid
替换为 1/emailid
),您将实际匹配您想要的路由
您根据操作的路线调用了错误的 URL。你得到 404 是因为你调用的 URL 与你在操作中使用的任何路由模板不匹配
[RoutePrefix("api/v1/clients")]
public class ClientsController : ApiController {
//...other code removed for brevity
[HttpGet]
[Route("")] //Matches GET api/v1/Clients
public IHttpActionResult Get() {
//code
}
[HttpGet]
[ResponseType(typeof(Client))]
[Route("{id:int}")] //Matches GET api/v1/Clients/5
public IHttpActionResult GetClientById(int id) {
//code
}
[HttpGet]
[ResponseType(typeof(string))]
[Route("{id:int}/emailid")] //Matches GET api/v1/Clients/5/emailid
public IHttpActionResult GetClientEmailId(int id) {
//code
}
}
注意评论中预期的 URLs
您还应该阅读 Attribute Routing in ASP.NET Web API 2 以更好地了解如何进行属性路由。
我在我的控制器上应用了属性路由,但它路由到错误的操作。我不知道我哪里弄错了。
这是我的控制器:
using System.Collections.Generic;
using System.Web.Http;
using System.Web.Http.Description;
using System.Linq;
using System;
namespace Iboo.API.Controllers
{
public class ClientsController : ApiController
{
private readonly IClientRepository _repository;
public ClientsController(IClientRepository repository)
{
_repository = repository;
}
// GET: api/Clients
[Route("api/v1/clients")]
public IEnumerable<Client> Get()
{
//code
}
// GET: api/Clients/5
[HttpGet]
[ResponseType(typeof(Client))]
[Route("api/v1/clients/get/{id}")]
public IHttpActionResult GetClientById(int id)
{
//code
}
// GET: api/Clients/5
[HttpGet]
[ResponseType(typeof(string))]
[Route("api/v1/clients/{id}/emailid")]
public IHttpActionResult GetClientEmailId(int id)
{
//code
}
}
}
我对 GetClientEmailId 方法特别感兴趣。下面是我的 WebApiConfig
public static void Register(HttpConfiguration config)
{
// Web API configuration and services
var container = new UnityContainer();
container.RegisterType<IClientRepository, ClientRepository>(new
HierarchicalLifetimeManager());
// Web API routes
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/v1/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
我的Global.asax.cs如下
public class WebApiApplication : System.Web.HttpApplication
{
protected void Application_Start()
{
AreaRegistration.RegisterAllAreas();
GlobalConfiguration.Configure(WebApiConfig.Register);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
}
}
在浏览器中如果我输入 http://localhost:54919/api/v1/clients/?id=1/getemailid it's taking me to http://localhost:54919/api/v1/clients 这不是我想要的。
如果我尝试 http://localhost:54919/api/v1/clients/1/getemailid 我收到 404 错误。
我不确定我弄错了什么。
您可以尝试在控制器上使用路由前缀。
[RoutePrefix("api/v1/clients")]
public class ClientsController : ApiController
{
// GET: api/Clients/5
[ResponseType(typeof(string))]
[Route("{id:int}/emailid"),HttpGet]
public IHttpActionResult GetClientEmailId(int id)
{
//code
}
}
你说:
In the browser If I type http://localhost:54919/api/v1/clients/?id=1/getemailid it's taking me to http://localhost:54919/api/v1/clients which is not what I want.
从你的路线设置方式来看,你似乎需要去 http://localhost:54919/api/v1/client/1/emailid
才能到达你想要的路线
为了解释差异,当您调用 http://localhost:54919/api/v1/clients/?id=1/getemailid
时,匹配的路由类似于:
[Route("api/v1/clients")]
public IHttpActionResult GetClientEmailId(string id)
{
//code
}
因为您已将 id
参数添加为查询字符串参数。在这种情况下,id
参数的值为 1/getemailid
,这没有多大意义。
通过使用路由参数(通过将 ?id=1/getemailid
替换为 1/emailid
),您将实际匹配您想要的路由
您根据操作的路线调用了错误的 URL。你得到 404 是因为你调用的 URL 与你在操作中使用的任何路由模板不匹配
[RoutePrefix("api/v1/clients")]
public class ClientsController : ApiController {
//...other code removed for brevity
[HttpGet]
[Route("")] //Matches GET api/v1/Clients
public IHttpActionResult Get() {
//code
}
[HttpGet]
[ResponseType(typeof(Client))]
[Route("{id:int}")] //Matches GET api/v1/Clients/5
public IHttpActionResult GetClientById(int id) {
//code
}
[HttpGet]
[ResponseType(typeof(string))]
[Route("{id:int}/emailid")] //Matches GET api/v1/Clients/5/emailid
public IHttpActionResult GetClientEmailId(int id) {
//code
}
}
注意评论中预期的 URLs
您还应该阅读 Attribute Routing in ASP.NET Web API 2 以更好地了解如何进行属性路由。