What the HMAC Generator Does
The HMAC Generator computes a Hash-based Message Authentication Code — a keyed hash — entirely in your browser via Web Crypto. Paste the message into the input panel, enter the shared secret in the Secret key field in the options bar, choose the hash algorithm (SHA-1, SHA-256, SHA-384, or SHA-512; SHA-256 by default), and the output panel shows the HMAC as a lowercase hexadecimal string.
The difference between this and a plain hash is the entire point. A plain digest like SHA-256 can be computed by anyone: same input, same output, no secrets involved. An HMAC folds a secret key into the computation, so the output can only be produced — and verified — by someone holding the key. That converts a fingerprint into an authenticator: matching output proves not only that the bytes are unchanged, but that whoever produced them holds the secret. It is the mechanism behind webhook signature verification, API request signing (AWS SigV4, Stripe), JWT's HS256/384/512 family, and HOTP one-time passwords.
Empty keys are rejected with an explicit error — the tool will not compute a keyless "HMAC," which would silently be a plain hash. The output length follows the chosen hash: 40 hex characters for SHA-1, 64 for SHA-256, 96 for SHA-384, 128 for SHA-512.
How HMAC Works
HMAC (RFC 2104) wraps any cryptographic hash in a two-pass key construction. The secret is first padded or hashed to the hash's block size, then XORed with a fixed pad of repeated bytes to form the inner key; the hash of inner-key ∥ message is computed; then the outer key (the same padded secret XORed with a different fixed pad) is hashed together with that intermediate result. The final output is the HMAC — a fixed-length code whose security reduces to the underlying hash plus the key's secrecy.
The two-pad construction is not decoration: it is what defeats the length-extension weakness of bare Merkle–Damgård hashes. Where SHA-256(secret ∥ message) can be extended by an attacker who knows the digest but not the secret, HMAC(secret, message) cannot — the outer pass makes the intermediate state unavailable. This is the formal reason HMAC is the correct keyed construction over a plain hash, and why concatenating a secret into a hash input is the classic crypto bug this construction exists to prevent.
Verifiers reproduce the same computation and compare in constant time, so timing leaks nothing about how many bytes matched. The tool computes via crypto.subtle.sign("HMAC", …) — the same primitive every platform's HMAC uses — with your key imported as raw bytes and the message UTF-8 encoded. Output is deterministic: same key, same message, same hex string, on every machine. That determinism is what makes webhook verification possible at all: both sides compute independently and the strings must match exactly.
Key quality drives real-world security more than algorithm choice does: the construction is robust to over-long keys (they are hashed down), but a guessable key makes everything guessable. The standard guidance — 32 random bytes for HMAC-SHA256 — is what the
Random API Key Generator produces.
Using the HMAC Generator
- Step 1 — Paste the message. The exact payload being authenticated: a webhook body, the canonical request string your API documents, a token's
header.payload segment. Byte-exactness is everything — a trailing newline changes the output completely. - Step 2 — Enter the secret key. In the options bar's
Secret key field. This must be the shared secret exactly as the other party holds it — case, spacing, and every character. Most HMAC debugging failures are paste artefacts in this field. - Step 3 — Choose the algorithm. Match whatever the other side specifies. SHA-256 is the modern default; SHA-512 when a spec calls for it; SHA-1 only for legacy schemes (still structurally sound inside HMAC, but superseded).
- Step 4 — Copy and compare. The output is lowercase hex in the canonical form webhook dashboards and signing libraries expect. Verification is exact string comparison — every character must match, and near-matches mean a byte-level difference in message or key.
- Step 5 — Debug mismatches at the byte level. When your HMAC and the sender's disagree, the candidates in order are: trailing whitespace in the message, a differently encoded key, an algorithm mismatch, or a message that was serialised differently (key order in JSON, for instance). The tool reproduces the computation faithfully, so the divergence is in the inputs.
Common Use Cases
Webhook signature verification. GitHub, Stripe, Slack, and Shopify all sign deliveries with HMAC and a shared secret. Reproducing the signature locally — before writing the verification code — confirms you have the right secret, the right payload bytes, and the right algorithm, which is 90% of webhook debugging.
API request signing schemes. AWS Signature Version 4 and countless internal API gateways sign canonical request strings with HMAC. When your signature is rejected, recomputing it here step by step isolates which component of the canonical string differs.
JWT HS-family token work. An HS256 token's signature is precisely HMAC-SHA256 over base64url(header).base64url(payload). Computing the raw HMAC here (and comparing against the token's third segment, Base64Url-decoded) is the deepest debugging view into "why doesn't my token verify."
Testing signing implementations. Before shipping verification code, generate known-answer test vectors: message, key, expected HMAC. This tool produces the expected values that your unit tests assert against, byte-exact.
Worked Example
The canonical HMAC test vector, used across every HMAC implementation's test suite: message The quick brown fox jumps over the lazy dog, key key, algorithm SHA-256.
Enter the message in the input panel, key in the Secret key field, leave the algorithm at SHA-256, and run. The output:
f7bc83f430538424b13298e6aa6fb143ef4d59a14946175997479dbc2d1a3cd8
That is the reference value — identical to what Node's crypto.createHmac, OpenSSL's openssl dgst -sha256 -hmac, and every library produce. Change the key to Key and the output changes completely: every character of the digest depends on every character of the key. That sensitivity is the mechanism — an attacker who guesses even one key character wrong learns nothing.
Then the message-sensitivity check: append a single trailing space to the message, re-run, and the 64 characters transform entirely. In webhook debugging, this is the exact reason a signature "randomly" fails — the payload your framework re-serialised differs by one invisible byte from the payload that was signed.
Tips and Common Mistakes
- Paste the exact signed bytes. If the webhook was signed over the raw request body, HMAC the raw body — not your framework's re-serialised version. JSON key reordering, added whitespace, and float reformatting are the top three causes of verification failures.
- Key case and whitespace are absolute.
key, Key, and key\n are three different keys producing three unrelated outputs. Secrets pasted through documents often acquire trailing whitespace or smart quotes — check this field first when outputs mismatch. - Match the algorithm the sender used. An HMAC-SHA256 string is 64 hex characters; if the expected signature is 40 characters, the sender used SHA-1 and no amount of key fiddling will reconcile them.
- HMAC is not password hashing. It is fast by design, and there is no salt. Password storage needs a deliberately slow, salted construction — Bcrypt Generator. The confusion is common and the consequences are serious.
- Keep the secret actually secret. The tool computes locally and transmits nothing, but the same discipline applies here as everywhere: production signing secrets belong in a secrets manager, and anything pasted into a browser page — this or any other — should be a key you can rotate.
Frequently Asked Questions
What is the difference between HMAC and a plain hash?
Secrecy of the key. A plain SHA-256 digest is computable by anyone, so matching output proves only that bytes are unchanged. HMAC folds a secret into the computation, so a matching output additionally proves the producer holds the key. Integrity alone: plain hash. Integrity plus authenticity: HMAC. Any verification where the verifier is not the only party who could have produced the data needs the keyed version.How long should my secret key be?
32 random bytes for HMAC-SHA256 is the standard answer — matching the hash's security level. Shorter keys reduce the effective margin; longer ones are hashed to the block size and work fine but buy nothing beyond entropy. The failure mode to avoid is not length but entropy: a human-chosen password as an HMAC key collapses the construction's security to the password's. Generate keys randomly — the
Random API Key Generator exists for exactly this.
Why does my computed HMAC not match the webhook signature?
Work the list in order: (1) payload bytes — HMAC what was actually signed, the raw body, not a re-serialised version; (2) key fidelity — trailing whitespace, case, or encoding differences in the secret; (3) algorithm — 40 vs 64 vs 96 vs 128 hex characters identifies SHA-1/256/384/512 at a glance; (4) encoding of the expected signature — hex vs Base64. In practice the first two account for the overwhelming majority.Can I use HMAC for password storage?
No. HMAC is fast — correct for message authentication, fatal for credential storage, where slowness is the point — and it has no salt. The The
Bcrypt Generator is the credential tool; this one is for request and message authentication.
Is the same key safe across multiple services?
No — key separation is the rule. Reusing one secret means a compromise of the weakest service exposes all of them, and forecloses per-service rotation. Derive independent keys per service and rotate on schedule or on suspicion.Related Tools