C# ASP.NET MVC页面URL和控制器/操作路由

C# ASP.NET MVC页面URL和控制器/操作路由,c#,asp.net,asp.net-mvc,asp.net-mvc-routing,C#,Asp.net,Asp.net Mvc,Asp.net Mvc Routing,我在构建允许两种路由的ASP.NET MVC页面时遇到问题 我有一个数据库,其中所有页面都以url路径存储,如:/Site1/Site2/Site3 我尝试在第一条路线中使用IRouteConstraint,检查请求的路线是否正确 站点是我的数据库中的站点(permalink) 在第二种情况下,我想使用默认的asp.net mvc{controller}/{action}功能,从*.cshtml提供简单的访问 现在我不知道这是不是最好的方法。此外,我还有一个问题,如何使用IRouteContra

我在构建允许两种路由的ASP.NET MVC页面时遇到问题

我有一个数据库,其中所有页面都以url路径存储,如:/Site1/Site2/Site3 我尝试在第一条路线中使用IRouteConstraint,检查请求的路线是否正确 站点是我的数据库中的站点(permalink

在第二种情况下,我想使用默认的asp.net mvc{controller}/{action}功能,从*.cshtml提供简单的访问

现在我不知道这是不是最好的方法。此外,我还有一个问题,如何使用IRouteContracint根

有人对此有经验吗

我正在使用asp.NETMVC5

问题已解决,最终解决方案:

  • 添加这两条路线:

    routes.MapRoute(
        "FriendlyUrlRoute",
        "{*FriendlyUrl}"
    ).RouteHandler = new FriendlyUrlRouteHandler();
    
    routes.MapRoute(
        name: "Default",
        url: "{controller}/{action}/{id}",
        defaults: new { controller = "Page", action = "Load", id = UrlParameter.Optional },
        namespaces: controllerNamespaces.ToArray()
    );
    
  • 我自己的路线处理程序:

    public class FriendlyUrlRouteHandler : System.Web.Mvc.MvcRouteHandler
    {
        protected override IHttpHandler GetHttpHandler(System.Web.Routing.RequestContext requestContext)
        {
            var friendlyUrl = (string)requestContext.RouteData.Values["FriendlyUrl"];
    
            WebPageObject page = null;
    
            if (!string.IsNullOrEmpty(friendlyUrl))
            {
                page = PageManager.Singleton.GetPage(friendlyUrl);
            }
    
            if (page == null)
            {
                page = PageManager.Singleton.GetStartPage();
            }
    
            // Request valid Controller and Action-Name
            string controllerName = String.IsNullOrEmpty(page.ControllerName) ? "Page" : page.ControllerName;
            string actionName = String.IsNullOrEmpty(page.ActionName) ? "Load" : page.ActionName;
    
            requestContext.RouteData.Values["controller"] = controllerName;
            requestContext.RouteData.Values["action"] = actionName;
            requestContext.RouteData.Values["id"] = page;
    
            return base.GetHttpHandler(requestContext);
        }
    }
    

  • 您可以使用MVC 5中的属性路由,并将属性路由与基于约定的路由相结合,以检查控制器类或操作方法上需要的条件

    您可以自己制作约束,将其用于以下动作方法:

    public class ValuesConstraint : IRouteConstraint
    {
        private readonly string[] validOptions;
        public ValuesConstraint(string options)
        {
            validOptions = options.Split('|');
        }
    
        public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDirection)
        {
            object value;
            if (values.TryGetValue(parameterName, out value) && value != null)
            {
                return validOptions.Contains(value.ToString(), StringComparer.OrdinalIgnoreCase);
            }
            return false;
        }
    }
    
    要使用属性路由,只需在配置期间调用
    MapMvcAttributeRoutes
    ,然后调用常规路由。此外,还应在映射属性之前添加约束,如以下代码所示:

    public static void RegisterRoutes(RouteCollection routes)
    {
        routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
    
        var constraintsResolver = new DefaultInlineConstraintResolver();
        constraintsResolver.ConstraintMap.Add("values", typeof(ValuesConstraint));
        routes.MapMvcAttributeRoutes(constraintsResolver);
    
        routes.MapRoute(
            name: "Default",
            url: "{controller}/{action}/{id}",
            defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
        );
    }
    
    现在,在控制器类上,您可以检查路由并决定如何处理不同的URL,如下所示:

    例如:///mysite/Site1/mysite/Site2但不是/mysite/Site3

    [Route("mysite/{site:values(Site1|Site2)}")]
    public ActionResult Show(string site)
    {
        return Content("from my database " + site);
    }
    
    您还可以在控制器类上执行各种检查


    我希望这能给你一点线索来实现你想要的东西。

    谢谢,但是当我使用属性路由时,我如何处理动态路由,哪些存储在我的数据库中?您可以从数据库中获取ValuesConstraint类中的rout值,并编写适合您需要的约定,然后将其应用于控制器类中的操作方法。我找到了解决我的问题的完美解决方案: