diff --git a/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/index.md b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/index.md
index 9585744f..827e94dc 100644
--- a/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/index.md
+++ b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/index.md
@@ -10,3 +10,4 @@ object [Companion](index.md)
| Name | Summary |
|---------------------|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| [invoke](invoke.md) | [androidJvm]
operator fun [invoke](invoke.md)(block: [OpenId4VciManager.Config.Builder](../-builder/index.md).() -> [Unit](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)): [OpenId4VciManager.Config](../index.md)
Create an instance of [Config](../index.md) |
+| [make](make.md) | [androidJvm]
fun [make](make.md)(block: [OpenId4VciManager.Config.Builder](../-builder/index.md).() -> [Unit](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)): [OpenId4VciManager.Config](../index.md)
Create an instance of [Config](../index.md) |
diff --git a/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/invoke.md b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/invoke.md
index 412a12f1..b24a2a35 100644
--- a/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/invoke.md
+++ b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/invoke.md
@@ -7,3 +7,11 @@ operator fun [invoke](invoke.md)(block: [OpenId4VciManager.Config.Builder](../-b
-> [Unit](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)): [OpenId4VciManager.Config](../index.md)
Create an instance of [Config](../index.md)
+
+#### Parameters
+
+androidJvm
+
+| | |
+|-------|------------------------------------------------------------|
+| block | the block to configure the [Builder](../-builder/index.md) |
diff --git a/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/make.md b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/make.md
new file mode 100644
index 00000000..8f4e7f0b
--- /dev/null
+++ b/docs/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/make.md
@@ -0,0 +1,17 @@
+//[wallet-core](../../../../../index.md)/[eu.europa.ec.eudi.wallet.issue.openid4vci](../../../index.md)/[OpenId4VciManager](../../index.md)/[Config](../index.md)/[Companion](index.md)/[make](make.md)
+
+# make
+
+[androidJvm]\
+fun [make](make.md)(block: [OpenId4VciManager.Config.Builder](../-builder/index.md).()
+-> [Unit](https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-unit/index.html)): [OpenId4VciManager.Config](../index.md)
+
+Create an instance of [Config](../index.md)
+
+#### Parameters
+
+androidJvm
+
+| | |
+|-------|------------------------------------------------------------|
+| block | the block to configure the [Builder](../-builder/index.md) |
diff --git a/docs/wallet-core/package-list b/docs/wallet-core/package-list
index dba8fb77..21c60500 100644
--- a/docs/wallet-core/package-list
+++ b/docs/wallet-core/package-list
@@ -86,6 +86,7 @@ $dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Conf
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.Builder/withIssuerUrl/#kotlin.String/PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-builder/with-issuer-url.md
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.Companion///PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/index.md
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.Companion/invoke/#kotlin.Function1[eu.europa.ec.eudi.wallet.issue.openid4vci.OpenId4VciManager.Config.Builder,kotlin.Unit]/PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/invoke.md
+$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.Companion/make/#kotlin.Function1[eu.europa.ec.eudi.wallet.issue.openid4vci.OpenId4VciManager.Config.Builder,kotlin.Unit]/PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-companion/make.md
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.LogLevel.Companion///PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-log-level/-companion/index.md
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.LogLevel.Companion/DEBUG/#/PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-log-level/-companion/-d-e-b-u-g.md
$dokka.location:eu.europa.ec.eudi.wallet.issue.openid4vci/OpenId4VciManager.Config.LogLevel.Companion/DEBUG_WITH_HTTP/#/PointingToDeclaration/wallet-core/eu.europa.ec.eudi.wallet.issue.openid4vci/-open-id4-vci-manager/-config/-log-level/-companion/-d-e-b-u-g_-w-i-t-h_-h-t-t-p.md
diff --git a/wallet-core/src/main/java/eu/europa/ec/eudi/wallet/issue/openid4vci/DefaultOpenId4VciManager.kt b/wallet-core/src/main/java/eu/europa/ec/eudi/wallet/issue/openid4vci/DefaultOpenId4VciManager.kt
index 242dcba0..00aa23fd 100644
--- a/wallet-core/src/main/java/eu/europa/ec/eudi/wallet/issue/openid4vci/DefaultOpenId4VciManager.kt
+++ b/wallet-core/src/main/java/eu/europa/ec/eudi/wallet/issue/openid4vci/DefaultOpenId4VciManager.kt
@@ -38,6 +38,7 @@ import org.bouncycastle.util.encoders.Hex
import java.net.URI
import java.util.*
import java.util.concurrent.Executor
+import java.util.concurrent.atomic.AtomicReference
/**
* Default implementation of [OpenId4VciManager].
@@ -224,7 +225,7 @@ internal class DefaultOpenId4VciManager(
).getOrThrow()
val addedDocuments = mutableSetOf()
-
+ val cNonceHolder = AtomicReference().apply { update(authorizedRequest) }
offer.offeredDocuments.forEach { item ->
val issuanceRequest = documentManager
.createIssuanceRequest(item, config.useStrongBoxIfSupported)
@@ -237,10 +238,12 @@ internal class DefaultOpenId4VciManager(
item.configurationIdentifier,
item.configuration,
issuanceRequest,
+ cNonceHolder,
addedDocuments,
onEvent
)
}
+ cNonceHolder.set(null)
onEvent(IssueEvent.Finished(addedDocuments.toList()))
}
}
@@ -271,6 +274,7 @@ internal class DefaultOpenId4VciManager(
* @param credentialConfigurationIdentifier The credential configuration identifier.
* @param credentialConfiguration The credential configuration.
* @param issuanceRequest The issuance request.
+ * @param cNonceHolder The cNonce holder. Holds the fresh cNonce.
* @param addedDocuments The added documents.
* @param onEvent The event listener.
* @throws Exception If an error occurs during the issuance.
@@ -281,6 +285,7 @@ internal class DefaultOpenId4VciManager(
credentialConfigurationIdentifier: CredentialConfigurationIdentifier,
credentialConfiguration: CredentialConfiguration,
issuanceRequest: IssuanceRequest,
+ cNonceHolder: AtomicReference,
addedDocuments: MutableSet,
onEvent: OpenId4VciManager.OnResult
) {
@@ -293,15 +298,17 @@ internal class DefaultOpenId4VciManager(
payload,
credentialConfiguration,
issuanceRequest,
+ cNonceHolder,
addedDocuments,
onEvent
)
is AuthorizedRequest.ProofRequired -> doRequestSingleWithProof(
- authRequest,
+ authRequest.copy(cNonce = cNonceHolder.get()),
payload,
credentialConfiguration,
issuanceRequest,
+ cNonceHolder,
addedDocuments,
onEvent
)
@@ -314,6 +321,7 @@ internal class DefaultOpenId4VciManager(
* @param payload The issuance request payload.
* @param credentialConfiguration The credential configuration.
* @param issuanceRequest The issuance request.
+ * @param cNonceHolder The cNonce holder. Holds the fresh cNonce.
* @param addedDocuments The added documents.
* @param onEvent The event listener.
* @receiver The issuer.
@@ -324,11 +332,14 @@ internal class DefaultOpenId4VciManager(
payload: IssuanceRequestPayload,
credentialConfiguration: CredentialConfiguration,
issuanceRequest: IssuanceRequest,
+ cNonceHolder: AtomicReference,
addedDocuments: MutableSet,
onEvent: OpenId4VciManager.OnResult
) {
logDebug("doRequestSingleNoProof for ${issuanceRequest.documentId}")
- when (val outcome = authRequest.requestSingle(payload).getOrThrow()) {
+ val outcome = authRequest.requestSingle(payload).getOrThrow()
+ cNonceHolder.update(outcome)
+ when (outcome) {
is SubmittedRequest.InvalidProof -> {
logDebug("doRequestSingleNoProof invalid proof")
doRequestSingleWithProof(
@@ -336,6 +347,7 @@ internal class DefaultOpenId4VciManager(
payload,
credentialConfiguration,
issuanceRequest,
+ cNonceHolder,
addedDocuments,
onEvent
)
@@ -361,6 +373,7 @@ internal class DefaultOpenId4VciManager(
* @param payload The issuance request payload.
* @param credentialConfiguration The credential configuration.
* @param issuanceRequest The issuance request.
+ * @param cNonceHolder The cNonce holder. Holds the fresh cNonce.
* @param addedDocuments The added documents.
* @param onEvent The event listener.
* @receiver The issuer.
@@ -371,6 +384,7 @@ internal class DefaultOpenId4VciManager(
payload: IssuanceRequestPayload,
credentialConfiguration: CredentialConfiguration,
issuanceRequest: IssuanceRequest,
+ cNonceHolder: AtomicReference,
addedDocuments: MutableSet,
onEvent: OpenId4VciManager.OnResult
) {
@@ -379,8 +393,7 @@ internal class DefaultOpenId4VciManager(
logDebug("doRequestSingleWithProof proofSigner: ${proofSigner::class.java.name}")
try {
val outcome = authRequest.requestSingle(payload, proofSigner.popSigner).getOrThrow()
- // refresh cNonce for next issuing
-// outcome.cNonce
+ cNonceHolder.update(outcome)
when (outcome) {
is SubmittedRequest.Failed -> {
clearFailedIssuance(issuanceRequest)
@@ -403,6 +416,7 @@ internal class DefaultOpenId4VciManager(
onEvent,
addedDocuments
)
+
}
} catch (e: Throwable) {
@@ -418,6 +432,7 @@ internal class DefaultOpenId4VciManager(
payload,
credentialConfiguration,
issuanceRequest,
+ cNonceHolder,
addedDocuments,
onEvent
)
@@ -437,6 +452,41 @@ internal class DefaultOpenId4VciManager(
}
}
+ /**
+ * Updates the cNonce.
+ * @param authRequest The authorized request.
+ * @receiver The cNonce holder.
+ */
+ private fun AtomicReference.update(authRequest: AuthorizedRequest) {
+ when (authRequest) {
+ is AuthorizedRequest.NoProofRequired -> {}
+ is AuthorizedRequest.ProofRequired -> {
+ val prev = getAndSet(authRequest.cNonce)
+ logDebug("cNonceUpdate: $prev -> ${authRequest.cNonce}")
+ }
+ }
+ }
+
+ /**
+ * Updates the cNonce.
+ * @param submittedRequest The submitted request.
+ * @receiver The cNonce holder.
+ */
+ private fun AtomicReference.update(submittedRequest: SubmittedRequest) {
+ when (submittedRequest) {
+ is SubmittedRequest.Failed -> {}
+ is SubmittedRequest.InvalidProof -> {
+ val prev = getAndSet(submittedRequest.cNonce)
+ logDebug("cNonceUpdate: $prev -> ${submittedRequest.cNonce}")
+ }
+
+ is SubmittedRequest.Success -> {
+ val prev = getAndSet(submittedRequest.cNonce)
+ logDebug("cNonceUpdate: $prev -> ${submittedRequest.cNonce}")
+ }
+ }
+ }
+
/**
* Stores the issued credential.
* @param issuedCredential The issued credential.