An Introduction to JSON Web Encryption: How It Works, Why It's Important, and When to Use It

This is an introduction to JSON Web Encryption: a standard designed to keep the data confidential.
If terms like “JSON Web Token” and “JSON Web Signature” are new to you, consider starting with our other articles:
Otherwise, let’s dive in!
What is JWE?
JSON Web Encryption (JWE) is an IETF standard for representing encrypted content in JSON format. It's part of a broader JOSE (JSON Object Signing and Encryption) framework, which also includes JSON Web Token (JWT) and JSON Web Signature (JWS).
JWE protects information and ensures its confidentiality. The cryptography behind JWE makes it so that only authorized parties with the correct decryption key can read the encrypted data.
Any kind of content, including a simple sentence, can be encrypted using JWE. However, its most common application involves encrypting a JWT. When a JWT is both signed (with JWS) and encrypted (with JWE), it is often referred to as a Nested JWT. Nested JWTs can be used in authentication scenarios with OAuth 2.0 and OpenID Connect, when an extra layer of protection is required for sensitive data.
In this blog post, we'll focus on the most common use case: the Nested JWT. We’ll also only cover the Compact Serialization format, as opposed to the less popular JSON Serialization.
Why use JWE?
Data security is a major challenge for modern applications, particularly when handling and transmitting sensitive information like financial details, personal data, or login credentials over the internet. JWE is invaluable when it comes to:
- Ensuring data confidentiality: JWE keeps sensitive data confidential. Even if a JWE-secured message is intercepted, its contents remain unreadable without the correct decryption key.
- Complying with regulations: Industries like healthcare and finance operate under strict regulations that require them to protect customer data through encryption. JWE helps organizations comply with these requirements.
Common use cases for JWE
JWE has several practical applications.
- Securing APIs: APIs often handle the exchange of sensitive data between clients and servers. Using JWE to encrypt API requests and responses keeps this information flow private. For instance, an authorization server may use JWE to encrypt the token and userinfo endpoint responses, adding a layer of security to OAuth 2.0-based authentication flows.
- Protecting data in transit: JWE is especially useful when transferring data over potentially insecure networks.
- Storing encrypted data in databases: For applications that store JWTs in databases for authentication or session management, encrypting these tokens with JWE prevents sensitive information from being exposed in the event of a database breach.
The difference between JWT, JWS, and JWE
JSON Web Tokens provide a standardized way to transmit information. JWTs leverage two related specifications:
- JSON Web Signature (JWS) for data integrity and authenticity
- JSON Web Encryption (JWE) for confidentiality.
Let’s take a closer look at each:
JSON Web Token (JWT)
A JWT is a compact, URL-safe method of representing claims to be transferred between two parties. It's a widely adopted standard for authentication and authorization, often conveying details about an authenticated user (as in OpenID Connect) or the permissions granted to the client application (as in OAuth 2.0).
A JWT:
- Is broadly defined by RFC 7519 as a way to represent claims to be transferred between two parties. It can be signed (using JWS) or encrypted (using JWE), or even be unsecured ("alg":"none").
- In practice and for any secure use case, a JWT is virtually always cryptographically signed using JSON Web Signature (JWS). The signature ensures the integrity and authenticity of the data contained in the JWT.
- A signed JWT consists of three parts: a header, a payload (the claims), and a signature.
- A signed JWT guarantees the data it contains hasn't been tampered with, but doesn't ensure confidentiality—anyone with the token can read its content.
JSON Web Signature (JWS)
JWS is a specification for digitally signing JSON data, which:
- Guarantees data integrity and authenticity, ensuring that the signed data has not been tampered with during transit. The recipient can verify that the data has not been altered by validating the signature.
- Leaves the data visible but tamper-proof.
- Is the standard mechanism for signing JWTs.
JSON Web Encryption (JWE)
JWE is a specification for representing an encrypted and integrity-protected message.
JWE:
- Encrypts the data to provide confidentiality.
- Relies on a class of cryptographic algorithms called Authenticated Encryption with Associated Data (AEAD). These algorithms both encrypt the data and provide an integrity check.
- Is commonly used to encrypt JWTs for authentication and authorization in sensitive environments (e.g., finance or healthcare). The signed and encrypted JWTs are known as Nested JWTs.
- While Nested JWTs are common, JWE allows for encrypting any arbitrary value. The plaintext encrypted by JWE doesn't have to be a full, formally structured JWT. It could simply be a JSON object containing claims (e.g., {"user_id": "123", "role": "admin"}) encrypted directly, without the JWT header and signature.
- Consists of five parts: header, encrypted key, initialization vector, ciphertext, and authentication tag.
The structure of a JWE
An actual JWE may look something like this:
eyJhbGciOiJSU0EtT0FFUCIsImVuYyI6IkEyNTZHQ00ifQ.
eyJpc3MiOiJqb2UiLCJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyLCJleHAiOjE1MTYyNDA5MjIsImF1ZCI6WyJodHRwOi8vbG9jYWxob3N0OjUwMDAiXSwianRpIjoiMTIzNDU2Nzg5MCJ9.
cZVhpnL47MivTYV7GfhHduRzUhHsxMSAwdpP4I4aFnk.
48V1_ALb6US04U3b.
5eym8TW_c8SuKKS-fv54EyXp10aJpE8rvCvIkDx9dXw
(Note: The actual JWE is a single continuous string; new lines are only added for readability.)
This example encrypts the plaintext "The true sign of intelligence is not knowledge but imagination." to the recipient. Notice how it consists of five parts, each base64url-encoded, separated by dots. Each part of a JWE plays a specific role in the encryption and decryption process.
This is an example of a JWE Compact Serialization, which is the most common format for JWE. Another option, which we won't cover in this blog post, is a JWE JSON Serialization.
The five parts of a JWE are:
JOSE Header
The JOSE Header carries information about the encryption process and the JWE itself. It specifies the algorithms used for both key management and content encryption, along with optional additional properties. It must include the following parameters:
- alg (Algorithm): specifies the Key Management Algorithm used to encrypt or determine the value of the Content Encryption Key (CEK). Common algorithms include RSA1_5, RSA-OAEP, A128KW, A256KW, etc.
- enc (Encryption Algorithm): specifies the Authenticated Encryption with Associated Data (AEAD) algorithm used to perform the actual encryption of the plaintext. This algorithm must have a specified key length and inherently provides both encryption and integrity protection. Examples include A128GCM, A256GCM (AES GCM), A128CBC-HS256, etc.
Optional header parameters, such as x5u (X.509 URL), kid (Key ID), cty (Content Type), etc., can be included.
A typical JWE header might look like this:
{
"alg": "RSA-OAEP",
"enc": "A256GCM"
}
This header specifies that the content encryption key is encrypted to the recipient using the RSA-OAEP algorithm, and that authenticated encryption is performed on the plaintext using AES GCM with a 256-bit key.
Encrypted Key
This section contains the Content Encryption Key (CEK), which is the symmetric key used to encrypt the actual content of the JWE. The alg parameter in the JOSE Header specifies how this CEK is encrypted or agreed upon.
Here are examples of how CEK is managed based on the alg value:
- If the alg is RSA-OAEP, the Content Encryption Key is encrypted using the RSA-OAEP algorithm with the recipient’s public key.
- If the alg is A128KW or A256KW (AES Key Wrap), the CEK is symmetrically wrapped (encrypted) using a pre-shared symmetric key.
- For algorithms like ECDH-ES (Elliptic-curve Diffie–Hellman), a shared secret is derived via key agreement. This derived secret is then typically used to wrap the CEK (ECDH-ES is often combined with A128KW), though it can also directly serve as the CEK.
When CEK is not transmitted within the JWE, such as with Direct Encryption or when an ECDH-ES-derived key directly serves as the CEK – this section will be empty. This occurs because the CEK is established through other means (pre-shared or derived).
For more information, see the Cryptographic Algorithms for Key Management section of the JSON Web Algorithms (JWA) RFC.
Initialization Vector
The Initialization Vector is a random value used when encrypting the plaintext (if used by the encryption algorithm). It enhances security by ensuring that the same plaintext will encrypt differently each time. If a symmetric encryption algorithm does not require an Initialization Vector, this section will be empty.
Ciphertext
The Ciphertext is the encrypted form of the original plaintext. It's produced by performing authenticated encryption, using the Content Encryption Key (CEK), the encryption algorithm (specified by the enc header parameter), and Additional Authenticated Data. The Ciphertext is the central part of the JWE as it holds the protected data.
Authentication Tag
This section contains the Authentication Tag generated by performing authenticated encryption. Its purpose is to ensure the integrity of the encrypted message by detecting any unauthorized modifications. If any part of the JWE is altered after encryption, the decryption process will detect tampering because the Authentication Tag will not match. This section remains empty if a symmetric encryption algorithm does not use an authentication tag.
The encryption and decryption process
JWE works by combining different cryptographic techniques: It uses a key management process to protect the Content Encryption Key, which is then used to symmetrically encrypt the actual plaintext. Here's how it works:
Key generation and management
- The alg parameter in the JWE Header dictates how the Content Encryption Key (CEK) is encrypted, generated, or derived.
- The sender generates a random symmetric CEK.
- This CEK is then secured (encrypted) or derived based on the chosen algorithm (alg).
Encrypting a message
- The sender prepares the plaintext to be encrypted.
- The sender creates the JWE Header, specifying the encryption algorithm (enc) and the key management algorithm (alg) to be used.
- The sender generates a random JWE Initialization Vector.
- The base64url-encoded form of the JOSE Header is used as Additional Authenticated Data (AAD).
- Authenticated encryption is performed on the plaintext using the algorithm specified by the enc parameter, with the CEK as the encryption key, the Initialization Vector, and the AAD. This process produces the Ciphertext (the encrypted content) and an Authentication Tag.
- The resulting components are base64url-encoded and concatenated with dots (.), forming the final JWE (Compact Serialization):
BASE64URL(UTF8(JWE Protected Header)) || '.' || BASE64URL(JWE Encrypted Key) || '.' || BASE64URL(JWE Initialization Vector) || '.' || BASE64URL(JWE Ciphertext) || '.' || BASE64URL(JWE Authentication Tag).
Decrypting a message
- The recipient checks the alg parameter. Based on this algorithm, they use their private key (if the CEK was asymmetrically encrypted) or a pre-shared symmetric key (if key wrapping was used), or perform a key agreement to obtain the CEK.
- The decrypted CEK and the JWE Initialization Vector are used to decrypt the Ciphertext.
- The recipient verifies the integrity of the data using the Authentication Tag and the AAD. If the tag does not match, it indicates that the message was tampered with, and the decryption attempt will fail.
Conclusion
JSON Web Encryption helps keep data safe in modern web applications. Knowing how it works and what it does enables you to decide when and how to use it.
Now that you're familiar with the basics of JWE, let's explore its practical applications. In our next article, we'll cover how JWE can be used to encrypt userinfo and token responses in authentication flows.