当 Id 是字符串时,路由到多个 GETS 失败
Routing to multiple GETS fails when the Id is a string
我试过其他类似问题的答案,但我仍然遇到这个问题。
我们正在实施 ASP.NET REST API,设置如下:
[Authorize]
[Route("api/cars/{id:int}")]
public HttpResponseMessage Get(int id)
{
//Some stuff
}
[Authorize]
[Route("api/cars/{brand?}/{color?}")]
public HttpResponseMessage GetBySource(string brand = null, string color = null)
{
//Some stuff
}
由于 Get(int id) 方法上的 int 约束,路由工作正常,它支持如下调用:
{host}/api/cars/1
{host}/api/cars/toyota
{host}/api/cars/toyota/blue
{host}/api/cars?brand=toyota&color=blue
现在有支持字符串 ID 的新要求
以下 "logical" 更改(删除 Id 上的 int 约束)破坏了设置:
[Authorize]
[Route("api/cars/{id}")]
public HttpResponseMessage Get(string id)
{
//Some stuff
}
现在之前的大部分调用都路由到 Get(string id):
{host}/api/cars/1 //---> Works OK
{host}/api/cars/toyota //---> "toyota" is the car Id instead of brand (No OK)
{host}/api/cars?brand=toyota //---> "brand=toyota" is the car Id instead of parsing the brand (No OK)
{host}/api/cars/toyota/blue //---> (404 Error)
{host}/api/cars?brand=toyota&color=blue //---> (404 Error)
毕竟有道理。 [Route("api/cars/{id}")] 将 cars 之后的任何字符串视为 Id,并期望像 [Route("api/cars/{id}/xxx/{yyy}")] 这样的路线满足其他请求。但是把一个唯一的Id放在其他过滤器的前面是没有意义的。
我们正在评估仅在确实需要时才更改我们以前的设计。所以我的问题是:
我们可以做出以下设计吗?:
{host}/api/cars/A100T50
{host}/api/cars/toyota
{host}/api/cars/toyota/blue
{host}/api/cars?brand=toyota&color=blue
如果不是,您会推荐我使用哪种设计?
我的路由配置很简单:
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
}
提前感谢您的指导
你能把这两种方法结合起来吗?
[Authorize]
//edit: add another route so that it recognizes id
[Route("api/cars/{id}")]
[Route("api/cars")]
public HttpResponseMessage Get(string brand = "", string color = "", string id = "")
{
//example to get from database based on whichever parameter provided
using(var ctx = new DbContext())
{
var cars = ctx.Cars
.Where(car => String.IsNullOrEmpty(id) || car.Id == id
&& String.IsNullOrEmpty(color) || car.Color == color
&& String.IsNullOrEmpty(brand) || car.Brand == brand);
//Some stuff
}
你可以打电话给
{host}/api/cars/AT100
{host}/api/cars?id=AT100
{host}/api/cars?color=black
我试过其他类似问题的答案,但我仍然遇到这个问题。 我们正在实施 ASP.NET REST API,设置如下:
[Authorize]
[Route("api/cars/{id:int}")]
public HttpResponseMessage Get(int id)
{
//Some stuff
}
[Authorize]
[Route("api/cars/{brand?}/{color?}")]
public HttpResponseMessage GetBySource(string brand = null, string color = null)
{
//Some stuff
}
由于 Get(int id) 方法上的 int 约束,路由工作正常,它支持如下调用:
{host}/api/cars/1
{host}/api/cars/toyota
{host}/api/cars/toyota/blue
{host}/api/cars?brand=toyota&color=blue
现在有支持字符串 ID 的新要求 以下 "logical" 更改(删除 Id 上的 int 约束)破坏了设置:
[Authorize]
[Route("api/cars/{id}")]
public HttpResponseMessage Get(string id)
{
//Some stuff
}
现在之前的大部分调用都路由到 Get(string id):
{host}/api/cars/1 //---> Works OK
{host}/api/cars/toyota //---> "toyota" is the car Id instead of brand (No OK)
{host}/api/cars?brand=toyota //---> "brand=toyota" is the car Id instead of parsing the brand (No OK)
{host}/api/cars/toyota/blue //---> (404 Error)
{host}/api/cars?brand=toyota&color=blue //---> (404 Error)
毕竟有道理。 [Route("api/cars/{id}")] 将 cars 之后的任何字符串视为 Id,并期望像 [Route("api/cars/{id}/xxx/{yyy}")] 这样的路线满足其他请求。但是把一个唯一的Id放在其他过滤器的前面是没有意义的。
我们正在评估仅在确实需要时才更改我们以前的设计。所以我的问题是: 我们可以做出以下设计吗?:
{host}/api/cars/A100T50
{host}/api/cars/toyota
{host}/api/cars/toyota/blue
{host}/api/cars?brand=toyota&color=blue
如果不是,您会推荐我使用哪种设计?
我的路由配置很简单:
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
}
提前感谢您的指导
你能把这两种方法结合起来吗?
[Authorize]
//edit: add another route so that it recognizes id
[Route("api/cars/{id}")]
[Route("api/cars")]
public HttpResponseMessage Get(string brand = "", string color = "", string id = "")
{
//example to get from database based on whichever parameter provided
using(var ctx = new DbContext())
{
var cars = ctx.Cars
.Where(car => String.IsNullOrEmpty(id) || car.Id == id
&& String.IsNullOrEmpty(color) || car.Color == color
&& String.IsNullOrEmpty(brand) || car.Brand == brand);
//Some stuff
}
你可以打电话给
{host}/api/cars/AT100
{host}/api/cars?id=AT100
{host}/api/cars?color=black