Set up a customer's device for secure payments

Link a customer's registered device to their bank account so they can approve future payments securely.

Use this operation when a customer gives permission for Blinc to use one of their registered devices for future payments. The bank checks the customer's permission, records the device's public key, and links that device to the customer's account. The customer must complete this setup before approving a payment from that account.

Only one device can be active for a customer at a time. When a new device is successfully provisioned, the bank automatically unprovisions the customer's previous active device and records the reason as DEVICE_CHANGED. The previous device can no longer be used for future debit authorization. The new device becomes the active device.

Request

Blinc sends the request as an encrypted POST to the URL agreed with the bank during onboarding. After the bank decrypts the request, it receives the following information.

{
  "clientReference": "prov-20260907-0001",
  "customer": {
    "customerName": "Ada Okafor",
    "idValue": "12345678901",
    "idType": "BVN"
  },
  "account": { "currency": "NGN" },
  "device": {
    "id": "device-ada-01",
    "name": "Ada's iPhone",
    "platform": "IOS",
    "authContext": "DEVICE_LOCAL_AUTH",
    "authIdentity": "CUSTOMER_DEVICE",
    "authHardware": "SECURE_ENCLAVE",
    "key": {
      "value": "MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEOByrQhbf5I4dHCzqfbtyge7PwsVEnlhETFwRT18OOtEzmCg0IK9A8rSLZNGH69ZjQsNKqoTR+okYSVECbH04HA==",
      "purpose": "debit-authorization",
      "algorithm": "ECDSA_P256"
    }
  },
  "institution": {
    "institutionCode": "EXAMPLE-001",
    "InstitutionConsentToken": "test-token-issued-by-example-institution"
  }
}

Field reasons and validation

FieldWhy it is neededRequired validation
clientReferenceCorrelates this request with the response and the institution's audit/reconciliation record.Non-empty string, at most 100 characters. A repeated value is not a new provisioning attempt.
customer.customerNameGives the institution a human-readable attribute for validation and audit.Non-empty string, at most 200 characters; do not use it as the sole identity check.
customer.idValueBinds the consent and device to the intended customer.Non-empty string, at most 100 characters; match it to the institution-issued consent.
customer.idTypeTells the institution how to interpret idValue.Use a supported enum: BVN or NIN. Do not assume other identifier types are accepted.
account.currencyEstablishes the currency context for the provisioning record.Three uppercase letters, such as NGN. The request does not contain an account number.
device.idDistinguishes this registered device from another device owned by the same customer.Non-empty string, at most 50 characters; bind it to the request's device record.
device.nameProvides a human-readable label for device management and support.Non-empty string, at most 200 characters.
device.platformIdentifies the operating-system family relevant to device-key handling.Use IOS or ANDROID.
device.authContextStates how the device authenticates the customer.Must be DEVICE_LOCAL_AUTH.
device.authIdentityStates whose credential is being registered.Must be CUSTOMER_DEVICE.
device.authHardwareRecords the secure hardware basis for the device key.Use SECURE_ENCLAVE, STRONGBOX, or TEE, as reported by the device.
device.key.valueSupplies the public half of the key pair used to verify future debit signatures.Non-empty, at most 4096 characters, and consistent with algorithm; never send the private key.
device.key.purposePrevents a key intended for another flow from being accepted for debits.Must be debit-authorization.
device.key.algorithmTells the institution how to parse and verify the public key.Use RSA_2048, ECDSA_P256, or ED25519.
institution.institutionCodeScopes the request to the institution that issued consent and owns the account context.Non-empty, at most 50 characters; validate against configured institution identity.
institution.InstitutionConsentTokenProves that the institution authenticated the customer and authorized this provisioning.Non-empty, at most 4096 characters; it must be valid, customer-bound, in scope, and unused.

The customer identifier and consent are sensitive. The request is encrypted to protect them while they are being sent. Before linking the device to the account, verify the request signature and confirm that the signed information has not been changed.

What happens at the bank

The bank handles every provisioning request in this order:

  1. Check the security headers described in Set up security and keys.
  2. Decrypt the request and verify that its signature is valid.
  3. Check that the request is recent and that the consent token and clientReference have not already been used.
  4. Confirm that the customer's permission belongs to this customer, this bank, and this payment purpose.
  5. Check the customer details, currency, device information, and public key.

First device for the customer

If the customer has no active device credential, the bank saves the new device-account relationship and marks the request as provisioned. The bank returns the account details and the new deviceCredentialProvisionId to Blinc.

Replacing an existing device

If the customer already has an active device credential, the bank first marks that credential as unprovisioned with reason code DEVICE_CHANGED. It then saves the new device-account relationship and returns the new deviceCredentialProvisionId. Only the new device remains active for future debit authorization.

The bank makes these changes together. If any validation fails, it must not create the new relationship or disable the existing one. It returns a protected rejection explaining why provisioning could not be completed.

Response from the bank

If the setup succeeds, the response gives Blinc the identifier it must use when the customer later approves a payment. It also gives Blinc the account name and number confirmed by the bank.

{
  "clientReference": "prov-20260907-0001",
  "deviceCredentialProvisionId": "7f2c1a9e-3b44-4d21-9c66-0a1b2c3d4e5f",
  "account": {
    "accountName": "Ada Okafor",
    "accountNumber": "0123456789"
  },
  "status": "provisioned",
  "provisioningTimestamp": "2026-09-07T12:00:00Z"
}
FieldWhy it is needed
clientReferenceLets Blinc match the outcome to the exact request it initiated.
deviceCredentialProvisionIdIdentifies the accepted persisted binding and is reused on later debit authorization. It is not the consent token.
account.accountNameReturns the institution-authoritative name associated with the binding.
account.accountNumberReturns the institution-authoritative account number; Blinc does not submit it in this request.
statusStates the business outcome explicitly: provisioned, unprovisioned, or rejected.
provisioningTimestampRecords when the outcome was produced, using a UTC timestamp ending in Z.

If the setup is rejected, return status: "rejected", leave deviceCredentialProvisionId empty, and include the required account object with its account name and number fields. Return the original clientReference so Blinc can match the response to its request.

When the setup fails

Reject the request when required information is missing or invalid, the permission has expired or was already used, the customer does not match the permission, the bank code is wrong, the device details do not agree, or the public key is unsupported. A missing security header is a security failure. In every case, return a protected response that tells Blinc whether the setup was accepted or rejected.

Blinc does not resend this setup request. After a rejection or timeout, the customer must start again and the bank must issue new permission. Do not reuse the previous permission or treat a repeated clientReference as permission to create another device-account relationship.


Did this page help you?