HMAC Generator
Generate an HMAC from a message and a secret key. Unlike a plain hash, an HMAC also proves the message came from someone holding the key — the basis of most webhook and API request signing.
Enter a message and keyAbout the HMAC Generator
A plain hash proves a message wasn't altered, but anyone can compute one — it proves nothing about who sent it. An HMAC (Hash-based Message Authentication Code) combines the message with a secret key before hashing, so only someone holding that key could have produced the same output. That's why webhook providers (Stripe, GitHub, Slack) sign their payloads with HMAC: it lets your server verify a request genuinely came from them, not just that the bytes are well-formed.
This is exactly the mechanism behind a JWT's HS256 signature, too — the "HS" stands for HMAC-SHA256. The token's header and payload are hashed together with a shared secret, and anyone verifying the token recomputes that HMAC and checks it matches.
How to use it
- 1Enter the message and the shared secret key.
- 2Choose the hash algorithm and output format.
- 3Copy the generated HMAC.
Features
- HMAC-SHA1, HMAC-SHA256, HMAC-SHA384 and HMAC-SHA512
- Hex or Base64 output
- Built on the Web Crypto API for standards-correct results
- One-click copy of the result
Frequently asked questions
What is the difference between a hash and an HMAC?
A hash only proves data integrity — that it wasn't altered. An HMAC adds a secret key into the computation, so it also proves authenticity — that whoever produced it holds the shared key.
What is HMAC used for in practice?
Signing webhook payloads (Stripe, GitHub, Slack all use it) so a receiving server can verify a request genuinely came from them, and signing JWTs with the HS256 algorithm.
Is my secret key uploaded anywhere?
No. Computation happens entirely in your browser via the Web Crypto API; the key and message are never sent to a server.
Can I verify an HMAC I received, not just generate one?
Yes — recompute the HMAC here with the same message, key and algorithm, and compare it to the one you received. If they match character-for-character, it's valid.