Spring 限制用户重复登录

10 篇文章 0 订阅

监听器:

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import javax.servlet.http.HttpSession;
import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;

import xxxxx.TSUser;

/**
 * 
 * @author yuki_ho
 *
 */
public class SessionUserListener implements HttpSessionListener{

    // key为sessionId,value为HttpSession,使用static,定义静态变量,使之程序运行时,一直存在内存中。  
   private static Map<String, HttpSession> sessionMap = new HashMap<String, HttpSession>(500);  
 
   /** 
    * HttpSessionListener中的方法,在创建session 
    */  
   @Override
   public void sessionCreated(HttpSessionEvent event) {  
       // TODO Auto-generated method stub  
   }  
 
   /** 
    * HttpSessionListener中的方法,回收session时,删除sessionMap中对应的session 
    */  
   @Override
   public void sessionDestroyed(HttpSessionEvent event) {  
       getSessionMap().remove(event.getSession().getId());  
   }  
 
   /** 
    * 得到在线用户会话集合 
    */  
   public static List<HttpSession> getUserSessions() {  
       List<HttpSession> list = new ArrayList<HttpSession>();  
       Iterator<String> iterator = getSessionMapKeySetIt();  
       while (iterator.hasNext()) {  
           String key = iterator.next();  
           HttpSession session = getSessionMap().get(key);  
           list.add(session);  
       }  
       return list;  
   }  
 
   /** 
    * 得到用户对应会话map,key为用户ID,value为会话ID 
    */  
   public static Map<String, String> getUserSessionMap() {  
       Map<String, String> map = new HashMap<String, String>();  
       Iterator<String> iter = getSessionMapKeySetIt();  
       while (iter.hasNext()) {  
           String sessionId = iter.next();  
           HttpSession session = getSessionMap().get(sessionId);  
           TSUser user = (TSUser) session.getAttribute("LOCAL_CLINET_USER");  
           if (user != null) {  
               map.put(user.getId(), sessionId);  
           }  
       }  
       return map;  
   }  
 
   /** 
    * 移除用户Session 
    */  
   public synchronized static void removeUserSession(String userId) {  
       Map<String, String> userSessionMap = getUserSessionMap();  
       if (userSessionMap.containsKey(userId)) {  
           String sessionId = userSessionMap.get(userId);  
           getSessionMap().get(sessionId).invalidate();  
           getSessionMap().remove(sessionId);  
       }  
   }  
 
   /** 
    * 增加用户到session集合中 
    */  
   public static void addUserSession(HttpSession session) {  
       getSessionMap().put(session.getId(), session);  
   }  
 
   /** 
    * 移除一个session 
    */  
   public static void removeSession(String sessionID) {  
       getSessionMap().remove(sessionID);  
   }  
 
   public static boolean containsKey(String key) {  
       return getSessionMap().containsKey(key);  
   }  
 
   /** 
    * 判断该用户是否已重复登录,使用 
    * 同步方法,只允许一个线程进入,才好验证是否重复登录 
    * @param user 
    * @return 
    */  
   public synchronized static boolean checkIfHasLogin(TSUser user) {  
       Iterator<String> iter = getSessionMapKeySetIt();  
       while (iter.hasNext()) {  
           String sessionId = iter.next();  
           HttpSession session = getSessionMap().get(sessionId);  
           TSUser sessionuser = (TSUser) session.getAttribute("LOCAL_CLINET_USER");  // 这是你设置 保存用户对应session名 
           if (sessionuser != null) {  
               if (sessionuser.getId().equals(user.getId())){  
                   return true;  
               }  
           }  
       }  
       return false;  
   }  
 
   /** 
    * 获取在线的sessionMap 
    */  
   public static Map<String, HttpSession> getSessionMap() {  
       return sessionMap;  
   }  
 
   /** 
    * 获取在线sessionMap中的SessionId 
    */  
   public static Iterator<String> getSessionMapKeySetIt() {  
       return getSessionMap().keySet().iterator();  
   }  
	
	
}

web.xml:

<listener>
	<listener-class>xxxxx.listener.SessionUserListener</listener-class>		
</listener>

帮组类:

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

public class ContextHolderUtils {
	/**
	 * SpringMvc下获取request
	 * 
	 * @return
	 */
	public static HttpServletRequest getRequest() {
		HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
		return request;

	}
	/**
	 * SpringMvc下获取session
	 * 
	 * @return
	 */
	public static HttpSession getSession() {
		HttpSession session = getRequest().getSession();
		return session;

	}

}

服务类:(接口就忽略) -- 把前一个用户剔除

import java.util.Map;

import javax.servlet.http.HttpSession;

import xxxxx.ContextHolderUtils;
import xxxxx.TSUser;
import org.springframework.stereotype.Service;

import xxxxx.listener.SessionUserListener;
import xxxxx.listener.service.SessionUserI;

/**
 * 
 * @author yuki_ho
 *
 */
@Service("sessionUser")
public class SessionUserImpl implements SessionUserI{

	/**
	 * 登录时使用 --  检查是否重复登录并把在线的 替换成 自己
	 */
	@Override
	public void changeLogin4Me(TSUser tsUser) {
		   Boolean hasLogin = SessionUserListener.checkIfHasLogin(tsUser); 
			HttpSession session = ContextHolderUtils.getSession();
		   if(hasLogin)
			   SessionUserListener.removeUserSession(tsUser.getId());
		   SessionUserListener.addUserSession(session);  
	}

	/**
	 * 使用 拦截器时 -- 检查是否当前 session用户
	 */
	@Override
	public Boolean checkLoginIsMe(TSUser tsUser) {
		if(null==tsUser)
			return false;
	    Map<String,String> SessionUser=	SessionUserListener.getUserSessionMap();
	    String curSession=SessionUser.get(tsUser.getId());
		HttpSession session = ContextHolderUtils.getSession();
	    if(curSession.equals(session.getId()))
	    	return true;
		return false;
	}

}

拦截器: -在controller前 拦截

			 Boolean flag	 =sessionUser.checkLoginIsMe(tsuer); 
				if(!flag)	{
					session.removeAttribute("LOCAL_CLINET_USER");
					response.sendRedirect("loginController.do?login");
					return false;
				}

ps:请别在登录时拦截,在配置拦截器之前 排除登录拦截


评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

_yuki_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值