이 문서는 단독 가이드입니다.

Spring Security가 인증 과정에서 사용자 정보를 어떻게 다루는지, UserDetailsGrantedAuthority가 무엇인지 설명합니다.


1. UserDetails란?

Spring Security는 인증된 사용자 정보를 직접 다루지 않습니다. 대신 UserDetails 인터페이스를 통해 사용자 정보를 표준화된 방식으로 받아옵니다.

쉽게 말하면, Spring Security가 "이 사람 누구야?"라고 물을 때 내놓는 신분증 양식입니다. 양식만 맞추면 내부 구현은 자유롭게 할 수 있습니다.

UserDetails 인터페이스가 요구하는 메서드:

메서드역할
getUsername()식별자 반환 (username, email 등)
getPassword()해시된 비밀번호 반환
getAuthorities()권한 목록 반환
isAccountNonExpired()계정 만료 여부
isAccountNonLocked()계정 잠금 여부
isCredentialsNonExpired()비밀번호 만료 여부
isEnabled()계정 활성화 여부
계정 상태 메서드 4개는 기본값으로 두어도 됩니다.

isAccountNonExpired(), isAccountNonLocked(), isCredentialsNonExpired(), isEnabled()는 별도 관리가 필요 없다면 모두 true를 반환하도록 구현하면 됩니다. UserDetails 인터페이스에 default 구현이 있어 오버라이드하지 않아도 true가 반환됩니다.


2. GrantedAuthority란?

GrantedAuthority 는 사용자에게 부여된 권한 하나를 나타내는 인터페이스입니다.

getAuthorities()가 반환하는 Collection<? extends GrantedAuthority> 가 바로 이 권한들의 목록입니다.

일반적으로 SimpleGrantedAuthority를 사용해 문자열로 권한을 표현합니다:

List.of(new SimpleGrantedAuthority("ROLE_USER"))
ROLE_ 접두사

Spring Security는 역할(Role)을 권한(Authority)과 구분하기 위해 ROLE_ 접두사를 사용합니다.

- 역할: ROLE_USER, ROLE_ADMIN — 사용자의 신분

- 권한: READ_POST, DELETE_POST — 특정 행위 가능 여부

hasRole("USER")는 내부적으로 ROLE_USER를 찾습니다. hasAuthority("ROLE_USER")와 동일합니다.


3. 현재 코드 분석

@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
    return List.of();
}
  • List.of() : 빈 컬렉션을 반환 → 이 사용자는 아무 권한도 없음
  • 현재는 역할 구분 없이 인증만 하면 모든 기능을 사용할 수 있는 구조이므로 빈 리스트로 두어도 동작은 합니다.
[실수] 권한 없이 hasRole() 체크를 하면 항상 거부됩니다.

SecurityConfig에서 특정 경로에 hasRole("USER") 같은 조건을 걸었다면, getAuthorities()가 빈 리스트를 반환하는 한 모든 요청이 403으로 거부됩니다.


4. 권한이 필요할 때 구현하는 방법

역할 기반 접근 제어가 필요해지면 다음과 같이 구현합니다.

User 엔티티에 role 필드 추가

@Column(nullable = false)
private String role; // "ROLE_USER", "ROLE_ADMIN" 등

getAuthorities()에서 역할 반환

@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
    return List.of(new SimpleGrantedAuthority(userDto.role()));
}
  • SimpleGrantedAuthority : GrantedAuthority의 가장 간단한 구현체. 문자열 하나를 권한으로 등록합니다.
  • userDto.role() : UserDto에서 역할 문자열을 꺼내 권한으로 변환합니다.

5. 전체 흐름

sequenceDiagram participant Client participant Filter as Security Filter participant UDS as UserDetailsService participant UD as UserDetails Client->>Filter: 로그인 요청 (username, password) Filter->>UDS: loadUserByUsername(username) UDS->>UD: DiscodeitUserDetails 생성 및 반환 UD-->>Filter: username, password, authorities 제공 Filter->>Filter: 비밀번호 검증 (PasswordEncoder.matches) Filter-->>Client: 인증 성공 / 실패