我在们使用ASP.Net开发WEB网站时,有的时候是不让同一个用户名在同一时间进行多次登陆的。
为了不影响原来的整个网站,我选择使用了HttpModuler来实现。
先让所有的Page从自己的Page类:BasePage类继承,并实现 ISigleLogin接口。相关代码如下:
public interface ISingleLogin
{
string SigleUserLoginId { get; }
void SigleUserLogout();
}
{
string SigleUserLoginId { get; }
void SigleUserLogout();
}
public class BasePage : System.Web.UI.Page , BNet.Web.Modulers.ISingleLogin
{
public BasePage()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
if (Session["UserId"] == null)
{
Response.Write("你还没有登陆");
Response.Redirect("login.aspx");
}
}
#region ISingleLogin 成员
public string SigleUserLoginId
{
get
{
if (Session["UserId"] != null)
{
return Session["UserId"].ToString();
}
else
return "";
}
}
public void SigleUserLogout()
{
Session.Abandon();
Response.Write("你在别处已经登陆,强制退出本次登陆!");
}
#endregion
}
{
public BasePage()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
if (Session["UserId"] == null)
{
Response.Write("你还没有登陆");
Response.Redirect("login.aspx");
}
}
#region ISingleLogin 成员
public string SigleUserLoginId
{
get
{
if (Session["UserId"] != null)
{
return Session["UserId"].ToString();
}
else
return "";
}
}
public void SigleUserLogout()
{
Session.Abandon();
Response.Write("你在别处已经登陆,强制退出本次登陆!");
}
#endregion
}
然后在Web.config中加入HttpModuler:
<system.web>
<httpModules>
<add name="SingleLogin" type="BNet.Web.Modulers.SingleLoginModuler"/>
</httpModules>
</system.web>
<httpModules>
<add name="SingleLogin" type="BNet.Web.Modulers.SingleLoginModuler"/>
</httpModules>
</system.web>
相关的SigleLoginModuler代码如下:[依评论修改后]
using System;
using System.Collections.Generic;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.UI;
namespace BNet.Web.Modulers
{
/// <summary>
/// SingleLoginModuler 的摘要说明
/// </summary>
public class SingleLoginModuler : System.Web.IHttpModule
{
const string sigle_login_userid = "evlon_siglelogin_userid";
const string sigle_pre_logout_sessionid = "evlon_sigle_pre_logout_sessionid";
public static StringLifeValueDictionary UsableGetter(ref StringLifeValueDictionary dic)
{
if (dic == null)
{
dic = new StringLifeValueDictionary();
}
else
{
List<string> listRemove = new List<string>();
StringLifeValueDictionary.Enumerator iter = dic.GetEnumerator();
while (iter.MoveNext())
{
if (iter.Current.Value.life < DateTime.Now)
{
listRemove.Add(iter.Current.Key);
}
}
foreach (string key in listRemove)
{
dic.Remove(key);
}
}
return dic;
}
static StringLifeValueDictionary loginedUserIdDictionary = null;
static StringLifeValueDictionary LoginedUserIdDictionary
{
get
{
return UsableGetter(ref loginedUserIdDictionary);
}
}
static StringLifeValueDictionary preLogoutSessionIdDictionary = null;
static StringLifeValueDictionary PreLogoutSessionIdDictionary
{
get
{
return UsableGetter(ref preLogoutSessionIdDictionary);
}
}
public SingleLoginModuler()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
#region IHttpModule 成员
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.PreRequestHandlerExecute += new EventHandler(context_PreRequestHandlerExecute);
context.PostRequestHandlerExecute += new EventHandler(context_PostRequestHandlerExecute);
}
void context_PreRequestHandlerExecute(object sender, EventArgs e)
{
HttpApplication context = sender as HttpApplication;
IHttpHandler httpHandler = context.Context.CurrentHandler;
ISingleLogin sl = httpHandler as ISingleLogin;
if (sl != null)
{
string suid = sl.SigleUserLoginId;
if (suid != string.Empty)
{
if (PreLogoutSessionIdDictionary.ContainsKey(context.Session.SessionID))
{
//这个用户应该强制登出
PreLogoutSessionIdDictionary.Remove(context.Session.SessionID);
Page page = (Page)httpHandler;
page.PreInit += new EventHandler(page_PreInit);
}
else if (!LoginedUserIdDictionary.ContainsKey(suid))
{
LoginedUserIdDictionary.Add(suid, new LifeValue(context.Session.SessionID));
}
}
}
}
void page_PreInit(object sender, EventArgs e)
{
Page page = sender as Page;
ISingleLogin sl = page as ISingleLogin;
if (sl != null)
{
sl.SigleUserLogout();
page.Response.End();
}
}
void context_PostRequestHandlerExecute(object sender, EventArgs e)
{
//从LogineduserId 里找到和当前用户一样的用户ID的SessionId
HttpApplication context = sender as HttpApplication;
IHttpHandler httpHandler = context.Context.CurrentHandler;
ISingleLogin sl = httpHandler as ISingleLogin;
if (sl != null)
{
string suid = sl.SigleUserLoginId;
if (suid != string.Empty)
{
if (LoginedUserIdDictionary.ContainsKey(suid))
border-right: #808080 1px solid; border-top: #808080 1px so
using System.Collections.Generic;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.UI;
namespace BNet.Web.Modulers
{
/// <summary>
/// SingleLoginModuler 的摘要说明
/// </summary>
public class SingleLoginModuler : System.Web.IHttpModule
{
const string sigle_login_userid = "evlon_siglelogin_userid";
const string sigle_pre_logout_sessionid = "evlon_sigle_pre_logout_sessionid";
public static StringLifeValueDictionary UsableGetter(ref StringLifeValueDictionary dic)
{
if (dic == null)
{
dic = new StringLifeValueDictionary();
}
else
{
List<string> listRemove = new List<string>();
StringLifeValueDictionary.Enumerator iter = dic.GetEnumerator();
while (iter.MoveNext())
{
if (iter.Current.Value.life < DateTime.Now)
{
listRemove.Add(iter.Current.Key);
}
}
foreach (string key in listRemove)
{
dic.Remove(key);
}
}
return dic;
}
static StringLifeValueDictionary loginedUserIdDictionary = null;
static StringLifeValueDictionary LoginedUserIdDictionary
{
get
{
return UsableGetter(ref loginedUserIdDictionary);
}
}
static StringLifeValueDictionary preLogoutSessionIdDictionary = null;
static StringLifeValueDictionary PreLogoutSessionIdDictionary
{
get
{
return UsableGetter(ref preLogoutSessionIdDictionary);
}
}
public SingleLoginModuler()
{
//
// TODO: 在此处添加构造函数逻辑
//
}
#region IHttpModule 成员
public void Dispose()
{
}
public void Init(HttpApplication context)
{
context.PreRequestHandlerExecute += new EventHandler(context_PreRequestHandlerExecute);
context.PostRequestHandlerExecute += new EventHandler(context_PostRequestHandlerExecute);
}
void context_PreRequestHandlerExecute(object sender, EventArgs e)
{
HttpApplication context = sender as HttpApplication;
IHttpHandler httpHandler = context.Context.CurrentHandler;
ISingleLogin sl = httpHandler as ISingleLogin;
if (sl != null)
{
string suid = sl.SigleUserLoginId;
if (suid != string.Empty)
{
if (PreLogoutSessionIdDictionary.ContainsKey(context.Session.SessionID))
{
//这个用户应该强制登出
PreLogoutSessionIdDictionary.Remove(context.Session.SessionID);
Page page = (Page)httpHandler;
page.PreInit += new EventHandler(page_PreInit);
}
else if (!LoginedUserIdDictionary.ContainsKey(suid))
{
LoginedUserIdDictionary.Add(suid, new LifeValue(context.Session.SessionID));
}
}
}
}
void page_PreInit(object sender, EventArgs e)
{
Page page = sender as Page;
ISingleLogin sl = page as ISingleLogin;
if (sl != null)
{
sl.SigleUserLogout();
page.Response.End();
}
}
void context_PostRequestHandlerExecute(object sender, EventArgs e)
{
//从LogineduserId 里找到和当前用户一样的用户ID的SessionId
HttpApplication context = sender as HttpApplication;
IHttpHandler httpHandler = context.Context.CurrentHandler;
ISingleLogin sl = httpHandler as ISingleLogin;
if (sl != null)
{
string suid = sl.SigleUserLoginId;
if (suid != string.Empty)
{
if (LoginedUserIdDictionary.ContainsKey(suid))
border-right: #808080 1px solid; border-top: #808080 1px so
相关推荐
首先,我们需要理解SSO的核心思想:当用户在一个地方登录后,他不能在其他地方再次登录,除非在原来的登录位置先进行登出。为了实现这个功能,我们通常会使用以下策略: 1. **会话管理**:在用户成功登录后,服务器...
在编程领域,特别是桌面应用程序开发中,有时我们希望程序在用户尝试多次启动时,只会运行一个实例。这种设计可以防止资源浪费,确保程序状态的一致性,并提供更好的用户体验。在VC++(Visual C++)环境下,我们可以...
在Windows Presentation Foundation(WPF)应用开发中,有时我们需要确保应用程序只能运行一个实例,即实现“单实例应用程序”。这样的设计可以防止用户意外打开多个相同的应用程序窗口,保持系统资源的有效利用。本...
标题中的“只打开应用程序的一个实例”是指在操作系统中运行某个应用程序时,确保同一时间只能有一个该应用的实例在运行。这种功能通常用于防止用户无意或有意地多次启动同一个程序,从而造成资源浪费或数据冲突。这...
在多用户环境中,确保一个ASP.NET网页在同一时刻仅被一个登录用户占用是非常重要的,这涉及到用户体验、数据一致性和安全性。这种需求通常被称为“独占访问”或“会话锁定”。 在ASP.NET中,实现独占访问的一种常见...
在开发过程中,有时我们需要确保应用程序在同一时间内只能有一个实例运行,尤其是在客户端应用或者一些特定的服务程序中。这种需求通常出现在多种编程语言和框架中,包括.NET框架下的ASP.NET应用程序。本文将详细...
标题中的“delphi_一次只运行一个程序原代码”指的是使用Delphi编程语言编写的一种机制,确保同一时间只有一个实例的程序在运行。这种技术通常用于单例应用,比如某些设置程序或守护进程,它们需要保证在系统中仅有...
本主题聚焦于如何利用PyQt5在同一个窗口下实现多个界面的切换,这对于构建复杂的桌面应用尤其有用。下面我们将深入探讨这个话题。 首先,了解PyQt5的基础。PyQt5是Python对Qt库的封装,Qt是一个功能强大的跨平台...
在IT行业中,尤其是在软件开发领域,确保程序只能在同一时间运行一个实例是非常常见的需求。这通常被称为单实例应用程序设计。这样的设计可以防止用户错误地启动多个相同程序的副本,避免资源浪费,或者解决某些程序...
最好只存储一个可以验证身份的标识,如哈希过的用户ID。 - 使用HTTPS协议以保护数据传输过程的安全。 - 设置适当的Cookie和Session生命周期,防止长期有效的登录令牌被滥用。 6. **最佳实践**: - 考虑使用更...
在这个平台上,开发者可以利用Web技术,通过浏览器直接访问和控制海康威视的设备,实现远程视频监控和管理。 "webVideoCtrl.js"是海康威视Web开发插件的核心组件,它是一段JavaScript源码,包含了丰富的API接口,...
在VB.NET编程中,有时我们需要让多个控件共享同一个事件处理程序,以简化代码和提高效率。本实例将深入探讨如何使用VB.NET的事件委托来实现这一目标,特别是在Windows Forms应用中。首先,理解事件和委托是关键。 ...
Delphi中防止运行一个应用程序的多个实例2个办法 弹出提醒 激活窗口 Delphi源代码3份。
通过多个典型工程实例对上述三个层次的开发技术和编程技巧进行讲解,并对同一实例的多个解决方案进行对比分析,切实帮助开发人员提高JAVA EE Web开发水平。 除了对JAVA EE Web编程基本技术的讲解淙外,还针对Web...
在IT领域,尤其是在系统管理和软件开发中,有时我们需要让一个应用程序的多个实例共享同一个进程空间。这通常是出于性能优化、资源共享或减少系统资源消耗的目的。本文将深入探讨如何实现这一目标,并提供相关技术...
在企业级应用开发中,为了提高服务器资源利用率以及更好地进行应用程序的隔离与管理,经常需要在同一台物理服务器上部署多个独立的应用服务器实例。本文将详细介绍如何在 JBoss 4.2 上实现这一需求,即在同一 IP ...
这一步至关重要,因为“新建会话”不同于“新建窗口”或“新建选项卡”,它创建的是一个独立的浏览器实例,拥有自己的Cookie存储空间。 3. 现在,你会看到一个新的IE浏览器窗口出现。虽然外观上与普通窗口无异,但这...
本书对Spring的核心概念进行详细讲解,并提供具体的持久化操作实例,例如实现一个图书馆管理系统。 4. 框架的整合应用:本书不仅讲解了各个框架的独立使用,还着重于如何将这些流行的框架进行整合,构建更加灵活和...
这种设计模式确保一个应用程序在同一时间只能有一个实例在运行,不允许用户启动第二个实例。这样的限制有助于避免资源浪费、数据冲突和其他潜在问题。以下是对这个主题的详细阐述: 1. **单实例应用程序的概念**: ...