비밀번호 암호화

황정준·2023년 10월 9일
0
post-thumbnail

인턴 중간발표 때 받은 질문

작년에 회사에서 인턴 중간 발표때의 일이다.
당시, Spring Boot와 Thymeleaf를 활용하여 풀스택 프로젝트를 진행 중이었다. 이 과정에서 Spring Security를 활용해 로그인 기능을 개발하였는데, 중간 발표 후 팀장님께서 흥미로운 질문을 던져주셨다.

비밀번호는 어떤 암호화 방식을 사용해서 저장했나요?

당시에는 개발시간이 부족해 Spring Security의 비밀번호 인코더가 어떻게 동작하는지 깊게 알지 못하고 있었다. 그래서 간단히 해시 함수를 사용했다고만 답했었다.

만약 해싱된 비밀번호가 유출되면 어떤 위험이 있을까요?

이 질문에는 명확한 답변을 준비하지 못했다.
해시된 문자열만 유출되면 원본 문자열을 유추하기는 어렵다고 생각했으나,
실제로는 여러 위험성이 존재했다.


해시 함수란?

해시 함수란 어떤 입력값을 받아서 고정된 크기의 알파벳과 숫자로 된 문자열을 출력하는 함수를 뜻한다.
이는 단방향 함수의 특성을 가지므로, 해싱된 결과를 통해 원래의 입력값을 직접 알아내는 것은 불가능하다. 그러나 무차별 대입 공격(brute force attack)을 통해 가능성 있는 입력 문자열들을 대입해보며 해싱값을 확인함으로써 원본 문자열을 유추하는 것은 가능하다.

아래는 "당신의 비밀번호"라는 문자열에 대해 여러 해시 알고리즘을 적용한 예시다.

MD5 (Message Digest Algorithm 5)

  • 1991년에 Ronald Rivest에 의해 탄생
  • 128비트 길이의 해시 값

SHA-1 (Secure Hash Algorithm 1)

  • NIST (미국 국립표준기술연구소)에 의해 1993년에 발표
  • 160비트 길이의 해시 값

SHA-2 (Secure Hash Algorithm 2)

  • SHA-1의 취약점을 해결하기 위해 NIST에 의해 2001년에 설계
  • 여러 버전의 출력 길이를 가짐: SHA-224, SHA-256, SHA-512

SHA-3 (Secure Hash Algorithm 3)

  • NIST의 암호화 해시 함수 경쟁을 통해 2015년에 표준화
  • SHA-2와 동일한 출력 길이를 모두 지원하며, 필요에 따라 SHA-2를 대체하여 사용 가능

비밀번호 암호화의 중요성

그러면 위의 해시 알고리즘을 사용하여 비밀번호를 암호화하면 문제가 없을까?
아니다. 길이가 짧고 보안 취약점이 드러난 알고리즘을 사용하면 문제가 될 가능성이 매우 크다.
현재 보안취약점이 발견된 MD5SHA-1은 보안목적으로 사용해선 안된다.

만약 MD5 알고리즘으로 암호화된 비밀번호를 사용하는데 해싱된 문자열이 유출된다면
몇시간안에 계정을 해킹할 수 있다. (SHA-1은 좀더 오래걸린다)

따라서 SHA-2 이상의 알고리즘을 사용하는 것이 좋다.


솔트를 통한 보안성 강화

단순 해시 알고리즘만을 사용하는 것은 여전히 위험할 수 있다.
해커가 단순히 해싱된 비밀번호 문자열만을 탈취하는 것이 아니라 원본 비밀번호를 알면, 동일한 해시값을 가진 다른 사용자의 계정까지 접근할 수 있기 때문이다.

이런 위험을 줄이기 위해 '솔트'라는 랜덤 문자열을 원본 비밀번호에 추가하여 해싱하는 방법을 사용한다. 이렇게 하면, 같은 원본 비밀번호라도 해시값이 다르게 나오기 때문에, 해커의 공격이 어려워진다.


Spring Security의 비밀번호 암호화 방식

그러면 내가 인턴 때 사용했던 Spring Security에서는 어떻게 비밀번호를 암호화할까?

비밀번호 암호화에 PasswordEncoder라는 인터페이스를 사용하는데
이 인터페이스의 구현체중 BCryptPasswordEncoder라는 BCrypt알고리즘을
사용한 클래스를 많이 사용한다.


BCrypt의 특징

BCrypt는 다음과 같은 특징을 가지고 있어 비밀번호의 안전한 저장을 지원한다.

솔트 사용

앞서 언급한 바와 같이, 각각의 해싱마다 솔트라는 임의의 문자열을 함께 사용한다.

반복적 해싱

BCrypt는 주어진 문자열을 여러 번 반복하여 해싱한다.
결과적으로 브루트 포스 공격에 대한 안전성이 높아진다.

비밀번호 검증 시, 사용자로부터 받은 비밀번호와 저장된 솔트를 합친 후
같은 해싱 과정을 거쳐서 저장된 해시 값과 비교한다.
일치한다면, 비밀번호가 올바른 것으로 판단한다.


결론

암호화된 비밀번호가 노출되더라도 해커가 비밀번호를 유추하기 힘들게 하려면
Bcrypt같은 솔트처리가 된 알고리즘을 사용하는게 좋다.

개발을 할 때는 내가 사용하는 기술에 대해 충분히 이해하고 사용해야겠다는 생각이 들었다.
특히 보안쪽은 한번더 고민하는 습관을 가지자.

profile
호기심 많은 주니어 백엔드 개발자입니다.

0개의 댓글