使用 SessionExpireFilterAttribute 捕获会话超时时如何防止重定向循环?
How do I prevent a redirect loop when using SessionExpireFilterAttribute to catch session timeouts?
同样,我是 MVC 的新手,所以请放轻松。当会话过期时,我需要将用户重定向到登录页面。我找到了一种通过重载 SessionExpireFilterAttribute class 来执行此操作的方法,但我的网站陷入了重定向循环。我对 MVC 了解不够,无法弄清楚发生了什么。有人可以解释如何防止重定向循环吗?
我用作模板的主页是 http://www.codeblockdrive.com/2012/12/mvc-custom-filters-session-timeout.html,但我也搜索了 Whosebug 并查看了几个页面,包括
MVC Session timeout issue,
ASP.NET MVC Session.IsNewSession issue with Google Chrome,
Redirecting to specified controller and action in asp.net mvc action filter.
这个页面Error: "This webpage has a redirect loop" in asp.net mvc似乎最接近我的问题,但我尝试了那里提到的解决方案(将 SessionExpireFilter 移动到单独的控制器),但它没有帮助我。
这是捕获会话超时的代码。它位于 App_Start:
文件夹中名为 FilterConfig.cs 的文件中
public class FilterConfig
{
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new HandleErrorAttribute());
filters.Add(new SessionExpireFilterAttribute());
}
}
public class SessionExpireFilterAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
HttpContext ctx = HttpContext.Current;
// check if session is supported
if (ctx.Session != null)
{
// check if a new session id was generated
if (ctx.Session.IsNewSession)
{
// If it says it is a new session, but an existing cookie exists, then it must
// have timed out
string sessionCookie = ctx.Request.Headers["Cookie"];
if ((null != sessionCookie) && (sessionCookie.IndexOf("ASP.NET_SessionId") >= 0 && sessionCookie != "reset"))
{
ctx.Response.Redirect("~/Admin/Login");
}
}
base.OnActionExecuting(filterContext);
}
}
}
然后我将这段代码放在一个名为 ErrorController.cs 的控制器中。我也在 AdminController.cs 中尝试过这个,但是我将它移到了一个单独的控制器而不是登录方法。
public class ErrorController : Controller
{
[SessionExpireFilter]
public ActionResult Index2()
{
// This method will not execute if our session has expired
// render Home Page
return View();
}
}
那么这里是登录方法。它位于 AdminController.cs。当它到达 "return view" 部分时,它转到 SessionExpireFilterAttribute.
public ActionResult Login()
{
if (Session["AdminUserName"] != null)
{
return RedirectToAction("Index");
}
ModelAdminLogin obj_MAL = new ModelAdminLogin();
Session["Captcha"] = ClientUtility.GenerateRandomCode();
Session["ErrMsg"] = null;
if ((Request.Cookies["ADMINUSERNAME"] != null) && (Request.Cookies["ADMINPASSWORD"] != null))
{
obj_MAL.UserName = ClientUtility.DecryptString(Request.Cookies["ADMINUSERNAME"].Value);
obj_MAL.Password = ClientUtility.DecryptString(Request.Cookies["ADMINPASSWORD"].Value);
obj_MAL.RememberMe = true;
return View(obj_MAL);
}
else
{
return View(obj_MAL);
}
}
总而言之,当会话超时时,站点调用 SessionExpireFilterAttribute.OnActionExecuting(根据需要)重定向到视图 Admin/Login(根据需要),但在页面显示给用户之前,它调用 SessionExpireFilterAttribute.OnActionExecuting 再次开始循环。最终,我收到错误消息 "This webpage has a redirect loop." 我需要一种方法在会话结束时重定向到登录页面,而不是让它在到达登录页面后返回到 SessionExpireFilterAttribute class。
如果有任何帮助,我将不胜感激。谢谢。
我怀疑您也在登录操作上设置了属性,这会导致循环。在登录操作上使用 AllowAnonymous
属性:
[AllowAnonymous]
public ActionResult Login()
{
}
同样,我是 MVC 的新手,所以请放轻松。当会话过期时,我需要将用户重定向到登录页面。我找到了一种通过重载 SessionExpireFilterAttribute class 来执行此操作的方法,但我的网站陷入了重定向循环。我对 MVC 了解不够,无法弄清楚发生了什么。有人可以解释如何防止重定向循环吗?
我用作模板的主页是 http://www.codeblockdrive.com/2012/12/mvc-custom-filters-session-timeout.html,但我也搜索了 Whosebug 并查看了几个页面,包括 MVC Session timeout issue, ASP.NET MVC Session.IsNewSession issue with Google Chrome, Redirecting to specified controller and action in asp.net mvc action filter.
这个页面Error: "This webpage has a redirect loop" in asp.net mvc似乎最接近我的问题,但我尝试了那里提到的解决方案(将 SessionExpireFilter 移动到单独的控制器),但它没有帮助我。
这是捕获会话超时的代码。它位于 App_Start:
文件夹中名为 FilterConfig.cs 的文件中 public class FilterConfig
{
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new HandleErrorAttribute());
filters.Add(new SessionExpireFilterAttribute());
}
}
public class SessionExpireFilterAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
HttpContext ctx = HttpContext.Current;
// check if session is supported
if (ctx.Session != null)
{
// check if a new session id was generated
if (ctx.Session.IsNewSession)
{
// If it says it is a new session, but an existing cookie exists, then it must
// have timed out
string sessionCookie = ctx.Request.Headers["Cookie"];
if ((null != sessionCookie) && (sessionCookie.IndexOf("ASP.NET_SessionId") >= 0 && sessionCookie != "reset"))
{
ctx.Response.Redirect("~/Admin/Login");
}
}
base.OnActionExecuting(filterContext);
}
}
}
然后我将这段代码放在一个名为 ErrorController.cs 的控制器中。我也在 AdminController.cs 中尝试过这个,但是我将它移到了一个单独的控制器而不是登录方法。
public class ErrorController : Controller
{
[SessionExpireFilter]
public ActionResult Index2()
{
// This method will not execute if our session has expired
// render Home Page
return View();
}
}
那么这里是登录方法。它位于 AdminController.cs。当它到达 "return view" 部分时,它转到 SessionExpireFilterAttribute.
public ActionResult Login()
{
if (Session["AdminUserName"] != null)
{
return RedirectToAction("Index");
}
ModelAdminLogin obj_MAL = new ModelAdminLogin();
Session["Captcha"] = ClientUtility.GenerateRandomCode();
Session["ErrMsg"] = null;
if ((Request.Cookies["ADMINUSERNAME"] != null) && (Request.Cookies["ADMINPASSWORD"] != null))
{
obj_MAL.UserName = ClientUtility.DecryptString(Request.Cookies["ADMINUSERNAME"].Value);
obj_MAL.Password = ClientUtility.DecryptString(Request.Cookies["ADMINPASSWORD"].Value);
obj_MAL.RememberMe = true;
return View(obj_MAL);
}
else
{
return View(obj_MAL);
}
}
总而言之,当会话超时时,站点调用 SessionExpireFilterAttribute.OnActionExecuting(根据需要)重定向到视图 Admin/Login(根据需要),但在页面显示给用户之前,它调用 SessionExpireFilterAttribute.OnActionExecuting 再次开始循环。最终,我收到错误消息 "This webpage has a redirect loop." 我需要一种方法在会话结束时重定向到登录页面,而不是让它在到达登录页面后返回到 SessionExpireFilterAttribute class。
如果有任何帮助,我将不胜感激。谢谢。
我怀疑您也在登录操作上设置了属性,这会导致循环。在登录操作上使用 AllowAnonymous
属性:
[AllowAnonymous]
public ActionResult Login()
{
}