[Spring Security] 인증 처리 흐름

·2022년 11월 21일
0

SpringSecurity

목록 보기
3/13
post-thumbnail

인증 처리 흐름🚰.🚰

Spring Security Filter Chain에서 사용자의 요청을 가로챈 후, 어떻게 처리를 진행할까?

사용자가 로그인을 시도한 경우로 인증 처리 흐름을 익혀보자!

UsernamePasswordAuthenticationFilter

  1. 사용자가 로그인을 위해 UsernamePassword를 포함한 요청 보내면 Spring Security의 Filter Chain의 Filter 중 UsernamePasswordAuthenticationFilter 가 해당 요청을 받는다.

💡UsernamePasswordAuthenticationFilter는 사용자가 로그인을 위해 요청을 보내면 가장 먼저 만나는 컴포넌트로, 사용자의 요청 정보(UsernamePassword)를 통한 인증을 처리하는 필터

👊 UsernamePasswordAuthenticationFilterAbstractAuthenticationProcessingFilter 를 상속받는 하위클래스
AbstractAuthenticationProcessingFilter는 인증 시도는 하위 클래스에게 맡기고, 인증에 성공하면 인증된 사용자 정보를 SecurityCotext에 저장하는 역할을 한다.

💡 FIiter에서 처리를 시작하는 시작점은 doFilter() 메서드이다.

  1. UsernamePasswordAuthenticationFilter는 사용자에게 전달 받은 UsernamePassword를 Spring Security 인증 프로세스에서 이용할 수 있도록 UsernamePasswordAuthenticationToken을 생성한다.

💡 UsernamePasswordAuthenticationTokenAuthentication 인터페이스를 구현한 클래스로 Authentication의 객체를 생성하는 것과 같다고 이해하자

이때, 생성된 Authentication는 아직 인증을 받지 않은 상태이다.

  1. 인증 받지 않은AuthenticationUsernamePasswordAuthenticationFilter를 통해 AuthenticationManager에게 전달된다.

💡AuthenticationManager는 인증 처리를 담당하는 인터페이스로 해당 인터페이스를 구현한 ProviderManager 클래스가 실질적인 인증 처리 작업 담당 매니저 일을 한다.

  1. ProviderManager는 인증 처리를 위해 인증 받지 않은AuthenticationAuthenticationProvider 에게 전달해 인증을 지시한다.

  2. 인증 받지 않은Authentication를 전달 받은AuthenticationProviderUserDetailsService를 통해 UserDetails를 조회한다.

💡잊지말자!
UserDetails는 데이터베이스 등의 저장소에서 저장된 사용자의 Username, 사용자의 자격을 증명해주는 크리덴셜, 사용자의 권한 정보를 포함하고 있는 컴포넌트!

  1. UserDetailsService는 데이터베이스와 같은 저장소(해당 그림에서는 크리덴셜 저장소)에서 사용자의 크리덴셜을 포함한 사용자의 정보를 조회한다.

  2. 조회한 크리덴셜을 포함한 사용자의 정보를 기반으로 UserDetails를 생성한 후, 이것을 AuthenticationProvider에 전달한다. 이 때 검증에 사용된 크리덴셜은 삭제된다.

8.AuthenticationProviderPasswordEncoder를 이용해 인증 받지 않은Authentication 안에 있는 Password를 암호화한 뒤, UserDetails에 포함된 크리덴셜과 비교 검증을 한다.

💥이때 비교에 실패하면 Exception을 발생시키고 인증 처리를 중단한다.

  1. 검증을 통과한 AuthenticationUserDetails를 이용해 인증된 Authentication를 생성한다.

💡이때 생성된 인증 받은 Authentication은 비교 검증을 위해 얻은 UserDetails의 정보를 기반으로 생성된다.

  1. 인증된AuthenticationAuthenticationProvider에 의해 ProviderManager에 전달 된다.

  2. ProviderManager인증된AuthenticationUsernamePasswordAuthenticationFilter에 전달한다.

  3. 인증된Authentication를 전달 받은 UsernamePasswordAuthenticationFilter는 최종적으로 SecurityContextHolder를 이용해 SecurityContext인증된Authentication를 저장한다.

💡 이 때 저장된 인증된Authentication, 즉 SecurityContext는 Spring Security의 세션 정책에 따라서 사용되기도 한다.

Authentication

인증 처리를 위해 생성한UsernamePasswordAuthenticationTokenAuthentication인터페이스의 메서드 일부를 구현한 구현 클래스이다.

인증을 위해 생성되는 인증 토큰 또는 인증 성공 후 생성되는 토큰은 UsernamePasswordAuthenticationToken과 같은 하위 클래스의 형태로 생성되지만 생성된 토큰을 리턴 받거나 SecurityContext에 저장할 경우 Authentication 객체로 리턴되거나 저장된다.

💡우선적으로는 UsernamePasswordAuthenticationToken이 생성된다는 것을 잊지말자!

UsernamePasswordAuthenticationToken

public class UsernamePasswordAuthenticationToken extends AbstractAuthenticationToken {

...
	private final Object principal;

	private Object credentials;
...
...

UsernamePasswordAuthenticationToken클래스는 두개의 필드 변수를 가진다.

  1. Principal : Username등의 신원을 의미
  2. Credentials : Password와 같은 사용자를 증명하기 위한 수단

인증 받지 않은 Authentication

인증에 필요한 용도의 UsernamePasswordAuthenticationToken객체를 생성한다.

public class UsernamePasswordAuthenticationToken extends AbstractAuthenticationToken {

...
public static UsernamePasswordAuthenticationToken unauthenticated(Object principal,
																Object credentials) {
                                                                
		return new UsernamePasswordAuthenticationToken(principal, credentials);
        
	}

인증 받은 Authentication

인증에 성공한 이후 SecurityContext에 저장될 UsernamePasswordAuthenticationToken객체를 생성한다.

  • Authorities : AuthenticationProvider에 의해 부여된 사용자의 접근 권한 목록.
public class UsernamePasswordAuthenticationToken extends AbstractAuthenticationToken {

...
public static UsernamePasswordAuthenticationToken authenticated(Object principal,
																Object credentials,
										Collection<? extends GrantedAuthority> authorities) {
                                        
		return new UsernamePasswordAuthenticationToken(principal, credentials, authorities);
        
	}

SecurityContext와 SecurityContextHolder

SecurityContext

인증된 Authentication 객체를 저장하는 컴포넌트

SecurityContextHolder

SecurityContext를 관리하는 역할

profile
🧑‍💻백엔드 개발자, 조금씩 꾸준하게

0개의 댓글