v1.7.0 新特性,在Cookie模式下timeout过期时间有效

This commit is contained in:
shengzhang
2020-12-23 18:49:22 +08:00
parent 149b2e54c9
commit ded6da5554
12 changed files with 206 additions and 55 deletions

View File

@@ -10,6 +10,14 @@ import cn.dev33.satoken.session.SaSession;
public interface SaTokenDao {
/** 常量表示一个key永不过期 (在一个key被标注为永远不过期时返回此值) */
public static final Long NEVER_EXPIRE = -1L;
/** 常量,表示系统中不存在这个缓存 (在对不存在的key获取剩余存活时间时返回此值) */
public static final Long NOT_VALUE_EXPIRE = -2L;
/**
* 根据key获取value ,如果没有,则返回空
* @param key 键名称
@@ -38,6 +46,12 @@ public interface SaTokenDao {
*/
public void delKey(String key);
/**
* 获取指定key的剩余存活时间 (单位: 秒)
* @param key 指定key
* @return 这个key的剩余存活时间
*/
public long getTimeout(String key);
/**
@@ -45,26 +59,36 @@ public interface SaTokenDao {
* @param sessionId 键名称
* @return SaSession
*/
public SaSession getSaSession(String sessionId);
public SaSession getSession(String sessionId);
/**
* 将指定session持久化
* 将指定session持久化
* @param session 要保存的session对象
* @param timeout 过期时间,单位: s
*/
public void saveSaSession(SaSession session, long timeout);
public void saveSession(SaSession session, long timeout);
/**
* 更新指定session
* @param session 要更新的session对象
*/
public void updateSaSession(SaSession session);
public void updateSession(SaSession session);
/**
* 删除一个指定的session
* 删除一个指定的session
* @param sessionId sessionId
*/
public void deleteSaSession(String sessionId);
public void deleteSession(String sessionId);
/**
* 获取指定SaSession的剩余存活时间 (单位: 秒)
* @param sessionId 指定SaSession
* @return 这个SaSession的剩余存活时间
*/
public long getSessionTimeout(String sessionId);
}

View File

@@ -17,50 +17,107 @@ public class SaTokenDaoDefaultImpl implements SaTokenDao {
*/
Map<String, Object> dataMap = new HashMap<String, Object>();
/**
* 过期时间集合 (单位: 毫秒) , 记录所有key的到期时间 [注意不是剩余存活时间]
*/
Map<String, Long> expireMap = new HashMap<String, Long>();
@Override
public String getValue(String key) {
clearKeyByTimeout(key);
return (String)dataMap.get(key);
}
@Override
public void setValue(String key, String value, long timeout) {
dataMap.put(key, value);
expireMap.put(key, (timeout == SaTokenDao.NEVER_EXPIRE) ? (SaTokenDao.NEVER_EXPIRE) : (System.currentTimeMillis() + timeout * 1000));
}
@Override
public void updateValue(String key, String value) {
this.setValue(key, value, 0);
dataMap.put(key, value);
}
@Override
public void delKey(String key) {
dataMap.remove(key);
}
@Override
public SaSession getSaSession(String sessionId) {
public long getTimeout(String key) {
return getKeyTimeout(key);
}
@Override
public SaSession getSession(String sessionId) {
clearKeyByTimeout(sessionId);
return (SaSession)dataMap.get(sessionId);
}
@Override
public void saveSaSession(SaSession session, long timeout) {
public void saveSession(SaSession session, long timeout) {
dataMap.put(session.getId(), session);
expireMap.put(session.getId(), (timeout == SaTokenDao.NEVER_EXPIRE) ? (SaTokenDao.NEVER_EXPIRE) : (System.currentTimeMillis() + timeout * 1000));
}
@Override
public void updateSaSession(SaSession session) {
public void updateSession(SaSession session) {
// 无动作
}
@Override
public void deleteSaSession(String sessionId) {
public void deleteSession(String sessionId) {
dataMap.remove(sessionId);
}
@Override
public long getSessionTimeout(String sessionId) {
return getKeyTimeout(sessionId);
}
// ---------------------
/**
* 如果指定key已经过期则立即清除它
* @param key 指定key
*/
void clearKeyByTimeout(String key) {
Long expirationTime = expireMap.get(key);
// 清除条件:如果不为空 && 不是[永不过期] && 已经超过过期时间
if(expirationTime != null && expirationTime != SaTokenDao.NEVER_EXPIRE && expirationTime < System.currentTimeMillis()) {
dataMap.remove(key);
expireMap.remove(key);
}
}
/**
* 获取指定key的剩余存活时间 (单位:秒)
*/
long getKeyTimeout(String key) {
// 先检查是否已经过期
clearKeyByTimeout(key);
// 获取过期时间
Long expire = expireMap.get(key);
// 如果根本没有这个值
if(expire == null) {
return SaTokenDao.NOT_VALUE_EXPIRE;
}
// 如果被标注为永不过期
if(expire == SaTokenDao.NEVER_EXPIRE) {
return SaTokenDao.NEVER_EXPIRE;
}
// 计算剩余时间并返回
return (expire - System.currentTimeMillis()) / 1000;
}

View File

@@ -137,7 +137,7 @@ public class SaSession implements Serializable {
* 将这个session从持久库更新一下
*/
public void update() {
SaTokenManager.getSaTokenDao().updateSaSession(this);
SaTokenManager.getSaTokenDao().updateSession(this);
}

View File

@@ -23,7 +23,7 @@ public class SaSessionCustomUtil {
* @return 是否存在
*/
public boolean isExists(String sessionId) {
return SaTokenManager.getSaTokenDao().getSaSession(getSessionKey(sessionId)) != null;
return SaTokenManager.getSaTokenDao().getSession(getSessionKey(sessionId)) != null;
}
/**
@@ -33,13 +33,14 @@ public class SaSessionCustomUtil {
* @return SaSession
*/
public static SaSession getSessionById(String sessionId, boolean isCreate) {
SaSession session = SaTokenManager.getSaTokenDao().getSaSession(getSessionKey(sessionId));
SaSession session = SaTokenManager.getSaTokenDao().getSession(getSessionKey(sessionId));
if(session == null && isCreate) {
session = new SaSession(getSessionKey(sessionId));
SaTokenManager.getSaTokenDao().saveSaSession(session, SaTokenManager.getConfig().getTimeout());
SaTokenManager.getSaTokenDao().saveSession(session, SaTokenManager.getConfig().getTimeout());
}
return session;
}
/**
* 获取指定key的session, 如果没有则新建并返回
* @param sessionId key
@@ -54,7 +55,7 @@ public class SaSessionCustomUtil {
* @param sessionId 删除指定key
*/
public static void deleteSessionById(String sessionId) {
SaTokenManager.getSaTokenDao().deleteSaSession(getSessionKey(sessionId));
SaTokenManager.getSaTokenDao().deleteSession(getSessionKey(sessionId));
}

View File

@@ -108,13 +108,14 @@ public class StpLogic {
}
/**
* 获取当前会话的token信息tokenNametokenValue
* 获取当前会话的token信息tokenNametokenValue、timeout
* @return 一个Map对象
*/
public Map<String, String> getTokenInfo() {
Map<String, String> map = new HashMap<String, String>();
public Map<String, Object> getTokenInfo() {
Map<String, Object> map = new HashMap<String, Object>();
map.put("tokenName", getTokenName());
map.put("tokenValue", getTokenValue());
map.put("tokenTimeout", getTimeout());
return map;
}
@@ -137,7 +138,7 @@ public class StpLogic {
if(tokenValue == null){ // 为null则创建一个新的
tokenValue = randomTokenValue(loginId);
} else {
// 不为null, 并且配置不共享,则:将原来的标记为[被顶替]
// 不为null, 并且配置不共享会话,则:将原来的会话标记为[被顶替]
if(config.getIsShare() == false){
// dao.delKey(getKeyTokenValue(tokenValue));
dao.updateValue(getKeyTokenValue(tokenValue), NotLoginException.BE_REPLACED);
@@ -196,7 +197,7 @@ public class StpLogic {
// 清除相关数据
SaTokenManager.getSaTokenDao().delKey(getKeyTokenValue(tokenValue)); // 清除token-id键值对
SaTokenManager.getSaTokenDao().delKey(getKeyLoginId(loginId)); // 清除id-token键值对
SaTokenManager.getSaTokenDao().deleteSaSession(getKeySession(loginId)); // 清除其session
SaTokenManager.getSaTokenDao().deleteSession(getKeySession(loginId)); // 清除其session
}
/**
@@ -214,7 +215,7 @@ public class StpLogic {
// 清除相关数据
SaTokenManager.getSaTokenDao().updateValue(getKeyTokenValue(tokenValue), NotLoginException.KICK_OUT); // 标记:已被踢下线
SaTokenManager.getSaTokenDao().delKey(getKeyLoginId(loginId)); // 清除id-token键值对
SaTokenManager.getSaTokenDao().deleteSaSession(getKeySession(loginId)); // 清除其session
SaTokenManager.getSaTokenDao().deleteSession(getKeySession(loginId)); // 清除其session
}
// 查询相关
@@ -366,10 +367,10 @@ public class StpLogic {
* @return .
*/
protected SaSession getSessionBySessionId(String sessionId, boolean isCreate) {
SaSession session = SaTokenManager.getSaTokenDao().getSaSession(sessionId);
SaSession session = SaTokenManager.getSaTokenDao().getSession(sessionId);
if(session == null && isCreate) {
session = new SaSession(sessionId);
SaTokenManager.getSaTokenDao().saveSaSession(session, SaTokenManager.getConfig().getTimeout());
SaTokenManager.getSaTokenDao().saveSession(session, SaTokenManager.getConfig().getTimeout());
}
return session;
}
@@ -400,7 +401,26 @@ public class StpLogic {
public SaSession getSession() {
return getSessionByLoginId(getLoginId());
}
// =================== 过期时间相关 ===================
/**
* 获取当前登录者的token剩余有效时间 (单位: 秒)
* @return token剩余有效时间
*/
public long getTimeout() {
return SaTokenManager.getSaTokenDao().getTimeout(getKeyTokenValue(getTokenValue()));
}
/**
* 获取指定loginId的token剩余有效时间 (单位: 秒)
* @param loginId 指定loginId
* @return token剩余有效时间
*/
public long getTimeoutByLoginId(Object loginId) {
return SaTokenManager.getSaTokenDao().getTimeout(getKeyTokenValue(getTokenValueByLoginId(loginId)));
}
// =================== 权限验证操作 ===================

View File

@@ -44,10 +44,10 @@ public class StpUtil {
}
/**
* 获取当前会话的token信息tokenNametokenValue
* 获取当前会话的token信息tokenNametokenValue、timeout
* @return 一个Map对象
*/
public static Map<String, String> getTokenInfo() {
public static Map<String, Object> getTokenInfo() {
return stpLogic.getTokenInfo();
}
@@ -158,6 +158,7 @@ public class StpUtil {
return stpLogic.getLoginIdByToken(tokenValue);
}
// =================== session相关 ===================
/**
@@ -187,6 +188,29 @@ public class StpUtil {
return stpLogic.getSession();
}
// =================== 过期时间相关 ===================
/**
* 获取当前登录者的token剩余有效时间 (单位: 秒)
* @return token剩余有效时间
*/
public long getTimeout() {
return stpLogic.getTimeout();
}
/**
* 获取指定loginId的token剩余有效时间 (单位: 秒)
* @param loginId 指定loginId
* @return token剩余有效时间
*/
public long getTimeoutByLoginId(Object loginId) {
return stpLogic.getTimeoutByLoginId(loginId);
}
// =================== 权限验证操作 ===================
/**