4

当用户从 ASP.net 网站注销时,有没有办法得到通知?

注意:用户可以在不访问或单击“注销”链接的情况下注销。

当用户注销时,我想清除一些与会话相关的信息,并写入数据库。

注意:LoginStatus.OnLoggedOut事件。问题是该控件并不存在于每个页面上,用户也不必使用LoginStatus控件来注销(例如,当登录超时或用户注销时)

与 Global.asax 具有全局 On Session Stop 通知的方式相同:

void Session_End(object sender, EventArgs e) 
{
}

我假设某处有一个 On User Logged Out 通知:

void LoggedOut(object sender, EventArgs e)
{
}

奖金阅读

4

3 回答 3

2

I disagree. There are times when you would want to know when a user logs out. For example I have an application that needs to scan all logged in users to see if there is "anyone home" at a management level. At times a manager might be surfing the site but not actually logged in. Their sessions might still be active because the manager would have recently logged out but is still surfing the site and the software needs to know that.

In this case I have made HttpRuntime.Cache logic to catch login events and data including user name and IP address, user name, etc. This method is called in:

public static void Application_AuthenticateRequest(object sender, EventArgs e)

I then use that data to perform logic calculating login status and other useful application details.

The following is quick and un-tested but if you are asking this sort of question I am sure you can clean it up :). I hope it helps.

 public static void HandleUserLoginLogic()
    {
        string UserName = HttpContext.Current.User.Identity.Name.ToString();
        if (UserName != null)
        {
            // if the user has logged in but we have not performed logic, do it now
            if (HttpRuntime.Cache["Authenticated_" + UserName] == null)
            {
                // absolutely confirm the user has logged in
                if (UsrMan.IsUserLoggedIn())
                {
                    // SETUP MY RUNTIME VARIABLES NOW
                    HttpRuntime.Cache["AuthenticatedIPAddress_" + System.Web.HttpContext.Current.Request.UserHostAddress] = UserName;
                    HttpRuntime.Cache["Authenticated_" + UserName] = true;
                    String[] roles = UsrMan.GetRolesForUser(UserName);
                    // handle roles for this user for future application uses in the future.
                    foreach (string role in roles)
                    {
                        // handle first time condition
                        if (HttpRuntime.Cache["AuthenticatedUserInRole_" + role] != null)
                        {
                            StringCollection scUserRole = (StringCollection)HttpRuntime.Cache["AuthenticatedUserInRole_" + role];
                            if (!scUserRole.Contains(UserName))
                            {
                                scUserRole.Add(UserName);
                                HttpRuntime.Cache["AuthenticatedUserInRole_" + role] = scUserRole;
                            }
                        }
                        // handle standard condition
                        else
                        {
                            StringCollection scUserRole = new StringCollection();
                            scUserRole.Add(UserName);
                            HttpRuntime.Cache["AuthenticatedUserInRole_" + role] = scUserRole;
                        }
                    }
                }
            }
        }

        // HANDLE LOGGED OUT CONDITION
        if ((HttpRuntime.Cache["AuthenticatedIPAddress_" + System.Web.HttpContext.Current.Request.UserHostAddress] != null) && (UserName == null))
        {
            string OldUserName = HttpRuntime.Cache["AuthenticatedIPAddress_" + System.Web.HttpContext.Current.Request.UserHostAddress].ToString();
            HttpRuntime.Cache["Authenticated_" + OldUserName] = null;
            String[] roles = UsrMan.GetRolesForUser(UserName);
            foreach (string role in roles)
            {
                StringCollection scUserRole = (StringCollection)HttpRuntime.Cache["AuthenticatedUserInRole_" + role];
                scUserRole.Remove(UserName);
                if (scUserRole.Count > 0)
                    HttpRuntime.Cache["AuthenticatedUserInRole_" + role] = scUserRole;
                else
                    HttpRuntime.Cache["AuthenticatedUserInRole_" + role] = null;
            }
        }
    }
    public static bool IsUserLoggedIn()
    {
        bool result = false;
        if (HttpContext.Current.User != null &&
      HttpContext.Current.User.Identity != null
          && HttpContext.Current.User.Identity.IsAuthenticated)
        { result = true; }
        return result;
    }
于 2013-01-11T07:07:55.923 回答
1

网站的一个基本问题是,如果用户关闭浏览器,网站永远不会知道。其含义指向更好的解决方案。您必须重新考虑“登录”到网站意味着什么。

通常,您没有理由需要知道用户何时“退出”我们的网站,因为没有“登录”。每次用户访问页面时,网络服务器都会验证他们的身份;这是否通过:

  • NTML
  • Kerberos
  • HttpAuth
  • 会话 cookie
  • 持久性 cookie
  • 其他一些机制(例如您的 IPv6 地址)

用户在每次页面加载时“登录” 。浏览器获取页面后,用户不再存在(就网络服务器而言)。这意味着用户在获取页面后立即“注销” 。

但是登录很慢

有一个特殊的登录事件的通常原因是您可以缓存用户的信息(例如名称、权限)。与其每次刷新页面时都必须进行昂贵的数据库获取,为什么不从缓存中获取呢?但是,作为一名优秀的开发人员,我们还需要在不再需要该信息时使其过期。但是由于无法知道用户何时“完成”使用您的网站,因此无法知道何时刷新缓存信息。

所以不要缓存它。

SQL Server 有一套非常先进的数据缓存机制;只需再次查询数据。

另一个尝试可能是将数据存储在用户的Session. 这是完全有效的;信息将保留在那里,直到会话结束。但是很多人反对将数据存储在 a 中Session,因为这会占用内存。他们主张将其存储在像 SQL Server 这样的数据库中。这又回到了:只需在 SQL Server 中再次查询即可。

如果获取信息很昂贵或耗时,那么您可以缓存它 - 但使用设计为缓存的缓存:

Page.Cache

这是一个别名

Page.Application.Cache
于 2012-12-01T18:07:00.150 回答
0

当您实际注销用户时,实现逻辑是否很重要?或者,如果你让它更全局处理,创建一个事件并订阅它,这样它将是事件驱动的......

于 2012-06-12T19:43:19.823 回答