Education

What Is HMAC? How It Works and Where It's Used

HMAC (Hash-based Message Authentication Code) is one of the most widely used cryptographic primitives in security engineering. You'll find it in API authentication, webhook verification, JWT signing, and โ€” at the heart of it โ€” in how TOTP 2FA codes are generated. Understanding HMAC helps you build more secure systems and understand why 2FA works.

What Is HMAC?

HMAC is a cryptographic algorithm that takes two inputs โ€” a message and a secret key โ€” and produces a fixed-length output called a MAC (Message Authentication Code). The MAC can be used to verify both that the message hasn't been tampered with (integrity) and that the sender knows the secret key (authenticity).

It was defined in RFC 2104 in 1997 and standardised by NIST. HMAC-SHA256 (using SHA-256 as the underlying hash) is the most widely used variant today.

How HMAC Works

HMAC combines the key and message through the hash function in a specific way to prevent length extension attacks. The formula is: HMAC(K, m) = H((K โŠ• opad) || H((K โŠ• ipad) || m)) where H is the hash function, K is the key, m is the message, and opad/ipad are fixed padding constants.

In practice, you don't implement this yourself โ€” you use a library function like hmac.new(key, message, hashlib.sha256) in Python, or use our browser-based HMAC generator to compute and verify HMACs without any code.

HMAC vs Plain Hash: The Key Difference

A plain SHA-256 hash of a message always produces the same output โ€” anyone can compute it without knowing any secret. This is useful for checksums and fingerprints, but useless for authentication because anyone can fake it.

HMAC requires the secret key. Without the key, you cannot compute the correct MAC for any message. This means the recipient of a message with a valid HMAC knows it came from someone who knows the key โ€” which is the foundation of authentication.

This is why you should never use a plain hash for webhook signature verification or API request signing โ€” always use HMAC.

Where HMAC Is Used in Practice

Webhook verification: Stripe, GitHub, Shopify, and virtually every major platform send webhooks with an HMAC-SHA256 signature in the headers. Your server computes the HMAC of the payload using a shared secret and compares it to the header โ€” if they match, the webhook is authentic.

JWT signing: JWTs with algorithm HS256 use HMAC-SHA256. The header and payload are signed with your secret key. The recipient verifies the signature before trusting any claims in the token.

API request signing: AWS Signature Version 4 uses HMAC-SHA256 to sign API requests. The signature proves the request was made by someone with the AWS secret key.

Session tokens: Some session management systems use HMAC to sign session identifiers, preventing session forgery.

HMAC at the Heart of TOTP 2FA

TOTP (Time-based One-Time Password) is built on HMAC. Specifically, it uses HMAC-SHA1 with the secret key and the current time window as inputs. The result is truncated to produce the 6-digit code you see in your authenticator app. This is why TOTP is described in RFC 6238 as "TOTP: Time-Based One-Time Password Algorithm" and why the underlying primitive is called HOTP (HMAC-based One-Time Password).

The HMAC ensures that only someone who knows the secret key can produce valid codes โ€” and the time component ensures each code is only valid for 30 seconds.

Which HMAC Algorithm Should You Use?

For new systems, use HMAC-SHA256. It produces a 256-bit (32-byte) output, is universally supported, and is considered secure for the foreseeable future. It's the standard for JWTs (HS256), Stripe webhooks, AWS, and most modern APIs.

HMAC-SHA512 is an option for higher security requirements โ€” it produces a 512-bit output but is otherwise equivalent in use. HMAC-SHA1 should be avoided for new systems, though it's still used internally by TOTP for backwards compatibility with authenticator apps.

Related Articles

HMAC in Plain English

HMAC stands for Hash-based Message Authentication Code. It is a method for verifying both the integrity of a message (that it has not been tampered with) and its authenticity (that it came from someone who knows the secret key). HMAC takes two inputs โ€” a message and a secret key โ€” and produces a fixed-length output called a MAC or tag. Anyone who receives the message and knows the secret key can independently compute the HMAC and compare it to the received tag. If the tags match, the message is genuine and unmodified.

How HMAC Works and Where It Is Used

HMAC is defined in RFC 2104 and uses a cryptographic hash function (typically SHA-256 or SHA-512) as its core, applying the hash function twice with padding to resist length extension attacks. HMAC-SHA256 provides 128 bits of security โ€” considered secure for all practical purposes. HMAC appears everywhere in modern security infrastructure: TOTP codes (the 6-digit codes from your authenticator app) are generated using HMAC-SHA1 or HMAC-SHA256 โ€” your secret key and the current time are the inputs. JWT tokens can be signed with HMAC-SHA256 (the HS256 algorithm). TLS uses HMAC to verify that transmitted data has not been modified in transit. AWS Signature Version 4 uses a chain of HMAC-SHA256 operations to sign all API requests.

HMAC vs Digital Signatures

Both HMAC and digital signatures can verify message authenticity, but HMAC uses a shared secret key โ€” both parties must know the same key, so HMAC cannot prove to a third party who sent a message. Digital signatures use public-key cryptography โ€” only the private key holder can create a signature, but anyone with the public key can verify it, providing non-repudiation. For closed systems like API authentication, HMAC is faster and simpler. For open systems where verification by untrusted third parties is needed, digital signatures are required.

Frequently Asked Questions

Is HMAC-MD5 still secure? HMAC-MD5 is still considered computationally secure for message authentication, but MD5 is deprecated and its use is discouraged. Use HMAC-SHA256 or HMAC-SHA512 for any new implementation.

How long should an HMAC key be? The HMAC key should be at least as long as the hash output โ€” 32 bytes for HMAC-SHA256, or 64 bytes for HMAC-SHA512. Keys should be randomly generated using a cryptographically secure random number generator.

Can I use HMAC to encrypt data? No โ€” HMAC provides authentication but does not encrypt data. For encryption, use AES-GCM or ChaCha20-Poly1305, which provide both encryption and authentication together.