본문 바로가기

Spring Security

[Spring Security] SecurityContextPersistenceFilter 이해

이번 포스팅에서는 SecurityContext 객체의 생성, 저장, 조회하는 역할을 담당하는 SecurityContextPersistenceFilter에 대해서 공부해 보도록 하겠습니다.

이 필터같은 경우 ThreadLocal에 인증 후 세션에서 가져온 SecurityContext를 넣어주는 역할도 하기때문에 SecurityContextHolder.getContext().getAuthentication()을 통해 어디서든지 인증한 사용자의 정보를 가져오는지 공부해 볼 수 있습니다.

 

SecurityContextPersistenceFilter의 동작방식을 살펴보면 아래와 같은 Flow로 진행되는 것을 알 수 있습니다.

이 필터에 동작방식을 코드로 보기위해 어떤 클래스가 사용되고 있는지 알아보도록 하겠습니다.

  • SecurityContextPersistenceFilter.java
  • HttpSessionSecurityContextRepository.java

먼저 SecurityContextPersistenceFilter클래스의 doFilter가 실행되면서 아래와 같이 로직이 실행되게 됩니다.

 

1. SecurityContextPersistenceFilter에서 인증 전인지 인증 후인지 판단하게 되는데, 판단 방법은 세션에 SecurityContext객체의 존재여부로 판단하게 됩니다. (처음 인증 시도라고 가정)

SecurityContextPersistenceFilter

HttpSessionSecurityContextRepository클래스의 loadContext메소드에서 context가 null이기 때문에 SecurityContext객체를 생성합니다.

HttpSessionSecurityContextRepository

2. 생성된 SecurityContext객체를 SecurityContextHolder에 저장합니다.

SecurityContextPersistenceFilter

3. 그 후 인증하는 필터로 넘어가게 되는데 인증필터가 인증에 성공하게 되면, 최종적으로 세션에 SecurityContext가 저장됩니다.

SecurityContextPersistenceFilter

springSecuritycontextKey는 아래와 같이 HttpSessionSecurityContextRepository클래스에 선언되어 있습니다.

private String springSecurityContextKey = SPRING_SECURITY_CONTEXT_KEY;

HttpSessionSecurityContextRepository

4. 인증된 사용자가 한번 더 요청을 하게되면, 이번에는 session에서 가져온 SecurityContext가 null이 아니기때문에 객체를 생성하지 않습니다.

HttpSessionSecurityContextRepository

5. 세션에서 가져온 SecurityContext객체를 SecurityContextHolder안에 저장합니다.

이때, SecurityContext객체는 ThreadLocal을 사용하기 때문에 쓰레드 어디서든지 접근이 가능합니다.

SecurityContextPersistenceFilter