Что ж, это сложно для запросов AJAX, как заметил Жаф, - Бен Дугид. Вот мое решение, чтобы заставить это работать с AJAX (используя веб-элементы управления Telerik, но я думаю, что они построены с использованием набора инструментов ASP.NET AJAX).
В двух словах, я прокрутил свою собственную вещь типа сеанса скользящего выдоха.
В моем Site.Master я обновляю переменную сеанса при КАЖДОЙ обратной передаче (запрос обратной передачи или AJAX, поскольку запросы AJAX по-прежнему инициируют событие Page_Load):
protected void Page_Load(object sender, EventArgs e)
{
if (!this.IsPostBack)
{
if (this.Request.IsAuthenticated)
this.pnlSessionKeepAlive.Visible = true;
else
this.pnlSessionKeepAlive.Visible = false;
}
if (this.Session["SessionStartDateTime"] != null)
this.Session["SessionStartDateTime"] = DateTime.Now;
else
this.Session.Add("SessionStartDateTime", DateTime.Now);
}
Затем в своей разметке для site.master я включил iframe со страницей ASPX, которую я использую «за кулисами», чтобы проверить, не истек ли мой пользовательский скользящий срок действия:
<asp:Panel runat="server" ID="pnlSessionKeepAlive" Visible="false">
<iframe id="frame1" runat="server" src="../SessionExpire.aspx" frameborder="0" width="0" height="0" / >
</asp:Panel>
Теперь на моей странице SessionExpire.aspx я просто обновляю страницу время от времени и проверяю, истекла ли временная метка, и если да, я перенаправляю на свою страницу logout.aspx, которая затем определяет, на какую страницу входа отправлять пользователя обратно. :
public partial class SessionExpire : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
/* We have to do all of this because we need to redirect to 2 different login pages. The default .NET
* implementation does not allow us to specify which page to redirect expired sessions, its a fixed value.
*/
if (this.Session["SessionStartDateTime"] != null)
{
DateTime StartTime = new DateTime();
bool IsValid = DateTime.TryParse(this.Session["SessionStartDateTime"].ToString(), out StartTime);
if (IsValid)
{
int MaxSessionTimeout = Convert.ToInt32(ConfigurationManager.AppSettings["SessionKeepAliveMins"]);
IsValid = (DateTime.Now.Subtract(StartTime).TotalMinutes < MaxSessionTimeout);
}
// either their session expired or their sliding session timeout has expired. Now log them out and redirect to the correct
// login page.
if (!IsValid)
this.Logout();
}
else
this.Logout();
// check every 60 seconds to see if the session has expired yet.
Response.AddHeader("Refresh", Convert.ToString(60));
}
private void Logout()
{
this.Page.ClientScript.RegisterClientScriptBlock(this.GetType(), "TimeoutScript",
"setTimeout(\"top.location.href = '../Public/Logout.aspx'\",\"1000\");", true);
}
}
Большое спасибо вышеупомянутым людям, которые разместили информацию, это привело меня к моему решению и надеюсь, что оно поможет другим.