/// <summary>
    /// Handler mapping handler.
    /// </summary>
    public static void CMSMapRequestHandler(object sender, EventArgs e)
    {
        URLRewritingResultEnum status = URLRewriter.CurrentStatus;
        if (ConnectionAvailable && (status != URLRewritingResultEnum.SentFromCache))
        {
            RequestHelper.LogRequestOperation("MapRequestHandler", null, 0);
            DebugHelper.SetContext("MapRequestHandler");

            // Handle the event
            var h = CMSRequestEvents.MapRequestHandler.StartEvent(e);
            if (h.Continue)
            {
                // Get request parameters
                string relativePath = URLHelper.CurrentRelativePath;

                ExcludedSystemEnum excludedEnum = RequestHelper.CurrentExcludedStatus;
                if (excludedEnum == ExcludedSystemEnum.Unknown)
                {
                    excludedEnum = URLHelper.IsExcludedSystemEnum(relativePath);
                }

                ViewModeOnDemand viewMode = new ViewModeOnDemand();
                SiteNameOnDemand siteName = new SiteNameOnDemand();

                // Handle the virtual context
                HandleVirtualContext(ref relativePath, ref excludedEnum);

                // Set flag to output filter for cms dialogs
                if (excludedEnum == ExcludedSystemEnum.CMSDialog)
                {
                    OutputFilter.UseFormActionWithCurrentURL = true;
                }

                // Perform the URL rewriting
                RewriteUrl(status, relativePath, excludedEnum, viewMode, siteName);
            }

            // Finalize the event
            h.FinishEvent();

            DebugHelper.ReleaseContext();
        }
    }
    /// <summary>
    /// Custom cache parameters processing.
    /// </summary>
    public static string CMSGetVaryByCustomString(HttpContext context, string custom)
    {
        if (context == null)
        {
            return "";
        }

        HttpResponse response = context.Response;

        // Do not cache on postback
        if (URLHelper.IsPostback())
        {
            response.Cache.SetNoStore();
            return Guid.NewGuid().ToString();
        }

        PageInfo currentPage = CMSContext.CurrentPageInfo;
        string result = null;

        // Cache control
        if ((currentPage != null) && !custom.StartsWith("control;"))
        {
            // Check page caching minutes
            int cacheMinutes = currentPage.NodeCacheMinutes;
            if (cacheMinutes <= 0)
            {
                // Do not cache
                response.Cache.SetNoStore();
                return Guid.NewGuid().ToString();
            }
        }

        SiteNameOnDemand siteName = new SiteNameOnDemand();
        ViewModeOnDemand viewMode = new ViewModeOnDemand();

        // Parse the custom parameters
        string contextString = CMSContext.GetContextCacheString(custom, viewMode, siteName);
        if (contextString == null)
        {
            // Do not cache
            response.Cache.SetNoStore();
            return Guid.NewGuid().ToString();
        }
        else
        {
            result = "cached" + contextString;
        }

        return result.ToLower();
    }
    /// <summary>
    /// Rewrites the URL and performs all operations required after URL rewriting.
    /// </summary>
    /// <param name="status">Current rewriting status</param>
    /// <param name="relativePath">Relative path</param>
    /// <param name="excludedEnum">Excluded page status</param>
    /// <param name="viewMode">View mode</param>
    /// <param name="siteName">Site name</param>
    private static void RewriteUrl(URLRewritingResultEnum status, string relativePath, ExcludedSystemEnum excludedEnum, ViewModeOnDemand viewMode, SiteNameOnDemand siteName)
    {
        // Do the rewriting if status not yet determined
        if (status == URLRewritingResultEnum.Unknown)
        {
            RequestHelper.LogRequestOperation("RewriteURL", relativePath, 0);

            // Rewrite URL
            status = URLRewriter.RewriteUrl(relativePath, excludedEnum, siteName, viewMode);
        }

        // Process actions after rewriting
        URLRewriter.ProcessRewritingResult(status, excludedEnum, siteName, viewMode, relativePath);
    }
    /// <summary>
    /// Request authorization handler.
    /// </summary>
    public static void CMSAuthorizeRequest(object sender, EventArgs e)
    {
        RequestHelper.LogRequestOperation("AuthorizeRequest", null, 0);
        DebugHelper.SetContext("AuthorizeRequest");

        if (ConnectionAvailable)
        {
            // Handle the event
            var h = CMSRequestEvents.Authorize.StartEvent(e);
            if (h.Continue)
            {
                string relativePath = URLHelper.CurrentRelativePath;

                // Check the excluded status
                ExcludedSystemEnum excludedEnum = URLHelper.IsExcludedSystemEnum(relativePath);

                RequestHelper.CurrentExcludedStatus = excludedEnum;

                ViewModeOnDemand viewMode = new ViewModeOnDemand();
                SiteNameOnDemand siteName = new SiteNameOnDemand();

                // Try to send the output from the cache without URL rewriting
                if (URLRewriter.SendOutputFromCache(relativePath, excludedEnum, viewMode, siteName))
                {
                    if (OutputFilter.OutputFilterEndRequestRequired)
                    {
                        HttpContext.Current.RewritePath("~/CMSPages/blank.aspx");
                    }
                    return;
                }
            }

            // Finalize the event
            h.FinishEvent();
        }

        DebugHelper.ReleaseContext();
    }
    /// <summary>
    /// Request authorization handler.
    /// </summary>
    public static void CMSAuthorizeRequest(object sender, EventArgs e)
    {
        RequestHelper.LogRequestOperation("AuthorizeRequest", null, 0);
        DebugHelper.SetContext("AuthorizeRequest");

        if (ConnectionAvailable)
        {
            // Handle the event
            using (var h = CMSRequestEvents.Authorize.StartEvent(e))
            {
                if (h.Continue)
                {
                    string relativePath = URLHelper.CurrentRelativePath;

                    // Check the excluded status
                    ExcludedSystemEnum excludedEnum = URLHelper.IsExcludedSystemEnum(relativePath);

                    RequestHelper.CurrentExcludedStatus = excludedEnum;

                    ViewModeOnDemand viewMode = new ViewModeOnDemand();
                    SiteNameOnDemand siteName = new SiteNameOnDemand();

                    // Try to send the output from the cache without URL rewriting
                    if (URLRewriter.SendOutputFromCache(relativePath, excludedEnum, viewMode, siteName))
                    {
                        if (OutputFilter.OutputFilterEndRequestRequired)
                        {
                            HttpContext context = HttpContext.Current;
                            string newQuery = null;

                            // Ensure the raw URL as a part of the request
                            if (URLRewriter.FixRewriteRedirect)
                            {
                                newQuery = "rawUrl=" + HttpUtility.UrlEncode(context.Request.RawUrl);
                            }

                            context.RewritePath("~/CMSPages/blank.aspx", null, newQuery);
                        }
                        return;
                    }

                    // Handle the virtual context
                    HandleVirtualContext(ref relativePath, ref excludedEnum);

                    // Ensure routes for current site
                    CMSMvcHandler.EnsureRoutes(CMSContext.CurrentSiteName);
                }

                // Finalize the event
                h.FinishEvent();
            }
        }

        DebugHelper.ReleaseContext();
    }