More Related Content Similar to Amazon Cognito使って認証したい?それならSpring Security使いましょう! (20) More from Ryosuke Uchitate (8) Amazon Cognito使って認証したい?それならSpring Security使いましょう!13. final class FilterComparator implements Comparator<Filter>,
Serializable {
private static final int INITIAL_ORDER = 100;
private static final int ORDER_STEP = 100;
private final Map<String, Integer> filterToOrder =
new HashMap<>();
FilterComparator() {
Step order =
new FilterComparator.Step(INITIAL_ORDER, ORDER_STEP);
put(ChannelProcessingFilter.class, order.next());
put(ConcurrentSessionFilter.class, order.next());
put(WebAsyncManagerIntegrationFilter.class, order.next());
put(SecurityContextPersistenceFilter.class, order.next());
put(HeaderWriterFilter.class, order.next());
put(CorsFilter.class, order.next());
put(CsrfFilter.class, order.next());
put(LogoutFilter.class, order.next());
// ……
40. @Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
private final UserDetailsServiceImpl userDetailsService;
// ……
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/js/**", "/css/**", "/webjars/**").permitAll()
.antMatchers("/users/**").hasRole(Role.STAFF.name())
.antMatchers("/**").authenticated()
.and()
.formLogin()
.loginPage("/login")
.loginProcessingUrl("/login")
.defaultSuccessUrl("/success", true)
.failureUrl("/login?error=true").permitAll();
}
}
41. @Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
private final UserDetailsServiceImpl userDetailsService;
// ……
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/js/**", "/css/**", "/webjars/**").permitAll()
.antMatchers("/users/**").hasRole(Role.STAFF.name())
.antMatchers("/**").authenticated()
.and()
.formLogin()
.loginPage("/login")
.loginProcessingUrl("/login")
.defaultSuccessUrl("/success", true)
.failureUrl("/login?error=true").permitAll();
}
}
45. public Authentication attemptAuthentication(
HttpServletRequest request, HttpServletResponse response)
throws AuthenticationException {
// ……
String username = obtainUsername(request);
String password = obtainPassword(request);
if (username == null) {
username = "";
}
if (password == null) {
password = "";
}
username = username.trim();
UsernamePasswordAuthenticationToken authRequest =
new UsernamePasswordAuthenticationToken(username, password);
setDetails(request, authRequest);
return this.getAuthenticationManager().authenticate(authRequest);
}
46. public Authentication attemptAuthentication(
HttpServletRequest request, HttpServletResponse response)
throws AuthenticationException {
// ……
String username = obtainUsername(request);
String password = obtainPassword(request);
if (username == null) {
username = "";
}
if (password == null) {
password = "";
}
username = username.trim();
UsernamePasswordAuthenticationToken authRequest =
new UsernamePasswordAuthenticationToken(username, password);
setDetails(request, authRequest);
return this.getAuthenticationManager().authenticate(authRequest);
}
48. public Authentication authenticate(Authentication authentication)
throws AuthenticationException {
// ……
for (AuthenticationProvider provider : getProviders()) {
if (!provider.supports(toTest)) {
continue;
}
// ……
try {
result = provider.authenticate(authentication);
if (result != null) {
copyDetails(authentication, result);
break;
}
}
// ……
50. protected final UserDetails retrieveUser(
String username, UsernamePasswordAuthenticationToken authentication)
throws AuthenticationException {
// ……
try {
UserDetails loadedUser =
this.getUserDetailsService().loadUserByUsername(username);
if (loadedUser == null) {
// ……
}
return loadedUser;
}
// ……
}
51. @Service
@RequiredArgsConstructor
public class UserDetailsServiceImpl implements UserDetailsService {
private final UserRepository userRepository;
@Override
public UserDetails loadUserByUsername(String username)
throws UsernameNotFoundException {
User user = userRepository.findByUsername(username)
.orElseThrow(
() -> new UsernameNotFoundException("username not found"));
return new org.springframework.security.core.userdetails.User(
user.getUsername(),
user.getPassword(),
createAuthorityList("ROLE_" + user.getRole().name()));
}
}
52. protected void additionalAuthenticationChecks(
UserDetails userDetails,
UsernamePasswordAuthenticationToken authentication)
throws AuthenticationException {
// ……
String presentedPassword =
authentication.getCredentials().toString();
if (!passwordEncoder.matches(
presentedPassword, userDetails.getPassword())) {
// ……
throw new BadCredentialsException(messages.getMessage(
"AbstractUserDetailsAuthenticationProvider.badCredentials",
"Bad credentials"));
}
}
75. public class CustomPreAuthenticatedProcessingFilter extends
AbstractPreAuthenticatedProcessingFilter {
@Override
protected Object getPreAuthenticatedPrincipal(
HttpServletRequest request) {
return "";
}
@Override
protected Object getPreAuthenticatedCredentials(
HttpServletRequest request) {
String accessToken =
request.getHeader(HttpHeaders.AUTHORIZATION);
if (StringUtils.isEmpty(accessToken)
|| !accessToken.startsWith("Bearer ")) {
return "";
}
return accessToken.split(" ")[1];
}
}
76. public class CustomPreAuthenticatedProcessingFilter extends
AbstractPreAuthenticatedProcessingFilter {
@Override
protected Object getPreAuthenticatedPrincipal(
HttpServletRequest request) {
return "";
}
@Override
protected Object getPreAuthenticatedCredentials(
HttpServletRequest request) {
String accessToken =
request.getHeader(HttpHeaders.AUTHORIZATION);
if (StringUtils.isEmpty(accessToken)
|| !accessToken.startsWith("Bearer ")) {
return "";
}
return accessToken.split(" ")[1];
}
}
77. private void doAuthenticate(
HttpServletRequest request, HttpServletResponse response)
throws IOException, ServletException {
Authentication authResult;
Object principal = getPreAuthenticatedPrincipal(request);
Object credentials = getPreAuthenticatedCredentials(request);
// ……
try {
PreAuthenticatedAuthenticationToken authRequest =
new PreAuthenticatedAuthenticationToken(
principal, credentials);
authRequest.setDetails(
authenticationDetailsSource.buildDetails(request));
authResult = authenticationManager.authenticate(authRequest);
successfulAuthentication(request, response, authResult);
}
catch (AuthenticationException failed) {
// ……
}
}
78. private void doAuthenticate(
HttpServletRequest request, HttpServletResponse response)
throws IOException, ServletException {
Authentication authResult;
Object principal = getPreAuthenticatedPrincipal(request);
Object credentials = getPreAuthenticatedCredentials(request);
// ……
try {
PreAuthenticatedAuthenticationToken authRequest =
new PreAuthenticatedAuthenticationToken(
principal, credentials);
// ……
authResult = authenticationManager.authenticate(authRequest);
successfulAuthentication(request, response, authResult);
}
catch (AuthenticationException failed) {
// ……
}
}
81. public Authentication authenticate(Authentication auth)
throws AuthenticationException {
String accessToken = Optional.ofNullable(auth.getCredentials())
.map(Object::toString)
.orElse(null);
if (accessToken == null) {
throw new BadCredentialsException("access token not found.");
}
DecodedJWT decodedAccessToken = JWTUtils.decode(accessToken);
// ……
String username = decodedAccessToken.getClaim("username").asString();
UserDetails ud = userDetailsService.loadUserDetails(
new PreAuthenticatedAuthenticationToken(
username, auth.getCredentials());
return new PreAuthenticatedAuthenticationToken(
ud, authentication.getCredentials(), ud.getAuthorities());
}
82. public Authentication authenticate(Authentication auth)
throws AuthenticationException {
String accessToken = Optional.ofNullable(auth.getCredentials())
.map(Object::toString)
.orElse(null);
if (accessToken == null) {
throw new BadCredentialsException("access token not found.");
}
DecodedJWT decodedAccessToken = JWTUtils.decode(accessToken);
// ……
String username = decodedAccessToken.getClaim("username").asString();
UserDetails ud = userDetailsService.loadUserDetails(
new PreAuthenticatedAuthenticationToken(
username, auth.getCredentials());
return new PreAuthenticatedAuthenticationToken(
ud, authentication.getCredentials(), ud.getAuthorities());
}
83. public Authentication authenticate(Authentication auth)
throws AuthenticationException {
String accessToken = Optional.ofNullable(auth.getCredentials())
.map(Object::toString)
.orElse(null);
if (accessToken == null) {
throw new BadCredentialsException("access token not found.");
}
DecodedJWT decodedAccessToken = JWTUtils.decode(accessToken);
// …… JWT
String username = decodedAccessToken.getClaim("username").asString();
UserDetails ud = userDetailsService.loadUserDetails(
new PreAuthenticatedAuthenticationToken(
username, auth.getCredentials());
return new PreAuthenticatedAuthenticationToken(
ud, authentication.getCredentials(), ud.getAuthorities());
}
85. @Service
public class CustomAuthenticationUserDetailsService
implements AuthenticationUserDetailsService {
private final CustomUserDetailsService userDetailsService;
// ……
@Override
public UserDetails loadUserDetails(Authentication token)
throws UsernameNotFoundException {
String username = token.getPrincipal().toString();
String accessToken = token.getCredentials().toString();
return
Optional.ofNullable(
userDetailsService.loadUserByUsername(username))
.map(u ->
new CustomUserDetails(
((CustomUserDetails) u).getUser(), accessToken))
.orElseThrow(() ->
new UsernameNotFoundException("user not found"));
}
}
90. @Test
void loginSuccess() throws Exception {
MvcResult result =
mockMvc
.perform(formLogin()
.user("ruchitate").password("password"))
.andReturn();
Assertions.assertThat(result.getResponse())
.extracting(
MockHttpServletResponse::getStatus,
MockHttpServletResponse::getRedirectedUrl)
.containsExactly(302, "/success");
}
91. @Test
void useWith200() throws Exception {
MvcResult result = mockMvc.perform(get("/users/{id}", 1)
.with(user("ruchitate").roles("STAFF")))
.andExpect(status().isOk())
.andReturn();
assertEquals(
"{"name":" ","username":"ruchitate",
"createdAt":"2018-10-01T00:00:00","lastSignInAt":null}",
result.getResponse().getContentAsString());
}
95. @PreAuthorize("hasRole('ADMIN')")
public List<User> list() {
return userRepository.findAll();
}
@PreAuthorize("#role == 'ADMIN'")
public List<User> list(String role) {
return userRepository.findAll();
}
@PreAuthorize("#r.name == 'ruchitate'")
public List<User> list(@P("r") UserRequest request) {
return userRepository.findAll();
}