UrlRouting principle notes

UrlRouting routing process:

Add routes: can call MapRoute (), MapPageRoute (), which are internal objects created Route, the final addition to the RouteCollection.

    Addition can also be used [Route ( "/ home / index")] manner, needs to be performed RouteConfig.RegisterRoutes (RouteTable.Routes) registration route;

    Or directly call RouteCollection.Add () method to register routing

Matching route: call RouteCollection of GetRouteData (), the final call GetRouteData Route (), if it returns a non-null, then match

Exclude route: IgnoreRoute (), but also to RouteCollection added a Route objects, Route of the handler is StopRoutingHandler. When routing configuration, if the matching route is to StopRoutingHandler Handler, the interrupt request

Description:

MapRoute () is added MVC routing, MapPageRoute () is added WebForm route. Their different RouteHandler, MVC is MVCRouteHandler, WebForm is PageRouteHandler

Internal MVCRouteHandler can get to IHttpHandler, implementation class is MVCHander, create Controller its PR approach, and calls Action

PageRouteHandler above, it IHttpHandler implementation class is Page, Page, there are several events, we can do the operation in the event callback.

ASP.NET MVC framework and WebForm are used, began to have differences from the routing, create a Controller, create a Page.

 

 

Custom Route:

You can customize the restrictions do some other operations, such as restrictions on domain name

    /// <summary>
    /// 支持泛域名的UrlRouting
    /// </summary>
    public class DomainRoute : RouteBase
    {
        #region 变量
        private string _domainName;
        private string _physicalFile;
        private string _routeUrl;
        private bool _checkPhysicalUrlAccess = false;
        private RouteValueDictionary _defaults;
        private RouteValueDictionary _constraints;
        private IList<PathSegment> _pathSegmentLists = new List<PathSegment>();
        private const string REPLACE_PATTEN = @"([\w,%]+)";
        private readonly Regex _patten = new Regex(@"\{([a-z,A-Z,0-9]+)\}", RegexOptions.Compiled);
        private int _segmentCount = 0;
        #endregion

        #region 构造函数
        /// <summary>
        /// 
        /// </summary>
        /// <param name="domainName">泛域名</param>
        /// <param name="routeUrl ">Url routing </ param> 
        ///  <param name = "physicalFile"> physical file mapping </ param> 
        ///  <param name = "checkPhysicalUrlAccess"> if a value that indicates whether the user should verify ASP.NET have access to the physical URL (always check the routing URL). This parameter setting System.Web.Routing.PageRouteHandler.CheckPhysicalUrlAccess </ param> 
        ///  <param name = "Defaults"> Default routes. </ param> 
        ///  <param name = "Constraints"> some constraints, URL request must satisfy to process a route. </ param> 

        public DomainRoute ( String domainName, String RouteUrl, String physicalFile, checkPhysicalUrlAccess,
             domainName.ToLower();
            this._routeUrl = routeUrl;
            this._physicalFile = physicalFile;
            this._checkPhysicalUrlAccess = checkPhysicalUrlAccess;
            this._defaults = defaults;
            this._constraints = constraints;

            IList<string> lists = SplitUrlToPathSegmentStrings(routeUrl);
            if (lists != null && lists.Count > 0)
            {
                this._segmentCount = lists.Count;
                for (int i = 0; i < lists.Count; i++)
                {
                    string strPatten = lists[i];
                    if (!string.IsNullOrWhiteSpace(strPatten) && this._patten.IsMatch(strPatten))
                    {
                        PathSegment segment = new PathSegment();
                        segment.Index = i;

                        Match match;
                        List<string> valueNames = new List<string>();
                        for (match = this._patten.Match(strPatten); match.Success; match = match.NextMatch())
                        {
                            strPatten = strPatten.Replace(match.Groups[0].Value, REPLACE_PATTEN);
                            valueNames.Add(match.Groups[1].Value);
                        }
                        segment.ValueNames = valueNames.ToArray();
                        segment.Regex = new Regex(strPatten, RegexOptions.Compiled | RegexOptions.IgnoreCase);
                        this._pathSegmentLists.Add(segment);
                    }
                }
            }
        }

        public DomainRoute(string domainName, string routeUrl, string physicalFile)
            : this(domainName, routeUrl, physicalFile, false, new RouteValueDictionary(), new RouteValueDictionary())
        {

        }
        #endregion

        #region 属性
        /// <summary>
        /// 泛域名
        /// </summary>
        public string DomainName
        {
            get { return this._domainName; }
            set { this._domainName = value; }
        }
        /// <summary>
        /// 映射的物理文件
        /// </summary>
        public string PhysicalFile
        {
            get { return this._physicalFile; }
            set { this._physicalFile = value; }
        }
        /// <summary>
        /// Url路由
        /// </summary>
        public string RouteUrl
        {
            get { return this._routeUrl; }
            set { this._routeUrl = value; }
        }
        #endregion

        #region 方法
        [DebuggerStepThrough]
        public override RouteData GetRouteData(HttpContextBase httpContext)
        {
            RouteData result = null;
            HttpRequestBase request = httpContext.Request;
            if (request.Url.Host.ToLower().Contains(this._domainName))
            {
                string virtualPath = request.AppRelativeCurrentExecutionFilePath.Substring(2) + request.PathInfo;
                IList<string> segmentUrl = SplitUrlToPathSegmentStrings(virtualPath);
                if (segmentUrl.Count == this._segmentCount)
                {
                    PathSegment pathSegment = null;
                    string path = null;
                    bool isOK = true;
                    for (int i = 0; i < this._pathSegmentLists.Count; i++)
                    {
                        pathSegment = this._pathSegmentLists[i];
                        path = segmentUrl[pathSegment.Index];
                        if (!pathSegment.Regex.IsMatch(path))
                        {
                            isOK = false;
                            break;
                        }
                    }
                    if (isOK)
                    {
                        result = new RouteData(this, new PageRouteHandler(this._physicalFile, this._checkPhysicalUrlAccess));
                        result.Values.Add("Domain", this._domainName);
                        Match match = null;
                        for (int i = 0; i < this._pathSegmentLists.Count; i++)
                        {
                            pathSegment = this._pathSegmentLists[i];
                            path = segmentUrl[pathSegment.Index];
                            match = pathSegment.Regex.Match(path);
                            if (pathSegment.ValueNames.Length + 1 == match.Groups.Count)
                            {
                                for (int j = 0; j < pathSegment.ValueNames.Length; j++)
                                {
                                    result.Values.Add(pathSegment.ValueNames[j], match.Groups[j + 1].Value);
                                }
                            }
                        }
                    }
                }
                segmentUrl.Clear();
                segmentUrl = null;
            }
            return result;
        }

        public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
        {
            return new VirtualPathData(this, this._physicalFile);
        }

        private static IList<string> SplitUrlToPathSegmentStrings(string url)
        {
            List<string> list = new List<string>();
            if (!string.IsNullOrEmpty(url))
            {
                int index;
                for (int i = 0; i < url.Length; i = index + 1)
                {
                    index = url.IndexOf('/', i);
                    if (index == -1)
                    {
                        string str = url.Substring(i);
                        if (str.Length > 0)
                        {
                            list.Add(str);
                        }
                        return list;
                    }
                    string item = url.Substring(i, index - i);
                    if (item.Length > 0)
                    {
                        list.Add(item);
                    }
                    //list.Add("/");
                }
            }
            list.TrimExcess();
            return list;
        }
        #endregion

        #region 内部类
        private class PathSegment
        {
            public int Index { get; set; }
            public Regex Regex { get; set; }
            public string[] ValueNames { get; set; }
        }
        #endregion
    }

Add routes:

 RouteTable.Routes.Add(new DomainRoute(urlRoutingSetting.DomainName, urlRoutingSetting.RouteUrl, urlRoutingSetting.PhysicalFile, urlRoutingSetting.CheckPhysicalUrlAccess, urlRoutingSetting.Defaults, constraints)); 

Guess you like

Origin www.cnblogs.com/fanfan-90/p/12078975.html