Dynamic Linking

You can leverage the Keyless authentication mechanism to sign unrelated transactions, including Strong customer authentication (SCA) transactions.

Payment service providers compliant with SCA PSD2 dynamic linking are required to:

  • Generate an authentication code specific to the amount of the payment transaction and the payee agreed to by the payer when initiating the transaction

  • Make the payer aware of the amount of the payment transaction, and of the payee

Keyless helps you by:

  • protecting the authentication code that you use for dynamic linking.

  • displaying a custom screen with information to make the payer aware of details of the transaction.

Keyless is not a payment service provider. It will not verify that information you provide to make the payer aware is the same information you tie to your authentication code.

Strong customer authentication (SCA)

By adding Keyless to your checkout flow you also benefit from Keyless Passwordless Multi Factor Authentication (MFA).

SCA requires authentication to use at least two of the following three elements.

  • Something that only the customer knows. For example, a password or PIN.

  • Something that only the customer has. For example, a mobile phone or hardware token.

  • Something that the customer is. For example, a biometric such as a fingerprint or face.

With Keyless Passwordless MFA you can satisfy the last two points from the list above.

SCA Compliant Dynamic Linking

The following sections contain some examples on implementing SCA with Keyless.

Display custom information (optional)

If you're generating your own display, skip this section.

If you're using the Keyless SDK to display the screen, you know the UX will be consistent with the "Authentication" UX preented to the payer when authenticating with biometric data.

Keyless can display a custom screen containing a list of labels and associated information on your behalf. You display the Keyless "Approval Screen" using the API showApprovalScreen.

// replace key:value with the label:info you want to display to payer
val jsonArrayPayload = "[{"key1":"value1"},{"key2":"value2"},{"key3":"value3"}]"

val result = Keyless.showApprovalScreen(
  jsonArrayPayload = jsonArrayPayload
)

when(result){
  is Keyless.KeylessResult.Success -> // perform authentication
  is Keyless.KeylessResult.Failure -> // handle errors
}

The showApprovalScreen API will show a custom screen to the payer. The payer can "Approve" or "Cancel" the transaction.

When the payer clicks on "Approve" the Keyless screen is dismissed. Payer will see your app UI until you call the next Keyles API. We recommend to give feedback to the payer that transaction data is being processed and that authentication will start shortly. You can use a loader indicator for example.

SCA tied to the authentication code

Once the payer approves the transaction data, Keyless returns a successful result from the showApprovalScreen API.

The next steps are to:

  1. Authenticate the payer with the device factor and the biometric factor using Keyless MFA.

  2. Tie the transaction data to the Keyless MFA

To authenticate the payer with the device factor and the biometric factor using Keyless MFA, call Keyless.authenticate section.

To tie the transaction data to the Keyless MFA, populate parameters of the authentication configuration AuthConfig by preparing the transaction data you displayed to the payer, add the authentication code or any other information you did not display but you want to keep in the transaction you are about to authenticate. For example, add the "authentication code".

Keyless can produce a signed JWT containing a claim titled td (transaction data) that contains any payload associated with the transaction. You may want to save the transaction amount, the payee, the payer and the authentication code. You are free to decide the formatting you prefer as long as it is a valid string.

//Keyless adds a td claim to the JWTs containing the data you specify
val transactionData = "<your custom data e.g. authentication code>"

// if you want to authenticate with biometric
val biomAuthConfig = BiomAuthConfig(transactionData = transactionData)
// if you want to authenticate with pin
val pinAuthConfig = PinAuthConfig(pin = "1234", transactionData = transactionData)

// perform the authentication
Keyless.authenticate(
    configuration = biomAuthConfig, // pinAuthConfig if you use pin
    onCompletion = { /*TODO: process result*/ }
)

Verify the transaction

If the authentication is successful, Keyless returns a signed JWT.

// JWT header
{
  "alg": "ES256",
  "typ": "JWT",
  "kid": "PIN/FACE"
}
// JWT payload
{
  "iat": 1720519812,
  "td": "your custom data e.g. authentication code",
  "version": "1.1.0",
  "sub": "keyless_id"
}

Verify the JWT using the public key from the key management section.

Congrats, you just performed a Strong Customer Authentication tying the authentication code to a transaction.

Last updated