網上有很多關於重複登錄的文章,我總結了一下,然後根據自己的業務做了一個:但是我覺得應該還有更好的解決辦法
如果有同志有其他的辦法的話歡迎留言哦!
原理也很簡單:首先需要實現一個Session監聽類SessionListener 使用HttpSessionListener接口實現 sessionCreated 和 sessionDestroyed方法:記得需要寫上@WebListener註解
@WebListener
public class SessionListener implements HttpSessionListener {
public static boolean isExpired = false;
public static SessionManagement sessionManagement = SessionManagement.getInstance();
@Override
public void sessionCreated(HttpSessionEvent httpSessionEvent) {
System.out.println("------------ sessionCreated");
//session被創建 添加到HashMap
sessionManagement.addSession(httpSessionEvent.getSession().getId(), httpSessionEvent.getSession());
}
@Override
public void sessionDestroyed(HttpSessionEvent httpSessionEvent) {
System.out.println("------------ sessionDestroyed");
isExpired = true; //標記 判斷session是否過期
sessionManagement.removeSession(httpSessionEvent.getSession().getId());
}
}
第二步:創建一個Session管理類SessionManagement 和 HashMap<string, HttpSession>
public class SessionManagement {
private static SessionManagement sessionManagement;
private HashMap<String, HttpSession> sessionHashMap;
private ReadWriteLock readWriteLock = new ReentrantReadWriteLock(); //線程同步
private SessionManagement() {
sessionHashMap = new HashMap<>();
}
public static SessionManagement getInstance() {
if (sessionManagement == null) {
sessionManagement = new SessionManagement();
}
return sessionManagement;
}
public void addSession(String id, HttpSession httpSession) {
readWriteLock.writeLock().lock();
try {
if (httpSession != null && id != null && id.length() > 0) {
sessionHashMap.put(id, httpSession);
}
} finally {
readWriteLock.writeLock().unlock();
}
}
public void removeSession(String id) {
readWriteLock.writeLock().lock();
try {
if (id != null && id.length() > 0) {
sessionHashMap.remove(id);
}
} finally {
readWriteLock.writeLock().unlock();
}
}
public HttpSession getSession(String sessionId) {
readWriteLock.readLock().lock();
try {
if (sessionId == null) {
return null;
}
return sessionHashMap.get(sessionId);
} finally {
readWriteLock.readLock().unlock();
}
}
public HashMap<String, HttpSession> getSessionHashMap() {
return sessionHashMap;
}
public void setSessionHashMap(HashMap<String, HttpSession> sessionHashMap) {
this.sessionHashMap = sessionHashMap;
}
}
第三:在登錄接口處理業務邏輯
//已登錄 && session未過期
HttpSession session_old = SessionManagement.getInstance().getSession(userID);
if (!SessionListener.isExpired && session_old != null) {
//強制過期
session_old.invalidate();
SessionManagement.getInstance().removeSession(String.valueOf(accountEntity.getId()));
//更新 -- 將sessionId 更換爲 userID
SessionManagement.getInstance().removeSession(session.getId());
SessionManagement.getInstance().addSession(String.valueOf(userID), session);
}
//未登錄
else {
HttpSession session_admin = SessionManagement.getInstance().getSession(session.getId());
if (session_admin == null) {
throw new ControllerException("業務異常");
}
//替換id - session
SessionManagement.getInstance().addSession(userID), session_admin);
SessionManagement.getInstance().removeSession(session.getId());
}
這樣可以實現效果。如果有更好的辦法歡迎大家留言 大家一起交流。