Security
Free HMAC Generator Online
Generate HMAC-SHA256 and HMAC-SHA512 message authentication codes from any text and secret key.
What is HMAC?
HMAC (Hash-based Message Authentication Code) is a cryptographic mechanism that combines a secret key with a hash function to produce a message authentication code. It answers two questions simultaneously: did this message come from someone with the secret key? and has the message been altered in transit?
HMAC is defined in RFC 2104 and is used everywhere in modern security infrastructure: webhook signature verification (Stripe, GitHub, Twilio), JWT signing (HS256 is HMAC-SHA256), cookie integrity checks, API request signing (AWS Signature Version 4 uses HMAC-SHA256 internally), and TOTP one-time password generation.
This tool computes HMAC-SHA256 and HMAC-SHA512 entirely in your browser using the Web Crypto SubtleCrypto API. Your message and secret key never leave your device.
How HMAC works
The HMAC construction takes three inputs: a hash function H (e.g. SHA-256), a secret key K, and a message M. The formula is:
In plain terms: the key is XOR-mixed with two padding constants (inner pad and outer pad), then used in two nested hash operations. This double-hashing structure prevents length extension attacks — a vulnerability in plain hashing where an attacker can append data to a message and produce a valid hash without knowing the key.
The security of HMAC depends on the hash function's collision resistance and the secrecy of the key. HMAC-SHA256 with a 256-bit key provides 256 bits of security — far beyond what any feasible attack can break. Even HMAC-SHA1 (deprecated for plain SHA-1 usage) remains secure in the HMAC construction, though HMAC-SHA256 or HMAC-SHA512 are preferred for new systems.
HMAC vs plain hash — the critical difference
- No key required — anyone can compute it
- Proves data integrity only (not altered in transit)
- Cannot prove origin — attacker can re-hash modified data
- Vulnerable to length extension attacks (SHA-256, SHA-512)
- Use for: checksums, content addressing, password hashing input
- Requires secret key — only key holders can verify or generate
- Proves both integrity AND authenticity
- Attacker cannot forge valid HMAC without the key
- Immune to length extension attacks by construction
- Use for: webhook verification, API auth, JWT signing, cookies
Webhook signature verification with HMAC
The most common use of HMAC in web development is verifying that webhook payloads were sent by the expected service. Stripe, GitHub, Twilio, Shopify, and most major platforms use HMAC-SHA256 for this. The pattern is always the same:
The webhook provider computes HMAC-SHA256(raw_request_body, your_webhook_secret) and includes the result in a request header (e.g. X-Stripe-Signature, X-Hub-Signature-256).
Read the raw request body before any parsing. JSON parsing may alter whitespace or key order, changing the HMAC. You must compute the HMAC of the exact bytes received.
Compute HMAC-SHA256(raw_body, your_webhook_secret) on your server using the same secret configured in the provider dashboard.
Compare your computed HMAC to the one in the header using a constant-time comparison function. Never use == or ===, which leak timing information that attackers can exploit to forge signatures character by character.
const crypto = require('crypto');
function verifyWebhook(rawBody, signature, secret) {
const expected = crypto
.createHmac('sha256', secret)
.update(rawBody)
.digest('hex');
// Constant-time comparison — prevents timing attacks
return crypto.timingSafeEqual(
Buffer.from(expected),
Buffer.from(signature)
);
}HMAC use cases for developers
HMAC in different programming languages
crypto.createHmac('sha256', key).update(message).digest('hex')import hmac, hashlib hmac.new(key.encode(), message.encode(), hashlib.sha256).hexdigest()
mac := hmac.New(sha256.New, []byte(key)) mac.Write([]byte(message)) hex.EncodeToString(mac.Sum(nil))
hash_hmac('sha256', $message, $key)OpenSSL::HMAC.hexdigest('SHA256', key, message)Mac mac = Mac.getInstance("HmacSHA256");
mac.init(new SecretKeySpec(key.getBytes(), "HmacSHA256"));
Hex.encodeHexString(mac.doFinal(message.getBytes()))To generate a cryptographically secure HMAC key, use the Random Token Generator (32 bytes, hex format gives a 64-character key). To compute plain SHA-256 hashes without a key, use the Hash Generator.
FAQ
Common questions
What is an HMAC and what is it used for?
HMAC (Hash-based Message Authentication Code) is a cryptographic signature that proves a message was created by someone who holds the secret key and that the message has not been altered since it was signed. Common uses: webhook signature verification (Stripe, GitHub), API request authentication, JWT signing with HS256/HS512, and cookie integrity checks.
What is the difference between HMAC-SHA256 and HMAC-SHA512?
Both provide equivalent security for most applications — the difference is digest size and performance. HMAC-SHA256 produces a 32-byte (256-bit) output and is faster on 32-bit systems. HMAC-SHA512 produces a 64-byte (512-bit) output and is faster on 64-bit systems. Choose SHA-256 for compatibility (it is more widely supported) and SHA-512 if you need longer output or are on 64-bit systems.
Is HMAC the same as a hash?
No. A plain hash (SHA-256, MD5) can be computed by anyone without a key — it only proves the data was not accidentally corrupted. An HMAC requires a shared secret key, so only parties with the key can verify or generate valid signatures. This makes HMAC suitable for authentication, whereas plain hashes are only suitable for integrity checks.
How do I verify a webhook using HMAC?
When you receive a webhook: 1) Get the raw request body (before JSON parsing). 2) Compute HMAC-SHA256 of the raw body using the webhook secret as the key. 3) Compare your computed HMAC to the signature in the webhook header (e.g., X-Stripe-Signature, X-Hub-Signature-256). Use a constant-time comparison function to prevent timing attacks. Never compare signatures with == or ===.
Why must I use a constant-time comparison for HMAC verification?
Standard string equality (==) short-circuits as soon as it finds the first mismatched character — the time taken leaks information about how many characters match. An attacker can use this timing difference to guess the correct signature one character at a time. Use crypto.timingSafeEqual() (Node.js) or hmac.compare_digest() (Python) to compare signatures in constant time.
How long should my HMAC secret key be?
The HMAC specification recommends a key at least as long as the hash output. For HMAC-SHA256, use at least 32 bytes (256 bits). For HMAC-SHA512, use at least 64 bytes (512 bits). Use the Random Token Generator tool to create a properly random key. Never use a human-readable word or phrase as an HMAC key — the entropy is too low.
Can I use HMAC to sign JWT tokens?
Yes. The HS256, HS384, and HS512 JWT signing algorithms are all HMAC variants (HS = HMAC-SHA). HS256 uses HMAC-SHA256. When you sign a JWT with a symmetric secret, the "signature" part of the JWT is the Base64url-encoded HMAC of the header and payload. Any party with the secret can both create and verify tokens — use asymmetric algorithms (RS256, ES256) if you need to separate signing from verification.
Is HMAC-SHA256 still considered secure?
Yes, HMAC-SHA256 is currently considered secure and is recommended by NIST. The SHA-256 hash function has no known practical vulnerabilities when used in HMAC mode. SHA-1-based HMAC (HMAC-SHA1) is still technically secure in HMAC mode (unlike bare SHA-1) but should be avoided in new systems due to perception issues and for future-proofing.
More in Security