1 Commits

Author SHA1 Message Date
Daeil Choi
4f13595479 Add custom filter 추가 2023-02-07 06:47:33 +09:00
3 changed files with 98 additions and 5 deletions

View File

@@ -1,25 +1,46 @@
package com.example.springsecuritystudy.config;
import com.example.springsecuritystudy.filter.StopwatchFilter;
import com.example.springsecuritystudy.filter.TesterAuthenticationFilter;
import lombok.RequiredArgsConstructor;
import org.springframework.boot.autoconfigure.security.servlet.PathRequest;
import org.springframework.context.annotation.Bean;
import org.springframework.http.HttpMethod;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.configuration.AuthenticationConfiguration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityCustomizer;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import lombok.RequiredArgsConstructor;
/**
* Security 설정 Config
*/
@EnableWebSecurity
@EnableWebSecurity(debug = true)
@RequiredArgsConstructor
public class SecurityConfig {
@Bean
public AuthenticationManager authenticationManager(AuthenticationConfiguration authenticationConfiguration) throws Exception {
return authenticationConfiguration.getAuthenticationManager();
}
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
// stopwatch filter
http.addFilterBefore(
new StopwatchFilter(),
WebAsyncManagerIntegrationFilter.class
);
// tester authentication filter
http.addFilterBefore(
new TesterAuthenticationFilter(authenticationManager(http.getSharedObject(AuthenticationConfiguration.class))),
UsernamePasswordAuthenticationFilter.class
);
http
.httpBasic().disable()
.csrf();
@@ -27,7 +48,7 @@ public class SecurityConfig {
.rememberMe();
http
.authorizeHttpRequests(auth -> auth
.antMatchers("/", "/home", "/signup", "/h2-console/**").permitAll()
.antMatchers("/", "/home", "/signup").permitAll()
.antMatchers("/note").hasRole("USER")
.antMatchers("/admin").hasRole("ADMIN")
.antMatchers(HttpMethod.POST, "/notice").hasRole("ADMIN")
@@ -53,7 +74,10 @@ public class SecurityConfig {
@Bean
public WebSecurityCustomizer webSecurityCustomizer() {
// 정적 리소스 spring security 대상에서 제외
return (web) -> web.ignoring().requestMatchers(PathRequest.toStaticResources().atCommonLocations());
return (web) -> web.ignoring()
.antMatchers("/h2-console/**")
.requestMatchers(PathRequest.toStaticResources().atCommonLocations())
;
}
}

View File

@@ -0,0 +1,27 @@
package com.example.springsecuritystudy.filter;
import java.io.IOException;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.util.StopWatch;
import org.springframework.web.filter.OncePerRequestFilter;
import lombok.extern.slf4j.Slf4j;
@Slf4j
public class StopwatchFilter extends OncePerRequestFilter {
@Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response,
FilterChain filterChain) throws ServletException, IOException {
StopWatch stopWatch = new StopWatch(request.getServletPath());
stopWatch.start();
filterChain.doFilter(request, response);
stopWatch.stop();
// Log StopWatch '/login' : running time = 150545041 ns
log.info(stopWatch.shortSummary());
}
}

View File

@@ -0,0 +1,42 @@
package com.example.springsecuritystudy.filter;
import com.example.springsecuritystudy.user.User;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.stream.Collectors;
import java.util.stream.Stream;
/**
* 테스트 유저인 경우에는 어드민과 유저 권한 모두를 줍니다.
*/
public class TesterAuthenticationFilter extends UsernamePasswordAuthenticationFilter {
public TesterAuthenticationFilter(AuthenticationManager authenticationManager) {
super(authenticationManager);
}
@Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws
AuthenticationException {
Authentication authentication = super.attemptAuthentication(request, response);
User user = (User) authentication.getPrincipal();
if (user.getUsername().startsWith("test")) {
// 테스트 유저인 경우 어드민과 유저 권한 모두 부여
return new UsernamePasswordAuthenticationToken(
user,
null,
Stream.of("ROLE_ADMIN", "ROLE_USER")
.map(authority -> (GrantedAuthority) () -> authority)
.collect(Collectors.toList())
);
}
return authentication;
}
}