如何使用路由属性进行Web API版本控制时获取控制器名称

我需要从我的路由中获取控制器名称,如果在WebApiConfig中使用标准路由代码,我可以这样做。

但是,如果我使用路由属性,它会开始变得有点困难,尤其是在尝试版本时。

示例:如果我调用api / terms / bonus并且我有一个BonusController和BonusV2Controller以及一个BonusV3Controller,这段代码将返回最新的控制器版本3.那没关系,我可以接受最新版本的默认版本。

var attributedRoutesData = request.GetRouteData().GetSubRoutes(); var subRouteData = attributedRoutesData.FirstOrDefault(); var actions = (ReflectedHttpActionDescriptor[])subRouteData.Route.DataTokens["actions"]; //This seems to get latest controller name. ie. V2 controllerName = actions[0].ControllerDescriptor.ControllerName; 

现在,如果我请求版本1,为简单起见,我将使用查询字符串并调用api / terms / bonus?v = 2

所以这段代码不再有效(显然)。

如何获取V2控制器名称?

如果我放弃路由属性并只使用WebApiConfig路由,则此代码可以正常工作。

 HttpControllerDescriptor controllerDescriptor = null; var controllers = GetControllerMapping(); var routeData = request.GetRouteData(); var controllerName = (string)routeData.Values["controller"]; 

谢谢。

更新:

这是我的完整选择器代码。

 IDictionary controllers = GetControllerMapping(); var attributedRoutesData = request.GetRouteData().GetSubRoutes(); var subRouteData = attributedRoutesData.LastOrDefault(); //LastOrDefault() will get PeopleController, FirstOrDefault will get People{version}Controller which we don't want var actions = (ReflectedHttpActionDescriptor[])subRouteData.Route.DataTokens["actions"]; var controllerName = actions[0].ControllerDescriptor.ControllerName; //For controller name without attribute routing //var controllerName = (string)routeData.Values["controller"]; HttpControllerDescriptor oldControllerDescriptor; if (controllers.TryGetValue(controllerName, out oldControllerDescriptor)) { //TODO: Different techniques for handling version api requests. var apiVersion = GetVersionFromQueryString(request); //var version = GetVersionFromHeader(request); //var version = GetVersionFromAcceptHeaderVersion(request); //var version = GetVersionFromMediaType(request); if (!String.IsNullOrEmpty(apiVersion)) { var newControllerName = String.Concat(controllerName, "V", apiVersion); HttpControllerDescriptor newControllerDescriptor; if (controllers.TryGetValue(newControllerName, out newControllerDescriptor)) { return newControllerDescriptor; } } return oldControllerDescriptor; } return null; 

  var subRouteData = request.GetRouteData().GetSubRoutes().LastOrDefault(); if (subRouteData != null && subRouteData.Route != null) { var actions = subRouteData.Route.DataTokens["actions"] as HttpActionDescriptor[]; if (actions != null && actions.Length > 0) { controllerName = actions[0].ControllerDescriptor.ControllerName; } }