Skip to content

Commit b1b5169

Browse files
committed
SDKS-5120: Allow configurable authenticationValidityDuration in DeviceBindingCallback and DeviceSigningVerifierCallback
1 parent da60801 commit b1b5169

7 files changed

Lines changed: 109 additions & 28 deletions

File tree

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,8 @@
1+
## [4.8.6]
2+
3+
#### Added
4+
- Added `authenticationValidityDuration` property to `DeviceBindingCallback` and `DeviceSigningVerifierCallback`, allowing callers to control the duration (in seconds) for which a generated key remains valid for user authentication. Defaults to `5` seconds.
5+
16
## [4.8.5]
27

38
#### Fixed

forgerock-auth/src/main/java/org/forgerock/android/auth/callback/DeviceBindingCallback.kt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,12 @@ open class DeviceBindingCallback : AbstractCallback, Binding {
104104
lateinit var attestation: Attestation
105105
private set
106106

107+
/**
108+
* The duration (in seconds) for which the generated key remains valid for user authentication.
109+
* Passed to [CryptoKey] during key generation. Defaults to 5 seconds.
110+
*/
111+
var authenticationValidityDuration: Int = 5
112+
107113
init {
108114
//If attestation is not provided, default to NONE
109115
if (!::attestation.isInitialized) {
@@ -222,7 +228,7 @@ open class DeviceBindingCallback : AbstractCallback, Binding {
222228
.build().identifier,
223229
prompt: Prompt? = null) {
224230

225-
deviceAuthenticator.initialize(userId, prompt ?: Prompt(title, subtitle, description))
231+
deviceAuthenticator.initialize(userId, authenticationValidityDuration, prompt ?: Prompt(title, subtitle, description))
226232

227233
if (deviceAuthenticator.isSupported(context, attestation).not()) {
228234
handleException(DeviceBindingException(Unsupported()))

forgerock-auth/src/main/java/org/forgerock/android/auth/callback/DeviceSigningVerifierCallback.kt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,12 @@ open class DeviceSigningVerifierCallback : AbstractCallback, Binding {
114114
super.setValue(clientError, 1)
115115
}
116116

117+
/**
118+
* The duration (in seconds) for which the generated key remains valid for user authentication.
119+
* Passed to the underlying crypto key during key generation. Defaults to 5 seconds.
120+
*/
121+
var authenticationValidityDuration: Int = 5
122+
117123
/**
118124
* Sign the challenge with bounded device keys.
119125
*
@@ -178,7 +184,7 @@ open class DeviceSigningVerifierCallback : AbstractCallback, Binding {
178184
customClaims: Map<String, Any> = emptyMap(),
179185
prompt: Prompt? = null) {
180186

181-
deviceAuthenticator.initialize(userKey.userId, prompt?: Prompt(title, subtitle, description))
187+
deviceAuthenticator.initialize(userKey.userId, authenticationValidityDuration, prompt?: Prompt(title, subtitle, description))
182188

183189
if (deviceAuthenticator.isSupported(context).not()) {
184190
handleException(DeviceBindingException(Unsupported()))

forgerock-auth/src/main/java/org/forgerock/android/auth/devicebind/DeviceBindAuthenticators.kt

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,10 @@ interface DeviceAuthenticator {
7272
* @param kid Generated kid from the Preference
7373
* @param userId userId received from server
7474
* @param challenge challenge received from server
75-
* @param customClaims A map of custom claims to be added to the jws payload
75+
* @param expiration token expiration time
76+
* @param attestation Attestation type to decide whether to include certificate chain in the JWS header
77+
*
78+
* @return the signed JWT as String
7679
*/
7780
fun sign(context: Context,
7881
keyPair: KeyPair,
@@ -89,7 +92,7 @@ interface DeviceAuthenticator {
8992
if (attestation !is Attestation.None) {
9093
builder.x509CertChain(getCertificateChain(userId))
9194
}
92-
val jwk = builder.build();
95+
val jwk = builder.build()
9396
val signedJWT = SignedJWT(JWSHeader.Builder(parse(getAlgorithm()))
9497
.keyID(kid).jwk(jwk).build(),
9598
JWTClaimsSet.Builder().subject(userId)
@@ -210,7 +213,7 @@ interface DeviceAuthenticator {
210213

211214
}
212215

213-
fun DeviceAuthenticator.initialize(userId: String, prompt: Prompt): DeviceAuthenticator {
216+
fun DeviceAuthenticator.initialize(userId: String, authenticationValidityDuration: Int, prompt: Prompt): DeviceAuthenticator {
214217

215218
//Inject objects
216219
if (this is BiometricAuthenticator) {
@@ -219,15 +222,15 @@ fun DeviceAuthenticator.initialize(userId: String, prompt: Prompt): DeviceAuthen
219222
prompt.description,
220223
deviceBindAuthenticationType = this.type()))
221224
}
222-
initialize(userId)
225+
initialize(userId, authenticationValidityDuration)
223226
this.prompt(prompt)
224227
return this
225228
}
226229

227-
fun DeviceAuthenticator.initialize(userId: String): DeviceAuthenticator {
230+
fun DeviceAuthenticator.initialize(userId: String, authenticationValidityDuration: Int = 5): DeviceAuthenticator {
228231
//Inject objects
229232
if (this is CryptoAware) {
230-
this.setKey(CryptoKey(userId))
233+
this.setKey(CryptoKey(userId, authenticationValidityDuration))
231234
}
232235
return this
233236
}

0 commit comments

Comments
 (0)