| | |
| | | */ |
| | | public class ShiroAuthFilter extends FormAuthenticationFilter { |
| | | |
| | | public ShiroAuthFilter(SessionManager sessionManager,ShiroCacheManager shiroCacheManager) { |
| | | super(); |
| | | this.sessionManager = (ShiroSessionManager)sessionManager; |
| | | this.cache = shiroCacheManager.getCache("shiro_redis_cache"); |
| | | } |
| | | @Override |
| | | protected boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) { |
| | | return false; |
| | | } |
| | | @Override |
| | | protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception { |
| | | |
| | | private int maxSession = 1; //最大会话数量 |
| | | |
| | | private boolean kickOutAfter = false; //踢出前者还是后者 |
| | | private Cache<String, Deque<Serializable>> cache; //缓存管理 |
| | | |
| | | |
| | | private ShiroSessionManager sessionManager; //会话管理 |
| | | |
| | | @Override |
| | | protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws Exception { |
| | | Subject subject = getSubject(request, response); |
| | | if (!subject.isAuthenticated() && !subject.isRemembered()) { //如果不是认证过和记住密码的,就直接放行请求,避免造成访问过慢 |
| | | // return Boolean.TRUE; |
| | | } |
| | | Session session = subject.getSession(); //获取会话session |
| | | Object principal = subject.getPrincipal(); |
| | | Serializable sessionId = session.getId(); |
| | | LoginUserInfo userInfo = (LoginUserInfo) principal; |
| | | if(userInfo == null ){ |
| | | HttpServletResponse servletResponse = (HttpServletResponse) response; |
| | | servletResponse.setHeader("content-type", "application/json;charset=UTF-8"); |
| | | servletResponse.getWriter().write(JSON.toJSONString(ApiResponse.failed(HttpStatus.UNAUTHORIZED.value(), "未登录或登录信息已过期"))); |
| | | return Boolean.FALSE; |
| | | // return super.onAccessDenied(request,response); |
| | | }else if( Constants.equalsInteger(userInfo.getType(), Constants.UserType.COMPANY.getKey()) ){ |
| | | return Boolean.TRUE; |
| | | // return super.onAccessDenied(request,response); |
| | | } |
| | | |
| | | String userName = userInfo.getCompanyId() +"_"+ userInfo.getId(); |
| | | Deque<Serializable> deque = cache.get(userName); |
| | | if (deque == null) { |
| | | deque = new LinkedList<>(); |
| | | } |
| | | if (!deque.contains(sessionId) && session.getAttribute("kickOut") == null) { |
| | | deque.push(sessionId); |
| | | cache.put(userName, deque); |
| | | } |
| | | while (deque.size() > maxSession) { |
| | | Serializable kickOutSessionId; |
| | | if (kickOutAfter) { |
| | | kickOutSessionId = deque.removeFirst(); |
| | | cache.put(userName, deque); |
| | | } else { |
| | | kickOutSessionId = deque.removeLast(); |
| | | cache.put(userName, deque); |
| | | } |
| | | |
| | | try { |
| | | Session kickOutSession = sessionManager.getSession(new DefaultSessionKey(kickOutSessionId)); |
| | | if (kickOutSession != null) { |
| | | kickOutSession.setAttribute("kickOut", Boolean.TRUE); |
| | | } |
| | | } catch (Exception e) { |
| | | e.printStackTrace(); |
| | | // log.error("踢出异常未踢出"); |
| | | } |
| | | } |
| | | |
| | | if (session!=null && session.getAttribute("kickOut") != null && (Boolean) session.getAttribute("kickOut") == true) { |
| | | try { |
| | | subject.logout(); |
| | | } catch (Exception e) { |
| | | e.printStackTrace(); |
| | | } |
| | | saveRequest(request); |
| | | HttpServletResponse servletResponse = (HttpServletResponse) response; |
| | | servletResponse.setHeader("content-type", "application/json;charset=UTF-8"); |
| | | servletResponse.getWriter().write(JSON.toJSONString(ApiResponse.failed(HttpStatus.UNAUTHORIZED.value(), "未登录或登录信息已过期"))); |
| | | return Boolean.FALSE; |
| | | } |
| | | return Boolean.TRUE; |
| | | } |
| | | |
| | | public int getMaxSession() { |
| | | return maxSession; |
| | | } |
| | | |
| | | public void setMaxSession(int maxSession) { |
| | | this.maxSession = maxSession; |
| | | } |
| | | |
| | | public boolean isKickOutAfter() { |
| | | return kickOutAfter; |
| | | } |
| | | |
| | | public void setKickOutAfter(boolean kickOutAfter) { |
| | | this.kickOutAfter = kickOutAfter; |
| | | } |
| | | |
| | | public Cache<String, Deque<Serializable>> getCache() { |
| | | return cache; |
| | | } |
| | | |
| | | public void setCache(Cache<String, Deque<Serializable>> cache) { |
| | | this.cache = cache; |
| | | } |
| | | |
| | | public ShiroSessionManager getSessionManager() { |
| | | return sessionManager; |
| | | } |
| | | |
| | | public void setSessionManager(ShiroSessionManager sessionManager) { |
| | | this.sessionManager = sessionManager; |
| | | } |
| | | } |