개발이군고구마

Spring Security의 로직 본문

SERVER/Spring

Spring Security의 로직

김구황 2024. 8. 16. 17:47
728x90

1. 목적

- 실무에서는 회원에 대한 정보를 공통으로 정의해서 쓰고 있는데, 이에 대한 정보는 securitycontext에 저장된 authentication 객체임

- authentication 안에 principal 객체에 회원에 대한 정보가 저장되어있는데, 이를 저장하는 로직을 살펴보고, 시큐리티 적용 방법에 대해 분석해보고자 함 

 

 

2. Spring Security와 사용 이유

- Spring Security란

  • 인증 (authentication) 과 인가 (authorization) 및 보안을 담당하는 스프링 하위 프레임 워크 
  • Filter 기반으로 동작하며, Spring MVC와는 분리되어 관리 동작함 
  • Spring Security 3.2 부터는 XML 설정하지 않과, Java Bean설정을 함 

 

- Spring Security를 사용하는 이유 

  • 보안에 필요한 로직을 일일이 다 작성하지 않아도 된다는 장점 
  • Session check, SuccessHandler 기능 등을 제공하여 간편함 

 

 

3. 로직 

일반적인 로직, 흐름도

 

- 시큐리티의 전체 큰 흐름은 다음과 같음 

  • 인증 필터 : SecurityFilter
    • doFilter => attemptAuthentication 을 통해 (시작점, 이 부분으로 다시 돌아옴)
    • 특정 로그인 방법에 url 이 들어오면 그에 맞는 필터 class를 타도록 정의함 
  • UsernamePasswordAuthenticationToken : authenticate 메소드를 호출하는 Token 클래스
  • AuthenticationManager : provider를 호출하는 manager
    • authenticate를 호출 
  • ProviderManager
    • support 메서드를 구현하여 해당 인증 처리를 판별할지 확인함 
    • userDetailService를 사용하여 userDetail 등 user 에 대한 정보를 비즈니스 로직을 통해서 확인함 
  • UserDetails - UserDetailsService
    • loadByUserName 메소드를 구현함 
      • 해당 메서드에서 로그인한 사용자와 로그인이 필요한 사용자를 구별하여 
      • 비즈니스 로직에서 userDetail 에 정보를 담음 
      • password encoding 진행 

 

[성공시 로직]

 

SecurityFilter 로 다시 돌아옴 

  • Session에  SPRING_SECURITY_CONTEXT_KEY 라는 이름으로 SecurityContext 가 저장
    • SecurityAuthenticationSuccessHandler 가 실행되는데, 이쪽에서 각종 쿠키 값을 설정
 securitySessionInitHandler.initSecuritySession(request, response, authentication, sessionRegistry);
  • 최종적으로 들어온 UserDetail은 SecurityContext 에 authentication 정보가 담기게 됨 
  • 그 외에 진행해야할 successfulHandler들이 실행됨 (remember-me 등)
    • Spring 설정에서 저장된 successfulHandler들을 filter에 따라서 실행함 

 

 

- Security Context 의 구조 

  • 인증 프로세스가 끝난 후 인증 엔티티에 대한 세부 정보 Authentication 객체가 담기는 곳 
  • Authentication 객체 안에는 Principal (회원정보) / Credentials / Authorities (role 정보) 가 담김 

 

- SuccessHandler

  • (현프로젝트) Filter가 성공적으로 구현시 그 다음으로 실행될 successHandler 들이 xml에 지정됨 
  • 그 중 대표적인 것이 바로 Remember-me SuccessHandler (Redis에 utid(key): value(cookid-id)로 값 적재) 
    • 추 후에 같은 utid로 들어왔을 때, redis db 에 있는 cookie id 를 decoding 하여 확인 
    • 존재하는 cookie id 인 경우에 자동 로그인 실현 

 

 

 

4. Oauth 인증 방식 

- Token을 직접 생성하지 않고, API 연결하여 외부 서버에서 token을 제공받음 

크게 총 3번의 API 호출 : 1) 로그인 화면 호출 2) Token 요청 3) Token 에 있는 정보들을 요청

  • script key를 제공 받아서, kakao.auth.get 과 같은 메서드를 구현하여 Token 정보를 받아옴 
  • 해당 클래스에 filter 를 타게 하는 url을 함께 지정하여, filter에서 그에 맞는 manager -> provider를 타게 함 
  • api script 에서 시작하여 결과 값을 다시 받아오고
    • 이에 따라 로그인 또는 회원가입이 진행됨 
    • session에 kakao에서 전달받은 정보들이 key : KAKAO / value : json 형태 로 저장됨