java实现同用户登录互挤,将前一个用户挤下线

1.场景

假设 Tom使用了用户1,Joker也是使用了用户1,两人同时对用户1 的相关数据进行了修改,就会造成数据的安全隐患,得保证多台设备登录账号只有一个账号能登录上。

2.思路

  • 2.1 利用map的key-value数据结构,key可以重复,value不能重复的特性,将用户名和sessionid绑定存储起来。
  • 2.2 首次登录在拦截器里面放行,登录成功将用户名和sessionid存储起来,当第二次登录时,用户名相同,sessionid不同的话则去登录,后面执行登录方法,发前一个账号和sessionid删除,然后把后一个的用户名和sessionid重新存起来,如果第二次登录时用户名相同,sessionid也相同,就直接放行,相当于单点登录。同一个会话sessionid是相同的,不同的会话sessionid肯定不同。
  • 2.3 删除了sessionid的账号,只有点击一个操作后就会下线。

3.代码实现

拦截器userInterceptor

public class userInterceptor implements HandlerInterceptor {
    @Override
    public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception {

    }

    @Override
    public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {

    }

    @Override
    public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception {
       
        User user=(User)httpServletRequest.getSession().getAttribute("user");
        String indexurl=httpServletRequest.getRequestURL().toString().replace(httpServletRequest.getRequestURI(),"");
        ServletContext application = httpServletRequest.getSession().getServletContext();

        if(user!=null){   //session中存在用户信息
            String sessionId=application.getAttribute(operator.getUserName()).toString();

            if(sessionId.equals(httpServletRequest.getSession().getId())){
                //请求的sessionId和此账号的sessionId一致,允许请求return true;
            }else{
                //如果请求的sessionId和此账号的sessionId不一致,跳转至异地登录提示页面
                httpServletResponse.sendRedirect(indexurl+"/relogin");
               return false;
            }
        }
        //第一次登陆系统,session中没有记录,转发通过
        httpServletRequest.getRequestDispatcher(indexurl).forward(httpServletRequest, httpServletResponse);
        return true;
    }

}

配置文件中设置拦截路径

<mvc:interceptors>
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
       <mvc:exclude-mapping path="/statis/**"/>   //exclude-mapping 不拦截的路径
       <mvc:exclude-mapping path="/dologin"/>
            <bean class="yi.survey.interceptor.UserInterceptor"/>
        </mvc:interceptor>
</mvc:interceptors>

在controller的登录方法dologin

@RequestMapping(value="/dologin",method = RequestMethod.POST)
    public String dologin(@RequestParam User user,
                HttpSession session, Model model){
     //获取ServletContext对象
        ServletContext application = session.getServletContext(); 
     //查找数据库中的用户信息
        User loginUser=userService.login(user);if(loginUser!=null){ //账号密码正确
             String sessionId = session.getId();
		if(application.getAttribute(userName) == null){
                 application.setAttribute(userName,sessionId);
             }else if (application.getAttribute(userName)!= null && !StringUtils.equals(sessionId,application.getAttribute(userName).toString())){
                 application.removeAttribute(userName);
                 application.setAttribute(userName,sessionId);
             }
        //将用户信息存入session中
             session.setAttribute("user", user);
             // 页面跳转main.jsp
             return "main";                  
         }else{ //账号密码错误
              model.addAttribute("error", "账号密码不正确");return "login";         
         }
   }

账号后一个把前一个挤下线

  • 4
    点赞
  • 15
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值