Asp.Net 拦截请求自定义处理
需求:
在Aps.Net 应用中,对于浏览器请求的部分url的地址自定义处理,不交给路由系统或页面。
解决方案:
在全局文件Global.asax中 ,提供Application_BeginRequest 事件,这个事件可以监听到,本网站的所有请求都会经过这。此处根据url自定义输出响应内容,并结束响应就可以了。
自定义拦截请求示例1:
1.Global.asax 中代码处理
public class MvcApplication : System.Web.HttpApplication { LogHelper.LogHelper _log = new LogHelper.LogHelper(); protected void Application_Start() { AreaRegistration.RegisterAllAreas(); RouteConfig.RegisterRoutes(RouteTable.Routes); } /// <summary> /// 接收请求 /// </summary> protected void Application_BeginRequest() { _log.WriteLine("请求地址:" + Request.Url.AbsoluteUri); //拦截请求 string[] segments = Request.Url.Segments; if (segments.Length > 1 && segments[1].ToLower() == "testone") { //需要自己指定输出内容和类型 Response.ContentType = "text/html;charset=utf-8"; Response.Write("请求拦截处理"); Response.End(); // 此处结束响应,就不会走路由系统 } } }
2.不拦截的默认Action 定义
public class TestOneController : Controller { // GET: TestOne public ActionResult Index() { return Content("测试首页"); } }
注:调试说明,如果指定Response.End() ,就不会走路由系统,执行Action。
自定义扩展模块拦截请求处理示例2
1.定义模块,继承IHttpModule
/// <summary> /// 定时任务常用逻辑封装 /// 注:每天指定小时内循环触发,原因,保证这个小时中程序在运行或有一次访问,定时任务可以执行 /// </summary> public class TimedTask:IHttpModule { /// <summary> /// 需要全局对象,保证多线程参数统一 /// </summary> public static TaskParams Params = new TaskParams(); /// <summary> /// 标记已经运行 /// </summary> public void SetRuned() { Params.Hour_State = true; } /// <summary> /// 任务对象 /// </summary> private static Task _Task = null; /// <summary> /// 执行事件处理 /// </summary> public Action OnRunning = null; /// <summary> /// 执行异常 /// </summary> public Action<Exception> OnError = null; /// <summary> /// 监听请求处理 /// </summary> private void Init() { } /// <summary> /// 开启监听处理 /// </summary> public void Start() { if (_Task != null) { //if (_Task.Status != TaskStatus.Running) //{ // _Task.RunSynchronously(); //} return; } //开启定时任务 _Task = new Task(() => { while (true) { try { //判断达到对应小时执行 if (DateTime.Now.Hour == Params.TaskHour) { //外部处理,具体内容 OnRunning?.Invoke(); } else { Params.Hour_State = false; } } catch (Exception ex) { Params.error_state = 1; Params.error_msg = ex.Message; OnError?.Invoke(ex); } //等待处理 Thread.Sleep(Params.SleepSpan); } }); _Task.Start(); } public void Init(HttpApplication app) { //请求监听处理 app.BeginRequest += (object sender, EventArgs e) => { HttpResponse resp = app.Response; HttpRequest req = app.Request; if (req.HttpMethod == "GET") { //拦截请求 string[] segments = req.Url.Segments; if (segments.Length > 1 && segments[1].ToLower() == "gettaskinfo") { if (_Task == null) throw new Exception("当前定时任务对象没有初始化"); JObject obj = JObject.FromObject(_Task); //合并参数 obj.Merge(JObject.FromObject(Params)); resp.Write(obj.ToString()); resp.ContentType = "application/json;charset=utf-8"; resp.End(); } } }; } public void Dispose() { throw new NotImplementedException(); } } /// <summary> /// 定时任务的参数定义 /// </summary> public class TaskParams { /// <summary> /// 定时任务每天运行的时间点 /// </summary> public int TaskHour { get; set; } = 3; /// <summary> /// 间隔执行的时间段,单位/毫秒,默认6分钟一次执行 /// </summary> public int SleepSpan { get; set; } = 1000 * 60 * 6; /// <summary> /// 判断当前小时是否已经执行,每次执行完任务标记为true /// </summary> public bool Hour_State { get; set; } /// <summary> /// 判断异常状态 /// </summary> public int error_state; /// <summary> /// 异常消息内容 /// </summary> public string error_msg; }
2.注册启动模块
在AssemblyInfo程序加载文件定义:
//定义程序启动时处理方法 [assembly: PreApplicationStartMethod(typeof(TestOne), "Start")]
在启动方法中,注册模块和启用定时任务,关于启动方法:http://www.cnblogs.com/tianma3798/p/8251858.html
public class TestOne { /// <summary> /// 程序启动时,PreApplicationStartMethod中指定的方法必须是公共静态的 /// </summary> public static void Start() { LogHelper.LogHelper _log = new LogHelper.LogHelper(); _log.WriteLine("程序启动成功1"); //启用定时任务 TimedTask _task = new TimedTask(); //指定运行的小时点 TimedTask.Params.TaskHour = DateTime.Now.Hour; TimedTask.Params.SleepSpan = 1000 * 5; _task.OnRunning += () => { _task.SetRuned(); _log.WriteLine("定时任务已经执行"); }; _task.OnError += (ex) => { _log.WriteLine("定时任务执行失败:" + ex.Message); }; _task.Start(); HttpApplication.RegisterModule(typeof(TimedTask)); } }
更多:
Asp.Net HttpApplication请求管道与Session(一)
Asp.Net HttpApplication请求管道与Session(二)