【问题标题】:Using WebAPI Route attribute使用 WebAPI 路由属性
【发布时间】:2014-09-26 11:35:03
【问题描述】:

我有一些方法,我想为它们的 URL 遵循特定的模式。

基本上有餐馆,有ID,下面有一系列终端。

我正在尝试出现以下类型的模式: api/Restaurant - 获取所有餐厅 api/Restaurant/Bobs - 获取 ID 为 Bobs 的餐厅 api/Restaurant/Bobs/terminals - 获取 bob 餐厅的所有终端 api/Restaurant/bobs/terminals/second - 获取餐厅 bob 中 ID 为 second 的终端

我已经有了执行此操作的方法,并且我已将 Route 属性分配给每个方法,如下所示:

    [HttpGet]
    public IEnumerable<IRestaurant> Get()
    {
        //do stuff, return all
    }

    [HttpGet]
        [Route("api/Restaurant/{restuarantName}")]
        public IRestaurant Get(string restaurantName)
        {
           //do stuff
        }

    [HttpGet]
    [Route("api/restuarant/{restaurantName}/terminals")]
    public IEnumerable<IMiseTerminalDevice> GetDevices(string restaurantName)
    {
       //do stuff
    } 

    [HttpGet]
    [Route("api/restaurant/{restaurantName}/terminals/{terminalName}")]
    public IMiseTerminalDevice GetDeviceByName(string restaurantName, string terminalName)
    {
        //do stuff
    }

但是,只有我的基本 GET (api/Restaurant) 有效。我的 WebAPI 配置是默认配置,并显示

    config.MapHttpAttributeRoutes();

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

    config.Formatters.JsonFormatter.SupportedMediaTypes.Add(new MediaTypeHeaderValue("text/html"));

有人知道我哪里出错了吗?所有其他方法都返回路由不匹配(​​带有 ID 的餐厅)或 404。

提前致谢!

【问题讨论】:

  • and reads config.MapHttpAttributeRoutes(); 是什么意思?...你打电话给config.MapHttpAttributeRoutes() 因为这是在路由表中探测控制器和注册属性路由的那个...还要注意请求匹配传统路由永远不会匹配用属性路由装饰的控制器/动作..
  • @Mathieson 您能否添加您的请求?我已经使用默认模板尝试了您的 API,并且效果很好。
  • 是的,该部分是 WebApiConfig 类的值 - 固定格式以使其更清晰。
  • @Toan - 当然! url localhost:4675/api/restaurant 返回正确的 JSON。 url localhost:4675/api/restaurant/bob 触发控制器构造函数,并返回 "{"Message":"未找到与请求 URI 'localhost:4675/api/restaurant/… 匹配的 HTTP 资源在与请求匹配的控制器 'Restaurant' 上找到操作。"}" url localhost:4675/api/restaurant/bob/terminals 只是返回 404,并不会触发控制器构造函数。
  • 也许“餐厅”的错字没有帮助。

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


【解决方案1】:

我刚刚创建了包含 ProductsController 的默认 WEB API 项目。接下来,我把你的 api 方法粘贴进去了。

  public class ProductsController:ApiController
    {



        [HttpGet]
        [Route("api/Restaurant/{restaurantName}")]
        public IHttpActionResult Get(string restaurantName)
        {
            //do stuff
            return Ok("api/Restaurant/{restuarantName}");
        }

        [HttpGet]
        [Route("api/restuarant/{restaurantName}/terminals")]
        public IHttpActionResult GetDevices(string restaurantName)
        {
            //do stuff
            return Ok("api/restuarant/{restaurantName}/terminals");
        }

        [HttpGet]
        [Route("api/restaurant/{restaurantName}/terminals/{terminalName}")]
        public IHttpActionResult GetDeviceByName(string restaurantName, string terminalName)
        {
            //do stuff
            return Ok("api/restaurant/{restaurantName}/terminals/{terminalName}");
        }
    }

最后,我用 Fiddler 发出请求

**http://localhost:9969/api/restuarant/Vanbeo/terminals**

一切正常!

系统配置:Visual Studio 2013、WEB API 2.2、Net 4.5

您能用一个空项目重试吗?

PS:由于评论空间不足,我必须将其发布为答案!

【讨论】:

  • 我创建了一个新的 WebAPI 项目,并用上面的代码替换了 ValuesController 方法 - 现在我发现 localhost:3322/API/restaurant/bob 返回正确。但是 localhost:3322/API/restaurant/bob/terminals 返回 404
  • 您可以将您的 Web API 包升级到 2.2 版并重试吗?
  • WebAPI 为 2.2。我认为方法名称有问题 - 将我的签名更改为 [Route("api/restaurants/{restaurantName}/{terminalName}")] [Route("api/restaurants/{restaurantName}/terminals/{terminalName}" )] [HttpGet] public IHttpActionResult GetTerminalByName(string restaurantName, string terminalName) 至少使我能够使用该方法。我已经重构以移动到更大的 Restaurant 聚合根,所以这可能是回避这个问题的好方法。但仍然令人沮丧 - 甚至 RouteDebugger 也没有显示太多!
猜你喜欢
  • 2016-12-17
  • 1970-01-01
  • 1970-01-01
  • 2013-08-04
  • 2014-03-25
  • 1970-01-01
  • 2013-06-07
  • 2013-11-26
  • 1970-01-01
相关资源
最近更新 更多