错误处理~跳转页面

我们经常遇到很多网站在出错时不报黄屏,而是跳转到了一个错误页面,那么这个效果如何实现的呢?请看下面→_→ 

第一种实现:

1.首先在Global里面将FilterConfig转到定义将filters.Add(new HandleErrorAttribute());这段代码注释掉

2.在WebConfig里面进行配置

 <customErrors mode="On" defaultRedirect="~/Home/Error1">
      <error statusCode="404" redirect="~/Home/Error2"/>
      <error statusCode="500" redirect="~/Home/Error3"/>
    </customErrors>

第二种实现:

1.首先在Global里面将FilterConfig转到定义将filters.Add(new HandleErrorAttribute());这段代码改为 filters.Add(new MyExpressionAttribute());

2.添加自定义实现:(PS:这个跳转的错误页路径一定要对,不然会因导致404错误进而实现不了想要的结果)

 public class MyExpressionAttribute : HandleErrorAttribute
        {
            public override void OnException(ExceptionContext filterContext)
            {

                //1.错误处理(写日志)
                string errorStr = filterContext.Exception.StackTrace;//获取错误信息
                                                                     //2.跳转错误页
                filterContext.HttpContext.Response.Redirect("~/Home/Error", true);//调到自己定义的Error.html页
            }
        }

--------还可以自己写一个过滤器类,然后加标记就行了

   public class ErrorAttribute : ActionFilterAttribute, IExceptionFilter
    {
        public void OnException(ExceptionContext filterContext)
        {
            //获取异常信息,入库保存
            Exception Error = filterContext.Exception;
            string Message = Error.Message;//错误信息
            string Url = HttpContext.Current.Request.RawUrl;//错误发生地址

            filterContext.ExceptionHandled = true;
            filterContext.Result = new RedirectResult("~/Home/Error");//跳转至错误提示页面
        }
    }

第三种实现: (通过Application_Error实现)

1.在Global.asax.cs实现如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Security;
using System.Web.SessionState;
using System.Text;
using net.itcast.cn.ashx.crud.utiliy;

namespace 请求流程
{
    public class Global : System.Web.HttpApplication
    {

        protected void Application_Start(object sender, EventArgs e)
        {

        }

        protected void Session_Start(object sender, EventArgs e)
        {

        }

        protected void Application_BeginRequest(object sender, EventArgs e)
        {

        }

        protected void Application_AuthenticateRequest(object sender, EventArgs e)
        {

        }
        //页面出错时执行的方法
        protected void Application_Error(object sender, EventArgs e)
        {
        //1.获取最后一次出错的错误对象
            Exception exMsg = Context.Server.GetLastError();
        //2.根据错误对象生成错误消息
            StringBuilder sbLogText = new StringBuilder();
        //写入时间
            sbLogText.AppendLine(DateTime.Now.ToString("yyyy-MM-dd hh:mm:ss"));
            //写入具体的错误信息
            sbLogText.AppendLine("错误消息:"+exMsg.Message);
            sbLogText.AppendLine("错误详细信息:" + exMsg.StackTrace);          
            if (exMsg.InnerException != null)
            {
                sbLogText.AppendLine("=============内部异常信息============"+exMsg.InnerException.Message);
                sbLogText.AppendLine(Environment.NewLine);                

            }
            sbLogText.AppendLine("-------------出错客户端IP:" + Context.Request.UserHostAddress + "-----------");
            //3.把错误的字符串传递给对应的记录日志的方法
            LogHelper.LogEnqueue(sbLogText.ToString());
            Context.Response.Redirect("~/MyErrorPage.aspx");//跳转到错误界面
        }

        protected void Session_End(object sender, EventArgs e)
        {

        }

        protected void Application_End(object sender, EventArgs e)
        {

        }
    }
}

上面用到的LogHelper实现如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Web;
using System.IO;

namespace net.itcast.cn.ashx.crud.utiliy
{
 //记录日志的方法 
    public static class LogHelper
    {
        //声明一个静态的队列集合
        private static Queue<string> _queue;

        //静态构造函数
        //静态构造函数只在第一次使用静态类之前执行一次。
        static LogHelper()
        {
            //new 一个队列集合对象
            _queue = new Queue<string>();

            //获取HttpContext上下文对象
            HttpContext context = HttpContext.Current;
            //获取日志文件的路径
            string path = context.Request.MapPath("~/App_Data/");//记录日志的目录

            //开启一个新的线程,这个线程的作用就是把_queue中的错误信息不断的写入到日志文件中
            Thread tWriteLog = new Thread(new ThreadStart(() =>
            {
                while (true)
                {
                    bool isQueueEmpty = false;//标记当前队列中的信息是否为空
                    string exMsg = string.Empty;
                    //1.判断队列中是否有错误信息
                    lock ("net.itcast.cn.heima13net.dibazu.ays_hfx")
                    {
                        //判断队列中是否有错误信息
                        if (_queue.Count > 0)
                        {
                            //则从队列中获取一条错误信息
                            exMsg = _queue.Dequeue();
                        }
                        else
                        {
                            isQueueEmpty = true;//标记队列中为空
                        }
                    }

                    if (isQueueEmpty)
                    {
                        Thread.Sleep(100);
                    }
                    else if (exMsg != null)
                    {

                        //将错误信息写入到日志文件中。
                        string logFilePath = Path.Combine(path, DateTime.Now.ToString("yyyy-MM-dd") + ".txt");
                        //1.获取日志文件要保存的路径
                        File.AppendAllText(logFilePath, exMsg);
                    }

                }
            }));
            tWriteLog.IsBackground = true;
            tWriteLog.Start();
        }

        // 向队列中写入数据
        public static void LogEnqueue(string logTxt)
        {
            lock ("net.itcast.cn.heima13net.dibazu.ays_hfx")
            {
                //把错误信息入队!
                _queue.Enqueue(logTxt);
            }

        }

    }

}

 

posted @ 2017-10-04 08:58  shuai7boy  阅读(1592)  评论(0编辑  收藏  举报