기본적인 흐름은 AuthenticationSuccessHandler , AutheticationFailureHandler 의 구성방법과 동일.
CustomAjaxAuthenticationSuccessHandler
jackson 의 ObjectMapper 를 사용하여 json 값으로 메시지를 넘긴다. HttpStatus 를 주는 점을 주목한다.
- Authentication 객체에는 유저정보인 AjaxAuthenticationToken 이 있기 때문에(구현) 가져와 값을 참조한다.
public class CustomAjaxAuthenticationSuccessHandler implements AuthenticationSuccessHandler {
private ObjectMapper objectMapper = new ObjectMapper();
@Override
public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException {
Account account = (Account)authentication.getPrincipal();
response.setStatus(HttpStatus.OK.value());
response.setContentType(MediaType.APPLICATION_JSON_VALUE);
objectMapper.writeValue(response.getWriter(),account);// objectMapper 로 변환시킴
}
}
CustomAjaxAuthenticationFailureHandler
jackson 의 ObjectMapper 를 사용한다. HttpStatus 코드 값과 Message 를 넘기고 있다.
- Exception Type 에 따라 다른 메세지를 분기한다.
public class CustomAjaxAuthenticationFailureHandler implements AuthenticationFailureHandler {
private ObjectMapper objectMapper = new ObjectMapper();
@Override
public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException {
String errorMessage = "Invalid Username of Password";
response.setStatus(HttpStatus.UNAUTHORIZED.value());
response.setContentType(MediaType.APPLICATION_JSON_VALUE);
if(exception instanceof UsernameNotFoundException){
errorMessage = "Username Not Found";
} else if (exception instanceof BadCredentialsException){
errorMessage = "Password Not Match";
} else if(exception instanceof DisabledException){
errorMessage = "Locked";
}
objectMapper.writeValue(response.getWriter(), errorMessage);// json 으로 에러메시지 전달
}
}
등록
SecurityConfig 클래스의 CustomAjaxAuthenticationFilter ( AbstractAuthenticationProcessingFilter 상속 ) 클래스 등록과정에서 Setter 로 해당 핸들러를 추가한다.
@Configuration
@EnableWebSecurity
@Order(0)
public class AjaxSecurityConfig extends WebSecurityConfigurerAdapter {
@Bean
public AuthenticationProvider ajaxAuthenticationProvider(){
return new AjaxAuthenticationProvider();
}
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(ajaxAuthenticationProvider());
}
@Bean
public AjaxLoginProcessingFilter ajaxLoginProcessingFilter() throws Exception {
AjaxLoginProcessingFilter ajaxLoginProcessingFilter = new AjaxLoginProcessingFilter();
ajaxLoginProcessingFilter.setAuthenticationManager(authenticationManagerBean());
ajaxLoginProcessingFilter.setAuthenticationSuccessHandler(customAjaxAuthenticationSuccessHandler());
ajaxLoginProcessingFilter.setAuthenticationFailureHandler(customAjaxAuthenticationFailureHandler());
return ajaxLoginProcessingFilter;
}
@Bean
public CustomAjaxAuthenticationSuccessHandler customAjaxAuthenticationSuccessHandler(){
return new CustomAjaxAuthenticationSuccessHandler();
}
@Bean
public CustomAjaxAuthenticationFailureHandler customAjaxAuthenticationFailureHandler(){
return new CustomAjaxAuthenticationFailureHandler();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.antMatcher("/api/**")
.authorizeRequests()
.anyRequest().authenticated()
.and()
.addFilterBefore(ajaxLoginProcessingFilter(), UsernamePasswordAuthenticationFilter.class)// 해당필터 앞에 위치시킴
.csrf().disable();
}
}
'springframework > 시작하자SpringSecurity' 카테고리의 다른 글
39.Ajax 로그인 구현, CSRF (0) | 2020.09.30 |
---|---|
38.AjaxLoginUrlAuthenticationEntryPoint, AjaxAccessDeniedHandler (0) | 2020.09.30 |
36.CustomAjaxAuthenticationProvider (0) | 2020.09.29 |
35.AjaxAuthenticationFilter (0) | 2020.09.29 |
34. Ajax Authentication Flow (0) | 2020.09.29 |