MiServe DevTools

내 스티커

도구를 여기에 고정하세요. 이 브라우저에 저장됩니다.

HMAC 생성기

시크릿 키와 HMAC-SHA256 등의 해시로 메시지에 서명하고, 받은 서명을 검증합니다.

HMAC (hex)
HMAC (Base64)

WebAssembly로 브라우저에서 실행됩니다. 붙여 넣은 내용은 업로드되지 않습니다.

이 도구에 대하여

HMAC이 증명하는 것

HMAC(RFC 2104)는 메시지와 시크릿 키를 해시 함수로 섞어 짧은 태그를 만듭니다. 같은 키를 가진 사람은 이 태그를 다시 계산할 수 있습니다. 두 태그가 같으면 메시지가 전달 중에 바뀌지 않았고(무결성), 키를 아는 사람이 만든 것(인증)임을 알 수 있습니다.

일반 해시로는 이렇게 할 수 없습니다. 메시지를 바꾼 사람이 해시도 다시 계산할 수 있기 때문입니다. HMAC은 메시지를 숨기지 않으므로 암호화가 아닙니다. 또 양쪽이 같은 키를 가지고 있으므로 둘 중 누가 메시지를 작성했는지는 보여 줄 수 없습니다. 그러려면 개인 키를 사용하는 디지털 서명이 필요합니다.

웹훅 서명

HMAC을 흔히 접하는 곳이 웹훅입니다. 제공자는 사용자와 공유하는 시크릿으로 요청 본문에 서명하고 태그를 헤더에 담아 보내며, 사용자의 서버는 요청을 신뢰하기 전에 같은 HMAC을 계산합니다. GitHub는 X-Hub-Signature-256: sha256=…을 hex로, Shopify는 X-Shopify-Hmac-SHA256을 Base64로 보내고, Stripe는 타임스탬프, 점, 본문을 이어 서명한 결과를 Stripe-Signature 안의 v1=…으로 보냅니다.

본문은 도착한 그대로의 원시 바이트에 서명해야 합니다. 프레임워크가 JSON을 파싱한 뒤 다시 직렬화하면 공백과 키 순서가 바뀌어 HMAC이 더 이상 일치하지 않습니다. 여기서 서명이 맞지 않으면 먼저 키 인코딩(텍스트, hex, Base64)을 확인하고, 그다음 메시지 끝의 줄바꿈을 확인하세요.

서버에서 상수 시간 비교를 하는 이유

일반적인 문자열 비교는 처음으로 다른 문자에서 멈춥니다. 서버에서는 이 때문에 위조된 서명의 앞부분 바이트가 틀리면 응답이 조금 빨라지고 맞으면 조금 느려지며, 이 차이를 측정할 수 있는 공격자는 유효한 태그를 한 바이트씩 알아낼 수 있습니다. 상수 시간 비교는 결과와 상관없이 모든 바이트를 읽습니다. 플랫폼이 제공하는 함수를 사용하세요. Node.js는 crypto.timingSafeEqual, Go는 hmac.Equal, Python은 hmac.compare_digest, PHP는 hash_equals입니다.

이 페이지의 비교 필드도 같은 방식으로 동작합니다. 두 값을 바이트로 디코딩한 뒤 모든 바이트를 읽습니다. 다만 이미 두 값을 모두 가지고 있는 브라우저 탭에서는 숨길 타이밍 정보가 없으므로, 여기서는 직접 작성한 코드가 올바른 태그를 만들었는지만 알려 줍니다.

실행 방식

태그는 Go의 crypto/hmac 패키지를 WebAssembly로 컴파일해 브라우저의 백그라운드 스레드에서 계산합니다. 메시지는 UTF-8로 처리하며 아무것도 덧붙이거나 잘라 내지 않습니다. 단, 한 가지는 바뀝니다. 브라우저의 텍스트 상자는 모든 줄바꿈을 LF 하나로 유지하므로, CRLF 줄바꿈으로 받은 메시지는 여기서 LF로 서명됩니다. 키는 UTF-8 텍스트로 처리하거나, 지정한 경우 hex 또는 Base64에서 디코딩합니다. 메시지와 키는 어디로도 전송되지 않습니다. 그래도 운영 환경의 시크릿은 웹 페이지에 넣지 않는 것이 좋습니다. 가능하면 테스트 키를 사용하세요.

자주 묻는 질문

서버에서 계산한 HMAC과 결과가 다른 이유는 무엇인가요?

흔한 원인은 키를 잘못된 인코딩으로 읽은 경우(hex나 Base64 키를 일반 텍스트로 처리), 메시지 끝의 줄바꿈이나 다른 줄바꿈 문자, 파싱 후 다시 직렬화된 본문, 다른 해시 알고리즘입니다. 상대편이 hex로 출력하는지 Base64로 출력하는지도 확인하세요.

HMAC은 키 뒤에 메시지를 붙여 해시한 것과 같나요?

아니요. SHA-256, SHA-512, SHA-1, MD5에서는 키와 메시지를 이어 붙인 해시를 확장할 수 있습니다. 해시를 본 사람이 키를 몰라도 데이터를 덧붙여 유효한 해시를 계산할 수 있다는 뜻입니다. HMAC은 두 개의 파생 키로 두 번 해시해 이 허점을 막습니다.

HMAC 키는 얼마나 길어야 하나요?

해시 출력 길이 이상의 무작위 키를 사용하세요. SHA-256은 32바이트, SHA-512는 64바이트입니다. 키를 더 길게 해도 이점은 크지 않으며, 해시의 블록 크기보다 긴 키는 먼저 해시되어 줄어듭니다. 짧거나 추측하기 쉬운 키는 알려진 메시지와 태그 하나만 있으면 후보를 대입해 찾아낼 수 있습니다.

HMAC-SHA1과 HMAC-MD5는 깨졌나요?

일반 해시로서의 SHA-1과 MD5를 깨뜨린 충돌 공격이 그대로 HMAC의 실질적인 위조로 이어지지는 않습니다. 오래된 프로토콜에서는 아직 볼 수 있지만, 새로 만드는 것에는 HMAC-SHA256 이상을 선택하세요.

해시의 다른 도구