Class ClientAssertionSigner
The private key stays in this process. It is handed to a Nimbus JWSSigner at
construction and is never exposed again: there is no accessor returning the key, and none
returning the JWK it came from. That is the property this credential kind buys over a
shared secret, so it is a property of this class rather than a promise made elsewhere. There is
deliberately no overload handing a key to the transport - a transport that could sign would be a
transport that holds keys, and every caller would then have to trust it not to log one.
A fresh assertion is minted on every sign(String) call, and there is no accessor
returning "the current" assertion. The API shape is what prevents reuse. The server claims
each jti exactly once, so an assertion cached and re-sent after a timeout is the client
replaying its OWN credential: the first attempt may well have been received and its jti
consumed before the response was lost. The retry is then refused with the same opaque
401 invalid_client as a bad key, and everyone reading the client's logs diagnoses a
server fault. This matters most on retry, which is exactly where a caching optimisation looks
harmless.
The audience is passed to sign(String), never derived here. A client
computing it would be guessing at a value the server owns, and would stop authenticating the day
a deployment's edge URL changed. The value to pass is the expectedAudience the
deployment returned when the key was registered.
Usage
JWK privateKey = JWK.parse(Files.readString(keyPath));
ClientAssertionSigner signer = new ClientAssertionSigner(actorId, privateKey);
AuthenticatedSdk sdk = factory.authenticateApplicationWithKeyPair(
actorId.toString(), signer, expectedAudience);
- See Also:
-
Field Summary
FieldsModifier and TypeFieldDescriptionstatic final StringTheclient_assertion_typeform value that selects this credential kind at the token endpoint, as fixed by RFC 7523 §2.2. -
Constructor Summary
ConstructorsConstructorDescriptionClientAssertionSigner(UUID actorId, com.nimbusds.jose.jwk.JWK privateKey) Binds this signer to one actor and one private key. -
Method Summary
-
Field Details
-
CLIENT_ASSERTION_TYPE
Theclient_assertion_typeform value that selects this credential kind at the token endpoint, as fixed by RFC 7523 §2.2. Any other value is refused with400 invalid_request.- See Also:
-
-
Constructor Details
-
ClientAssertionSigner
public ClientAssertionSigner(UUID actorId, com.nimbusds.jose.jwk.JWK privateKey) throws com.nimbusds.jose.JOSEException Binds this signer to one actor and one private key.- Parameters:
actorId- the actor UUID; it becomes bothissandsub, which the server requires to name the actor presenting the assertionprivateKey- the actor's private JWK. It must carry private key material - a public-only JWK cannot sign - and its key type must be RSA or EC. The key is consumed here and never retained in a form this class can hand back.- Throws:
com.nimbusds.jose.JOSEException- if the key carries no private material, its key type or curve is one the platform does not admit, or no admissible signature algorithm can be resolved for itNullPointerException- if either argument isnull
-
-
Method Details
-
sign
Mints a fresh assertion for the given audience.Every call produces a new
jtiand a new validity window. The returned assertion is for immediate use by a single request; see the class javadoc for why re-sending one is a replay of the caller's own credential rather than a retry.- Parameters:
audience- theexpectedAudiencethis deployment returned when the key was registered. Passed rather than derived: a client computing it would be guessing at a value the server owns.- Returns:
- the signed assertion in JWS compact serialization, to be sent as
client_assertion - Throws:
com.nimbusds.jose.JOSEException- if the signature cannot be produced, or if the resulting assertion exceeds the length the verifier admitsNullPointerException- ifaudienceisnullIllegalArgumentException- ifaudienceis blank
-
toString
Returns a description that names the actor and the algorithm and reveals nothing about the key, so an accidental log statement cannot leak signing material.
-