public abstract class JWSSigner extends Object
This class represents a single signer of a JWS. According to RFC 7515, a single "signature" consists of a the JOSE headers, a JWS payload, and a JWS signature. The JOSE headers in turn consist of protected and unprotected headers. The base 64 url representation of the protected headers concatenated with the JWS payload (separated by a single dot) is the input for the signing process. The protected headers have to at least include the AlgHeader, whereas the unprotected headers may be absent.
There exist multiple ways to serialize a JWS. When using the General Json Serialization, it is possible to bundle multiple "signatures" into a single JWS (see Section 7.2.1). To avoid misunderstandings, we refer to the logical structure consisting of JOSE headers and a JWS signature as "Signer". Furthermore, we refer to the container holding the JWS Payload, which possibly encapsulates multiple Signers, as "Signature" or "SignedData". Neither the RFC 7515, nor the JAdES specification are consistent with the terminology. To give an example, a JWS serialized with the flattened serialization, is one "signature" containing one "signer". Furthermore, consider the following JWS:
{
"payload":"payload contents",
"signatures":[
{"protected":"integrity-protected header 0 contents",
"header":non-integrity-protected header 0 contents,
"signature":"signature 0 contents"},
{"protected":"integrity-protected header 1 contents",
"header":non-integrity-protected header 1 contents,
"signature":"signature 1 contents"}]
}
We refer to the whole JSON as "signature". This signature contains two signers. For signing, the class JWSSignedData (for validation, JWSValidationData) represents the signature, which then contains two instances of JWSSigner.
In order to sign data, a caller has to call getInstance(JWA, PrivateKey). This will initiate the object for signing, and set up the ProtectedHeaders. To add headers, use addProtectedHeader(ProtectedHeader), addUnprotectedHeader(UnprotectedHeader), and addEtsiUHeader(JadesUnprotectedHeader), depending on the purpose. Do not add the etsiU header with addUnprotectedHeader(UnprotectedHeader).
In order to validate data, a caller has to parse a JWS with a JAdESParser and obtain all JWSSigners in the signature. When using this method, the class is setup for validation. To verify a signer, call verify(PublicKey) or verify(X509Certificate). Note that success or failure does not imply anything about other signers in the signature.
Depending on the state of the object, certain methods throw exception. For example, if the object is in validation state, the method addProtectedHeader(ProtectedHeader) will throw an exception, as it is not possible to add a new protected header after signing.
| Modifier and Type | Field and Description |
|---|---|
static Set<String> |
JWS_HEADERS
All headers from RFC 7515 in an unmodifiable set.
|
static Set<String> |
KNOWN_HEADERS
All header keys know by this library in an unmodifiable set.
|
protected ProtectedHeaders |
protectedHeaders
The protected headers of this signer
|
protected Signature |
signatureInstance
The signature instance of this signer
|
protected String |
signatureValue
The signature value (always base 64 url encoded if present) or
null |
protected UnprotectedHeaders |
unprotectedHeaders
The unprotected headers of this signer
|
| Modifier | Constructor and Description |
|---|---|
protected |
JWSSigner(JWA jwa,
PrivateKey privateKey)
Protected Constructor for signing.
|
protected |
JWSSigner(ProtectedHeaders protectedHeaders,
UnprotectedHeaders unprotectedHeaders,
String signatureValue)
Protected Constructor for validation/augmentation.
|
| Modifier and Type | Method and Description |
|---|---|
void |
addEtsiUHeader(JadesUnprotectedHeader jadesUnprotectedHeader)
Adds an a JadesUnprotectedHeader to the EtsiUHeader of this signer.
|
abstract void |
addProtectedHeader(ProtectedHeader header)
Adds a ProtectedHeader to the protected headers of this signer.
|
void |
addUnprotectedHeader(UnprotectedHeader header)
Adds a UnprotectedHeader to the unprotected headers of this signer.
|
static JWSSigner |
getInstance(JWA jwa,
PrivateKey privateKey)
Creates a signer in signing state using the provided JWA and PrivateKey.
|
ProtectedHeaders |
getProtectedHeaders()
Returns the ProtectedHeaders of this signer.
|
String |
getSignatureValue()
Returns the JWS signature string of the signature.
|
UnprotectedHeaders |
getUnprotectedHeaders()
Returns the UnprotectedHeaders of this signer.
|
abstract boolean |
validateCritHeader()
RFC 7515 defines the CritHeader
as protected header parameter, that "indicates extensions to this specification [...] that MUST be understood
and processed".
|
abstract boolean |
verify(PublicKey key)
Performs the cryptographic validation of the signer with the provided PublicKey.
|
abstract boolean |
verify(iaik.x509.X509Certificate certificate)
Performs the cryptographic validation of the signer with the provided X509Certificate.
|
public static final Set<String> JWS_HEADERS
public static final Set<String> KNOWN_HEADERS
protected final ProtectedHeaders protectedHeaders
protected final UnprotectedHeaders unprotectedHeaders
protected final Signature signatureInstance
protected String signatureValue
nullprotected JWSSigner(JWA jwa, PrivateKey privateKey) throws JWSException
Protected Constructor for signing. getInstance(JWA, PrivateKey) calls this constructor.
JWSExceptionprotected JWSSigner(ProtectedHeaders protectedHeaders, UnprotectedHeaders unprotectedHeaders, String signatureValue) throws JWSParsingException
Protected Constructor for validation/augmentation. The concrete implementations ofJAdESParser call this.
JWSParsingExceptionpublic static JWSSigner getInstance(JWA jwa, PrivateKey privateKey) throws JWSException
Creates a signer in signing state using the provided JWA and PrivateKey. When calling this method, the implementation adds an AlgHeader, wrapping the provided JWA, to the protected headers.
This created object represents a single signer and manages its JOSE headers and the signing process. See JWSSignedData to actually perform the signing process.
Certain methods will throw an exception, like validateCritHeader() or any of the
verify() methods.
jwa - the jwa representing the signature algorithm of this signerprivateKey - the private key of the signerJWSException - if the provided private key is incompatible with jwapublic abstract boolean validateCritHeader()
RFC 7515 defines the CritHeader as protected header parameter, that "indicates extensions to this specification [...] that MUST be understood and processed". It is an array, listing the json keys of protected headers incorporated in the signature, that were not defined by the JWS specification. This method validates whether the crit header is semantically correct.
The method iterates over the crit header array and verifies if it contains all necessary and no
redundant headers. As this verification is purely for JWS conformance, it is not included in the
verify() methods. It does not imply anything about the validity of the signature NOR the status of the
signing certificate.
When calling in sign state, will throw an IllegalStateException.
True iff the crit header conforms the JWS specification. False
otherwise.public abstract void addProtectedHeader(ProtectedHeader header)
Adds a ProtectedHeader to the protected headers of this signer. The implementation handles the following headers, so DO NOT add them with this method (will throw an exception):
This method will also throw an exception if the protected headers already contain a header with the same json key. Of course this method will throw an exception, when not in signing state.
header - a protected headerpublic final void addUnprotectedHeader(UnprotectedHeader header)
Adds a UnprotectedHeader to the unprotected headers of this signer. The implementation handles the EtsiUHeader, so DO NOT add it with this method (will throw an exception).
This method will also an exception if the unprotected headers already contain a header with the same json key. This method works in signing and validation/augmentation state.
header - an unprotected headerpublic final void addEtsiUHeader(JadesUnprotectedHeader jadesUnprotectedHeader)
Adds an a JadesUnprotectedHeader to the EtsiUHeader of this signer. See the JAdES specification for the supported headers of headers.
On the first call, adds an etsiU header to the unprotected headers of this signer.
This method will also an exception if the unprotected headers already contain a header with the same json key. This method works in signing and validation/augmentation state.
To archive the headers in the etsiU header it is necessary to add an ArcTstHeader. If a caller adds an arcTst, the implementation will include all headers in the etsiU header to the imprint computation which are preceding the arcTst in the etsiU array. This may include other arcTsts.
jadesUnprotectedHeader - an unprotected header defined by the JAdES specificationpublic abstract boolean verify(iaik.x509.X509Certificate certificate)
throws JWSException
Performs the cryptographic validation of the signer with the provided X509Certificate. This method unwraps the PublicKey of the certificate and calls verify(PublicKey).
Note that this method DOES NOT perform any validations on the certificate. To get a complete validation result, a caller has to perform a PKI check of the certificate.
This method throws an exception if in signing state.
certificate - the signing X509CertificateTrue iff the incorporated PublicKey of the provided certificate did
sign the protected headers and the respective payload with the signature algorithm obtained from the AlgHeader. False otherwise.JWSException - if there occurs an error during signature validation (e.g. wrong key).public abstract boolean verify(PublicKey key) throws JWSException
Performs the cryptographic validation of the signer with the provided PublicKey.
This method throws an exception if in signing state.
key - a PublicKeyTrue iff the incorporated PublicKey of the provided certificate did
sign the protected headers and the respective payload with the signature algorithm obtained from the AlgHeader. False otherwise.JWSException - if there occurs an error during signature validation (e.g. wrong key).public final ProtectedHeaders getProtectedHeaders()
Returns the ProtectedHeaders of this signer.
public final UnprotectedHeaders getUnprotectedHeaders()
Returns the UnprotectedHeaders of this signer. Use this object to obtain the EtsiUHeader.
public final String getSignatureValue()
Returns the JWS signature string of the signature. May return null, when still in signing
state and before executing the signing process. If not null, always returns a base 64 url encoded string.
nullCopyright © 2022 Stiftung SIC. All rights reserved.