# 当前登录用户
# 认证凭据解析
在 Heimdall 框架中,用户认证凭据通过 SimpleSession 进行管理。SimpleSession是 Http Session 的一个实现,包括了,首次访问时间,最后访问时间,是否过期,对端主机地址等基本信息。
用户认证通过,则生成对应的 Session,并且将 Session 信息缓存,通知将 Session 返回给上层应用,如果开启了 Cookie 功能,Session 创建后,还会同步往前端浏览器发出 Set-Cookie 指令,写入 Cookie。
客户端访问后台服务,携带认证凭据(SessionId token 等),Heimdall 框架解析认证凭据,并从缓存中查找,如果找到,则返回当前登录用户信息,否则抛出未认证异常。
Heimdall 支持从 Cookie、Header、Query 中获取认证凭据。对于某些非浏览器应用场景(如:app、小程序等),不支持 Cookie,则可以禁用 Cookie,只使用 Session。此时 SessionID也就相当于是俗称的:”token“,你懂的,咪和猫的区别。。。。
获取认证凭据的方法如下:
/**
* 解析请求中的SessionId
* <p>
* <p>
* 1、如果Cookie开启,首先从Cookie解析,有,则返回
* <p>
* 2、如果没有,从Header中解析,有则返回
* <p>
* 3、header中没有,从request parameters参数中解析,返回
*
* @param request the request
* @return the string
*/
public String resolveSessionId(HttpServletRequest request) {
final String sessionName = ConfigManager.getConfig().getSession().getSessionName();
if (ConfigManager.getConfig().getCookie().getEnabled()) {
final Cookie cookie = sessionDAO.getCookieService().getCookie();
if (null != cookie) {
log.debug("解析请求 SessionId | Cookie 中携带了SessionId: [{} = {}]", sessionName, cookie.getValue());
return cookie.getValue();
}
}
String token = request.getHeader(sessionName);
if (StrUtils.isBlank(token)) {
String sessionId = request.getParameter(sessionName);
log.debug("解析请求 SessionId | Parameters 中携带了SessionId: [{} = {}]", sessionName, sessionId);
return sessionId;
}
log.debug("解析请求 SessionId | Headers 中携带了SessionId: [{} = {}]", sessionName, token);
return token;
}
# 获取当前登录用户
Heimdall 框架提供了如下几种获取当前登录用户信息的方式:
- 认证管理器获取
- 注解获取
# 认证管理器获取
使用方法:
authenticationManager.getCurrentUser(Boolean throwEx)
示例如下:
/**
* 认证管理器
*/
@Autowired
private AuthenticationManager authenticationManager;
//获取当前登录用户信息
@Override
public SysUserDTO getCurrentUser(boolean fromDb, boolean throwEx) {
final SimpleSession currentUser = authenticationManager.getCurrentUser(throwEx);
if (null != currentUser && null != currentUser.getDetails()) {
AppUserDetails userDetails = (AppUserDetails) currentUser.getDetails();
if (fromDb) {
final Long id = userDetails.getUser().getId();
final SysUserEntity entityById = getEntityById(SysUserEntity.class, id);
return userMapper.toDto(entityById);
}
return userDetails.getUser();
}
return null;
}
# 注解获取
针对 Spring 框架 Heimdall 提供了当前用户注解实现,可通过定义addArgumentResolvers实现,参考以下代码:
public class AbstractWebMvcConfigurer implements WebMvcConfigurer {
.......
/**
* 当前登录用户参数解析器
*/
@Autowired
private CurrentUserRequestArgumentResolver currentUserRequestArgumentResolver;
@Override
public void addArgumentResolvers(List<HandlerMethodArgumentResolver> argumentResolvers) {
log.warn("初始化 当前用户参数注解解析器");
argumentResolvers.add(currentUserRequestArgumentResolver);
}
.......
}
同时,框架也提供了 Mvc 配置基础类:com.luter.heimdall.boot.starter.config.AbstractWebMvcConfigurer, 如果没有特殊需求,可直接扩展使用即可,如下:
@Configuration
@Slf4j
public class MvcConfig extends AbstractWebMvcConfigurer {
}
# 注解使用
@GetMapping("/user")
public SimpleSession getCurrentUser(@CurrentUser SimpleSession user) {
return user;
}
注意:此注解是通过authenticationManager.getCurrentUser()来获取的当前登录用户信息,所以需要对返回结果进行空值判断。当用户未登录或者已经过期的情况下,会主动抛出 401 异常。