在MVC里面使用Response.Redirect方法后记得返回EmptyResult
在ASP.NET MVC中我们很多时候都会在拦截器和Controller中直接使用Response.Redirect方法做跳转,但是实际上Response.Redirect方法执行后ASP.NET并不会立即结束当前请求的执行,而是要过一段时间才会终止当前请求的执行,然后命令客户端浏览器去访问Response.Redirect方法中传入的新的URL地址。这会导致一个问题,有时候我们希望Response.Redirect方法执行后后面的代码就取消执行了,因为这并不是我们预期的行为,当代码执行了Response.Redirect方法后,如果其后面的部分代码还继续在执行甚至有可能报错。
比如在下面的代码中我们演示了在MVC的IAuthorizationFilter拦截器中,如果用户没有登录应该立刻停止当前页面的请求,然后跳转到登录页面。我们使用了Response.Redirect方法来做跳转。
1 public class AuthenticationFilterAttribute:ActionFilterAttribute,IAuthorizationFilter,IActionFilter 2 { 3 #region IAuthorizationFilter Members 4 5 public void OnAuthorization(AuthorizationContext filterContext) 6 { 7 8 string curActionName = filterContext.ActionDescriptor.ActionName; 9 string curControllerName = filterContext.ActionDescriptor.ControllerDescriptor.ControllerName; 10 11 if (!filterContext.HttpContext.Request.IsAuthenticated && (curControllerName.ToLower() != "login" || curActionName.ToLower() != "index")) 12 { 13 filterContext.HttpContext.Response.Redirect(LoginHelper.LoginPageUrl, true); 14 return; 15 } 16 } 17 18 #endregion 19 }
结果我惊讶的发现即便代码在上面13行Response.Redirect了,ASP.NET还是执行了当前请求URL对应Controller的Action中的代码,甚至执行了Action返回的View的Razor引擎代码。。。虽然最终这个view的内容没有呈现给客户端浏览器,浏览器最后还是正确跳转到了登录页。但是根据调试我们发现即便是我们执行了Response.Redirect方法,ASP.NET之后还是执行了一大堆本不该执行的代码。
所以这个时候我们需要用到EmptyResult这个对象,我们将上面的代码改成如下所示:
1 public class AuthenticationFilterAttribute:ActionFilterAttribute,IAuthorizationFilter,IActionFilter 2 { 3 #region IAuthorizationFilter Members 4 5 public void OnAuthorization(AuthorizationContext filterContext) 6 { 7 8 string curActionName = filterContext.ActionDescriptor.ActionName; 9 string curControllerName = filterContext.ActionDescriptor.ControllerDescriptor.ControllerName; 10 11 if (!filterContext.HttpContext.Request.IsAuthenticated && (curControllerName.ToLower() != "login" || curActionName.ToLower() != "index")) 12 { 13 filterContext.HttpContext.Response.Redirect(LoginHelper.LoginPageUrl, true); 14 filterContext.Result = new EmptyResult();//加入EmptyResult就告诉ASP.NET MVC在本拦截器执行结束后,不必再为当前请求执行Controller中Action的代码 15 return; 16 } 17 } 18 19 #endregion 20 }
那么ASP.NET MVC在执行完上面的IAuthorizationFilter拦截器后,就会发现EmptyResult被赋值在了参数filterContext的Result属性上,就会终止执行Controller的Action,立即结束当前请求的执行,不会再去执行多余的代码了。
所以很多时候我们在ASP.NET中使用Response.Redirect方法时要相当小心,一定要知道Response.Redirect方法执行后并不等于代码就结束执行了,还要考虑到后面的代码一旦被误执行会有什么后果,有什么办法可以避免。在MVC中使用EmptyResult就是个不错的选择。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· C#/.NET/.NET Core优秀项目和框架2025年2月简报
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 【杭电多校比赛记录】2025“钉耙编程”中国大学生算法设计春季联赛(1)
2016-02-20 jQuery之选择器