Springboot security cas整合方案中不可或缺的校验Filter类或者称为认证Filter类,其内部包含校验器、权限获取等,特开辟新地啃啃
继承结构
- AbstractAuthenticationProcessingFilter
- CasAuthenticationFilter
其中父类AbstractAuthenticationProcessingFilter#doFilter()是模板处理逻辑方法,而子类主要实现了校验方法CasAuthenticationFilter#attemptAuthentication()方法。下面就对这两块进行代码层面的分析
AbstractAuthenticationProcessingFilter#doFilter-处理逻辑
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) req;
HttpServletResponse response = (HttpServletResponse) res;
//是否需要验证,这里cas子类对其进行了复写
if (!requiresAuthentication(request, response)) {
chain.doFilter(request, response);
return;
}
if (logger.isDebugEnabled()) {
logger.debug("Request is to process authentication");
}
//凭证信息
Authentication authResult;
try {
//调用子类来进行相关的验证操作,供子类复写
authResult = attemptAuthentication(request, response);
if (authResult == null) {
//返回为空,则校验停止
return;
}
//session策略校验,默认不校验
sessionStrategy.onAuthentication(authResult, request, response);
}
catch (InternalAuthenticationServiceException failed) {
logger.error(
"An internal error occurred while trying to authenticate the user.",
failed);
//对其中产生的异常进行页面输出,即直接以页面呈现错误
unsuccessfulAuthentication(request, response, failed);
return;
}
catch (AuthenticationException failed) {
// Authentication failed
//对其中产生的异常进行页面输出,即直接以页面呈现错误
unsuccessfulAuthentication(request, response, failed);
return;
}
// Authentication success
//认证成功后是否还往下走,默认为false
if (continueChainBeforeSuccessfulAuthentication) {
chain.doFilter(request, response);
}
//直接跳转至配置好的登录成功页面,这里cas子类对其进行了复写
successfulAuthentication(request, response, chain, authResult);
}
其中CasAuthenticationFilter对以下方法进行了复写,分别为requiresAuthentication()、successfulAuthentication()、attemptAuthentication()方法
CasAuthenticationFilter#requiresAuthentication-是否校验判断
protected boolean requiresAuthentication(final HttpServletRequest request,
final HttpServletResponse response) {
//是否与设置的登录路径匹配
final boolean serviceTicketRequest = serviceTicketRequest(request, response);
//对含有ticket参数的请求会返回true
final boolean result = serviceTicketRequest || proxyReceptorRequest(request)
|| (proxyTicketRequest(serviceTicketRequest, request));
if (logger.isDebugEnabled()) {
logger.debug("requiresAuthentication = "