3

The goal is to allow these four endpoints:

POST    v1/invoices<br/>
POST    v1/invoices/12345<br/>
POST    v1/invoices/12345/attachment<br/>
POST    v1/invoices/12345/image

Routing entries:

routes.MapHttpRoute(
        name: "InvoiceAttachments",
        routeTemplate: "v1/invoices/{id}/attachments",
        defaults: new { controller = "invoices", action = "PostAttachment" }
    );

routes.MapHttpRoute(
        name: "InvoiceImages",
        routeTemplate: "v1/invoices/{id}/images",
        defaults: new { controller = "invoices", action = "PostImage" }
    );

These are my four function definitions in the controller:

[HttpPost]
[ActionName("PostAttachment")]
public HttpResponseMessage PostAttachment(int id)

[HttpPost]
[ActionName("PostImage")]
public HttpResponseMessage PostImage(int id)

[HttpPost]
public HttpResponseMessage Post(int id)    

[HttpPost]
public HttpResponseMessage Post()

Yet when I post an invoice using the first URI, the route that gets recognized is the attachments route. How do i have endpoints with different sections after the ID variable?

4

4 回答 4

7

知道了!

路线:

routes.MapHttpRoute(
        name: "InvoiceStuff",
        routeTemplate: "v1/invoices/{id}/{*action}",
        defaults: new { controller = "invoices", action = "" }
    );

函数定义:

[HttpPost]
[ActionName("Attachments")]
public HttpResponseMessage Attachments([FromUri]int id)

[HttpPost]
[ActionName("Images")]
public HttpResponseMessage Images([FromUri]int id)

[HttpPost]
public HttpResponseMessage Post()

[HttpPost]
[ActionName("")]
public HttpResponseMessage Post([FromUri]int id)

完美运行。请注意,由于带有通配符的 webAPI 路由存在缺陷,我在路由中指定了默认操作“”。如果我没有做默认设置,就会抛出空引用异常。可以在此处找到有关该缺陷的更多信息:http: //aspnetwebstack.codeplex.com/workitem/718 - 计划在 ASP.NET v5 中修复。

感谢你的帮助!

于 2013-06-06T03:11:06.900 回答
1

我认为您必须定义另一个路由,因为第一个 URI 不应该与 InvoiceAttachments 路由匹配,因为它末尾没有“/attachments”

于 2013-06-04T21:09:37.097 回答
0

尝试使用单一路线

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

然后装饰功能,如

[HttpPost]
[ActionName("DefaultAction")]
public HttpResponseMessage Post()


[HttpPost]
public HttpResponseMessage PostImage(int id)
于 2013-06-04T22:43:35.763 回答
0

您是否尝试过使用约束而不是默认值?

routes.MapHttpRoute(
        name: "InvoiceAttachments",
        routeTemplate: "v1/invoices/{id}/attachments",
        defaults: new { controller = "invoices" },
        constraints: new { action = "PostAttachment" } 
    );

routes.MapHttpRoute(
        name: "InvoiceImages",
        routeTemplate: "v1/invoices/{id}/images",
        defaults: new { controller = "invoices" },
        constraints: new { action = "PostImage" } 
    );

routes.MapHttpRoute(
        name: "Default",
        routeTemplate: "v1/invoices/{id}",
        defaults: new { controller = "invoices" }
    );

更新:

您可以通过将操作作为 url 部分来破解它:

routes.MapHttpRoute(
        name: "InvoiceAttachments",
        routeTemplate: "v1/invoices/{id}/{action}",
        defaults: new { controller = "invoices" },
        constraints: new {action = "attachments|images"}
    );

routes.MapHttpRoute(
            name: "default",
            routeTemplate: "v1/invoices/{id}",
            defaults: new { controller = "invoices", id = RouteParameter.Optional },
            constraints: new {action = "attachments|images"}
        );

和控制器方法:

[HttpPost]
[ActionName("attachments")]
public HttpResponseMessage PostAttachment(int id)

[HttpPost]
[ActionName("images")]
public HttpResponseMessage PostImage(int id)

public HttpResponseMessage Post(int id)

public HttpResponseMessage Post()
于 2013-06-05T16:41:23.943 回答