扩展基于JSON登陆
由于长时间位于服务器交互,导致客户端与服务器超时,认证失效。但用户不想跳转到登陆界面进行登陆,期望在当前界面弹窗框进行登陆,然后进行下一步操作。
解决方案:当服务端拦截到请求发现认证失效时,返回Code的值提示客户端进行JSON登陆,客户端登陆成功之后继续上一步操作。
注:HTTP CODE不能返回302,此码游览器会拦截自动转到登陆页面
实现方式:在Spring security中添加拦截器,拦截指定JSON请求进行登陆操作。
/**
* 支持JSON登陆
* AuthenticationFilter that supports rest login(json login) and form login.
*/
@Slf4j
public class AuthenticationRestfullFilter extends UsernamePasswordAuthenticationFilter {
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
//attempt Authentication when Content-Type is json
if (MediaType.APPLICATION_JSON_UTF8_VALUE.equals(request.getContentType()) || MediaType.APPLICATION_JSON_VALUE.equals(request.getContentType())) {
//use jackson to deserialize json 在这里可以使用jackson, 因为Security对它进行包装
ObjectMapper mapper = new ObjectMapper();
UsernamePasswordAuthenticationToken authRequest = null;
try (InputStream is = request.getInputStream()) {
UsernamePasswordVm userDto = mapper.readValue(is, UsernamePasswordVm.class);
authRequest = new UsernamePasswordAuthenticationToken(userDto.getUsername(), userDto.getPassword());
} catch (IOException e) {
log.warn(e.getMessage(), e);
e.printStackTrace();
authRequest = new UsernamePasswordAuthenticationToken("", "");
} finally {
setDetails(request, authRequest);
}
log.debug("User Rest login app !");
return this.getAuthenticationManager().authenticate(authRequest);
}
return super.attemptAuthentication(request, response);
}
}
@Getter
@Setter
public class UsernamePasswordVm {
private String username;
private String password;
private Boolean rememberMe;
}
共享 Session
简介:当应用演变成分布式或者集群时,用户的请求可能会被负载到不同服务器,此时Web容器的会话不能通用,所以通过Spring Session实现共享用户会话信息。
解决方案: Spring Session 拦截用户会话(包装Http Request)信息,保存在一个指定的存储地方,同时其他服务器也能操作此数据,从而实现Session共享,提高应用的性能和并发量。
实现方式:
@EnableRedisHttpSession(maxInactiveIntervalInSeconds="请求间隔最大周期,可以理解为Session Timeout")
public class StarUpAdminApp {
}
相关配置
spring:
http:
encoding:
charset: UTF-8
enabled: true
force: true
session:
store-type: redis
redis:
flush-mode: on-save
namespace: session
database: 2
host: 127.0.0.1
lettuce:
pool:
max-active: 4
max-wait: -1ms
max-idle: 2
min-idle: 0