메시지 요약 (해시)은 byte [] in byte [] out
메시지 다이제스트는 원시 바이트 배열을 사용하여 원시 바이트 배열 (일명 byte[]
)을 반환하는 함수로 정의됩니다 . 예를 들어 SHA-1 (Secure Hash Algorithm 1) 의 다이제스트 크기는 160 비트 또는 20 바이트입니다. 원시 바이트 배열은 일반적으로 UTF-8 과 같은 문자 인코딩 으로 해석 할 수 없습니다 . 모든 순서의 모든 바이트가 올바른 인코딩이 아니기 때문입니다. 따라서 와 함께 로 변환 :String
new String(md.digest(subject), StandardCharsets.UTF_8)
잘못된 시퀀스를 만들거나 정의되지 않은 유니 코드 매핑에 대한 코드 포인터가있을 수 있습니다 .
[�a�ɹ??�%l�3~��.
이진 텍스트 인코딩
이를 위해 이진 - 텍스트 인코딩에 사용됩니다. 해시에서 가장 많이 사용되는 것은 HEX 인코딩 또는 Base16 입니다. 기본적 바이트의 값을 가질 수 0
로 255
(또는 -128
행 127
의 HEX 표현에 해당 서명을) 0x00
- 0xFF
. 따라서 16 진수는 필요한 출력 길이의 두 배가됩니다. 즉, 20 바이트 출력은 40 자 길이의 16 진 문자열을 작성합니다.
2fd4e1c67a2d28fced849ee1bb76e7391b93eb12
16 진 인코딩을 사용할 필요는 없습니다. base64 와 같은 것을 사용할 수도 있습니다 . 16 진은 사람이 쉽게 읽을 수 있고 패딩없이 출력 길이가 정의되어 있기 때문에 종종 선호됩니다.
JDK 기능만으로 바이트 배열을 16 진으로 변환 할 수 있습니다.
new BigInteger(1, token).toString(16)
그러나 BigInteger
주어진 바이트 배열을 바이트 문자열이 아닌 숫자 로 해석 합니다. 즉, 선행 0이 출력되지 않고 결과 문자열이 40 자보다 짧을 수 있습니다.
라이브러리를 사용하여 HEX로 인코딩
이제 스택 오버플로에서 테스트되지 않은 바이트 대 16 진수 방법을 복사하여 붙여 넣거나 Guava 와 같은 대규모 종속성을 사용할 수 있습니다 .
대부분의 바이트 관련 문제에 대한 해결책을 찾기 위해 다음과 같은 경우를 처리하는 유틸리티를 구현했습니다. bytes-java (Github)
메시지 다이제스트 바이트 배열을 변환하려면 다음을 수행하십시오.
String hex = Bytes.wrap(md.digest(subject)).encodeHex();
또는 내장 해시 기능을 사용할 수 있습니다
String hex = Bytes.from(subject).hashSha1().encodeHex();
SHA1
에는 하이픈이 없으므로 차이가 있는지 알 수 없습니다.