728x90
PasswordEncoder를 이용한 Spring Security 비밀번호 암호화
비밀번호는 사용자 인증 시스템에서 가장 중요한 요소 중 하나로, 이를 안전하게 저장하는 것은 매우 중요합니다. 비밀번호가 평문으로 저장될 경우, 데이터베이스가 해킹 당했을 때 사용자 계정이 쉽게 노출될 위험이 있습니다. 이를 방지하기 위해 비밀번호를 단방향 암호화하여 저장하는 것이 필수적입니다.
Spring Security
비밀번호를 안전하게 저장할 수 있도록 비밀번호의 단방향 암호화를 지원하는 PasswordEncoder 인터페이스와 구현체들을 제공
Spring Security를 이용한 구현과정
Spring Security 의존성 주입
build.gradle
dependencies {
implementation 'org.springframework.boot:spring-boot-starter-security'
}
Config 설정
WebSecurityConfig.java
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Bean
public PasswordEncoder getPasswordEncoder() {
return new BCryptPasswordEncoder();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.cors().disable()
.csrf().disable()
.formLogin().disable()
.headers().frameOptions().disable();
}
}
PasswordEncoder 인터페이스 내부
public interface PasswordEncoder {
// 비밀번호 단방향 암호화
String encode(CharSequence rawPassword);
// 암호화되지 않은 비밀번호(raw)와 암호화된 비밀번호(encode)가 일치하는지 비교
boolean matches(CharSequence rawPassword, String encodedPassword);
// 기본적으로 false를 return, Custom하게 구현할 경우 이를 기반으로 더 강력한 암호화 구현
default boolean upgradeEncoding(String encodedPassword) {
return false;
}
}
SHA-256 기반 비밀번호 암호화 구현하기
PasswordEncoder
@Component
public class PasswordEncoder {
// 비밀번호 단방향 암호화 메서드
public String encode(String password) {
try {
// SHA-256 알고리즘 인스턴스 생성
MessageDigest md = MessageDigest.getInstance("SHA-256");
md.update(password.getBytes()); // 비밀번호의 바이트 표현을 해시 함수에 업데이트
byte[] byteData = md.digest(); // 해시 함수의 최종 해시 값 얻기
// 바이트 배열을 16진수 문자열로 변환
StringBuilder sb = new StringBuilder();
for (byte b : byteData) {
sb.append(String.format("%02x", b));
}
return sb.toString(); // 16진수 문자열 반환
} catch (NoSuchAlgorithmException e) {
throw new RuntimeException(e); // 알고리즘이 없는 경우 예외 처리
}
}
// 암호화되지 않은 비밀번호와 암호화된 비밀번호 비교 메서드
public boolean matches(String rawPassword, String encodedPassword) {
return encode(rawPassword).equals(encodedPassword); // 비밀번호 일치 여부 확인
}
}
- MessageDigest.getInstance("SHA-256")을 통해 SHA-256 해시 함수의 인스턴스를 얻어옵니다.
- md.update(password.getBytes())를 통해 비밀번호의 바이트 표현을 해시 함수에 업데이트합니다.
- md.digest()를 호출하여 해시 함수의 최종 해시 값을 얻어옵니다.
- 얻어온 해시 값을 16진수 문자열로 변환하여 반환합니다.
평문 암호화 문제
동일한 비밀번호를 암호화하면 항상 동일한 해시 값이 생성됩니다. 이를 해결하기 위해 솔트(Salt)를 도입하는 방법이 있으며, 솔트는 해시할 때 추가되는 무작위 데이터로 매번 다른 해시 값을 생성하게 만든다.
728x90
'IT 개발 관련 > [Spring]' 카테고리의 다른 글
[Spring] Eureka Server (Discovery Server) 생성 (0) | 2024.06.28 |
---|---|
[Spring] MSA(MicroService Architecture) 란? (0) | 2024.06.27 |
Thymeleaf를 이용한 Header, Footer 재사용 및 유지보수성 향상 (1) | 2024.06.02 |
[Spring] Swagger 라이브러리 가이드 (0) | 2024.05.28 |
[Spring] Binding Result 사용 가이드 (0) | 2024.05.25 |