论坛首页 Java企业应用论坛

限制多窗口重复登陆

浏览 23478 次
精华帖 (9) :: 良好帖 (2) :: 新手帖 (11) :: 隐藏帖 (1)
作者 正文
   发表时间:2009-12-25   最后修改:2009-12-25
Joo 写道
melin 写道
增加一个filter,保存userid和sessionid,

ConcurrentSessionController是一个接口,有两个需要实现的方法:checkAuthenticationAllowed()和registerSuccessfulAuthentication(),Spring Security提供了一个实现类ConcurrentSessionControllerImpl,经过分析缺省的实现类,发现方法allowableSessionsExceeded()处理多次并发会话,在SecurityRegistry中保存每个会话的信息,主要是用户帐号对应的会话ID(sessionId)和最后发起时间,在并发发生时,从SecurityRegistry中取出关于某个用户帐号的所有会话(spring security 可以可以控制同时同一个用户登录几次),如果exceptionIfMaximumExceeded = false,找到最早一个会话,将其释放掉,腾出空间给新会话,如果exceptionIfMaximumExceeded = true,将发出一个异常。

多谢,我去看看这个能否满足要求。我们现在使用的是在Spring源码上扩展后的一个框架,不知道是否有保留Spring Security部分了呵呵
另外,如果是多台WEB集群,每台上面的SecurityRegistry会互相复制吗?


SecurityRegistry 只是一个接口,你可以去实现字节的,例如把数据存储到memcached中或者(tt+tc)
,默认是存储在当前jvm内存中,

我这是只是说了spring security的实现方式,你可以参考,没有必要非要把spring security整合进来
0 请登录后投票
   发表时间:2009-12-25   最后修改:2009-12-25
melin 写道


SecurityRegistry 只是一个接口,你可以去实现字节的,例如把数据存储到memcached中或者(tt+tc)
,默认是存储在当前jvm内存中,

我这是只是说了spring security的实现方式,你可以参考,没有必要非要把spring security整合进来


汗,貌似这个工程就大了,有些杀鸡用牛刀的感觉
我们现在是没有分布式缓存机制的。其实之前有同学提出存在ApplicaionContext里面,但就是不知道集群情况下是否会共享ApplicationContext
0 请登录后投票
   发表时间:2009-12-25  
Joo 写道
但就是不知道集群情况下是否会共享ApplicationContext
没有那么牛叉的功能吧,


在集群环境下同步就更难了,成本更大,memcached使用很简单,是比较好的实现方式。
0 请登录后投票
   发表时间:2009-12-25  
   其实楼主换一个思路就能解决这个问题。其实我们理解的session已经包括了两个东西,一个是http session机制,而另外一个是实现servlet规范的JVM session存储对象。楼上如果将这两个理解区分开就能解决这个问题了。
    在很多具有分布式负载均衡的系统中,为了确保一个用户的多次访问都在同一个机器上(如果是不同机器就涉及到session复制),或者说能获取同一个session存储内容,都采取了加上jsessionId这样的url参数方式,它其实就是我前面讲的后者。
    楼主限制重复登录,其实只需要对后者进行管理控制,不需要关心前者是否会被创建.
0 请登录后投票
   发表时间:2009-12-25  
凤舞凰扬 写道
   其实楼主换一个思路就能解决这个问题。其实我们理解的session已经包括了两个东西,一个是http session机制,而另外一个是实现servlet规范的JVM session存储对象。楼上如果将这两个理解区分开就能解决这个问题了。
    在很多具有分布式负载均衡的系统中,为了确保一个用户的多次访问都在同一个机器上(如果是不同机器就涉及到session复制),或者说能获取同一个session存储内容,都采取了加上jsessionId这样的url参数方式,它其实就是我前面讲的后者。
    楼主限制重复登录,其实只需要对后者进行管理控制,不需要关心前者是否会被创建.


好像服务器就是根据session id来判断是否是同一个用户的,如果是一有的seesion id,则会将请求分流到之前处理这个请求的节点上。现在的问题是session id在每次IE关掉之后在客户端都没有了,服务器没办法进行识别。
不知道我的理解是否正确
1 请登录后投票
   发表时间:2009-12-25  
不知道可不可以将LZ的需求简化(一个服务器、一个应用)为?:
1、同一个用户ID,禁止其创建多个session会话。
2、同一客户端机器,依然允许登录多个不同的用户ID,但需满足第1点。

如果这样的话,我的方案是:
1、首先在应用层,是有办法可以记录该应用当前所有session会话的;
2、在1的基础上,在应用的最靠前的环节(在该环节,任何一次HTTP请求沿未导致新session会话的建立)设立过滤器(过滤每一次HTTP请求),就是在这过滤环节,判断当前session会话列表中是否包括该用户ID,如果是的话,则作出A和B中的其中一种决策:
   A、终止此次HTTP请求,请将错误信息响应给客户端,后续不再作任何处理;
   B、提示客户端,已有相同的用户ID登录,询问是否注销之前已有的同用户ID的session,并建立新的session会话(简单生硬一点的做法,干脆不“询问”,直接注销旧的session会话,然后放行此次请求)。

当然,这里的“询问”又是一个新的HTTP请求,这个请求主要包含两个关键信息,即“用户ID”及“登录密码”。

----------------------------
PS:LZ说使用到了集群,偶对多个Server间的session如何协同管理的没了解过。
0 请登录后投票
   发表时间:2009-12-26  
在session这一层写个简单的map实现session缓存吧 这样下次就直接在缓存中查找相应session信息。
0 请登录后投票
   发表时间:2009-12-26  
很简单的问题,为啥会有这么复杂的做法呢,建议楼主跳出现有的思路,重新设计吧。

一个application级的缓存就应该能解决楼主的问题了,如果群集可以借助jbosscache这样的缓存做简单的辅助就好。
0 请登录后投票
   发表时间:2009-12-26  
   楼上其实说得是蛮对的,楼主换个思路就可以了。
0 请登录后投票
   发表时间:2009-12-26  
引用
好像服务器就是根据session id来判断是否是同一个用户的,如果是一有的seesion id,则会将请求分流到之前处理这个请求的节点上。现在的问题是session id在每次IE关掉之后在客户端都没有了,服务器没办法进行识别。
不知道我的理解是否正确

   我们常说的session id是服务器判断与之相连接的客户端的会话,实质上,和我们另外一个角度理解的用户是有区别的。你说的没错,如果已经存在session,就转发。不过后面一句就陷进去了。其实我前面说过,你需要传递另外一个东西,jsessionId,你在很多网站都可以看到这种应用(尤其是IBM的),对于转发服务器来说,是否存在http session并不重要,没有创建一个就是。你session中存储的数据并不在其中,而是在你对应的JVM节点中,而它是可以通过jsessionId这样的方式去获取的。
   至于说怎么识别这样的东西,其实所有的支持负载均衡多个JVM节点并存的服务器都支持。或者大不了如楼上所说,自己建立中央缓存,自己在程序中识别这样的request参数。
0 请登录后投票
论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics