3

学习了很多关于 MapRouting 的知识,并且花了太多时间试图完成我需要做的事情,所以我希望有人能提供帮助。:)

我正在寻找执行以下操作:

/api/Entities/1 <- 查看 id 为 1 的详细信息实体(这是一个字符串,不是 int)

/api/Entities/1/Action <- 对 id 为 1 的实体调用特定操作。

/api/Entities <- 查看实体集。

/api/Entities/Action <- 调用实体集的特定操作。

我遇到的问题是最后一个。目前正被第一种情况拦截,因为 id 是一个字符串。

任何帮助将不胜感激!

4

1 回答 1

2

一个很好的参考是here

如果不使用基于属性的路由,答案会有些冗长,因为如果您匹配同一个动词,则 RPC 样式(Action)和 Rest 方法不能很好地共存。正如您所注意到的,GET() 和 DOSOMETHING() 被视为同一控制器上的重复方法签名。要解决这个问题,您可以尝试使用两个控制器:

所以我建议使用基于属性的路由;但是,可以使用常规方法:

使用标准路由...

像这样设置你的路线

        config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
        config.Routes.MapHttpRoute(
            name: "ActionDefaultApi",
            routeTemplate: "api/entities/{action}/{actionId}",
            defaults: new
                          {
                              //Add more as needed
                              action = "(|dosomething|dosomethingelse)",
                              actionId = RouteParameter.Optional,
                              controller = "EntitiesRpc"
                          });

控制器 1:

public class EntitiesController : ApiController
{
    public string Get()
    {
        return "http://server/api/Entities";
    }

    public string Get(string id)
    {
        return string.Format("http://server/api/Entities/{0}", id);
    }
}

控制器 2:

public class EntitiesRpcController : ApiController
{
    [HttpGet]
    public string DoSomething()
    {
        return "http://server/api/Entities/doSomething";
    }

    [HttpGet]
    public string DoSomething(string actionId)
    {
        return string.Format("http://server/api/Entities/doSomething/{0}", actionId);
    }

    [HttpGet]
    public string DoSomethingElse()
    {
        return "http://server/api/Entities/doSomethingelse";
    }

    [HttpGet]
    public string DoSomethingElse(string actionId)
    {
        return string.Format("http://server/api/Entities/doSomethingelse/{0}", actionId);
    }
}

现在假设您使用了基于属性的路由,您可以返回到一个控制器并使用如下内容:

public class EntitiesController : ApiController
{
    [Get("Entities")]
    public string Get()
    {
        return "http://server/api/Entities";
    }

    [Get("Entities/{id}")]
    public string Get(string id)
    {
        return string.Format("http://server/api/Entities/{0}", id);
    }

    [Get("Entities/doSomething")]
    public string DoSomething()
    {
        return "http://server/api/Entities/doSomething";
    }

    [Get("Entities/doSomething/{actionId}")]
    public string DoSomething(string actionId)
    {
        return string.Format("http://server/api/Entities/doSomething/{0}", actionId);
    }

    [Get("Entities/doSomethingelse")]
    public string DoSomethingElse()
    {
        return "http://server/api/Entities/doSomethingelse";
    }

    [Get("Entities/doSomethingelse/{actionId}")]
    public string DoSomethingElse(string actionId)
    {
        return string.Format("http://server/api/Entities/doSomethingelse/{0}", actionId);
    }
}
于 2012-11-30T10:21:05.037 回答