New payment URLs
Following the decommissioning of the Payconiq brand in Belgium, these URL changes are essential to ensure compliance and
mark the final phase in aligning our branding with the new Bancontact Pro identity.

Please implement adaptations described here promptly to avoid service interruptions and guarantee the continued acceptance of mobile payments via Bancontact Pay and Wero.

Changes are already available in our pre-production environement and will be rolled out in production starting 11/05/2026

# On a display

## Introduction

On a Display allows you to generate a one-time usage digital QR code  and show it on a consumer-facing screen. Your consumers scan the QR code with their preferred payment application and confirm the transaction.

## Process Flow

The following section outlines the key steps involved in a "On a Display" Instore payment with Bancontact Pro. The process involves several key parties, each playing a specific role in completing the transaction.

### Prerequisites

* **API Key** – This is used to secure the request between the **Merchant’s backend** and **Bancontact Pros backend**. Do not share your API keys in public areas such as online sites or client-side code.
* **Merchant CallbackUrl** (*Optional*) – This URL will be called by Bancontact Pro's backend servers in order to send the status of the payment to the merchant.


### Involved Parties

The following parties participate in a display-based in-store payment with Bancontact Pro:

* **Payer Application**: The consumer's preferred payment app used to complete the transaction.
* **Merchant Frontend**: The consumer-facing screen (e.g., POS or tablet) where the QR code is displayed.
* **Merchant Backend**: The merchant’s server-side system that integrates with Bancontact Pro.
* **Bancontact Pro's Backend**: The backend system responsible for handling payment processing and integration services.


### Step-by-Step Payment Flow

This section outlines a typical **“On a Display”** in-store payment flow using Bancontact Pro. The process begins when the transaction is initiated at the merchant’s location and ends when both the merchant and the consumer receive the final confirmation.

On a Display can be used with or without the **"Void Functionality"**. Void is an intermediary step that allows your backend to remain in the lead of a payment transaction after your consumer has confirmed the payment.

With **Void**, you will be required to individually acknowledge each payment within a maximum of seven (7) calendar days. If a payment is voided, your consumer will be automatically refunded.

**Important Note**: in case Void is required, it should be specified upon contract signature. The functionality needs to be activated by our Support Team.

The **initial steps are identical** whether the **Void feature** is enabled or disabled. Differences between the two flows are clearly presented in the comparison table that follows.

#### Common Initial Steps

* The **merchant frontend** sends payment creation details to the **merchant backend**. Request should at least contain the payment amount.
* The **merchant backend** issues a REST request to the **Bancontact Pro backend** to create the payment, providing parameters like amount, currency, description, and other relevant parameters.
* The **Bancontact Pro backend** responds with the created payment ID and other relevant details, including a unique QR code URL.
* The **merchant backend** forwards the QR code URL to the **merchant frontend**, which displays it for the consumer.
* The **Payer app** scans the QR code and sends a request to retrieve payment details from the backend.
* The **Bancontact Pro backend** sends payment details to the **Payer App**, including merchant name and amount to pay.
* The consumer confirms the payment using PIN, fingerprint, or face ID. The app then submits the payment request to the backend for authorization.


#### Flow Differences: Void Enabled vs. Void Disabled

| **Void Disabled** | **Void Enabled** |
|  --- | --- |
| A payment response is sent back to the **Payer App**, indicating whether the payment was successful or failed. | The consumer is debited, and the payment enters a `PENDING_MERCHANT_ACKNOWLEDGEMENT` state, awaiting confirmation from the **merchant backend**. |
| The **Bancontact Pro backend** sends a payment notification with the payment status to the **merchant backend** via the configured callback URL. | The **Bancontact Pro backend** sends a callback to the **Merchant backend** with the payment status. The merchant can also poll for updates. |
| The **merchant frontend** displays the payment confirmation status. | The consumer is prompted in the app to check the consumer-facing screen for the final payment status. |
| — | The **merchant backend** sends a positive acknowledgment to indicate successful processing. |
| — | The **Bancontact Pro backend** marks the payment as `SUCCEEDED` and initiates a payout to the merchant. |
| — | The **merchant frontend** displays the final confirmation to the consumer. |
| — | The **Payer App** notifies the consumer of the final payment outcome. |


> **Important Note:** The order in which the merchant and consumer receive payment status notifications is **not guaranteed**. Network and connectivity differences may cause one party to receive the update before the other.


### Payment Flow Diagrams

In the following diagrams you will find a visual overview of the process flows presented above:

#### Flow Diagram - Void Disabled

![Visualized diagram of the Void Disabled flow](/assets/onadisplayvoiddisabled.86c1a2b904d833d1eab955ec8549b99febc7d5382abe404089b9f735888fcab7.85e0cfdd.jpg)

#### Flow Diagram - Void Enabled

![Visualized diagram of the Void Enabled flow](/assets/onadisplayvoidenabled.7483f0007196c53dc24a09ee4b8115b019f61837f7ada624abbc15874b766aad.85e0cfdd.jpg)

## Implementation Guide

Please follow the below steps to successfully implement "On a Display" on your or consumer facing display.

> For the full endpoint documentation, please refer to the [Merchant Payment API](/apis/merchant-payment.openapi).


### 1. Create Payment

In order to initiate a payment, you will first have to create it through Bancontact Pro via a **POST** request. Each request will result in a unique payment identifier which will be valid for **two minutes (120 seconds)**.

If the payment does not take place within these two minutes, a new payment must be created.

#### 📦 Request Body

> **Important Note**: for **On a Display** the returnURL is not necessary.


#### 📥 Response

> **Important Note**: for **On a Display** the  checkout link will not be provided in the response.


#### 🔧 Error Codes for `create`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 400 | `BODY_MISSING` | A json needs to be provided |
| 400 | `FIELD_IS_REQUIRED` | Field X is mandatory |
| 400 | `FIELD_IS_INVALID` | Field X is invalid |
| 401 | `UNAUTHORIZED` | user does not have an access token |
| 403 | `ACCESS_DENIED` | The JWT could not be verified (different format) - The JWT does not contain the required authority to access the resource requested |
| 404 | `MERCHANT_PROFILE_NOT_FOUND` | The merchant profile does not exist |
| 422 | `UNABLE_TO_PAY_CREDITOR` | Variable reason(Depends on automatic processing). |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |
| 503 | `TRY_AGAIN_LATER` | one of the internal services is unavailable |


#### 🔍 Sample Request – `create payment`

### 2. The Bancontact Pro QR Code

To display the Bancontact Pro QR code, you can render the URL from the attribute `_links.self.href` received in the Create Payment response in a web view. By doing so, you will make use of Bancontact Pro's QR code generation service and will generate by default a small QR code (cf. Brand Guidelines).

**Important:** the format, size and colour of the QR code can be modified if necessary using the parameters below. Please make sure to read our Brand Guidelines for more guidance on the minimum sizes and scanning distances.

| **Attribute** | **Description** |
|  --- | --- |
| `f` [String :: Enum]  Allowed Values: SVG, PNG | Image format |
| `s` [String :: Enum]  Allowed Values: S, M, L, XL | Image size of the QR code to generate. Small (S) = 180x180 Medium (M) = 250x250Large (L) = 400x400 Extra Large (XL) = 800x800  The sizes only applies to PNG format. |


### 3. The Bancontact Pro Callback

You can specify a callback URL where the **Bancontact Pro backend** will send notifications about the status of a payment. This will allow you to take appropriate action and process the payment data.

The **merchant backend** must verify that the notification message originated from **Bancontact Pro backend** was not altered or corrupted during the transmission. To do so, please ensure signature validation.

> For the full Callback documentation, please refer to the [Callback Guide](/guides/general/callback052025).


#### 📦 Request Body

#### 📥 Response

*(No defined response schema)*

#### 🔍 Sample Request – `callback`

#### Callback Failure

In the event you do not receive a callback or the callback validation fails, please refer to **"Get Payment Details"**. This alternative will also allow you to confirm the status of a transaction in order to complete the payment.

### 4. Get Payment Details

By calling this endpoint you can obtain the details of an existing payment transaction by passing the unique payment ID.

**Note:** it is highly recommended to implement this call as a fallback option if callback fails.

#### 🧩 Path Parameters

- `id` *(string, required)*


#### 📥 Response

#### 🔧 Error Codes for `merchant-get-payment`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 401 | `UNAUTHORIZED` | caller does not have an api-key access token |
| 403 | `ACCESS_DENIED` | api-key access token is invalid, creditor it's not a participant of the requested payment |
| 404 | `PAYMENT_NOT_FOUND` | no payment could be found |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |


#### 🔍 Sample Request – `merchant-get-payment`

### 5. Get Payment List

You can also retrieve a list of payments by specifying how many records to return, as well as a filter on the results for the total number of records returned per page.

#### 📦 Request Body

#### 📥 Response

#### 🔧 Error Codes for `search`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 401 | `UNAUTHORIZED` | caller does not have an api-key access token |
| 403 | `ACCESS_DENIED` | api-key access token is invalid, creditor it's not a participant of the requested payment |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |


#### 🔍 Sample Request – `search`

### 6. Void Payment

**Important Note**: Void Functionality is not yet available on our new Merchant API. Void will be available end of September 2025.

Void is an intermediary step that allows your backend to remain in the lead of a payment transaction after your consumer has confirmed the payment.

You will be required to individually acknowledge each payment within a maximum of seven (7) calendar days. If a payment is voided, your consumer will be automatically refunded.

If Void is enabled, the following three scenarios are possible

#### 6.1 Void Payment - Happy Flow

* Merchant creates a payment via Bancontact Pro API and displays the QR code.
* Consumer scans the QR code to retrieve payment information.
* Consumer signs (enter pin/fingerprint/FaceId) the payment successfully.
* The consumer is debited, and the payment is in a state that is pending an acknowledgment (`PENDING_MERCHANT_ACKNOWLEDGEMENT`) from the merchant/terminal.
* Bancontact Pro sends a callback to the merchant to notify them about the status of the payment. The merchant can also poll Bancontact Pro for the status of the payment.
* Towards the consumer we will inform them to check the terminal for the final status of the payment.
* The merchant terminal sends a positive acknowledgement for the payment to indicate that the terminal processed the payment successfully.
* Bancontact Pro marks the payment as `SUCCEEDED` and initiates a payout to the merchant.
* Bancontact Pro updates the consumer about the status of the payment.


#### 🧩 Path Parameters

- `id` *(string, required)*


#### 📦 Request Body

#### 🔧 Error Codes for `merchant-acknowledge`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 400 | `FIELD_IS_REQUIRED` | Field X is mandatory |
| 400 | `FIELD_IS_INVALID` | Field X is invalid |
| 401 | `UNAUTHORIZED` | caller does not have an api-key access token |
| 403 | `ACCESS_DENIED` | The JWT could not be verified or does not contain the required authority to access the resource requested |
| 404 | `PAYMENT_NOT_FOUND` | no payment could be found for the supplied identifier |
| 422 | `PAYMENT_VOIDED` | Payment is already voided |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |
| 503 | `SERVICE_UNAVAILABLE` | Payment service could not be reached or some unexpected error occurred |


#### 🔍 Sample Request – `merchant-acknowledge`

#### 6.2 Void Payment - Unhappy Flow, Merchant Void

* Merchant creates a payment via Bancontact Pro and displays the Bancontact Pro QR code.
* Consumer scans the QR code to retrieve payment information.
* Consumer signs (enter pin/fingerprint/FaceId) the payment successfully.
* The consumer is debited, and the payment is in a state that is pending an acknowledgment (`PENDING_MERCHANT_ACKNOWLEDGEMENT`) from the merchant/terminal.
* Bancontact Pro sends a callback to the merchant to notify them about the status of the payment. The merchant can also poll Bancontact Pro for the status of the payment.
* Towards the consumer we will inform them to check the terminal for the final status of the payment.
* The merchant terminal cancels the payment because something went wrong while processing the payment on the terminal.
* Bancontact Pro marks the payment as `VOIDED` and initiates a payout to the consumer.
* Bancontact Pro updates the consumer about the status of the payment.


#### 🧩 Path Parameters

- `id` *(string, required)* — Bancontact Pro Payment Id


#### 🔧 Error Codes for `delete-payment`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 401 | `UNAUTHORIZED` | user does not have an access token |
| 403 | `ACCESS_DENIED` | access token is invalid |
| 403 | `CALLER_NOT_ALLOWED_TO_CANCEL` | if caller is not a participant of the payment |
| 404 | `PAYMENT_NOT_FOUND` | payment is not found in the system |
| 422 | `PAYMENT_NOT_PENDING` | payment is not in pending or identify state |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |


#### 🔍 Sample Request – `delete-payment`

#### 6.2 Void Payment - Unhappy Flow, Timeout

* Consumer scans the QR code to retrieve payment information.
* Consumer signs (enter pin/fingerprint/FaceId) the payment successfully.
* The consumer is debited, and the payment is in a state that is pending an acknowledgment (`PENDING_MERCHANT_ACKNOWLEDGEMENT`) from the merchant/terminal.
* Bancontact Pro sends a callback to the merchant to notify them about the status of the payment. The merchant can also poll Bancontact Pro for the status of the payment.
* Towards the consumer we will inform them to check the terminal for the final status of the payment.
* The merchant terminal does not send a positive acknowledgement/cancel the payment in the X hours timeout.
* Bancontact Pro marks the payment as `VOIDED` and initiates a payout to the consumer.
* Bancontact Pro updates the consumer about the status of the payment.


## Canceling a Payment

Endpoint `delete-payment` can be used to cancel a created payment that is still in status `PENDING`.
The endpoint can also be used to cancel a payment in `IDENTIFIED` status, as long as the consumer has
not initiated payment confirmation.

### 🧩 Path Parameters

- `id` *(string, required)* — Bancontact Pro Payment Id


### 🔧 Error Codes for `delete-payment`

| HTTP Status | Code | Meaning |
|  --- | --- | --- |
| 401 | `UNAUTHORIZED` | user does not have an access token |
| 403 | `ACCESS_DENIED` | access token is invalid |
| 403 | `CALLER_NOT_ALLOWED_TO_CANCEL` | if caller is not a participant of the payment |
| 404 | `PAYMENT_NOT_FOUND` | payment is not found in the system |
| 422 | `PAYMENT_NOT_PENDING` | payment is not in pending or identify state |
| 500 | `TECHNICAL_ERROR` | Technical error in Payment service |


### 🔍 Sample Request – `delete-payment`