C# 路由重写 地址重写 操作类

本文介绍了一个自定义的HTTP模块,该模块用于处理Web应用程序中的异常,并通过配置实现URL重写功能。文章详细解释了如何捕获并处理404和500错误,同时展示了如何根据不同配置项重定向或改写URL。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using System.Web;
using XiaoFeng.UrlRewrite;

namespace XiaoFeng.Web
{
    /// <summary>
    /// Web HttpModule
    /// </summary>
    public class HttpModule : IHttpModule, IDisposable
    {
        /// <summary>
        /// 构造器
        /// </summary>
        public HttpModule() { }
        /// <summary>
        /// 释放资源
        /// </summary>
        public void Dispose() { GC.SuppressFinalize(this); }
        /// <summary>
        /// 析构方法
        /// </summary>
        ~HttpModule() { }
        /// <summary>
        /// 实现接口的Init方法
        /// </summary>
        /// <param name="context">全局对象</param>
        public void Init(HttpApplication context)
        {
            context.BeginRequest += new EventHandler(Application_BeginRequest);
            context.Error += new EventHandler(Application_OnError);
            context.EndRequest += new EventHandler(Application_EndRequest);
            context.PreSendRequestHeaders += new EventHandler(OnPreSendRequestHeaders);
        }
        /// <summary>
        /// 错误方法
        /// </summary>
        /// <param name="sender">对象</param>
        /// <param name="e">对象</param>
        protected void Application_OnError(Object sender, EventArgs e)
        {
            StringBuilder Sbr = new StringBuilder();
            //此处处理异常
            //HttpResponse Response = HttpContext.Current.Response;
            // HttpRequest Request = HttpContext.Current.Request;

            //获取到HttpUnhandledException异常,这个异常包含一个实际出现的异常
            Exception ex = HttpContext.Current.Server.GetLastError();
            //实际发生的异常
            Exception iex = ex.InnerException;
            /*记录异常到日志*/
            LogHelper.WriteLog(iex);
            HttpException httpException = ex as HttpException;
            if (httpException.GetHttpCode() == 404)
            {
                HttpContext.Current.Server.ClearError();
                Sbr.Append(@"
                 <tr>
                     <th>错误信息:</th>
                     <td>当前请求地址不存在,或已被管理员删除。</td>
                 </tr>
                ");
                Web.Error.writeContent("404", Sbr.ToString(), true);
            }
            string _Error = Config.GetConfig("Error");
            Boolean f = true;
            if (_Error == "1")
            {
                Sbr.Append(@"
                <tr>
                     <th>错误源:</th>
                     <td>" + iex.Source + @"</td>
                </tr>
                <tr>
                     <th>所属类:</th>
                     <td>" + iex.TargetSite.DeclaringType.FullName + @"[" + iex.TargetSite.DeclaringType.Namespace + @"]</td>
                </tr>
                <tr>
                     <th>错误信息:</th>
                     <td>" + iex.Message + @"</td>
                </tr>
                <tr>
                     <th>错误堆栈:</th>
                     <td>" + Regex.Replace(Regex.Replace(iex.StackTrace, @"[\n]", "<br/>"), @"(行号\s*\d*)", "<span>$1</span>", RegexOptions.IgnoreCase) + @"</td>
                </tr>
");
                f = false;
            }
            else if (_Error == "0" || _Error.IsNullOrEmpty())
            {
                Sbr.Append(@"
                 <tr>
                     <th>错误信息:</th>
                     <td>当前请求出现了异常,如果您是管理员,请到空间相关目录查看当前异常信息。</td>
                 </tr>
                 ");
                f = true;
            }
            if (_Error != "2")
            {
                HttpContext.Current.Server.ClearError();
                Web.Error.writeContent("500", Sbr.ToString(), f);
            }
        }
        /// <summary>
        /// 重写Url
        /// </summary>
        /// <param name="sender">事件的源</param>
        /// <param name="e">包含事件数据的 EventArgs</param>
        protected void Application_BeginRequest(object sender, EventArgs e)
        {
            HttpApplication context = (HttpApplication)sender;
            HttpRequest Request = context.Request;
            //HttpResponse Response = context.Response;
            string root = System.AppDomain.CurrentDomain.BaseDirectory;
            string curPath = Request.Url.AbsolutePath;
            string MyHost = Request.Url.Host;
            string goUrl = curPath;
            string QueryString = Request.Url.Query.Trim('?');
            string _curPath = root + curPath.Replace("/", "\\").TrimStart('\\');
            if (!curPath.isPattern(@"\.asmx/?"))
            {
                if (!File.Exists(_curPath))
                {
                    List<ConfigElement> MyConfig = XiaoFeng.UrlRewrite.Config.GetData();
                    string SendType = "";
                    foreach (ConfigElement Element in MyConfig)
                    {
                        string LookFor = Element.LookFor.TrimStart('~'), SendTo = Element.SendTo.TrimStart('~');
                        if (curPath == "/")
                        {
                            if (LookFor == "/" || LookFor == MyHost) { goUrl = SendTo;SendType = Element.SendType; break; }
                        }
                        else
                        {
                            if (LookFor == "/" || LookFor == MyHost) continue;
                            if (Regex.IsMatch(curPath, @"^" + LookFor + @"$", RegexOptions.IgnoreCase))
                            {
                                if (LookFor.IndexOf("(", StringComparison.OrdinalIgnoreCase) > -1 && LookFor.IndexOf(")") > -1)
                                {
                                    if (Regex.IsMatch(SendTo, @"\$\d+"))
                                    {
                                        goUrl = Regex.Replace(curPath, LookFor, SendTo + (QueryString == "" ? "" : ((SendTo.IndexOf("?", StringComparison.OrdinalIgnoreCase) == -1 ? "?" : "&") + QueryString)), RegexOptions.IgnoreCase);
                                    }
                                    else
                                        goUrl = SendTo + (SendTo.IndexOf("?", StringComparison.OrdinalIgnoreCase) == -1 ? "?" : "&") + QueryString;
                                }
                                else
                                    goUrl = SendTo;
                                SendType = Element.SendType;
                                break;
                            }
                        }
                    }
                    if (MyConfig != null && MyConfig.Count > 0)
                    {
                        if (SendType == "301")
                        {
                            context.Context.Response.StatusCode = 301;
                            context.Context.Response.Status = "301 Moved Permanently";
                            context.Context.Response.Headers.Add("Location", goUrl);
                        }
                        else if (SendType == "302")
                            context.Context.Response.Redirect(goUrl, true);
                        else
                            context.Context.RewritePath(goUrl, true);
                    }
                }
            }
        }
        /// <summary>
        /// 结束请求
        /// </summary>
        /// <param name="sender">对象</param>
        /// <param name="e">对象</param>
        protected void Application_EndRequest(object sender, EventArgs e) { }
        /// <summary>
        /// 发送Header头请求
        /// </summary>
        /// <param name="sender">对象</param>
        /// <param name="e">对象</param>
        protected void OnPreSendRequestHeaders(object sender, EventArgs e)
        {
            HttpApplication context = (HttpApplication)sender;

            var headers = context.Context.Response.Headers;
            if (headers != null) headers.Remove("server");
        }
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值