Sourcemeta Core 0.0.0
Loading...
Searching...
No Matches
JOSE

Standards-driven primitives for validating JSON Web Tokens. More...

Classes

class  sourcemeta::core::JWKParseError
class  sourcemeta::core::JWKSParseError
class  sourcemeta::core::JWTParseError
class  sourcemeta::core::JWEParseError
class  sourcemeta::core::JWE
class  sourcemeta::core::JWK
class  sourcemeta::core::JWKPrivate
class  sourcemeta::core::JWKS
class  sourcemeta::core::JWKSProvider
class  sourcemeta::core::JWT
struct  sourcemeta::core::JWTClockSkew

Enumerations

enum class  sourcemeta::core::JWSAlgorithm : std::uint8_t {
  JWSAlgorithm::RS256 , JWSAlgorithm::RS384 , JWSAlgorithm::RS512 , JWSAlgorithm::PS256 ,
  JWSAlgorithm::PS384 , JWSAlgorithm::PS512 , JWSAlgorithm::ES256 , JWSAlgorithm::ES384 ,
  JWSAlgorithm::ES512 , JWSAlgorithm::EdDSA , JWSAlgorithm::HS256 , JWSAlgorithm::HS384 ,
  JWSAlgorithm::HS512
}
enum class  sourcemeta::core::JWEAlgorithm : std::uint8_t {
  JWEAlgorithm::RSA_OAEP , JWEAlgorithm::RSA_OAEP_256 , JWEAlgorithm::ECDH_ES , JWEAlgorithm::ECDH_ES_A128KW ,
  JWEAlgorithm::ECDH_ES_A192KW , JWEAlgorithm::ECDH_ES_A256KW , JWEAlgorithm::A128KW , JWEAlgorithm::A192KW ,
  JWEAlgorithm::A256KW , JWEAlgorithm::DIR
}
enum class  sourcemeta::core::JWEEncryption : std::uint8_t {
  JWEEncryption::A128GCM , JWEEncryption::A192GCM , JWEEncryption::A256GCM , JWEEncryption::A128CBC_HS256 ,
  JWEEncryption::A192CBC_HS384 , JWEEncryption::A256CBC_HS512
}
enum class  sourcemeta::core::JWTClaimError : std::uint8_t {
  JWTClaimError::Issuer , JWTClaimError::Subject , JWTClaimError::Audience , JWTClaimError::Expiration ,
  JWTClaimError::NotBefore , JWTClaimError::IssuedAt
}
enum class  sourcemeta::core::JWTVerificationError : std::uint8_t {
  JWTVerificationError::AlgorithmNotAllowed , JWTVerificationError::UnknownKey , JWTVerificationError::Signature , JWTVerificationError::Type ,
  JWTVerificationError::Issuer , JWTVerificationError::Subject , JWTVerificationError::Audience , JWTVerificationError::Expiration ,
  JWTVerificationError::NotBefore , JWTVerificationError::IssuedAt
}

Functions

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jws_algorithm (const std::string_view value) noexcept -> std::optional< JWSAlgorithm >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_name (const JWSAlgorithm algorithm) noexcept -> std::string_view
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_is_asymmetric (const JWSAlgorithm algorithm) noexcept -> bool
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_digest_bits (const JWSAlgorithm algorithm) noexcept -> std::uint16_t
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jwe_algorithm (const std::string_view value) noexcept -> std::optional< JWEAlgorithm >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_algorithm_name (const JWEAlgorithm algorithm) noexcept -> std::string_view
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jwe_encryption (const std::string_view value) noexcept -> std::optional< JWEEncryption >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encryption_name (const JWEEncryption encryption) noexcept -> std::string_view
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_algorithm_is_asymmetric (const JWEAlgorithm algorithm) noexcept -> bool
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encryption_key_bytes (const JWEEncryption encryption) noexcept -> std::size_t
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_decrypt (const JWE &jwe, const JWKPrivate &key) -> std::optional< std::string >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encrypt (const JSON &header, const std::string_view plaintext, const JWK &key) -> std::optional< std::string >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_sign (const JWSAlgorithm algorithm, const std::string_view signing_input, const JWKPrivate &key) -> std::optional< std::string >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_sign (const JSON &header, const JSON &payload, const JWKPrivate &key) -> std::optional< std::string >
auto sourcemeta::core::jwt_bounded_clock_skew (const std::chrono::seconds skew) noexcept -> std::chrono::seconds
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_check_claims (const JWT &token, const std::string_view expected_issuer, const std::string_view expected_audience, const std::chrono::system_clock::time_point now, const JWTClockSkew clock_skew={}, const std::optional< std::string_view > expected_subject=std::nullopt) -> std::optional< JWTClaimError >
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_verify_signature (const std::optional< JWSAlgorithm > algorithm, const std::string_view signing_input, const std::string_view signature, const JWK &key) -> bool
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_verify_signature (const JWT &token, const JWK &key) -> bool
SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_verify (const JWT &token, const JWKS &keys, const std::span< const JWSAlgorithm > allowed_algorithms, const std::string_view expected_issuer, const std::string_view expected_audience, const std::chrono::system_clock::time_point now, const JWTClockSkew clock_skew, const std::optional< std::string_view > expected_subject, const std::optional< std::string_view > expected_type) -> std::optional< JWTVerificationError >

Detailed Description

Standards-driven primitives for validating JSON Web Tokens.

This functionality is included as follows:

#include <sourcemeta/core/jose.h>

Class Documentation

◆ sourcemeta::core::JWKParseError

class sourcemeta::core::JWKParseError

An error that occurs when parsing an invalid JSON Web Key.

Inheritance diagram for sourcemeta::core::JWKParseError:

◆ sourcemeta::core::JWKSParseError

class sourcemeta::core::JWKSParseError

An error that occurs when parsing an invalid JSON Web Key Set.

Inheritance diagram for sourcemeta::core::JWKSParseError:

◆ sourcemeta::core::JWTParseError

class sourcemeta::core::JWTParseError

An error that occurs when parsing an invalid JSON Web Token.

Inheritance diagram for sourcemeta::core::JWTParseError:

◆ sourcemeta::core::JWEParseError

class sourcemeta::core::JWEParseError

An error that occurs when parsing an invalid JSON Web Encryption object.

Inheritance diagram for sourcemeta::core::JWEParseError:

◆ sourcemeta::core::JWE

class sourcemeta::core::JWE

A parsed JSON Web Encryption object in compact serialization (RFC 7516). It owns its decoded segments, so the string it was parsed from need not outlive it. The plaintext is recovered by passing it to jwe_decrypt. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
const auto object{sourcemeta::core::JWE::from(compact)};
assert(object.has_value());
assert(object.value().encryption().has_value());
auto encryption() const noexcept -> std::optional< JWEEncryption >
Definition jose_jwe.h:55
static auto from(const std::string_view input) -> std::optional< JWE >

Public Member Functions

 JWE (const std::string_view input)
auto algorithm () const noexcept -> std::optional< JWEAlgorithm >
auto encryption () const noexcept -> std::optional< JWEEncryption >
auto key_id () const noexcept -> std::optional< std::string_view >
 The key identifier from the protected header, if present.
auto header () const noexcept -> const JSON &
 The decoded protected header.
auto protected_header () const noexcept -> std::string_view
auto encrypted_key () const noexcept -> std::string_view
auto initialization_vector () const noexcept -> std::string_view
 The decoded JWE Initialization Vector.
auto ciphertext () const noexcept -> std::string_view
 The decoded JWE Ciphertext.
auto tag () const noexcept -> std::string_view
 The decoded JWE Authentication Tag.

Static Public Member Functions

static auto from (const std::string_view input) -> std::optional< JWE >

Constructor & Destructor Documentation

◆ JWE()

sourcemeta::core::JWE::JWE ( const std::string_view input)
explicit

Parse a JSON Web Encryption object from its compact serialization, throwing a JWEParseError on invalid input.

Member Function Documentation

◆ algorithm()

auto sourcemeta::core::JWE::algorithm ( ) const -> std::optional< JWEAlgorithm >
inlinenodiscardnoexcept

The key-management algorithm declared in the protected header, if it names a supported one.

◆ encrypted_key()

auto sourcemeta::core::JWE::encrypted_key ( ) const -> std::string_view
inlinenodiscardnoexcept

The decoded JWE Encrypted Key, empty for direct key agreement and direct encryption.

◆ encryption()

auto sourcemeta::core::JWE::encryption ( ) const -> std::optional< JWEEncryption >
inlinenodiscardnoexcept

The content encryption algorithm declared in the protected header, if it names a supported one.

◆ from()

auto sourcemeta::core::JWE::from ( const std::string_view input) -> std::optional< JWE >
staticnodiscard

Parse a JSON Web Encryption object from its compact serialization, returning no value on invalid input.

◆ protected_header()

auto sourcemeta::core::JWE::protected_header ( ) const -> std::string_view
inlinenodiscardnoexcept

The exact base64url-encoded protected header, the Additional Authenticated Data the content encryption is bound to (RFC 7516 Section 5.1).

◆ sourcemeta::core::JWK

class sourcemeta::core::JWK

A parsed public JSON Web Key (RFC 7517), restricted to RSA, elliptic curve, octet key pair (RFC 8037), and symmetric octet (RFC 7518 Section 6.4) keys. The key owns its decoded material, so the source JSON document does not need to outlive it. For example:

#include <sourcemeta/core/jose.h>
#include <sourcemeta/core/json.h>
#include <cassert>
const auto document{sourcemeta::core::parse_json(
R"({ "kty": "RSA", "n": "0vx7ag", "e": "AQAB" })")};
const auto key{sourcemeta::core::JWK::from(document)};
assert(key.has_value());
assert(key.value().type() == sourcemeta::core::JWK::Type::RSA);
@ RSA
The RSA key type.
Definition jose_jwk.h:45
static auto from(const JSON &value) -> std::optional< JWK >
SOURCEMETA_CORE_JSON_EXPORT auto parse_json(std::basic_istream< JSON::Char, JSON::CharTraits > &stream) -> JSON

Public Types

enum class  Type : std::uint8_t { RSA , EllipticCurve , OctetKeyPair , Octet }
 The family of key material a key holds. More...

Public Member Functions

 JWK (const JSON &value)
 Parse a JSON Web Key from a JSON value, throwing on invalid input.
 JWK (JSON &&value)
 Parse a JSON Web Key from a JSON value, throwing on invalid input.
 JWK (JWK &&other) noexcept=default
 A key exclusively owns its parsed public key, so it is move-only.
 JWK (const JWK &)=delete
auto type () const noexcept -> Type
 The family of key material this key holds.
auto key_id () const noexcept -> std::optional< std::string_view >
 The key identifier used to select this key, if present.
auto algorithm () const noexcept -> std::optional< JWSAlgorithm >
 The algorithm this key is intended for, if present.
auto curve () const noexcept -> std::string_view
 The curve this key is pinned to, empty when it carries none.
auto public_key () const noexcept -> const PublicKey *
auto secret () const noexcept -> std::string_view
 The raw symmetric secret, empty for asymmetric keys.
auto public_jwk () const -> std::optional< JSON >
auto thumbprint () const -> std::optional< std::string >

Static Public Member Functions

static auto from (const JSON &value) -> std::optional< JWK >
static auto from (JSON &&value) -> std::optional< JWK >
static auto from_octets (const std::string_view secret) -> JWK

Member Enumeration Documentation

◆ Type

enum class sourcemeta::core::JWK::Type : std::uint8_t
strong

The family of key material a key holds.

Enumerator
RSA 

The RSA key type.

EllipticCurve 

The elliptic-curve key type.

OctetKeyPair 

The Edwards-curve octet key pair type.

Octet 

The symmetric octet sequence key type.

Member Function Documentation

◆ from() [1/2]

auto sourcemeta::core::JWK::from ( const JSON & value) -> std::optional< JWK >
staticnodiscard

Parse a JSON Web Key from a JSON value, returning no value on invalid input.

◆ from() [2/2]

auto sourcemeta::core::JWK::from ( JSON && value) -> std::optional< JWK >
staticnodiscard

Parse a JSON Web Key from a JSON value, returning no value on invalid input.

◆ from_octets()

auto sourcemeta::core::JWK::from_octets ( const std::string_view secret) -> JWK
staticnodiscard

Build a symmetric octet key (RFC 7518 Section 6.4) directly from raw secret octets, taken as-is rather than base64url-decoded, so a caller holding a shared secret does not assemble and re-parse an oct JSON Web Key. The minimum secret size each symmetric algorithm demands is enforced where the key is used, not here. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
const auto key{sourcemeta::core::JWK::from_octets("my-shared-secret")};
assert(key.type() == sourcemeta::core::JWK::Type::Octet);
@ Octet
The symmetric octet sequence key type.
Definition jose_jwk.h:51
static auto from_octets(const std::string_view secret) -> JWK

◆ public_jwk()

auto sourcemeta::core::JWK::public_jwk ( ) const -> std::optional< JSON >
nodiscard

Serialize the public part of this key as a JSON Web Key (RFC 7517), returning no value for a symmetric key, which has no public form.

◆ public_key()

auto sourcemeta::core::JWK::public_key ( ) const -> const PublicKey *
inlinenodiscardnoexcept

The parsed platform key, null when the material could not be turned into one.

◆ thumbprint()

auto sourcemeta::core::JWK::thumbprint ( ) const -> std::optional< std::string >
nodiscard

The SHA-256 JSON Web Key thumbprint of this key (RFC 7638), base64url-encoded.

◆ sourcemeta::core::JWKPrivate

class sourcemeta::core::JWKPrivate

A parsed private JSON Web Key (RFC 7517), the private counterpart to a public one, restricted to RSA, elliptic curve, octet key pair (RFC 8037), and symmetric octet (RFC 7518 Section 6.4) keys. The key owns its decoded material, so neither the source JSON document nor the source PEM needs to outlive it. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
assert(key.has_value());
assert(key.value().private_key() != nullptr);
static auto from_pem(const std::string_view pem) -> std::optional< JWKPrivate >

Public Types

enum class  Type : std::uint8_t { RSA , EllipticCurve , OctetKeyPair , Octet }
 The family of key material a key holds. More...

Public Member Functions

 JWKPrivate (JWKPrivate &&other) noexcept=default
 A key exclusively owns its parsed private key, so it is move-only.
 JWKPrivate (const JWKPrivate &)=delete
auto type () const noexcept -> Type
 The family of key material this key holds.
auto key_id () const noexcept -> std::optional< std::string_view >
 The key identifier used to select this key, if present.
auto algorithm () const noexcept -> std::optional< JWSAlgorithm >
 The algorithm this key is intended for, if present.
auto curve () const noexcept -> std::string_view
 The curve this key is pinned to, empty when it carries none.
auto private_key () const noexcept -> const PrivateKey *
 The parsed private key, or null when the material could not be decoded.
auto secret () const noexcept -> std::string_view
 The raw symmetric secret, empty for asymmetric keys.
auto public_jwk () const -> std::optional< JSON >
auto thumbprint () const -> std::optional< std::string >

Static Public Member Functions

static auto from (const JSON &value) -> std::optional< JWKPrivate >
static auto from (JSON &&value) -> std::optional< JWKPrivate >
static auto from_pem (const std::string_view pem) -> std::optional< JWKPrivate >
static auto from_octets (const std::string_view secret) -> JWKPrivate

Member Enumeration Documentation

◆ Type

enum class sourcemeta::core::JWKPrivate::Type : std::uint8_t
strong

The family of key material a key holds.

Enumerator
RSA 

The RSA key type.

EllipticCurve 

The elliptic-curve key type.

OctetKeyPair 

The Edwards-curve octet key pair type.

Octet 

The symmetric octet sequence key type.

Member Function Documentation

◆ from() [1/2]

auto sourcemeta::core::JWKPrivate::from ( const JSON & value) -> std::optional< JWKPrivate >
staticnodiscard

Parse a private JSON Web Key from a JSON value, returning no value on invalid input. The private parameters (RFC 7518 Sections 6.2.2 and 6.3.2, RFC 8037 Section 2) are required, so a public-only key is rejected.

◆ from() [2/2]

auto sourcemeta::core::JWKPrivate::from ( JSON && value) -> std::optional< JWKPrivate >
staticnodiscard

Parse a private JSON Web Key from a JSON value, returning no value on invalid input.

◆ from_octets()

auto sourcemeta::core::JWKPrivate::from_octets ( const std::string_view secret) -> JWKPrivate
staticnodiscard

Build a symmetric octet key (RFC 7518 Section 6.4) directly from raw secret octets, taken as-is rather than base64url-decoded, so a caller minting a token under a shared secret does not assemble and re-parse an oct JSON Web Key. The minimum secret size each symmetric algorithm demands is enforced where the key is used, not here. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
const auto key{
static auto from_octets(const std::string_view secret) -> JWKPrivate
@ Octet
The symmetric octet sequence key type.
Definition jose_jwk_private.h:46

◆ from_pem()

auto sourcemeta::core::JWKPrivate::from_pem ( const std::string_view pem) -> std::optional< JWKPrivate >
staticnodiscard

Parse a private key from an unencrypted PKCS#8 PEM document (RFC 5958), returning no value on invalid input. The key identifier and algorithm are left unset, as a PEM document carries no such metadata.

◆ public_jwk()

auto sourcemeta::core::JWKPrivate::public_jwk ( ) const -> std::optional< JSON >
nodiscard

Serialize the public part of this key as a JSON Web Key (RFC 7517), returning no value for a symmetric key, which has no public form, or for a key parsed from a PEM document whose public part could not be recovered.

◆ thumbprint()

auto sourcemeta::core::JWKPrivate::thumbprint ( ) const -> std::optional< std::string >
nodiscard

The SHA-256 JSON Web Key thumbprint of this key (RFC 7638), base64url-encoded, returning no value for a key whose public part could not be recovered.

◆ sourcemeta::core::JWKS

class sourcemeta::core::JWKS

A parsed JSON Web Key Set (RFC 7517 Section 5). Keys that individually fail to parse, such as those of an unsupported type, are skipped rather than failing the whole set, so one exotic key cannot break verification of tokens signed by the others. The set owns its keys. For example:

#include <sourcemeta/core/jose.h>
#include <sourcemeta/core/json.h>
#include <cassert>
const auto document{sourcemeta::core::parse_json(
R"({ "keys": [ { "kty": "RSA", "n": "0vx7ag", "e": "AQAB",
"kid": "2024" } ] })")};
const auto keys{sourcemeta::core::JWKS::from(document)};
assert(keys.has_value());
assert(keys.value().find("2024") != nullptr);
static auto from(const JSON &value) -> std::optional< JWKS >

Public Member Functions

 JWKS (const JSON &value)
 JWKS (JSON &&value)
 JWKS (JWKS &&other) noexcept=default
 A key set exclusively owns its keys, so it is move-only.
 JWKS (const JWKS &)=delete
auto find (const std::string_view key_id) const noexcept -> const JWK *
auto size () const noexcept -> std::size_t
 The number of keys in the set.
auto empty () const noexcept -> bool
 Whether the set holds no keys.

Static Public Member Functions

static auto from (const JSON &value) -> std::optional< JWKS >
static auto from (JSON &&value) -> std::optional< JWKS >

Constructor & Destructor Documentation

◆ JWKS() [1/2]

sourcemeta::core::JWKS::JWKS ( const JSON & value)
explicit

Parse a JSON Web Key Set from a JSON value, throwing a JWKSParseError on invalid input.

◆ JWKS() [2/2]

sourcemeta::core::JWKS::JWKS ( JSON && value)
explicit

Parse a JSON Web Key Set from a JSON value, throwing a JWKSParseError on invalid input.

Member Function Documentation

◆ find()

auto sourcemeta::core::JWKS::find ( const std::string_view key_id) const -> const JWK *
nodiscardnoexcept

Look up a key by its identifier (RFC 7515 Section 4.1.4), returning no pointer when no key in the set carries it.

◆ from() [1/2]

auto sourcemeta::core::JWKS::from ( const JSON & value) -> std::optional< JWKS >
staticnodiscard

Parse a JSON Web Key Set from a JSON value, returning no value on invalid input.

◆ from() [2/2]

auto sourcemeta::core::JWKS::from ( JSON && value) -> std::optional< JWKS >
staticnodiscard

Parse a JSON Web Key Set from a JSON value, returning no value on invalid input.

◆ sourcemeta::core::JWKSProvider

class sourcemeta::core::JWKSProvider

A stateful, thread-safe resolver that owns a key set URL and verifies tokens against it, fetching and refreshing the keys internally. It adds caching, a freshness-aware refresh, a guarded refetch on rotation, and serving of the previously held keys through a transient outage. The current time is read internally from an injectable clock, so a caller never deals with it and tests can drive expiry, rotation, and the refetch cooldown deterministically.

Public Types

using Fetcher
using Clock = std::function<std::chrono::system_clock::time_point()>

Public Member Functions

 JWKSProvider (std::string jwks_uri, Fetcher fetcher)
 JWKSProvider (std::string jwks_uri, Fetcher fetcher, Options options)
 JWKSProvider (std::string jwks_uri, Fetcher fetcher, Options options, Clock clock)
 JWKSProvider (const JWKSProvider &)=delete
 JWKSProvider (JWKSProvider &&)=delete
auto verify (const JWT &token, const std::span< const JWSAlgorithm > allowed_algorithms, const std::string_view expected_issuer, const std::string_view expected_audience, const std::optional< std::string_view > expected_subject, const std::optional< std::string_view > expected_type) -> std::optional< JWTVerificationError >
auto verify_access_token (const JWT &token, const std::span< const JWSAlgorithm > allowed_algorithms, const std::string_view expected_issuer, const std::string_view expected_audience, const std::optional< std::string_view > expected_subject=std::nullopt) -> std::optional< JWTVerificationError >
auto verify (const JWT &token, const std::span< const JWSAlgorithm > allowed_algorithms, const std::string_view expected_issuer, const std::string_view expected_audience, const std::optional< std::string_view > expected_subject, const std::optional< std::string_view > expected_type, std::chrono::system_clock::time_point &resolved_now) -> std::optional< JWTVerificationError >

Member Typedef Documentation

◆ Clock

using sourcemeta::core::JWKSProvider::Clock = std::function<std::chrono::system_clock::time_point()>

A source of the current time. It defaults to the system clock and exists as an injection point so that expiry, rotation, and the refetch cooldown can be driven deterministically under test.

◆ Fetcher

Initial value:
std::function<std::optional<FetchResult>(std::string_view url)>

A pluggable transport that turns a URL into raw key set bytes plus an optional freshness hint. Returns no value on a failed retrieval, such as a transport error, an unsuccessful response, or an oversized body. Injecting the transport keeps this module free of any networking dependency and makes the provider substitutable for testing.

Constructor & Destructor Documentation

◆ JWKSProvider() [1/4]

sourcemeta::core::JWKSProvider::JWKSProvider ( std::string jwks_uri,
Fetcher fetcher )

Construct a provider for a concrete key set URL with an injected transport, using the default policy and the system clock.

◆ JWKSProvider() [2/4]

sourcemeta::core::JWKSProvider::JWKSProvider ( std::string jwks_uri,
Fetcher fetcher,
Options options )

Construct a provider for a concrete key set URL with an injected transport, overriding the caching and verification policy.

◆ JWKSProvider() [3/4]

sourcemeta::core::JWKSProvider::JWKSProvider ( std::string jwks_uri,
Fetcher fetcher,
Options options,
Clock clock )

Construct a provider for a concrete key set URL with an injected transport, overriding the policy and the clock.

◆ JWKSProvider() [4/4]

sourcemeta::core::JWKSProvider::JWKSProvider ( const JWKSProvider & )
delete

The provider owns a lock guarding its cache, so it is neither copyable nor movable. Store it behind a pointer or construct it in place.

Member Function Documentation

◆ verify() [1/2]

auto sourcemeta::core::JWKSProvider::verify ( const JWT & token,
const std::span< const JWSAlgorithm > allowed_algorithms,
const std::string_view expected_issuer,
const std::string_view expected_audience,
const std::optional< std::string_view > expected_subject,
const std::optional< std::string_view > expected_type ) -> std::optional< JWTVerificationError >
nodiscard

Verify a token against the provider's key set, fetching or refreshing the keys as needed. Returns no value when the token is fully valid, otherwise the first failing step. The current time and the clock skew tolerance are the provider's own concern, so a caller supplies only what identifies the token: the expected subject, or no value to accept any, and the expected typ header, or no value to accept any.

Neither is defaulted. RFC 9068 Section 4 requires a resource server to "verify that the `typ` header value is `at+jwt` or `application/at+jwt` and reject tokens carrying any other value", and Section 5 explains that this is what keeps an OpenID Connect ID Token from being accepted as an access token. A default of no value would make skipping that check the thing a caller gets for writing less, so the decision is spelled at the call site instead. Prefer verify_access_token when the token is an access token.

◆ verify() [2/2]

auto sourcemeta::core::JWKSProvider::verify ( const JWT & token,
const std::span< const JWSAlgorithm > allowed_algorithms,
const std::string_view expected_issuer,
const std::string_view expected_audience,
const std::optional< std::string_view > expected_subject,
const std::optional< std::string_view > expected_type,
std::chrono::system_clock::time_point & resolved_now ) -> std::optional< JWTVerificationError >
nodiscard

Verify a token exactly as the other overload does, additionally exposing the clock reading the verification ran at, so that a caller performing its own time checks on the same token, such as an issued-at age or an authentication-time freshness window, shares the verifier's clock rather than injecting a second, independently read one.

◆ verify_access_token()

auto sourcemeta::core::JWKSProvider::verify_access_token ( const JWT & token,
const std::span< const JWSAlgorithm > allowed_algorithms,
const std::string_view expected_issuer,
const std::string_view expected_audience,
const std::optional< std::string_view > expected_subject = std::nullopt ) -> std::optional< JWTVerificationError >
nodiscard

Verify a token as an RFC 9068 JWT access token, pinning the typ header to at+jwt so the profile's Section 4 requirement cannot be omitted.

◆ sourcemeta::core::JWT

class sourcemeta::core::JWT

A parsed JSON Web Token in compact serialization (RFC 7519, RFC 7515). The token does not own its input, so the string it was parsed from must outlive it. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
#include <string>
const std::string input{
"eyJhbGciOiJSUzI1NiJ9.eyJpc3MiOiJhY21lIn0.c2ln"};
const auto token{sourcemeta::core::JWT::from(input)};
assert(token.has_value());
assert(token.value().algorithm() == sourcemeta::core::JWSAlgorithm::RS256);
static auto from(const std::string_view input) -> std::optional< JWT >
@ RS256
RSASSA-PKCS1-v1_5 using SHA-256.
Definition jose_algorithm.h:23

Public Member Functions

 JWT (const std::string_view input)
auto algorithm () const noexcept -> std::optional< JWSAlgorithm >
 The signing algorithm declared in the token header, if present.
auto key_id () const noexcept -> std::optional< std::string_view >
 The key identifier from the token header, if present.
auto type () const noexcept -> std::optional< std::string_view >
 The token type declared in the header, if present.
auto has_type (const std::string_view media_type) const -> bool
auto header () const noexcept -> const JSON &
 The decoded token header.
auto issuer () const noexcept -> std::optional< std::string_view >
 The issuer that created the token, if present.
auto subject () const noexcept -> std::optional< std::string_view >
 The subject the token is about, if present.
auto has_audience (const std::string_view audience) const noexcept -> bool
 Whether the token is intended for the given audience.
auto expires_at () const -> std::optional< std::chrono::system_clock::time_point >
 The time after which the token is no longer valid, if present.
auto not_before () const -> std::optional< std::chrono::system_clock::time_point >
 The time before which the token is not yet valid, if present.
auto issued_at () const -> std::optional< std::chrono::system_clock::time_point >
 The time at which the token was issued, if present.
auto token_id () const noexcept -> std::optional< std::string_view >
 The unique identifier of the token, if present.
auto payload () const noexcept -> const JSON &
 The decoded token payload.
auto signing_input () const noexcept -> std::string_view
 The exact wire bytes the signature is computed over.
auto signature () const noexcept -> std::string_view
 The raw token signature.

Static Public Member Functions

static auto from (const std::string_view input) -> std::optional< JWT >

Constructor & Destructor Documentation

◆ JWT()

sourcemeta::core::JWT::JWT ( const std::string_view input)
explicit

Parse a JSON Web Token from its compact serialization, throwing a JWTParseError on invalid input.

Member Function Documentation

◆ from()

auto sourcemeta::core::JWT::from ( const std::string_view input) -> std::optional< JWT >
staticnodiscard

Parse a JSON Web Token from its compact serialization, returning no value on invalid input.

◆ has_type()

auto sourcemeta::core::JWT::has_type ( const std::string_view media_type) const -> bool
nodiscard

Whether the token declares the given type, treating a subtype without a slash as application/-prefixed and comparing case-insensitively (RFC 7519 Section 5.1, RFC 7515 Section 4.1.9).

◆ sourcemeta::core::JWTClockSkew

struct sourcemeta::core::JWTClockSkew

A tolerance for clock disagreement between the token issuer and the verifier, carried per time-based claim so that, for example, a deployment can forgive a small expiration overshoot without also accepting tokens issued in the future. A plain seconds value converts to a uniform tolerance across every claim. For example:

#include <sourcemeta/core/jose.h>
#include <chrono>
const sourcemeta::core::JWTClockSkew uniform{std::chrono::seconds{30}};
std::chrono::seconds{60}, std::chrono::seconds{30},
std::chrono::seconds{0}};
Definition jose_verify.h:57

Public Member Functions

 JWTClockSkew () noexcept=default
 Apply no tolerance to any time-based claim.
 JWTClockSkew (const std::chrono::seconds uniform) noexcept
 Apply the same tolerance to every time-based claim.
 JWTClockSkew (const std::chrono::seconds expiration_tolerance, const std::chrono::seconds not_before_tolerance, const std::chrono::seconds issued_at_tolerance) noexcept
 Apply a distinct tolerance to each time-based claim.

Public Attributes

std::chrono::seconds expiration {0}
 The tolerance applied to the expiration time claim.
std::chrono::seconds not_before {0}
 The tolerance applied to the not-before time claim.
std::chrono::seconds issued_at {0}
 The tolerance applied to the issued-at time claim.

Enumeration Type Documentation

◆ JWEAlgorithm

enum class sourcemeta::core::JWEAlgorithm : std::uint8_t
strong

The JSON Web Encryption key-management algorithms (the alg value) from RFC 7518 Section 4.1. Each one determines how the content encryption key is delivered to the recipient, and demands a key of exactly one family, which is what keeps algorithm confusion attacks unexploitable.

Enumerator
RSA_OAEP 

RSAES OAEP using default parameters (SHA-1).

RSA_OAEP_256 

RSAES OAEP using SHA-256.

ECDH_ES 

Elliptic Curve Diffie-Hellman Ephemeral Static key agreement, direct.

ECDH_ES_A128KW 

ECDH-ES using Concat KDF and the CEK wrapped with AES-128 Key Wrap.

ECDH_ES_A192KW 

ECDH-ES using Concat KDF and the CEK wrapped with AES-192 Key Wrap.

ECDH_ES_A256KW 

ECDH-ES using Concat KDF and the CEK wrapped with AES-256 Key Wrap.

A128KW 

AES-128 Key Wrap.

A192KW 

AES-192 Key Wrap.

A256KW 

AES-256 Key Wrap.

DIR 

Direct use of a shared symmetric key as the CEK.

◆ JWEEncryption

enum class sourcemeta::core::JWEEncryption : std::uint8_t
strong

The JSON Web Encryption content encryption algorithms (the enc value) from RFC 7518 Section 5.1. Each one seals the plaintext under the content encryption key with an authenticated encryption scheme.

Enumerator
A128GCM 

AES-128 in Galois/Counter Mode.

A192GCM 

AES-192 in Galois/Counter Mode.

A256GCM 

AES-256 in Galois/Counter Mode.

A128CBC_HS256 

AES-128 in CBC mode with an HMAC SHA-256 authentication tag.

A192CBC_HS384 

AES-192 in CBC mode with an HMAC SHA-384 authentication tag.

A256CBC_HS512 

AES-256 in CBC mode with an HMAC SHA-512 authentication tag.

◆ JWSAlgorithm

enum class sourcemeta::core::JWSAlgorithm : std::uint8_t
strong

The JSON Web Signature algorithms from RFC 7518 Section 3.1 and the Edwards-curve algorithm from RFC 8037 Section 3.1. The null algorithm is intentionally absent. Each algorithm demands a key of exactly one family, the symmetric algorithms an octet sequence and the asymmetric ones their own key type, which is what keeps algorithm confusion attacks unexploitable.

Enumerator
RS256 

RSASSA-PKCS1-v1_5 using SHA-256.

RS384 

RSASSA-PKCS1-v1_5 using SHA-384.

RS512 

RSASSA-PKCS1-v1_5 using SHA-512.

PS256 

RSASSA-PSS using SHA-256 and MGF1 with SHA-256.

PS384 

RSASSA-PSS using SHA-384 and MGF1 with SHA-384.

PS512 

RSASSA-PSS using SHA-512 and MGF1 with SHA-512.

ES256 

ECDSA using the NIST P-256 curve and SHA-256.

ES384 

ECDSA using the NIST P-384 curve and SHA-384.

ES512 

ECDSA using the NIST P-521 curve and SHA-512.

EdDSA 

Edwards-curve Digital Signature Algorithm.

HS256 

HMAC using SHA-256.

HS384 

HMAC using SHA-384.

HS512 

HMAC using SHA-512.

◆ JWTClaimError

enum class sourcemeta::core::JWTClaimError : std::uint8_t
strong

The claim validation errors that claim checking can return, one per check performed rather than an exhaustive list of registered claims.

Enumerator
Issuer 

The issuer claim is missing or does not match the expected value.

Subject 

The subject claim is missing or does not match the expected value.

Audience 

The audience claim is missing or does not contain the expected value.

Expiration 

The expiration time claim is missing or the token has expired.

NotBefore 

The not-before time claim is malformed or lies in the future.

IssuedAt 

The issued-at time claim is malformed or lies in the future.

◆ JWTVerificationError

enum class sourcemeta::core::JWTVerificationError : std::uint8_t
strong

The steps of full token verification that can fail, in the order they are evaluated.

Enumerator
AlgorithmNotAllowed 

The token's algorithm is missing or absent from the allow-list.

UnknownKey 

No key in the set could be selected or verified the signature.

Signature 

The named key was found but its signature did not verify.

Type 

The token type does not match the expected media type.

Issuer 

The issuer claim is missing or does not match the expected value.

Subject 

The subject claim is missing or does not match the expected value.

Audience 

The audience claim is missing or does not contain the expected value.

Expiration 

The expiration time claim is missing or the token has expired.

NotBefore 

The not-before time claim is malformed or lies in the future.

IssuedAt 

The issued-at time claim is malformed or lies in the future.

Function Documentation

◆ jwe_algorithm_is_asymmetric()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_algorithm_is_asymmetric ( const JWEAlgorithm algorithm) -> bool
noexcept

Whether the key-management algorithm consumes an asymmetric recipient key (RSA-OAEP*, ECDH-ES*) rather than a shared octet secret (A*KW, dir) (RFC 7518 Section 4.1). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_algorithm_is_asymmetric(const JWEAlgorithm algorithm) noexcept -> bool
@ RSA_OAEP
RSAES OAEP using default parameters (SHA-1).
Definition jose_algorithm.h:127
@ A128KW
AES-128 Key Wrap.
Definition jose_algorithm.h:139

◆ jwe_algorithm_name()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_algorithm_name ( const JWEAlgorithm algorithm) -> std::string_view
noexcept

Map a JSON Web Encryption key-management algorithm to its alg value, the inverse of parsing (RFC 7518 Section 4.1). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_algorithm_name(const JWEAlgorithm algorithm) noexcept -> std::string_view
@ DIR
Direct use of a shared symmetric key as the CEK.
Definition jose_algorithm.h:145

◆ jwe_decrypt()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_decrypt ( const JWE & jwe,
const JWKPrivate & key ) -> std::optional< std::string >

Decrypt a JSON Web Encryption object with the recipient key, returning the plaintext (RFC 7516). The key is the recipient private key for the asymmetric algorithms and the shared octet secret for A*KW and dir. Returns no value on any failure, uniformly, so that a key-unwrap failure, an authentication tag mismatch, and a structural error are indistinguishable and the recipient cannot be used as a decryption oracle (RFC 7516 Sections 11.4 and 11.5). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
const auto object{sourcemeta::core::JWE::from(compact)};
assert(object.has_value());
const auto plaintext{sourcemeta::core::jwe_decrypt(object.value(), key)};
assert(plaintext.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_decrypt(const JWE &jwe, const JWKPrivate &key) -> std::optional< std::string >

◆ jwe_encrypt()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encrypt ( const JSON & header,
const std::string_view plaintext,
const JWK & key ) -> std::optional< std::string >

Encrypt a plaintext into a JSON Web Encryption object in compact serialization (RFC 7516). The key-management algorithm and content encryption algorithm are taken from the protected header alg and enc parameters (RFC 7516 Sections 4.1.1 and 4.1.2). A fresh initialization vector is always generated. The content encryption key is generated as the algorithm requires: freshly random for the key-wrapping and RSA algorithms, derived from the agreement for direct ECDH-ES, and the shared secret itself for dir. For the ECDH-ES algorithms an ephemeral key is minted and its public part added to the emitted protected header as the epk parameter. The key is the recipient public key for the asymmetric algorithms and the shared octet secret for A*KW and dir. Returns no value when the header is not an object, has duplicate members, carries a critical extension or a compression parameter, names an unsupported or key-incompatible algorithm, or the key cannot serve it. For example:

#include <sourcemeta/core/jose.h>
#include <sourcemeta/core/json.h>
#include <cassert>
sourcemeta::core::parse_json(R"({ "alg": "RSA-OAEP-256",
"enc": "A128GCM" })"),
"secret message", recipient)};
assert(object.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_encrypt(const JSON &header, const std::string_view plaintext, const JWK &key) -> std::optional< std::string >

◆ jwe_encryption_key_bytes()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encryption_key_bytes ( const JWEEncryption encryption) -> std::size_t
noexcept

The content encryption key length, in bytes, that a content encryption algorithm requires (RFC 7518 Sections 5.2 and 5.3). The CBC-HMAC algorithms take a double-width key that is split into a MAC key and an encryption key. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_encryption_key_bytes(const JWEEncryption encryption) noexcept -> std::size_t
@ A128CBC_HS256
AES-128 in CBC mode with an HMAC SHA-256 authentication tag.
Definition jose_algorithm.h:160
@ A128GCM
AES-128 in Galois/Counter Mode.
Definition jose_algorithm.h:154

◆ jwe_encryption_name()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwe_encryption_name ( const JWEEncryption encryption) -> std::string_view
noexcept

Map a JSON Web Encryption content encryption algorithm to its enc value, the inverse of parsing (RFC 7518 Section 5.1). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jwe_encryption_name(const JWEEncryption encryption) noexcept -> std::string_view

◆ jws_algorithm_digest_bits()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_digest_bits ( const JWSAlgorithm algorithm) -> std::uint16_t
noexcept

The size, in bits, of the digest each signature algorithm is defined over (RFC 7518 Section 3.1), so that derived hash claims such as OpenID Connect's at_hash and c_hash select their digest by table rather than by slicing the algorithm name. The Edwards-curve algorithm names no digest and OpenID Connect leaves the choice unspecified, so it is pinned to SHA-512, the convention deployed implementations follow for Ed25519, whose signature scheme is internally defined over that hash (RFC 8032 Section 5.1). Hash claims minted over Ed448 by a SHAKE256-based implementation need curve-specific handling that no algorithm-only table can provide. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jws_algorithm_digest_bits(const JWSAlgorithm algorithm) noexcept -> std::uint16_t
@ ES384
ECDSA using the NIST P-384 curve and SHA-384.
Definition jose_algorithm.h:37

◆ jws_algorithm_is_asymmetric()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_is_asymmetric ( const JWSAlgorithm algorithm) -> bool
noexcept

Whether an algorithm is an asymmetric digital signature algorithm rather than a symmetric message authentication code (RFC 7518 Section 3.1). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jws_algorithm_is_asymmetric(const JWSAlgorithm algorithm) noexcept -> bool
@ HS256
HMAC using SHA-256.
Definition jose_algorithm.h:43
@ ES256
ECDSA using the NIST P-256 curve and SHA-256.
Definition jose_algorithm.h:35

◆ jws_algorithm_name()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_algorithm_name ( const JWSAlgorithm algorithm) -> std::string_view
noexcept

Map a JSON Web Signature algorithm to its alg value, the inverse of parsing (RFC 7515 Section 4.1.1). For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
SOURCEMETA_CORE_JOSE_EXPORT auto jws_algorithm_name(const JWSAlgorithm algorithm) noexcept -> std::string_view

◆ jws_sign()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_sign ( const JWSAlgorithm algorithm,
const std::string_view signing_input,
const JWKPrivate & key ) -> std::optional< std::string >

Produce the raw signature bytes for a signing input under an algorithm, the signing counterpart to signature verification. Returns no value for a key whose type or curve cannot serve the algorithm, a key declaring a contradicting algorithm, or a key whose material never formed a usable private key. The signing input is the exact bytes to sign, which carry no constraint on their content. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
assert(key.has_value());
const auto signature{sourcemeta::core::jws_sign(
sourcemeta::core::JWSAlgorithm::RS256, "header.payload", key.value())};
assert(signature.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jws_sign(const JWSAlgorithm algorithm, const std::string_view signing_input, const JWKPrivate &key) -> std::optional< std::string >

◆ jws_verify_signature()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jws_verify_signature ( const std::optional< JWSAlgorithm > algorithm,
const std::string_view signing_input,
const std::string_view signature,
const JWK & key ) -> bool

Verify a JSON Web Signature given its algorithm, its signing input, and its decoded signature against a JSON Web Key, returning false rather than throwing for an unrecognized algorithm, a key whose type or curve cannot serve the algorithm, a key declaring a contradicting algorithm, or a signature that does not verify. The signing input is the exact bytes the signature was computed over, which carry no constraint on their content. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
R"JSON({ "kty": "RSA", "n": "", "e": "" })JSON"))};
assert(!key.has_value() ||
"signature", key.value()));
SOURCEMETA_CORE_JOSE_EXPORT auto jws_verify_signature(const std::optional< JWSAlgorithm > algorithm, const std::string_view signing_input, const std::string_view signature, const JWK &key) -> bool

◆ jwt_bounded_clock_skew()

auto sourcemeta::core::jwt_bounded_clock_skew ( const std::chrono::seconds skew) -> std::chrono::seconds
inlinenoexcept

Reduce a caller-supplied clock skew to the grace period token validation honours, one mean Gregorian year, treating a negative tolerance as none. Every path that validates a token applies this, so the same tolerance means the same thing whichever one runs. For example:

#include <sourcemeta/core/jose.h>
#include <chrono>
#include <cassert>
std::chrono::seconds{30}) == std::chrono::seconds{30});
std::chrono::seconds{-30}) == std::chrono::seconds{0});
auto jwt_bounded_clock_skew(const std::chrono::seconds skew) noexcept -> std::chrono::seconds
Definition jose_verify.h:98

◆ jwt_check_claims()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_check_claims ( const JWT & token,
const std::string_view expected_issuer,
const std::string_view expected_audience,
const std::chrono::system_clock::time_point now,
const JWTClockSkew clock_skew = {},
const std::optional< std::string_view > expected_subject = std::nullopt ) -> std::optional< JWTClaimError >

Validate the registered claims of a JSON Web Token against the expected issuer and audience at a given time, returning the first failing check or no value when every check passes. The expiration claim is required (RFC 9068 Section 2.2), and the subject is checked only when an expected value is supplied. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
#include <chrono>
#include <string>
const std::string input{
"eyJhbGciOiJSUzI1NiJ9."
"eyJpc3MiOiJhY21lIiwiYXVkIjoiY2xpZW50IiwiZXhwIjoyMDAwMDAwMDAwfQ.c2ln"};
const auto token{sourcemeta::core::JWT::from(input)};
assert(token.has_value());
token.value(), "acme", "client",
std::chrono::system_clock::from_time_t(1500000000))};
assert(!error.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jwt_check_claims(const JWT &token, const std::string_view expected_issuer, const std::string_view expected_audience, const std::chrono::system_clock::time_point now, const JWTClockSkew clock_skew={}, const std::optional< std::string_view > expected_subject=std::nullopt) -> std::optional< JWTClaimError >

◆ jwt_sign()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_sign ( const JSON & header,
const JSON & payload,
const JWKPrivate & key ) -> std::optional< std::string >

Build and sign a JSON Web Token in compact serialization (RFC 7519, RFC 7515) from a header and a payload, returning the base64url header, payload, and signature joined by dots. The algorithm is taken from the header algorithm parameter (RFC 7515 Section 4.1.1). Returns no value when the header or payload is not an object, the header names no supported algorithm, or the key cannot produce the signature. For example:

#include <sourcemeta/core/jose.h>
#include <sourcemeta/core/json.h>
#include <cassert>
assert(key.has_value());
const auto token{sourcemeta::core::jwt_sign(
sourcemeta::core::parse_json(R"({ "alg": "RS256" })"),
sourcemeta::core::parse_json(R"({ "iss": "acme" })"), key.value())};
assert(token.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jwt_sign(const JSON &header, const JSON &payload, const JWKPrivate &key) -> std::optional< std::string >

◆ jwt_verify()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_verify ( const JWT & token,
const JWKS & keys,
const std::span< const JWSAlgorithm > allowed_algorithms,
const std::string_view expected_issuer,
const std::string_view expected_audience,
const std::chrono::system_clock::time_point now,
const JWTClockSkew clock_skew,
const std::optional< std::string_view > expected_subject,
const std::optional< std::string_view > expected_type ) -> std::optional< JWTVerificationError >

Verify a JSON Web Token end to end against a key set, in the mandated order: the algorithm must be in the allow-list, a key is selected by its identifier or, when absent, tried against every compatible key, the signature must verify, and the claims must pass. Returns no value when the token is fully valid, or the first failing step. The type check enforces the access token profile (RFC 9068 Section 2.1) only when an expected type is supplied. For example:

#include <sourcemeta/core/jose.h>
#include <array>
#include <cassert>
#include <chrono>
#include <optional>
#include <string>
const std::string input{
"eyJhbGciOiJSUzI1NiJ9.eyJpc3MiOiJhY21lIn0.c2ln"};
const auto token{sourcemeta::core::JWT::from(input)};
assert(token.has_value());
sourcemeta::core::parse_json(R"JSON({ "keys": [] })JSON"))};
assert(keys.has_value());
const std::array allowed{sourcemeta::core::JWSAlgorithm::RS256};
token.value(), keys.value(), allowed, "acme", "client",
std::chrono::system_clock::from_time_t(1500000000), {}, std::nullopt,
std::nullopt)};
assert(error.has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto jwt_verify(const JWT &token, const JWKS &keys, const std::span< const JWSAlgorithm > allowed_algorithms, const std::string_view expected_issuer, const std::string_view expected_audience, const std::chrono::system_clock::time_point now, const JWTClockSkew clock_skew, const std::optional< std::string_view > expected_subject, const std::optional< std::string_view > expected_type) -> std::optional< JWTVerificationError >

◆ jwt_verify_signature()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::jwt_verify_signature ( const JWT & token,
const JWK & key ) -> bool

Verify the signature of a JSON Web Token against a JSON Web Key, returning false rather than throwing whenever the token does not carry a confirmed valid signature for the key. This includes an unrecognized algorithm, a key whose type or curve cannot serve the algorithm, a key declaring a contradicting algorithm, and a signature that does not verify. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
#include <string>
const std::string input{
"eyJhbGciOiJSUzI1NiJ9.eyJpc3MiOiJhY21lIn0.c2ln"};
const auto token{sourcemeta::core::JWT::from(input)};
assert(token.has_value());
"kty": "RSA", "n": "", "e": ""
})JSON"))};
assert(!key.has_value() ||
!sourcemeta::core::jwt_verify_signature(token.value(), key.value()));
SOURCEMETA_CORE_JOSE_EXPORT auto jwt_verify_signature(const JWT &token, const JWK &key) -> bool

◆ to_jwe_algorithm()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jwe_algorithm ( const std::string_view value) -> std::optional< JWEAlgorithm >
noexcept

Map a JSON Web Encryption alg value to its algorithm, returning no value for any unrecognized name. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
assert(sourcemeta::core::to_jwe_algorithm("RSA-OAEP-256").has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto to_jwe_algorithm(const std::string_view value) noexcept -> std::optional< JWEAlgorithm >

◆ to_jwe_encryption()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jwe_encryption ( const std::string_view value) -> std::optional< JWEEncryption >
noexcept

Map a JSON Web Encryption enc value to its algorithm, returning no value for any unrecognized name. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
assert(sourcemeta::core::to_jwe_encryption("A128GCM").has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto to_jwe_encryption(const std::string_view value) noexcept -> std::optional< JWEEncryption >

◆ to_jws_algorithm()

SOURCEMETA_CORE_JOSE_EXPORT auto sourcemeta::core::to_jws_algorithm ( const std::string_view value) -> std::optional< JWSAlgorithm >
noexcept

Map a JSON Web Signature alg value to its algorithm, returning no value for any unrecognized name. For example:

#include <sourcemeta/core/jose.h>
#include <cassert>
assert(sourcemeta::core::to_jws_algorithm("RS256").has_value());
assert(!sourcemeta::core::to_jws_algorithm("none").has_value());
SOURCEMETA_CORE_JOSE_EXPORT auto to_jws_algorithm(const std::string_view value) noexcept -> std::optional< JWSAlgorithm >