Spring Security - 인가 처리 (개념)

이유석·2024년 11월 22일
1

Spring-Security

목록 보기
6/10
post-thumbnail

출처

Spring Security 인가

  • 정상적인 인증 처리 이후에 SecurityContext에 인증정보인 Authentication 이 저장된다.
  • Authentication 은 Authorities 에 사용자의 권한 정보를 담고있다.
    → Authorities(사용자 권한 목록)는 인가 처리에 활용된다.
    → 사용자는 여러개의 권한을 갖고있을 수 있다.

  • Authentication → getAuthorities() 함수
    • 사용자의 권한 목록 반환 함수

      public interface Authentication extends Principal, Serializable {
          Collection<? extends GrantedAuthority> getAuthorities();
      }
  • Authority 는 GrantedAuthority 상위 interface를 상속받아 구현한다.
    • GrantedAuthority interface 는 하나의 메서드를 갖고있다.
      String getAuthority();
    • 이 메서드는 GrantedAuthority 을 String으로 표현한 값을 얻기 위해서 AuthorizationManager 인스턴스에 의해 사용된다.
  • Spring Security는 SimpleGrantedAuthority라는 GrantedAuthority 구현체를 갖고있다.
    • 이 구현체는 user-specified String 을 GrantedAuthority 로 변환될 수 있게 해준다.
    • 또, security architecture 에 포함된 모든 AuthenticationProvider 인스턴스들은 Authentication 객체에 SimpleGrantedAuthority 를 추가한다.
  • 기본적으로, ROLE 기반 인가 규칙들은 접두사로 ROLE_ 을 포함한다.
    • 즉, security context가 "USER"의 역할을 필요로하는 인가 규칙이 있다면, Spring Security는 기본적으로 ROLE_USER를 반환하는 GrantedAuthority#getAuthority를 찾는다는 것이다.

    • 이러한 기본 설정은 변경할 수 있는데, GrantedAuthorityDefaults를 사용하여 이를 사용자 정의할 수 있다.

      // MethodSecurityExpressionHandler
      @Bean
      static GrantedAuthorityDefaults grantedAuthorityDefaults() {
      	return new GrantedAuthorityDefaults("MYPREFIX_");
      }

      Tip

      Spring Security에서 변경된 GrantedAuthorityDefaults를 적용하기 위해서는, @Configuration 클래스보다 GrantedAuthorityDefaults가 먼저 빈으로 등록되어야하는데, static 키워드는 해당 메서드가 @Configuration 클래스 보다 먼저 등록되는 것을 보장하기 위해 사용된다.

Spring Security 인가 처리

  • Spring Security는 메서드 호출이나 웹 요청과 같은 secure objects에 대한 접근을 제어하는 interceptor들을 제공한다.
    • AuthorizationManager 인스턴스에 의해 인가 작업이 이루어진다.
      • 메서드 호출 또는 웹 요청 진행 가능 여부 (pre-invocation)
      • 결과값이 반환될 수 있는지 여부 (post-invocation)

AuthorizationManager

  • XX 버전부터 AuthorizationMagerAccessDecisionManagerAccessDecisionVoter 를 대체한다.

  • AuthorizationManager는 Spring Security의 request-based, method-based 및 message-based 인증 컴포넌트들에 의해 호출되며 최종 접근 제어 결정을 내리는 역할을 한다.

  • AuthorizationManager 인터페이스는 아래 2개의 메서드들을 포함한다

    AuthorizationDecision check(Supplier<Authentication> authentication, Object secureObject);
    
    default AuthorizationDecision verify(Supplier<Authentication> authentication, Object secureObject)
            throws AccessDeniedException {
        // ...
    }
    • check 메서드
      • 인가 결정을 내리기 위해 필요한 모든 정보를 전달받는다.
      • 특히, Authentication 을 전달받아, secureObject 에 접근 가능한지 검사할 수 있다.
        • 접근이 허용될 경우 → positive(granted 가 true인) AuthorizationDecision 반환
        • 접근이 반려될 경우 → negative(granted 가 false인) AuthorizationDecision 반환
        • 결정을 내릴 수 없는 경우 → null AuthorizationDecision 반환
          ex. 명확한 인가 기준을 전달하지 못했을 경우
    • verify 메서드
      • check 메서드를 호출한다.
        • check 메서드의 결과가 negative AuthorizationDecision 이면
          • throw AccessDeniedException

Delegate-based AuthorizationManager 구현체 목록

  • 개발자는 인가의 모든 측면을 제어하기 위해 커스텀 AuthorizationManager 를 구현할 수 있다.

  • 하지만, SpringSecurity 는 각각의 AuthorizationManager 들과 이들과 협력할 수 있는 delegating(위임형) AuthorizationManager 를 함께 제공한다.

    • AuthorizationManager 구현체

    • 이들을 활용하여, 각 AuthorizationManager 구현체들의 조합이 인가 결정에 대한 투표를 수행할 수 있도록 한다. (?)

AuthorityAuthorizationManager

  • AuthorityAuthorizationManager는 Spring Security에서 제공되는 가장 일반적인 AuthorizationManager이다.
  • 만약 Authentication 이 지정된 권한들 중 하나라도 포함하고 있다면, positive AuthorizationDecision 을 반환한다.
  • 반대의 경우에는 negative AuthorizationDecision 을 반환한다.

AuthenticatedAuthorizationManager

  • anonymous, fully-authenticatedremember-me authenticated users 를 구분하는데 사용될 수 있다.

AuthorizationManagers

  • 개별 AuthorizationManager를 더 정교한 표현으로 구성하기 위해 도움이 되는 static factory method 존재한다.
    • authenticated() : 인증된 모든 사용자만 접근할 수 있도록 설정할 때 사용됩니다.
    • permitAll() : 모든 사용자(인증되지 않은 사용자 포함)가 접근할 수 있도록 허용합니다.
    • denyAll() : 모든 요청을 거부합니다. → 특정 리소스에 대해 접근을 차단할 때 사용됩니다.
    • hasRole(String role) : 사용자가 특정 역할(ROLE_)을 가지고 있는지 확인합니다.
    • hasAuthority(String authority) : 사용자가 특정 권한을 가지고 있는지 확인합니다.
    • anyOf() : 전달된 여러 AuthorizationManager 중 하나만 만족하면 접근을 허용합니다.
    • allOf() : 전달된 모든 AuthorizationManager 조건을 만족해야 접근을 허용합니다.
    • custom(Predicate) : 커스텀 로직을 기반으로 동작하는 인가 매니저를 정의할 수 있습니다.
      ex. 요청에 특정 헤더가 포함되어야만 접근 가능하도록 설정할 때.

Custom Authorization Managers

  • 사용자 정의 AuthorizationManager를 구현하여, 원하는 어떤 접근 제어 로직도 구현할 수 있다.
  • 이는 자신의 애플리케이션에 특정(specific)할 수도 있으며(비즈니스 로직 관련), 또는 일부 보안 관리 로직을 구현할 수도 있다.
  • 예를 들어, Open Policy Agent 또는 소유하고있는 인가 데이터베이스를 쿼리할 수 있는 구현체를 생성할 수 있다.
profile
소통을 중요하게 여기며, 정보의 공유를 통해 완전한 학습을 이루어 냅니다.

0개의 댓글