How to Accept Digital Credentials (W3C, SD-JWT VC mDL) via OID4VC using External Signatures with walt.id

TL;DR

Learn how to accept digital credentials (W3C, SD-JWT VC, mDL) via OID4VCI using external signatures with walt.id's Wallet API, including the prepare/submit flow and creating proof of possession tokens.

What you'll learn

  • Use the prepare/submit flow for accepting credentials with external signature management
  • Create proof of possession tokens (JWT or CWT) for credential offers
  • Handle external signature flows for W3C, SD-JWT VC, and mDL credential formats

There are several methods by which a user can receive a credential into their wallet, and all are supported by the wallet API:

  1. User may receive a direct link, which opens the wallet and prompts credential acceptance.
  2. A website may display a QR code for the user to scan and accept the credential.
  3. The user may manually input an offer URL string into a text field.

Irrespective of the chosen method, these are just different ways of receiving, parsing and fulfilling a request URL.

Credential Offer URL

A credential offer URL is a standardized method, as per the OID4VCI specification, to communicate the issuance of credentials between issuer and wallet. This URL can take various forms, such as a QR code or a link, and generally begins with openid-credential-offer://.

Example Offer URL

openid-credential-offer://issuer.portal.walt.id/?credential_offer=<credential_offer>

Within the URL, a query parameter credential_offer provides the actual offer as a JSON object.

Example of a Credential Offer Object

{
  "credential_issuer": "https://issuer.demo.walt.id",
  // This is the URL of the issuer of the credential(s)
  "credential_configuration_ids": [
    // identifies specific credentials that the Credential Issuer is offering.
    "OpenBadgeCredential_jwt_vc_json"
  ],
  "grants": {
    // Specifies how the credentials can be obtained
    "authorization_code": {
      "issuer_state": "5380b758-9778-4a4c-908a-0ad921516e80"
      // Contains an issuer_state, a unique identifier for the grant
    },
    "urn:ietf:params:oauth:grant-type:pre-authorized_code": {
      // Provides details for a pre-authorized code grant type,
      //including the actual pre-authorized_code and a flag user_pin_required indicating whether a PIN is required
      // for user authentication.
      "pre-authorized_code": "eyJhbGciOiJFZERTQSJ9.eyJzdWIiOiI1MzgwYjc1OC05Nzc4LTRhNGMtOTA4YS0wYWQ5MjE1MTZlODAiLCJpc3MiOiJodHRwczovL2lzc3Vlci5wb3J0YWwud2FsdC5pZCIsImF1ZCI6IlRPS0VOIn0.DeYsZgnx4oBmIa25_cnBFazdrVkSGiDqFxSGL88lKlZkpgcJUcgFBMBc-n8XFdGbJ-gHFsGxTJ4rdamqTmIPCA"
    }
  }
}

Accepting the Offer

To receive offered credentials, the wallet must provide the issuer with a proof of possession.

When using external signatures:

  1. In the regular Wallet API setup, the API manages the keys and can generate the proof of possession in the background.
  2. With external signatures, the proof of possession must instead be created in the system that manages the keys.
  3. Because of this, the regular useOfferRequest endpoint is split into two steps when working with external signatures.

The /prepare step:

  • Lets the Wallet API gather all required information.
  • Returns structured data that should either be signed or passed to the next step /submit.
  • Prepares everything needed to finalize the exchange between wallet and issuer so credentials can be received and stored in the specified wallet account.
  • Ensures the proof of possession, along with other required information, is sent to the issuer.

Please note that the external signatures are an optional feature of the Wallet API. It needs to be enabled via the feature.conf by providing external-signature-endpoints in the enabledFeatures array. Learn more here.


W3C
SD-JWT VC (IETF)
mDL

1. Prepare

CURL

Endpoint:/{wallet}/exchange/external_signatures/offer/prepare

curl -X 'POST' \
  'http://0.0.0.0:7001/wallet-api/{wallet}/exchange/external_signatures/offer/prepare' \
  -H 'accept: */*' \
  -H 'Content-Type: application/json' \
  -d '{
  "did": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ",
  "offerURL": "openid-credential-offer://localhost:22222/?credential_offer_uri=http%3A%2F%2Flocalhost%3A22222%2Fopenid4vc%2FcredentialOffer%3Fid%3D8030eb87-fa89-4820-ad36-8e89cc9ccdfe"
}'

Path Parameters

  • wallet: - You can receive the needed wallet id parameter via the /wallet-api/wallet/accounts/wallets endpoint.

Body Parameters

  • did - DID to which the credential should be bound to.
  • offerURL - the credential offer from the issuer.

Example Response

{
  "did": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ",
  "offerURL": "openid-credential-offer://localhost:22222/?credential_offer_uri=http%3A%2F%2Flocalhost%3A22222%2Fopenid4vc%2FcredentialOffer%3Fid%3D8030eb87-fa89-4820-ad36-8e89cc9ccdfe",
  "accessToken": "eyJhbGciOiJFZERTQSJ9.eyJzdWIiOiI4MDMwZWI4Ny1mYTg5LTQ4MjAtYWQzNi04ZTg5Y2M5Y2NkZmUiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiYXVkIjoiQUNDRVNTIn0.GpB9QZ-ZgCSNxBzlnkf_RBKmfMI15wH5rR2gW4EfLa640gOo9taaMLgYKax8f8kOgd5byvEf6hmGhWyGt7xTCQ",
  "offeredCredentialsProofRequests": [
    {
      "offeredCredential": {
        "format": "jwt_vc_json",
        "credential_definition": {
          "type": [
            "VerifiableCredential",
            "OpenBadgeCredential"
          ]
        },
        "cryptographic_binding_methods_supported": [
          "did"
        ],
        "customParameters": {}
      },
      "proofOfPossessionParameters": {
        "proofType": "jwt",
        "header": {
          "typ": "openid4vci-proof+jwt",
          "kid": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ#0"
        },
        "payload": {
          "aud": "http://localhost:22222",
          "iat": 1727417971,
          "nonce": "4d513194-fa61-4099-9bbc-3fb0808ca4f1"
        }
      }
    }
  ],
  "credentialIssuer": "http://localhost:22222"
}

The response provides all the information required for the next /submit step:

  • offeredCredentialsProofRequests – list of credentials offered by the issuer.
  • For each offered credential, the offeredCredential block describes the credential itself.
  • Each entry also includes proofOfPossessionParameters, which define the proof to generate and contain the following attributes:
  • proofType - the type of proof required. In our case jwt.
  • header - header for to be signed jwt.
  • payload - payload for to be signed jwt.

2. Creating Proof of Possession

To create the proof of possession:

  1. Create a jwt for each offered credential using the header and payload from the proofOfPossessionParameters in the response.
  2. In the example above, only one credential (OpenBadgeCredential) is offered, so you only need a single signed jwt.

3. Submit

With the /submit endpoint, you:

  • Send most of the information returned by the /prepare endpoint.
  • Include the proof-of-possession jwt created in step 2.

Preparing the body of the request

  1. We copy over the value did, offerURL, accessToken and credentialIssuer from the response to /prepare.
request body
{
  "did": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ",
  "offerURL": "openid-credential-offer://localhost:22222/?credential_offer_uri=http%3A%2F%2Flocalhost%3A22222%2Fopenid4vc%2FcredentialOffer%3Fid%3Db953cc8a-4fb3-449b-9ab0-c9c281152e1b",
  "accessToken": "eyJhbGciOiJFZERTQSJ9.eyJzdWIiOiJiOTUzY2M4YS00ZmIzLTQ0OWItOWFiMC1jOWMyODExNTJlMWIiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiYXVkIjoiQUNDRVNTIn0.ygzp7_r-0SVcSzHTdLSTa_kt3A3iNM98wXYlJagoiPy9wzDDvE654rp_K5-uSZWUBHFrAOOGZ-28b9cmv1AFBg",
  "credentialIssuer": "http://localhost:22222"
}
  1. We add an array called offeredCredentialProofsOfPossession including all offered credentials with the related proof type and the signed jwt from step 2 "Creating Proof of Possession".
request body
{
  ...
  "offeredCredentialProofsOfPossession": [
    {
      "offeredCredential": {
        "format": "jwt_vc_json",
        "credential_definition": {
          "type": [
            "VerifiableCredential",
            "OpenBadgeCredential"
          ]
        },
        "cryptographic_binding_methods_supported": [
          "did"
        ]
      },
      "proofType": "jwt",
      "signedProofOfPossession": "eyJraWQiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEjMCIsInR5cCI6Im9wZW5pZDR2Y2ktcHJvb2Yrand0IiwiYWxnIjoiRVMyNTYifQ.eyJpc3MiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEiLCJhdWQiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiaWF0IjoxNzI3MDk0NjY2LCJub25jZSI6ImIzNTk3MmUwLTAzM2EtNDE5My1iOTE3LTBlZmZmMTljMWZkMCJ9.gveI7M2CNeCX8qdmFyToatLLigmyMNn-rgxjDHBFGz-BRr0PGi0j1KDOeDY--K8heXVD0E3LBL2cI1ap5Sl3lw"
    }
  ]
  ...
}

Object in offeredCredentialProofsOfPossession Array

{
  "offeredCredential": {
    "format": "jwt_vc_json",
    "credential_definition": {
      "type": [
        "VerifiableCredential",
        "OpenBadgeCredential"
      ]
    },
    "cryptographic_binding_methods_supported": [
      "did"
    ]
  },
  "proofType": "jwt",
  "signedProofOfPossession": "eyJraWQiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEjMCIsInR5cCI6Im9wZW5pZDR2Y2ktcHJvb2Yrand0IiwiYWxnIjoiRVMyNTYifQ.eyJpc3MiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEiLCJhdWQiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiaWF0IjoxNzI3MDk0NjY2LCJub25jZSI6ImIzNTk3MmUwLTAzM2EtNDE5My1iOTE3LTBlZmZmMTljMWZkMCJ9.gveI7M2CNeCX8qdmFyToatLLigmyMNn-rgxjDHBFGz-BRr0PGi0j1KDOeDY--K8heXVD0E3LBL2cI1ap5Sl3lw"
}
  • offeredCredential - Holds the same value as the object describing one offered credential in the offeredCredentialsProofRequests array of the /prepare response.
  • cryptographic_binding_methods_supported - Mirrors the corresponding value from the offeredCredentialsProofRequests entry in the /prepare response.
  • proofType - Will be jwt.
  • signedProofOfPossession - The signed proof of possession (jwt) from step 2 for the related credential.

For the offeredCredentialProofsOfPossession array:

  • Include one object for each credential offered by the issuer.
  • Ensure the array has the same length as the offeredCredentialsProofRequests array returned by /prepare.

Final body

request body
{
  "did": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ",
  "offerURL": "openid-credential-offer://localhost:22222/?credential_offer_uri=http%3A%2F%2Flocalhost%3A22222%2Fopenid4vc%2FcredentialOffer%3Fid%3D8030eb87-fa89-4820-ad36-8e89cc9ccdfe",
  "accessToken": "eyJhbGciOiJFZERTQSJ9.eyJzdWIiOiI4MDMwZWI4Ny1mYTg5LTQ4MjAtYWQzNi04ZTg5Y2M5Y2NkZmUiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiYXVkIjoiQUNDRVNTIn0.GpB9QZ-ZgCSNxBzlnkf_RBKmfMI15wH5rR2gW4EfLa640gOo9taaMLgYKax8f8kOgd5byvEf6hmGhWyGt7xTCQ",
  "offeredCredentialProofsOfPossession": [
    {
      "offeredCredential": {
        "format": "jwt_vc_json",
        "credential_definition": {
          "type": [
            "VerifiableCredential",
            "OpenBadgeCredential"
          ]
        },
        "cryptographic_binding_methods_supported": [
          "did"
        ]
      },
      "proofType": "jwt",
      "signedProofOfPossession": "eyJraWQiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pUTNabFV6RlpkV2RVTldWMlZub3hPR3N3V0hCalZHUXRVVlZzUzFBeFJ6ZENkVEpKTWtwb1NqRjJZeUlzSW5naU9pSkNlR04yZDBsQlZEaHVkelJ0ZGpWdFVEaFNUemxyWW1jM04yNXNiVlpvT0c1UmNXWlZVRXR1UkRWQklpd2llU0k2SWt0aFUwMXNlVEJSUVVoU1F6WktNWEZEUkRsb1JrWm5WMGRYTVhwMWNFeHdVM1p0Vkd0SE1ESm1OSGNpZlEjMCIsInR5cCI6Im9wZW5pZDR2Y2ktcHJvb2Yrand0IiwiYWxnIjoiRVMyNTYifQ.eyJhdWQiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiaWF0IjoxNzI3NDE3OTcxLCJub25jZSI6IjRkNTEzMTk0LWZhNjEtNDA5OS05YmJjLTNmYjA4MDhjYTRmMSJ9.-NOvj6bfl0l8_BSxPR3UAyO-KkZ4zdfPZ401GNZl8DWg4MCtZN3lWIdnPBsqTY1aAiYfN3symtMzhdtCqpivAA"
    }
  ],
  "credentialIssuer": "http://localhost:22222"
}

Making the Request

CURL

Endpoint: wallet-api/{wallet}/exchange/external_signatures/offer/submit

curl -X 'POST' \
  'http://0.0.0.0:7001/wallet-api/{wallet}/exchange/external_signatures/offer/submit' \
  -H 'accept: */*' \
  -H 'Content-Type: application/json' \
  -d '{
  "did": "did:jwk:eyJrdHkiOiJFQyIsImNydiI6IlAtMjU2Iiwia2lkIjoiQ3ZlUzFZdWdUNWV2VnoxOGswWHBjVGQtUVVsS1AxRzdCdTJJMkpoSjF2YyIsIngiOiJCeGN2d0lBVDhudzRtdjVtUDhSTzlrYmc3N25sbVZoOG5RcWZVUEtuRDVBIiwieSI6IkthU01seTBRQUhSQzZKMXFDRDloRkZnV0dXMXp1cExwU3ZtVGtHMDJmNHcifQ",
  "offerURL": "openid-credential-offer://localhost:22222/?credential_offer_uri=http%3A%2F%2Flocalhost%3A22222%2Fopenid4vc%2FcredentialOffer%3Fid%3D8030eb87-fa89-4820-ad36-8e89cc9ccdfe",
  "accessToken": "eyJhbGciOiJFZERTQSJ9.eyJzdWIiOiI4MDMwZWI4Ny1mYTg5LTQ4MjAtYWQzNi04ZTg5Y2M5Y2NkZmUiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiYXVkIjoiQUNDRVNTIn0.GpB9QZ-ZgCSNxBzlnkf_RBKmfMI15wH5rR2gW4EfLa640gOo9taaMLgYKax8f8kOgd5byvEf6hmGhWyGt7xTCQ",
  "offeredCredentialProofsOfPossession": [
    {
      "offeredCredential": {
        "format": "jwt_vc_json",
        "credential_definition": {
          "type": [
            "VerifiableCredential",
            "OpenBadgeCredential"
          ]
        },
        "cryptographic_binding_methods_supported": [
          "did"
        ]
      },
      "proofType": "jwt",
      "signedProofOfPossession": "eyJraWQiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pUTNabFV6RlpkV2RVTldWMlZub3hPR3N3V0hCalZHUXRVVlZzUzFBeFJ6ZENkVEpKTWtwb1NqRjJZeUlzSW5naU9pSkNlR04yZDBsQlZEaHVkelJ0ZGpWdFVEaFNUemxyWW1jM04yNXNiVlpvT0c1UmNXWlZVRXR1UkRWQklpd2llU0k2SWt0aFUwMXNlVEJSUVVoU1F6WktNWEZEUkRsb1JrWm5WMGRYTVhwMWNFeHdVM1p0Vkd0SE1ESm1OSGNpZlEjMCIsInR5cCI6Im9wZW5pZDR2Y2ktcHJvb2Yrand0IiwiYWxnIjoiRVMyNTYifQ.eyJhdWQiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiaWF0IjoxNzI3NDE3OTcxLCJub25jZSI6IjRkNTEzMTk0LWZhNjEtNDA5OS05YmJjLTNmYjA4MDhjYTRmMSJ9.-NOvj6bfl0l8_BSxPR3UAyO-KkZ4zdfPZ401GNZl8DWg4MCtZN3lWIdnPBsqTY1aAiYfN3symtMzhdtCqpivAA"
    }
  ],
  "credentialIssuer": "http://localhost:22222"
}'

Path Parameters

  • wallet: - You can receive the needed wallet id parameter via the /wallet-api/wallet/accounts/wallets endpoint.

Body Parameters

  • did - value copied from response to /prepare
  • offerURL - value copied from response to /prepare
  • accessToken - value copied from response to /prepare
  • credentialIssuer - value copied from response to /prepare
  • offeredCredentialProofsOfPossession - array of offered credentials with proofs.
Expand To Learn More

Object in offeredCredentialProofsOfPossession Array

{
  "offeredCredential": {
    "format": "jwt_vc_json",
    "credential_definition": {
      "type": [
        "VerifiableCredential",
        "OpenBadgeCredential"
      ]
    },
    "cryptographic_binding_methods_supported": [
      "did"
    ]
  },
  "proofType": "jwt",
  "signedProofOfPossession": "eyJraWQiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEjMCIsInR5cCI6Im9wZW5pZDR2Y2ktcHJvb2Yrand0IiwiYWxnIjoiRVMyNTYifQ.eyJpc3MiOiJkaWQ6andrOmV5SnJkSGtpT2lKRlF5SXNJbU55ZGlJNklsQXRNalUySWl3aWEybGtJam9pYTJrMFduaGlXRVJqTFVjM1QxRjVNa3gwY1d4Wk5IRkxVbXQ2UkdKTVF6TmhjWE5rVTFSNlRFcGlUU0lzSW5naU9pSlhiMmM1YWtaVllqbElkMWMzYWpsYVF6VjZZakZVZHkxWE5HMUpaVzVETUZkZlZXNWtjbXh5YVZoVklpd2llU0k2SWtoS2FWUkRjR0ZhVG5oM2JHUkpYMWxoVDFkVlVsTjZTVTVQT0daak0zQnVibEZXVWpoclREVjRNVGdpZlEiLCJhdWQiOiJodHRwOi8vbG9jYWxob3N0OjIyMjIyIiwiaWF0IjoxNzI3MDk0NjY2LCJub25jZSI6ImIzNTk3MmUwLTAzM2EtNDE5My1iOTE3LTBlZmZmMTljMWZkMCJ9.gveI7M2CNeCX8qdmFyToatLLigmyMNn-rgxjDHBFGz-BRr0PGi0j1KDOeDY--K8heXVD0E3LBL2cI1ap5Sl3lw"
}
  • offeredCredential - Holds the same value as the object describing one offered credential in the offeredCredentialsProofRequests array of response provided by /prepare.
  • cryptographic_binding_methods_supported - Holds the same value as the object describing one offered credential in the offeredCredentialsProofRequests array of response provided by /prepare.
  • proofType - Will be jwt
  • signedProofOfPossession - the signed proof of possession (jwt) from step 2 for the related credential.

Example Response

[
  {
    "wallet": "6e802709-7d60-4dd2-a599-6c775c8a66eb",
    "id": "urn:uuid:90271bc9-8879-4565-830a-6d01596dbb9c",
    "document": "eyJraWQiOiJkaWQ6a2V5Ono2TWtqb1JocTFqU05KZExpcnVTWHJGRnhhZ3FyenRaYVhIcUhHVVRLSmJjTnl3cCIsInR5cCI6IkpXVCIsImFsZyI6IkVkRFNBIn0.eyJpc3MiOiJkaWQ6a2V5Ono2TWtqb1JocTFqU05KZExpcnVTWHJGRnhhZ3FyenRaYVhIcUhHVVRLSmJjTnl3cCIsInN1YiI6ImRpZDpqd2s6ZXlKcmRIa2lPaUpQUzFBaUxDSmpjbllpT2lKRlpESTFOVEU1SWl3aWEybGtJam9pTVMxSk9FdHBPSGN4TkRGRGNpMVRaRUpHYUMxWVoyaHlUMjlHVVV0cFZGQTVXSEZtV1VVeGNXYzRSU0lzSW5naU9pSlJXVFZ3WlZKbmVucG9kRTUwVTJKNFQwZEtOMGRRVUhWa1NGVkxaRmwzYzFOTU4xb3lUVWxJYjJ4SkluMCIsInZjIjp7IkBjb250ZXh0IjpbImh0dHBzOi8vd3d3LnczLm9yZy8yMDE4L2NyZWRlbnRpYWxzL3YxIiwiaHR0cHM6Ly9wdXJsLmltc2dsb2JhbC5vcmcvc3BlYy9vYi92M3AwL2NvbnRleHQuanNvbiJdLCJpZCI6InVybjp1dWlkOjkwMjcxYmM5LTg4NzktNDU2NS04MzBhLTZkMDE1OTZkYmI5YyIsInR5cGUiOlsiVmVyaWZpYWJsZUNyZWRlbnRpYWwiLCJPcGVuQmFkZ2VDcmVkZW50aWFsIl0sIm5hbWUiOiJKRkYgeCB2Yy1lZHUgUGx1Z0Zlc3QgMyBJbnRlcm9wZXJhYmlsaXR5IiwiaXNzdWVyIjp7InR5cGUiOlsiUHJvZmlsZSJdLCJuYW1lIjoiSm9icyBmb3IgdGhlIEZ1dHVyZSAoSkZGKSIsInVybCI6Imh0dHBzOi8vd3d3LmpmZi5vcmcvIiwiaW1hZ2UiOiJodHRwczovL3czYy1jY2cuZ2l0aHViLmlvL3ZjLWVkL3BsdWdmZXN0LTEtMjAyMi9pbWFnZXMvSkZGX0xvZ29Mb2NrdXAucG5nIiwiaWQiOiJkaWQ6a2V5Ono2TWtqb1JocTFqU05KZExpcnVTWHJGRnhhZ3FyenRaYVhIcUhHVVRLSmJjTnl3cCJ9LCJjcmVkZW50aWFsU3ViamVjdCI6eyJ0eXBlIjpbIkFjaGlldmVtZW50U3ViamVjdCJdLCJhY2hpZXZlbWVudCI6eyJpZCI6InVybjp1dWlkOmFjMjU0YmQ1LThmYWQtNGJiMS05ZDI5LWVmZDkzODUzNjkyNiIsInR5cGUiOlsiQWNoaWV2ZW1lbnQiXSwibmFtZSI6IkpGRiB4IHZjLWVkdSBQbHVnRmVzdCAzIEludGVyb3BlcmFiaWxpdHkiLCJkZXNjcmlwdGlvbiI6IlRoaXMgd2FsbGV0IHN1cHBvcnRzIHRoZSB1c2Ugb2YgVzNDIFZlcmlmaWFibGUgQ3JlZGVudGlhbHMgYW5kIGhhcyBkZW1vbnN0cmF0ZWQgaW50ZXJvcGVyYWJpbGl0eSBkdXJpbmcgdGhlIHByZXNlbnRhdGlvbiByZXF1ZXN0IHdvcmtmbG93IGR1cmluZyBKRkYgeCBWQy1FRFUgUGx1Z0Zlc3QgMy4iLCJjcml0ZXJpYSI6eyJ0eXBlIjoiQ3JpdGVyaWEiLCJuYXJyYXRpdmUiOiJXYWxsZXQgc29sdXRpb25zIHByb3ZpZGVycyBlYXJuZWQgdGhpcyBiYWRnZSBieSBkZW1vbnN0cmF0aW5nIGludGVyb3BlcmFiaWxpdHkgZHVyaW5nIHRoZSBwcmVzZW50YXRpb24gcmVxdWVzdCB3b3JrZmxvdy4gVGhpcyBpbmNsdWRlcyBzdWNjZXNzZnVsbHkgcmVjZWl2aW5nIGEgcHJlc2VudGF0aW9uIHJlcXVlc3QsIGFsbG93aW5nIHRoZSBob2xkZXIgdG8gc2VsZWN0IGF0IGxlYXN0IHR3byB0eXBlcyBvZiB2ZXJpZmlhYmxlIGNyZWRlbnRpYWxzIHRvIGNyZWF0ZSBhIHZlcmlmaWFibGUgcHJlc2VudGF0aW9uLCByZXR1cm5pbmcgdGhlIHByZXNlbnRhdGlvbiB0byB0aGUgcmVxdWVzdG9yLCBhbmQgcGFzc2luZyB2ZXJpZmljYXRpb24gb2YgdGhlIHByZXNlbnRhdGlvbiBhbmQgdGhlIGluY2x1ZGVkIGNyZWRlbnRpYWxzLiJ9LCJpbWFnZSI6eyJpZCI6Imh0dHBzOi8vdzNjLWNjZy5naXRodWIuaW8vdmMtZWQvcGx1Z2Zlc3QtMy0yMDIzL2ltYWdlcy9KRkYtVkMtRURVLVBMVUdGRVNUMy1iYWRnZS1pbWFnZS5wbmciLCJ0eXBlIjoiSW1hZ2UifX0sImlkIjoiZGlkOmp3azpleUpyZEhraU9pSlBTMUFpTENKamNuWWlPaUpGWkRJMU5URTVJaXdpYTJsa0lqb2lNUzFKT0V0cE9IY3hOREZEY2kxVFpFSkdhQzFZWjJoeVQyOUdVVXRwVkZBNVdIRm1XVVV4Y1djNFJTSXNJbmdpT2lKUldUVndaVkpuZW5wb2RFNTBVMko0VDBkS04wZFFVSFZrU0ZWTFpGbDNjMU5NTjFveVRVbEliMnhKSW4wIn0sImlzc3VhbmNlRGF0ZSI6IjIwMjQtMDktMjRUMDY6NTg6NTUuOTAzOTQ2Nzc5WiIsImV4cGlyYXRpb25EYXRlIjoiMjAyNS0wOS0yNFQwNjo1ODo1NS45MDQwOTgxNzBaIn0sImp0aSI6InVybjp1dWlkOjkwMjcxYmM5LTg4NzktNDU2NS04MzBhLTZkMDE1OTZkYmI5YyIsImV4cCI6MTc1ODY5NzEzNSwiaWF0IjoxNzI3MTYxMTM1LCJuYmYiOjE3MjcxNjExMzV9.XmN-rsNKlo-umayMOcrclGWcXYCEZF0warrJ7eV3juuTxHJyoxdoQ9YrWGv8rs6Om6jegWbUulbpu5amjo9ECw",
    "disclosures": "",
    "addedOn": "2024-09-24T06:58:55.909707051Z",
    "format": "jwt_vc_json"
  }
]

The response indicates that the credential was stored successfully in the wallet.

Last updated on November 18, 2025