推荐.NET教程: ASP.NET C# 开发环境 Ajax教程 控件开发 统计报表 数据库 Web服务 安装部署 CommunityServer NHibernate DataGrid/GridView 实用代码 VS2005
示例源码 MVC/三层 SqlHelper 入门源码 开源 CMS Ajax/Atlas C#.net 毕业设计 源码 经典代码 商业 本站作品 持久层 随书源码 WebService 英文/汉化 Asp.net2.0

阿牛·乐园

每天进步一点点

  博客园 :: 首页 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::
  80 随笔 :: 14 文章 :: 389 评论 :: 13 引用
/*
作者:阿牛(牛昆亮) QQ:273352165 MSN:niukl@hotmail.com

声明:可以免费使用,请您保留此信息
    如果您有什么改过,记得告诉我!
*/


我在们使用ASP.Net开发WEB网站时,有的时候是不让同一个用户名在同一时间进行多次登陆的。
      为了不影响原来的整个网站,我选择使用了HttpModuler来实现。

      先让所有的Page从自己的Page类:BasePage类继承,并实现 ISigleLogin接口。相关代码如下:

    public interface ISingleLogin
    
{
        
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");
        }

    }


    
ISingleLogin 成员
}

      然后在Web.config中加入HttpModuler:

<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: 在此处添加构造函数逻辑
            
//
        }


        
IHttpModule 成员
    }


    
public class LifeValue
    
{
        
public string value;
        
public DateTime life;

        
public LifeValue(string value)
        
{
            
this.value = value;
            
this.life = DateTime.Now.AddMinutes(HttpContext.Current.Session.Timeout + 5);
        }

    }


    
public class StringLifeValueDictionary : Dictionary<string, LifeValue>
    
{

    }



    
public interface ISingleLogin
    
{
        
string SigleUserLoginId get; }

        
void SigleUserLogout();

    }

}

     如此,只在在你自己的BasePage中改动相关的代码(只两三行)就可以实现功能了。
posted on 2006-03-20 17:06 阿牛 阅读(3066) 评论(15)  编辑 收藏 网摘 所属分类: ASP.netC#

评论

#1楼  2006-03-21 09:35 高海东      
不错
  回复  引用  查看    

#2楼  2006-03-21 11:21 NeilChen123      
谢谢楼主的分享。对于代码层面我有一些小的建议:

1.
if (httpHandler is ISingleLogin)
{
ISingleLogin sl = httpHandler as ISingleLogin;

这个代码通常写为

if (httpHandler is ISingleLogin)
{
ISingleLogin sl = (ISingleLogin) httpHandler;

效率高一点,因为前面已经用过 is 判断了,强制类型转换是安全的。


2.
static StringLifeValueDictionary LoginedUserIdDictionary
static StringLifeValueDictionary PreLogoutSessionIdDictionary

这两个属性的读写逻辑是完全一样的,有重复的 bad smell,可以重构为一个同样的 getter 方法。
  回复  引用  查看    

#3楼  2006-03-21 17:53 HardRock      
asp.net 1.1下如何实现呢?
谢谢!
  回复  引用  查看    

#4楼 [楼主] 2006-03-22 10:30 阿牛      
用C#1.1的语法来实现
StringLifeValueDictionary

替换 List<string> 为 StringCollection

其它的,就没有了什么了

  回复  引用  查看    

#5楼  2006-06-28 11:49 torome      
试了几次,都不成功,能不能提供你的测试代码
linlibinmail@gmail.com
  回复  引用  查看    

#6楼 [楼主] 2006-07-01 09:04 阿牛      
@torome
http://www.cnblogs.com/Files/evlon/WebSiteSingleLogin.rar
  回复  引用  查看    

#7楼  2006-07-04 21:37 horse [未注册用户]
如何用C#1.1的语法来实现StringLifeValueDictionary ?请指导一下。
yzqhorse@hotmail.com
  回复  引用    

#8楼 [楼主] 2006-07-05 10:06 阿牛      
    //public class StringLifeValueDictionary : Dictionary<string, LifeValue>
    
//{

    
//}

    
public class StringLifeValueDictionary : System.Collections.DictionaryBase
    
{
        
public LifeValue this[string key]
        
{
            
get 
            
{
                
return (LifeValue)this.Dictionary[key];
            }

            
set
            
{
                
this.Dictionary[key] = value;