비밀번호 같은 중요한 정보는 DB에 저장할 때 입력받은 값 그대로 저장하면 안됨
암호화 방식에는
단방향 / 양방향 이 있는데 아주 간단하게만 얘기해볼겡
단방향 암호화는 암호화는 할 수 있지만, 복호화하여 원본 비밀번호를 알 수 없다.
양방향 암호화는 암호화하고, 복호화하면 원본 비밀번호를 알 수 있다.
이런것임.
지금 쓰게될
Spring Security의 BCryptPasswordEncoder 사용하는 BCrypt 방식은
회원가입의 경우를 예시로 들면
회원가입을 할 때 사용자가 입력한 원본 비밀번호와
랜덤으로 생성된 솔트를 결합해 생성된 해시 값이 DB에 들어가는것임!
salt는 매번 랜덤하게 생성되기 때문에 동일한 비밀번호도 매번 다른 해시 값을 생성함.
그래서 해시값으로 복호화해서 원본 비밀번호를 복원하는 것은 불가능함.
나는 지금 다른 회사랑 같이 일을 하고있어서salt값을 공통값으로 사용해야한당(다른 회사에서 비밀번호를 확인해야하는데 복호화가 안되는 방식이니까?)
사실 랜덤하게 생성되는 salt값을 내가 임의로 정하겠다는건
암호화 방식을 보안에 취약하게 만들겠다는건데,,
더 좋은 방법은 추후에 생각해보기로하고
주기를 정해놓고 랜덤값을 생성한다든지,,
회사마다 솔트값을 정해놓고 쓴다든지?
그게 아니면 아예 다른 암호화방법을 쓴다든지
일단 오늘은 솔트를 임의로 박아두고 작업을 해야한다
솔트를 고정값으로 지정하면
동일한 비밀번호는 같은 해시가 생성됨.
고정값을 사용하더라도 원본 비밀번호로 직접적으로 복호화는 불가능, 확인 방법은 있음.
비밀번호 확인 방법 (아래 코드 참고)
비밀번호와 고정된 솔트를 결합하고, 결합된 문자열을 BCrypt로 해시화해서
새로 생성된 해시와 동일한 비밀번호로 이미 생성되어있는 해시를 비교한다.
솔트형식
예시
$2a$10$abcdefghijABCDEFGHIJ12
$2a$<cost>$<22자 솔트>
$2a$ : 해시 알고리즘의 식별자, 일반적으로 $2a$가 가장 많이 사용됨
<cost> : 해시 비용을 나타냄, 숫자가 클수록 해시 계산이 더 느려지고, 보통 4에서 31 사이의 값이 들어감. $10$은 2의 10제곱의 반복 횟수
<22자 솔트> : 22자리의 랜덤 문자열, Base64 인코딩된 문자열
public class PasswordVerification {
// 고정 솔트값 예시
private static final String FIXED_SALT = "$2a$10$bbbbABCDabcdABCDaaaa12";
public static void main(String[] args) {
// 사용자가 입력한 비밀번호
String inputPassword = "admin";
// 기존에 생성된 해시
String storedHash = "$2a$10$abcdefghijABCCCCGHIJ1udL2bUUJdaqJdPqd8cDRGXxmh9U0rgOw";
boolean isMatch = verifyPassword(inputPassword, storedHash);
System.out.println("일치 여부: " + isMatch);
}
public static boolean verifyPassword(String inputPassword, String storedHash) {
BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
String saltedHash = passwordEncoder.encode(FIXED_SALT + inputPassword);
return passwordEncoder.matches(inputPassword, storedHash);
}
}
코드 이런식으로 짜서 비교해보면 확인 해보면 됨
'Chapter01 > Sping boot' 카테고리의 다른 글
[ SMTP 메일 전송 ] Could not convert socket to TLS (12) | 2024.10.02 |
---|---|
[ Spring boot ] config.xml (0) | 2024.05.29 |
[ Spring Boot ] annotation (3) | 2024.03.20 |