[JAVA] SHA-256 암호화 (salt 사용)

P__.mp4·2022년 9월 7일

JAVA

목록 보기
1/2

SHA-256은 SHA(Secure Hash Algorithm) 단방향 알고리즘의 한 종류로, 해시 값을 이용한 암호화 방식 중 하나이다. 256비트로 구성되며 64자리 문자열을 반환한다.

단방향이란 암호화는 가능하나 복호화가 불가능한 것을 의미한다.(반대는 양방향 : 암호화와 복호화 둘 다 가능)

예를 들어, "ABC"라는 값을 SHA-256 알고리즘을 적용하면 "4d35adf24fe634..."와 같은 64자리의 문자열을 반환한다. 해시 값은 한 글자 차이라도 천지 차이로 달라지기 때문에 암호화된 문자열로 원래 문자열을 절대 유추할 수 없다.

보안상의 이유로 DB에 사용자 비밀번호를 직접적으로 넣기보다는 SHA-256 알고리즘을 적용한 후 insert한다. 로그인 시에는 사용자가 입력한 비밀번호에 SHA-256 알고리즘을 적용하고, 입력된 아이디로 DB에 등록된 암호화 비밀번호를 찾아 비교하여 로그인 로직을 처리한다.

사용자 입력 비밀번호을 SHA-256 암호화 == 이미 암호화하여 저장된 비밀번호(사용자 입력 아이디로 레코드 검색)

하지만!! 레인보우 테이블이라는게 생기고, 해커가 암호화된 데이터를 유추할 수 있게 되었다.

레인보우 테이블이란?
해시 함수(MD5, SHA-1, SHA-2 등)을 사용하여 만들어낼 수 있는 값들을 왕창 저장한 표이다


Salt란?

레인보우 테이블의 약점은 원본 문자열이 길고 복잡할수록 테이블에 존재할 가능성이 낮아진다. 이러한 약점을 이용하 원본 문자열에 무작위 문자열(salt)를 합치고, SHA-256 알고리즘을 적용하는 것이다. 그럼 원본 문자열 자체가 더욱 길고 복잡해질테니 레인보우 테이블에 존재하지 않을 가능성이 높아진다.

로그인 시, 사용자가 입력한 아이디로 조회한 레코드에 salt 값을 찾고 입력한 비밀번호에 합친다. 그 후 레코드에 등록된 비밀번호와 비교하면 된다.

사용자 입력 비밀번호을 SHA-256 암호화 + 무작위 문자열(salt) == 이미 암호화하여 저장된 비밀번호

SHA-256 + Salt 적용 코드

package com.pmp4.amoimproject.common;

import org.springframework.stereotype.Component;

import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;

@Component
public class Encrypt {
		// 무작위 문자열 Salt
    public String getSalt() {
        //1. Random, salt 생성
        SecureRandom sr = new SecureRandom();
        byte[] salt = new byte[20];

        //2. 난수 생성
        sr.nextBytes(salt);

        //3. byte To String (10진수 문자열로 변경)
        StringBuffer sb = new StringBuffer();
        for(byte b : salt) {
            sb.append(String.format("%02x", b));
        }

        return sb.toString();
    }

  	// SHA-256 알고리즘 적용
    public String getEncrypt(String pwd, String salt) {
        String result = "";
        try {
            MessageDigest md = MessageDigest.getInstance("SHA-256");

//            System.out.println("PWD + SALT 적용 전 : " + pwd + salt);
            md.update((pwd + salt).getBytes());
            byte[] pwdSalt = md.digest();

            StringBuffer sb = new StringBuffer();
            for(byte b : pwdSalt) {
                sb.append(String.format("%02x", b));
            }

            result = sb.toString();
//            System.out.println("PWD + SALT 적용 후 : " + result);

        } catch (NoSuchAlgorithmException e) {
            throw new RuntimeException(e);
        }

        return result;
    }
}

"testtest123" 이라는 비밀번호를 입력한 후, 암호화를 하면 저렇게 반환된다.

JAVA에서 SHA-256 알고리즘을 위해 제공하는 패키지는 java.security 이다.

profile
개발은 자신감

1개의 댓글

comment-user-thumbnail
2023년 6월 28일

감사합니다 큰 도움되었습니다

답글 달기