-
REST API 보안 적용 - 1백기선(인프런 강의)/스프링 기반 REST API 개발 2021. 1. 27. 16:50반응형
위 GIT주소에 개발 step 별로 commit 해두었다.
진행 과정
이벤트 조회 및 수정 REST API 개발
- Account 도메인 추가
- 스프링 시큐리티 적용
- 예외 테스트
- 스프링 시큐리티 기본 설정
- 스프링 시큐리티 폼 인증 설정
- 스프링 시큐리티 OAuth2 인증 서버 설정
- 리소스 서버 설정
- 문자열을 외부 설정으로 빼내기
- 이벤트 API 점검
- 현재 사용자 조회
- 출력값 제한하기
1. Account 도메인 추가
2. 스프링 시큐리티 적용
스프링 시큐리티
스프링 5 부터는 웹이 2종류가 됨
- Web flux
- Web servlet (이번 강의에서 이기준으로 설명)
SecurityInterceptor
- 웹 요청 같은 경우는 srpingFilterChain이 연관이 되어있있음
- 웹 시큐리티 (Filter 기반 시큐리티)
- 메소드 시큐리티
- 이 둘 다 Security Interceptor를 사용합니다.
- 리소스에 접근을 허용할 것이냐 말것이냐를 결정하는 로직이 들어있음.
- AOP랑 비슷한 기능
웹 시큐리티 흐름
1. 어떤 요청이 들어왓을때 서블릿 필터가 가로 챈다.
2. 스프링 빈에 등록되어있는 시큐리티 인터셉터 쪽으로 요청을 보낸다.
3. 인터셉터가 요청을 보고 인증을 해야되는지 확인 한다.
4. 적용해야 한다면 인터셉터에 들어오게 된다.
5. 인증정보를 확인은 기본적으로 SecutrityContextHolder가 담당한다.
6. SecutrityContextHolder 에서는 기본적인 구현체 ThreadLocal 이다.(ThreadLocal 한쓰레드에서 공유하는 자원)
7. ThreadLocal을 사용하기 때문에 인증 정보는 한번만 전달하고 공유해서 사용가능하다
3. 예외 테스트
@Test(expected)
- 예외 타입만 테스트 가능
@Test(expected = UsernameNotFoundException.class) public void findByUserNameFail() { String userName = "random@test.com"; accountService.loadUserByUsername(userName); }
try-catch
- 예외 타입과 메시지 확인 가능.
- 하지만 코드가 다소 복잡.
@Test public void findByUserNameFail() { String userName = "random@test.com"; try { accountService.loadUserByUsername(userName); fail("supposed to be failed"); } catch (UsernameNotFoundException e) { assertThat(e.getMessage()).containsSequence(userName); } }
@Rule ExpectedException
@Test public void findByUserNameFail() { // Expected String userName = "random@test.com"; expectedException.expect(UsernameNotFoundException.class); expectedException.expectMessage(Matchers.containsString(userName)); // When accountService.loadUserByUsername(userName); }
4. 스프링 시큐리티 기본 설정
시큐리티 필터를 적용하기 않음
/docs/index.html
로그인 없이 접근 가능
- GET /api/events
- GET /api/events/{id}
로그인 해야 접근 가능
- POST /api/events
- PUT /api/events/{id}
스프링 시큐리티 OAuth 2.0
AuthorizationServer: OAuth2 토큰 발행(/oauth/token) 및 토큰 인증(/oauth/authorize)
- Oder 0 (리소스 서버 보다 우선 순위가 높다.)
ResourceServer: 리소스 요청 인증 처리 (OAuth 2 토큰 검사)
- Oder 3 (이 값은 현재 고칠 수 없음)
스프링 시큐리티 설정
@EnableWebSecurity
- 스프링 부트에서 설정하는 시큐리티 설정을 적용하지 않고 직접 설정한다.
- 스프링 시큐리티의 기본설정을 상속받는다.
@Configuration @EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { }
@EnableGlobalMethodSecurity
extends WebSecurityConfigurerAdapter
- PasswordEncoder: PasswordEncoderFactories.createDelegatingPassworkEncoder()
- prefix로 인코딩 방식 기입 및 prefix에 따라 매칭확인
- 아래의 방색대로 사용가능
@Bean public PasswordEncoder passwordEncoder(){ PasswordEncoder encoder = new BCryptPasswordEncoder(); return encoder; }
TokenStore: InMemoryTokenStore
- 토큰을 저장하는 곳. (OAuth 토큰을 저장)
- InMemoryTokenStore
/** * auth 토큰 저장소 * @return */ @Bean public TokenStore tokenStore() { return new InMemoryTokenStore(); }
AuthenticationManagerBean
- AuthenticationManager를 어떤 형태로 만들지
@Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.userDetailsService(accountService) .passwordEncoder(passwordEncoder); }
configure(AuthenticationManagerBuidler auth)
SecurityFilter를 적용할지 말지를 설정 (http로 가기전에 확인)
- PathRequest.toStaticResources().atCommonLocations()
- 스프링 부트에서 지원(Servlet, Reactive)
- 정적 리소스들에 대한 기본위치
configure(HttpSecurity http)
- /docs/**: permitAll
configure(WebSecurty web)
- igore
- /dosc/**
- /favicon.ico
@Override public void configure(WebSecurity web) throws Exception { web.ignoring().mvcMatchers("/docs/index.html"); web.ignoring().requestMatchers(PathRequest.toStaticResources().atCommonLocations()); }
반응형'백기선(인프런 강의) > 스프링 기반 REST API 개발' 카테고리의 다른 글
REST API 보안 적용 - 2 (0) 2021.01.29 이벤트 조회 및 수정 REST API 개발 (0) 2021.01.27 REST API 보안 적용 (0) 2021.01.24 이벤트 생성 API 개발 -3 (0) 2021.01.24 이벤트 생성 API 개발 -2 (0) 2021.01.23