在我的MVC应用程序中,我们有大约200多页我们正在使用网格。最近我们添加了history.js与网格集成,增加了" page"网址中的参数,如http://localhost/User/ManageUsers/?page=1。
这会给面包屑带来问题。如果我的网址为http://localhost/User/ManageUsers,则会显示" 主页>管理用户>用户"在面包屑。但是,如果使用页面http://localhost/User/ManageUsers/?page=1更改网址,则面包屑会更改为父级,即" 主页>管理用户"管理用户没有超链接。
我的站点地图的设计如下:
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" preservedRouteParameters="id">
<mvcSiteMapNode title="Facilities" controller="User" action="ManageUserFacilities" preservedRouteParameters="id,conf"/>
<mvcSiteMapNode title="Conversations" controller="User" action="UserConversations" preservedRouteParameters="id,conf"/>
</mvcSiteMapNode>
<mvcSiteMapNode title="User Postings" controller="User" action="ManageUserPostings"/>
</mvcSiteMapNode>
我发现如果我以某种方式删除&#34; /&#34;从URL中的最后一个,面包屑工作正常,例如。
http://localhost/User/ManageUsers?page=1 //shows correct breadcrumbs
http://localhost/User/ManageUsers/?page=1 //shows parent node in breadcrumbs
请帮我找到合适的解决方案。
答案 0 :(得分:0)
我无法解释(或重现)您使用尾部斜杠看到的行为,但我确实看到了潜在的问题。
当涉及将节点与传入路由匹配时,以下2个节点是不明确的:
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" preservedRouteParameters="id">
在这两种情况下,它们都会匹配网址/User/ManageUsers
。这是因为savedRouteParameters仅在有保留参数时才起作用,因此它就像一个可选值。
解决此问题的最简单方法是重命名其中一个操作方法。通常,这些是两个不同的功能部件(名为Index
和Details
),并通过将关注点放入不同的操作方法来应用关注点分离是一件好事。
或者,您可以为第一个节点定义单独的路由,然后显式调出该路由。
routes.MapRoute(
name: "User_MangageUsers",
url: "User/ManageUsers",
defaults: new { controller = "User", action = "ManageUsers" }
);
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
你的节点:
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers" route="User_MangageUsers">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" preservedRouteParameters="id">
这确实无法解决page
参数的问题。但是你不应该有一个,因为默认情况下会忽略查询字符串值。我怀疑您的路由配置存在问题,但由于您没有发布,我无法确切地告诉您它是什么。
在v4.6.10中添加了一项功能,允许您使用查询字符串参数作为路由匹配的一部分,并且有一项增强功能可以使查询字符串键在v4.6.18中不区分大小写。
如果您使用的是低于v4.6.10的版本,则应升级。如果您至少使用v4.6.10,则可以通过将page
参数添加为保留路由参数来解决此问题。
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers" route="User_MangageUsers" preservedRouteParameters="page">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" preservedRouteParameters="id">
根据您的路线更新
我仍然无法重现这个问题。
但是,您的路由配置确实存在问题 - 即,在单个路由上指定2个可选参数无效。这可能与您的尾部斜杠问题有关,因为当您关闭两个可选参数时,结果将在生成URL时包含额外的尾部斜杠。使用当前路由配置,Default
路由是无法访问的执行路径。
您可以通过更改路由来解决此问题。
routes.MapRoute(
name: "DefaultwithType",
url: "{controller}/{action}/{id}/{type}",
defaults: new { type = UrlParameter.Optional });
routes.MapRoute(
name: "Default",
url: "{controller}/{action}",
defaults: new { controller = "Home", action = "Index" });
现在:
/User/ManageUsers/1/SomeType - matches DefaultwithType
/User/ManageUsers/1 - matches DefaultwithType
/User/ManageUsers - matches Default
/User - matches Default (with action "Index")
/ - matches Default (with controller "Home", action "Index")
使用此路由配置,您可以通过显式指定路由来消除节点之间的歧义。这可能是必要的,也可能不是必需的 - 首先尝试修复节点,然后再修复此节点。
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers" route="Default">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" route="DefaultwithType" preservedRouteParameters="id">
更新以使网格在“用户”节点上工作
// Route to force match with "Users" node
routes.MapRoute(
name: "User",
url: "User/ManageUsers/{id}",
defaults: new { controller = "User", action = "ManageUsers" });
routes.MapRoute(
name: "DefaultwithType",
url: "{controller}/{action}/{id}/{type}");
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional });
节点:
<mvcSiteMapNode title="Manage Users" controller="User" action="ManageUsers" route="Default">
<mvcSiteMapNode title="Users" controller="User" action="ManageUsers" route="User" preservedRouteParameters="id,page">
现在User
路线优先于Default
路线。除非提供了4段网址,否则DefaultwithType
路由将不匹配 - 如果您的应用中有4个您不打算调用最后一个段的网址,则可能需要一些固定的细分或约束{1}}。
我还在savedRouteParameters中包含了“page”。这可能不是必需的,但如果包含它,它应匹配页码是否在请求中。
“MvcSiteMapProvider_AttributesToIgnore”用于在节点上创建未包含在路由匹配中的自定义属性。它与忽略传入URL中的值无关。