route.GetRouteData(httpContext).Values["action"] 对于属性路由为空

route.GetRouteData(httpContext).Values["action"] is null for Attribute Routing

我正在尝试获取 HttpModule 中的控制器名称和操作名称。

在我的 http 模块的 OnBeginRequest 中,我有以下代码:

foreach (var route in RouteTable.Routes)
{
    if (route.GetRouteData(httpContext) != null)
    {
        Console.WriteLine(string.Format(CultureInfo.InvariantCulture, 
            "Route info ====== {0}, {1} ======", 
            route.GetRouteData(httpContext).Values["controller"], 
            route.GetRouteData(httpContext).Values["action"]));
    }
}

如果路由是使用这样的常规路由注册的:

routes.MapRoute("BlogDetails", "blog/{blogId}", new { controller = "Blog", action = "Details" });

当我转到:~/blog/1 我可以看到输出

"Route info ====== Blog, Details ======"

但如果使用以下方式注册:

routes.MapMvcAttributeRoutes();

在控制器中我有:

[RouteArea("blog", AreaPrefix = "blog")]
[Route("{action}")]

关于我的行动:[Route("{blogId}", Name="blogDetailRoute")]

当我去:~/blog/1 我只看到输出

"Route info ====== Blog,  ======"

该路线数据中缺少操作名称。

属性路由有什么不同吗?我在哪里可以找到操作名称?

感谢您的帮助!

属性路由的路由存储在一个名为 MS_DirectRouteMatches 的嵌套 IEnumerable<RouteData> 中。

var routeData = routes.GetRouteData(httpContext);
if (routeData != null)
{
     if (routeData.Values.ContainsKey("MS_DirectRouteMatches"))
     {
          routeData = ((IEnumerable<RouteData>)routeData.Values["MS_DirectRouteMatches"]).First();
     }
}

这个例子展示了我们如何获取与当前上下文匹配的常规路由数据,如果恰好存在则用属性路由数据替换它。